好得很程序员自学网

<tfoot draggable='sEl'></tfoot>

基于接口和队列的线程操作UI方式

基于接口和队列的线程操作UI方式

在实际开发应用中,非UI线程操作UI是普遍存在的,在.net下一般是通过Control.Invoke的方法来进行操作,但到处都是Control.Invoke代码维护可是一件麻烦的事情。以下通过接口和队列来规范非UI线程操UI的实现。

   既然要规范处理那接口是个不错的选择,以下定义一个简单的执行接口

?

public   interface   IInvokeItem

     {

         void   Execute();

     }

  以下是扩展一个简单的操作类封装

?

class   ControlInvoke<CONTROL,DATA> : IInvokeItem

     {

         public   ControlInvoke(CONTROL control, DATA data, Action<CONTROL, DATA> action)

         {

             mControl = control;

             mData = data;

             mAction = action;

         }

         private   CONTROL mControl;

         private   DATA mData;

         private   Action<CONTROL, DATA> mAction;

         public   void   Execute()

         {

             mAction(mControl, mData);

         }

     }

  规则定好了,那接下来要做的事情就是写一个简单的队列处理。

?

public   class   Dispatch

     {

         static   Dispatch()

         {

             Instance = new   Dispatch();

         }

         public   void   Add<CONTROL, DATA>(CONTROL control, DATA data, Action<CONTROL, DATA> action)

         {

             ControlInvoke<CONTROL, DATA> item = new   ControlInvoke<CONTROL, DATA>(control, data, action);

             Add(item);

         }

         private   Queue<IInvokeItem> mQueues = new   Queue<IInvokeItem>();

         public   static   Dispatch Instance

         {

             get ;

             set ;

         }

         public   void   Add(IInvokeItem item)

         {

             lock   ( this )

             {

                 mQueues.Enqueue(item);

             }

         }

         public   void   Execite()

         {

             lock   ( this )

             {

                 while   (mQueues.Count > 0)

                 {

                     mQueues.Dequeue().Execute();

                 }

             }

         }

     }

  一个简单的调用规则就完成,接下来就是如果在winform下面用了;首先可以在界面定义一个timer,可以指定时间内执行Dispatch的工作。

?

private   void   timer1_Tick( object   sender, EventArgs e)

         {

             ThreadInvoke.Dispatch.Instance.Execite();

         }

  当需要在线程中操作UI只需要向ThreadInvoke.Dispatch添加item即可,对于它的执行是完全不用关心的。以下是起一个线程不停地向一个文本框添加一个GUID值

?

private   void   cmdTest_Click( object   sender, EventArgs e)

         {

             System.Threading.ThreadPool.QueueUserWorkItem(OnTest);

         }

         private   void   OnTest( object   state)

         {

             while   ( true )

             {

                 ThreadInvoke.Dispatch.Instance.Add<RichTextBox, Guid>(

                     richTextBox1, Guid.NewGuid(), (c, d) => {

                         richTextBox1.AppendText(d.ToString( "N" ));

                         richTextBox1.AppendText( "\r\n" );

                     });

                 System.Threading.Thread.Sleep(10);

             }

         }

 这样一个不使用Control.Invoke来实现非UI线程操作UI的方法就完成了.至于灵活性来说那就看你如何发挥IInvokeItem了:)

专注于可靠、高性能的Socket TCP通讯组件

作者: Leo_wl

    

出处: http://www.cnblogs.com/Leo_wl/

    

本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。

版权信息

查看更多关于基于接口和队列的线程操作UI方式的详细内容...

  阅读:48次