一、背景

由于在窗体程序中通过点击一个button按键后需要更新TreeView控件的内容,由于等待时间比较长,主程序无法一起在那边等待,需要去处理其它的事情,所以就需要创建新的子线程来处理。因为主线程主要用于窗体程序的更新,但子线程又存在问题是C#中禁止跨线程直接访问控件,所以子线程中要更新窗体程序的控件要使用委托主线程来处理更新控件。

二、程序分析

using System.Threading; 													   //声明线程命名空间

 private void Updatebutton_Click(object sender, EventArgs e)				   //按键控件处理程序
{
Thread SearchDevice = new Thread(FindCanDevice); //子线程的创建 if (update_flag ==false) //开始更新网络设备
{
update_flag =true;
UpdateprogressBar.Maximum= 127; //总共会查询126个设备
DevicetreeView.Nodes.Clear(); //快速清空TreeView的内容
NodeList = new TreeNode("Device List", 0, 0);
this.DevicetreeView.Nodes.Add(NodeList); //加入根节点
//Thread SearchDevice = new Thread(FindCanDevice);
SearchDevice.IsBackground = true; //当主线程关闭时,子线程也随着关闭
SearchDevice.Start(); //子线程启动 }
else //停止更新网络设备
{
update_flag = false;
}
}
private void FindCanDevice() //子线程处理程序
{
int ret; //寻找设备的状态
int countnum = 0; for (int j = 1; j < 128; j++)
{
if (!update_flag) //退出网络设备的更新
break;
countnum++;
ret = GloableVar.WzCanOpenUpdateNetwork(j);
ShowDevice(ret, j, countnum);
}
}
public delegate void aa(int flagSuccess, int data, int count); //委托类型的说明 private void ShowDevice(int flagSuccess, int data, int count)
{
if(this.InvokeRequired) //判断是不是控件所在线程调用的,不是的话为true,Invoke用于跨线程调用控件进行操作
{
aa a = new aa(ShowDevice); //定义委托的函数
this.Invoke(a, new object[] { flagSuccess, data, count }); //指定用主线程中的控件去调用这个委托,相当于主线程来执行这个函数
}
else
{
if(flagSuccess== 0)
{
TreeNode NodeDevice = new TreeNode("Node ID " + data.ToString());
NodeList.Nodes.Add(NodeDevice); //加入子节点
DevicetreeView.ExpandAll(); //展开所有的节点
}
UpdateprogressBar.Value = count; }
}

1、 Thread SearchDevice = new Thread(FindCanDevice)为新建的子线程,子线程的处理函数为void FindCanDevice() ,完成线程创建后需要启动线程 SearchDevice.Start(),线程才会运行。

2、在进入子线程处理函数后,如果因为控件是主线程创建的,子线程不是控件所在的线程调用,所以this.InvokeRequired一直为true,进入判断程序后通过this.Invoke将子线程的处理委托给主线程去处理,由于委托的函数为ShowDevice并且当前调用执行的线程为控件所在的主线程调用,这时又判断this.InvokeRequired为false,所以执行控件的更新处理

                if(flagSuccess== 0)
{
TreeNode NodeDevice = new TreeNode("Node ID " + data.ToString());
NodeList.Nodes.Add(NodeDevice); //加入子节点
DevicetreeView.ExpandAll(); //展开所有的节点
}
UpdateprogressBar.Value = count;

三、参考文档

http://www.cnblogs.com/miniwiki/archive/2010/06/18/1760540.html //线程的创建

http://www.cnblogs.com/songxingzhu/p/3677307.html //InvokeRequired和Invoke的使用

by 羊羊得亿

2017-07-04 ShenZhen

C#创建子线程,子线程使用委托更新控件的更多相关文章

  1. [转]MFC子线程中更新控件内容的两种办法

    一.概述 每个系统中都有线程(至少都有一个主线程),而线程最重要的作用就是并行处理,提高软件的并发率.针对界面来说,还能提高界面的响应能力.一般的,为了应用的稳定性,在数据处理等耗时操作会单独在一个线 ...

  2. Winfrom 如何安全简单的跨线程更新控件

    来源:http://www.cnblogs.com/rainbowzc/archive/2010/09/29/1838788.html 由于多线程可能导致对控件访问的不一致,导致出现问题.C#中默认是 ...

  3. C# 线程调用主线程中的控件

    由于项目的需要,最近几天一直在做串口和数据库.由于C#使用的时间不长,所以在编写代码和调试的过程中总是遇到意想不到的问题,比如在使用串口接收数据的时候,在接收数据事件中想把接收的数据放入一个textb ...

  4. C# 通过委托控制进度条以及多线程更新控件

    using System; using System.Collections.Generic; using System.ComponentModel; using System.Data; usin ...

  5. QT 创建一个具有复选功能的下拉列表控件

    最近研究了好多东西,前两天突然想做一个具有复选功能的下拉列表框.然后在网上"学习"了很久之后,终于发现了一个可以用的,特地发出来记录一下. 一.第一步肯定是先创建一个PROJECT ...

  6. VB.NET章鱼哥出品—怎样解决MDI子窗口被父窗口中的控件覆盖的问题

    近期有个网友问我这个问题,我就上网搜了下,结果非常失望.有几个在CSDN上发的求助帖.看到最后都没有找到明白的答案. 这里笔者在网上找到了API函数SetParent(),并对网上的错误进行了改动,并 ...

  7. AE二次开发,解决子窗体使用父窗体的AxControl控件

    在子窗体写构造函数,然后再在父窗体按钮点击事件下写 public frmIDW(AxMapControl axMapControl1) { InitializeComponent(); this.ax ...

  8. iOS代码实现:创建按钮,绑定按钮事件,读取控件值

    // // main.m // Hello // // Created by lishujun on 14-8-28. // Copyright (c) 2014年 lishujun. All rig ...

  9. C#子线程更新UI控件的方法总结

    http://blog.csdn.net/jqncc/article/details/16342121 在winform C/S程序中经常会在子线程中更新控件的情况,桌面程序UI线程是主线程,当试图从 ...

随机推荐

  1. 对照 Android 的 Intent 与 iOS StoryBoard 的 Segue - Intent 假设也能添加个prepareForSegue回调就好了

    对照 Android 的 Intent 与 iOS StoryBoard 的 Segue - Intent 假设也能添加个prepareForSegue回调就好了 太阳火神的漂亮人生 (http:// ...

  2. Xcode加入应用图标以及启动界面

    寻找了许久的资料,记录下Xcode加入应用图标以及启动界面的学习笔记: 很实用的网址: 1.(苹果官网)Designing for iOS 2.iOS 8 人机交互指南 图标和图片的尺寸參考: 更加具 ...

  3. modSecurity规则学习(六)——检测模式

    传统检测模式-自主规则 传统检测模式所有规则都是“闭环”的模式.就像HTTP本身一样,单独的规则是无状态的.这意味着规则之间不共享信息,每个规则都没有关于任何先前规则匹配的信息.它仅使用其当前的单个规 ...

  4. Lesson 1 Basic Concepts: Part 3

    A cheaper option Some people may not want to buy a domain or pay for hosting because they only have ...

  5. VS中,打开文件时自动定位到目录树中

    工具--选项--项目和解决方案--常规--在解决方案资源管理器中跟踪活动项 这样就能快速跟踪了.

  6. php中对象转数组有哪些方法(总结测试)

    php中对象转数组有哪些方法(总结测试) 一.总结 一句话总结:json_decode(json_encode($array),true)和array强制转换(或带递归) 1.array方式强制转换对 ...

  7. SCOPE_IDENTITY()和 SELECT @@IDENTITY 的用法

    这俩个,是在插入数据的时候使用,返回刚刚插入数据行的ID 大家慎用@@IDENTITY,而尽量采用 SCOPE_IDENTITY() 函数替换之. SCOPE_IDENTITY()  也是得到最后一条 ...

  8. java读取jpg图片旋转按比例缩放

    //入口 public static BufferedImage constructHeatWheelView(int pageWidth, int pageHeight, DoubleHolder ...

  9. spring 中国下载点

    http://repo.spring.io/libs-release-local/org/springframework/spring/ spring 中国下载点

  10. SQL SERVER 新增表、新增字段、修改字段 判断表是否存在

    // 新增之前判断表是否存在 IF NOT EXISTS (SELECT NAME FROM SYSOBJECTS WHERE ID = OBJECT_ID('tb_MessageHistory')) ...