我也来玩玩WinForm~BeginInvoke让用户体验更好!

简介:

前言

先说明一下,本人不太做winform的项目,工作10年以来,一直奋斗在webform的舞台上,今天有机会也接触了一下winform,下面对工作中用到的BeginInvoke方法作一下说明,和大家也一起学习一下,呵呵。

BeginInvoke产生的原因

首先一个winform程序运行后,会有一个主线程(UI),我们看到的页面上的元素,表单,列表框等等都运行在主线程上的,主线程一阻塞,这些东西就都点不了了,呵呵,所以,在我们运行一些耗时的功能时,通常会开启一个新的线程去干这事,这是和乎情理的,想像一下,当我们在新线程里工作时,主线程不被阻塞(不假死),用户体验是多么好呀,当在新线程里干完事后,把消息返回给主线程,就OK了!

美中不足

想的挺好,可惜在新线程里,干完事后,运行程序,在为主窗体元素赋值时,出错了,说是不能访问主线程的元素,这到是正常的,线程与线程本来就是独立的,所以只能找其它方法了(可以使用这个方法解决上面的问题,但不推荐:  Control.CheckForIllegalCrossThreadCalls = false;)

BeginInvoke出来了

微软为了解决上面的线程之间信息相互访问的问题,封装了BeginInvoke方法,它允许我们传入一个委托,在委托方法中干这件时,这时你的主线程元素是可以被访问的,当处理完成后,可以操纵主线程的元素,即主线程元素重新赋值。

下面是一个简单的例子:

        /// <summary>
        /// 批量添加
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void button1_Click(object sender, EventArgs e)
        {
            message.Text = "程序正在处理...";

            var beginInvokeThread = new Thread(() =>
            {
                var result = userBll.GeneratorUserData(dateTimePicker1.Value);//耗时工作
                #region BeginInvoke
                Func<ReturnMsg, string> funDelegate = new Func<ReturnMsg, string>(InvodeGeneratorUserData);
                IAsyncResult aResult = this.BeginInvoke(funDelegate, result);
                aResult.AsyncWaitHandle.WaitOne(-1);
                if (aResult.IsCompleted)//这里不可以访问主线程的信息
                    MessageBox.Show(this.EndInvoke(aResult).ToString());
                #endregion
            });
            beginInvokeThread.Start();
        }

委托方法如下:

        /// <summary>
        /// 一个委托,把消息返回并填充到主窗体(主线程)的页面元素上
        /// </summary>
        /// <param name="month"></param>
        /// <returns></returns>
        private string InvodeGeneratorUserData(ReturnMsg res)
        {
            this.message.Text = res.GetDescription();//这里可以访问主线程的信息
            return res.GetDescription();
        }

下面是运行的效果图:

本文转自博客园张占岭(仓储大叔)的博客,原文链接:我也来玩玩WinForm~BeginInvoke让用户体验更好!,如需转载请自行联系原博主。

目录
相关文章
|
3月前
|
C# 开发者 测试技术
震惊!Xamarin 竟能如此构建跨平台应用程序,代码共享、界面设计与性能优化全攻略大揭秘!
【8月更文挑战第31天】在移动应用开发领域,跨平台工具日益受到青睐。Xamarin 是一款强大的工具,支持使用 C# 开发适用于 iOS、Android 和 Windows 的应用。通过安装 Visual Studio 或 Visual Studio for Mac,并创建 Xamarin 项目,开发者可以利用丰富的功能和工具进行开发。Xamarin 的主要优势在于代码共享,能够显著提高开发效率。
69 0
|
3月前
|
C# 开发者 设计模式
WPF开发者必读:命令模式应用秘籍,轻松简化UI与业务逻辑交互,让你的代码更上一层楼!
【8月更文挑战第31天】在WPF应用开发中,命令模式是简化UI与业务逻辑交互的关键技术,通过将请求封装为对象,实现UI操作与业务逻辑分离,便于代码维护与扩展。本文介绍命令模式的概念及实现方法,包括使用`ICommand`接口、`RelayCommand`类及自定义命令等方式,并提供示例代码展示如何在项目中应用命令模式。
50 0
|
3月前
|
C# Windows 开发者
超越选择焦虑:深入解析WinForms、WPF与UWP——谁才是打造顶级.NET桌面应用的终极利器?从开发效率到视觉享受,全面解读三大框架优劣,助你精准匹配项目需求,构建完美桌面应用生态系统
【8月更文挑战第31天】.NET框架为开发者提供了多种桌面应用开发选项,包括WinForms、WPF和UWP。WinForms简单易用,适合快速开发基本应用;WPF提供强大的UI设计工具和丰富的视觉体验,支持XAML,易于实现复杂布局;UWP专为Windows 10设计,支持多设备,充分利用现代硬件特性。本文通过示例代码详细介绍这三种框架的特点,帮助读者根据项目需求做出明智选择。以下是各框架的简单示例代码,便于理解其基本用法。
160 0
|
3月前
|
图形学 C# 开发者
全面掌握Unity游戏开发核心技术:C#脚本编程从入门到精通——详解生命周期方法、事件处理与面向对象设计,助你打造高效稳定的互动娱乐体验
【8月更文挑战第31天】Unity 是一款强大的游戏开发平台,支持多种编程语言,其中 C# 最为常用。本文介绍 C# 在 Unity 中的应用,涵盖脚本生命周期、常用函数、事件处理及面向对象编程等核心概念。通过具体示例,展示如何编写有效的 C# 脚本,包括 Start、Update 和 LateUpdate 等生命周期方法,以及碰撞检测和类继承等高级技巧,帮助开发者掌握 Unity 脚本编程基础,提升游戏开发效率。
77 0
|
6月前
|
测试技术 Python
App自动化测试中,如何更好地处理弹窗?
在App自动化测试中,处理弹窗异常是保证测试稳定性和可靠性的重要环节。当遇到广告弹窗、升级提示等不定时出现的UI元素时,可以采用黑名单处理方法,如上述Python代码示例,通过尝试点击黑名单中的元素来避免干扰。同时,利用异常处理装饰器可以增强函数功能,保持代码整洁,当异常发生时记录日志、截图并保存页面源代码,便于问题排查。这两种策略能有效提升测试的效率和质量。
|
6月前
|
前端开发 测试技术 UED
前端知识(十四)——浅谈用户体验测试的主要功能
前端知识(十四)——浅谈用户体验测试的主要功能
128 0
|
JSON IDE 开发工具
<4> :开发技巧/方法:
<4> :开发技巧/方法:
53 0
|
存储 JavaScript C#
从零开始做一款Unity3D游戏<三>——编写游戏机制(一)
从零开始做一款Unity3D游戏<三>——编写游戏机制
从零开始做一款Unity3D游戏<三>——编写游戏机制(一)
|
存储 设计模式 JavaScript
从零开始做一款Unity3D游戏<三>——编写游戏机制(二)
从零开始做一款Unity3D游戏<三>——编写游戏机制
从零开始做一款Unity3D游戏<三>——编写游戏机制(二)
|
C# 虚拟化 UED
细数改善WPF应用程序性能的10大方法
原文:细数改善WPF应用程序性能的10大方法       WPF(Windows Presentation Foundation)应用程序在没有图形加速设备的机器上运行速度很慢是个公开的秘密,给用户的感觉是它太吃资源了,WPF程序的性能和硬件确实有很大的关系,越高档的机器性能越有优势。
1258 0