【WPF】C#跨线程操作窗体控件



    为防止任务处理对界面操作的阻塞,用多线程进行处理是自然对用到的方法,不过也引入了跨线程操作的问题。今天碰到的问题是任务线程需要获取和设置窗体控件的属性,解决还是蛮容易的,引入delegate即可解决。

    写了一个实例程序,效果是文本框txtOutput中实时显示文本框txtUsername和密码框txtPassword的内容,代码如下:



    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    using System.Windows;
    using System.Windows.Controls;
    using System.Windows.Data;
    using System.Windows.Documents;
    using System.Windows.Input;
    using System.Windows.Media;
    using System.Windows.Media.Imaging;
    using System.Windows.Navigation;
    using System.Windows.Shapes;
    using System.Threading;
    
    namespace WPF
    {
        /// <summary>
        /// Interaction logic for MainWindow.xaml
        /// </summary>
        public partial class MainWindow : Window
        {
            public MainWindow()
            {
                InitializeComponent();
            }
    
            /// <summary>
            /// 监控线程
            /// </summary>
            private Thread mThread = null;
    
            /// <summary>
            /// 获取控件文本内容的线程代理
            /// </summary>
            /// <param name="control">Control</param>
            /// <returns>string</returns>
            private delegate string GetTextHandle(Control control);
    
            /// <summary>
            /// 获取控件文本内容
            /// </summary>
            /// <param name="control">Control</param>
            /// <returns>string</returns>
            private string GetText(Control control)
            {
                if (this.Dispatcher.Thread != System.Threading.Thread.CurrentThread)
                {
                    return (string)this.Dispatcher.Invoke(new GetTextHandle(this.GetText), control);
                }
                else
                {
                    if (control.GetType() == typeof(TextBox))
                    {
                        return ((TextBox)control).Text;
                    }
                    else if (control.GetType() == typeof(PasswordBox))
                    {
                        return ((PasswordBox)control).Password;
                    }
                    else
                    {
                        return string.Empty;
                    }
                }
            }
    
            /// <summary>
            /// 显示文本的线程代理
            /// </summary>
            /// <param name="text">string</param>
            private delegate void ShowTextHandle(string text);
    
            /// <summary>
            /// 显示文本
            /// </summary>
            /// <param name="text">string</param>
            private void ShowText(string text)
            {
                if (this.Dispatcher.Thread != System.Threading.Thread.CurrentThread)
                {
                    this.Dispatcher.Invoke(new ShowTextHandle(this.ShowText), text);
                }
                else
                {
                    this.txtOutput.Text = text;
                }
            }
    
            /// <summary>
            /// 监控输入并实时显示
            /// </summary>
            private void MonitorInput()
            {
                while (true)
                {
                    string username = this.GetText(txtUsername);
                    string password = this.GetText(txtPassword);
                    string output = String.Format("Username:{0}, Password:{1}", username, password);
                    this.ShowText(output);
                }
            }
    
            /// <summary>
            /// 窗口内容渲染好时启动监控线程
            /// </summary>
            /// <param name="sender"></param>
            /// <param name="e"></param>
            private void Window_ContentRendered(object sender, EventArgs e)
            {
                mThread = new Thread(MonitorInput);
                mThread.Start();
            }
    
            /// <summary>
            /// 窗口关闭时结束线程
            /// </summary>
            /// <param name="sender"></param>
            /// <param name="e"></param>
            private void Window_Closed(object sender, EventArgs e)
            {
                mThread.Abort();
            }
        }
    }

    列几个C#多线程相关的参考资料:

    1. 正确使用异步操作
    2. 第一期总结之三:Thread的问题
    3. .Net多线程总结(一) 
    4. .Net多线程总结(二)-BackgroundWorker


    本博客所有文章如无特别注明均为原创。
    复制或转载请以超链接形式注明转自枫芸志,原文地址《【WPF】C#跨线程操作窗体控件
    标签:
    分享:

还没有人抢沙发呢~

无觅相关文章插件,快速提升流量