namespace GalaSoft.MvvmLight.Messaging { using System; /// /// Use this class to send a message when the busy state of an application changes. /// public class BusyMessage : MessageBase { /// /// Initializes a new instance of the class. /// /// true if the application is busy; otherwise, false. /// Optional. User state information to include with the message. public BusyMessage(bool isBusy, object userState) : this(isBusy, userState, null) { } /// /// Initializes a new instance of the class. /// /// true if the application is busy; otherwise, false. /// Optional. User state information to include with the message. /// Optional. The message's original sender. public BusyMessage(bool isBusy, object userState, object sender) : base(sender) { this.IsBusy = isBusy; this.UserState = userState; } /// /// Gets a value indicating whether the application is currently in a busy state. /// public bool IsBusy { get; private set; } /// /// Gets user state information to include with the message. /// public object UserState { get; private set; } } } namespace GalaSoft.MvvmLight.Threading { using System; using System.Threading; using GalaSoft.MvvmLight.Messaging; /// /// Provides a thread-safe controller for managing the busy state of the application. /// public class BusyController : GalaSoft.MvvmLight.ObservableObject { private readonly object SyncRoot = new object(); private int count; /// /// Initializes static members of the class. /// static BusyController() { _default = new BusyController(); } /// /// Initializes a new instance of the class. /// public BusyController() : this(Messenger.Default) { } /// /// Initializes a new instance of the class. /// /// Optional. An which will be used to send messages. public BusyController(IMessenger messenger) { this.MessengerInstance = messenger; } private static BusyController _default; /// /// Gets the default busy controller instance. /// public static BusyController Default { get { return _default; } } private bool _isBusy; /// /// Gets a value indicating whether the controller is currently in the busy state. /// public bool IsBusy { get { return this._isBusy; } private set { if (this._isBusy != value) { this._isBusy = value; this.RaisePropertyChanged(() => this.IsBusy); } } } private IMessenger _messengerInstance; /// /// Gets the messenger instance used by the controller. /// protected IMessenger MessengerInstance { get { return this._messengerInstance; } set { if (this._messengerInstance != value) { this._messengerInstance = value; this.RaisePropertyChanged(() => this.MessengerInstance); } } } /// /// Resets the controller. /// public void Reset() { lock (this.SyncRoot) { this.IsBusy = false; this.count = 0; if (this.MessengerInstance != null) { // Send the message indicating that the controller is no longer busy. this.MessengerInstance.Send(new BusyMessage(this.IsBusy, null)); } } } /// /// Sends the message. /// /// true if the application is busy; otherwise, false when the application is no longer busy. public void SendMessage(bool value) { this.SendMessage(value, null); } /// /// Sends the message. /// /// true if the application is busy; otherwise, false when the application is no longer busy. /// Optional. User state data to include with the message if the controller transitions between busy states. public void SendMessage(bool value, object userState) { lock (this.SyncRoot) { bool send = false; if (value) { Interlocked.Increment(ref this.count); if (this.count == 1) { this.IsBusy = true; // The controller is now busy, send the message. send = true; } } else { if (this.count > 0) { Interlocked.Decrement(ref this.count); if (this.count == 0) { this.IsBusy = false; // The controller is no longer busy, send the message. send = true; } } } if (send && this.MessengerInstance != null) { this.MessengerInstance.Send(new BusyMessage(this.IsBusy, userState, this)); } } } } }