Introduction

The download contains three simple examples of implementing a responsive multi-thread WPF UI. Two examples uses the Dispstch.Invoke() method and one uses the Background WorkerTheead class and the ProcessBar UI. I’m a newbie… and probably will not be able to answer any follow-up questions. The code is simple and intuitive. Its only purpose is to give other newbies a good start, in how to implement responsive multi-thread UI.

  • Project StopWatch: is a technique for recursively calling the Dispatch of a worker thread.
  • Project WpfDispatch: is a technique using a sample Dispatch call to the main thread
  • Project WpfBackgrd: is a technique in using the Background Worker thread, note only the ProcessBar is updated.

The code behind snippets below are listed for your inspection, to determine whether, or not, you want to download the projects zip.

StopWatch C# code

using System;
using System.Threading;
using System.Windows;
using System.Windows.Threading;

namespace StopWatch
{
    /// <summary>
    /// Interaction logic for Window1.xaml
    /// </summary>
    public partial class Window1 : Window
    {
        private int iTimeMax;
        private int CurrCount;
        private bool _go = false;
        private bool countdown = false;
        private delegate void WatchDegete();

        public Window1() : base()
        {
            InitializeComponent();
        }

        #region UI Events
        public void StartOrStop(object sender, RoutedEventArgs e)
        {
            if (countdown)
            {
                countdown = false;
                startStopButton.Content = "Resume";
            }
            else
            {
                countdown = true;
                Comment.Text = "RUNNING...";
                startStopButton.Content = "Stop";
                if (!_go)
                {
                    outputBox.Text = inputBox.Text;
                    _go = true;
                }
                string[] arr = outputBox.Text.Split(':');
                CurrCount = (int.Parse(arr[0]) * 60 + int.Parse(arr[1])) * 1000;

                startStopButton.Dispatcher.BeginInvoke(
                    DispatcherPriority.Normal,
                    new WatchDegete(Clock));
            }
        }

        private void Reset_Click(object sender, EventArgs e)
        {
            _go = false;
            countdown = false;
            Comment.Text = "READLY";
            outputBox.Text = null;
            startStopButton.Content = "Start";


        }

        private void Clock()
        {
            if (!countdown) return;
            Thread.Sleep(1000);
            CurrCount -= 1000;
            if (CurrCount <= 0)
            {
                _go = false;
                countdown = false;
                Comment.Text = "READLY";
                startStopButton.Content = "Start";
                outputBox.Text = null;
                System.Console.Beep(3000, 1000);
                MessageBox.Show("TimeOut: exceeded Time alotment!");
            }
            else
            {
                int ms = CurrCount / 1000;
                int minutes = ms / 60;
                int seconds = ms % 60;

                outputBox.Text = minutes + ":" +
                    string.Format("{0:D2}", seconds);

                startStopButton.Dispatcher.BeginInvoke(
                    DispatcherPriority.SystemIdle,
                    new WatchDegete(Clock));
            }
        }
        #endregion
    }
}

WpfDispatch C# code

using System;
using System.Threading;
using System.Windows;
using System.Windows.Controls;

namespace WpfDispatch
{
    /// <summary>
    /// Interaction logic for Window1.xaml
    /// </summary>
    public partial class Window1 : Window
    {
        private bool ready = true;
        private Thread workerThread;

        public Window1()
        {
            InitializeComponent();
        }

        private void start_Click(object sender, RoutedEventArgs e)
        {
            ready = false;
            workerThread = new Thread(DoWork);
            workerThread.Start();
        }

        private void stop_Click(object sender, RoutedEventArgs e)
        {
            ready = true;
            workerThread.Join();
        }

        private void Window_Closing(object sender,

 System.ComponentModel.CancelEventArgs e)
        {
            if (!ready)
            {
                MessageBox.Show("Stop the clock process");
                e.Cancel = true;
            }
        }

        private delegate void updateControlDelegate(Control ui, String text);

        private void updateControl(Control ui, String text)
        {
            Label l = ui as Label;
            l.Content = text;
        }

        private void DoWork()
        {
            updateControlDelegate c = updateControl;
            while (!ready)
            {
                Dispatcher.Invoke( c, label1,  DateTime.Now.ToLongTimeString());
                Thread.Sleep(200);
            }

            label1.Dispatcher.BeginInvoke(c, label1, "STOPPED");
        }
    }
}

WpfBackgrd C# code

using System.Windows;
using System.Threading;
using System.ComponentModel;

namespace WpfBackGrd
{
    /// <summary>
    /// Interaction logic for Window1.xaml
    /// </summary>
    public partial class Window1 : Window
    {
        private BackgroundWorker _worker;

        public Window1()
        {
            InitializeComponent();
        }

        private void start_Click(object sender, RoutedEventArgs e)
        {
            _worker = new BackgroundWorker();

            _worker.WorkerReportsProgress = true;
            _worker.WorkerSupportsCancellation = true;

            _worker.DoWork += delegate(object s, DoWorkEventArgs args)
            {
                BackgroundWorker worker = s as BackgroundWorker;

                for (int i = 0; i < 10; i++)
                {
                    if (worker.CancellationPending)
                    {
                        args.Cancel = true;
                        return;
                    }

                    Thread.Sleep(1000);
                    worker.ReportProgress(i + 1);
                }

                System.Console.Beep(8000, 1000);
            };

            _worker.ProgressChanged += delegate(object s,
                    ProgressChangedEventArgs args)
            {
                progressBar1.Value = args.ProgressPercentage;
            };

            _worker.RunWorkerCompleted += delegate(object s,
                    RunWorkerCompletedEventArgs args)
            {
                start.IsEnabled = true;
                cancel.IsEnabled = false;
                progressBar1.Value = 0;
            };

            _worker.RunWorkerAsync();
            start.IsEnabled = false;
            cancel.IsEnabled = true;
        }

        private void cancel_Click(object sender, RoutedEventArgs e)
        {
            _worker.CancelAsync();
        }
    }
}
推荐.NET配套的通用数据层ORM框架:CYQ.Data 通用数据层框架
新浪微博粉丝精灵,刷粉丝、刷评论、刷转发、企业商家微博营销必备工具"