Skip to main content

SystemEvents issues

SystemEvents is a class that allows users to receive events that are system-wide. These events range from system time changing (due to daylight savings or time sync or manual time changes) to SessionEnding to LowBattery, to FontsInstalled events, etc.

There are many issues with this class
1- It does not work in a Windows Service, unless the service interacts with the desktop (which is an XP feature only). Vista and Windows 7 has an awkward support to say the least for services that interact with the windows desktop. As far as I'm concerned, it is not supported.
2- If you call any SystemEvent.XYZ += OnXYZ;, this ends up creating a hidden window. So what's the problem? if you have any WCF objects that register themselves (using WCF's ServiceHost) in the same thread as the one that called SystemEvents, then all subsequent calls to the WCF services will be serialized on that thread. Most likely that thread is the main UI thread for your application. This results in nasty deadlocks that are very difficult to debug and isolate.

So what's the solution?
I tried various methods including the Microsoft's suggested way to handle this issue http://msdn.microsoft.com/en-us/library/microsoft.win32.systemevents_events.aspx but SystemEvents seems to have a mind of its own and you will fix #1 above but you will still end up with #2.

I decided to write my own System Events class as  it is simple and straight forward.
I was mainly focused on the TimeChanged event but you can add other events as needed

public class SystemEventsEx : NativeWindow
{
   public event EventHandler TimeChanged = null;


   public SystemEventsEx()
   {
       CreateParams cp = new CreateParams();
       cp.Caption = "WindowsMessageTarget";
       cp.Width = 0;
       cp.Height = 0;
       cp.X = 0;
       cp.Y = 0;
       cp.Parent = IntPtr.Zero;
       CreateHandle(cp);
     }


   protected override void WndProc(ref Message m)
   {
      if (m.Msg == WindowsMessages.WmTimeChanged)
      {
          TimeChanged((object)null, (EventArgs)null);
      }
      base.WndProc(ref m);
   }
}

Make a stsatic class that can host the SystemEvents instance and allow subscriptions to systm events as follows:

public static class MyApplication
{
   private static SystemEventsEx _systemEvents = null;


   public static SystemEventsEx SystemEvents
  {    get { return _systemEvents; } }


   public static EnableSystemEvents()
   {
       Thread t = new Thread(OnEnableSystemEvents);  
       t.IsBackground = true;
       t.Start();
   }


   private static void OnEnableSystemEvents()
   {
      _systemEvents = new SystemEventsEx();
      Application.Run();
   }
}

In you main.cs
you can do the following:
[STAThread]
public static void Main(string[] args)
{
   . . .
    MyApplication.EnableSystemEvents();
   . . .
}

Comments

Popular posts from this blog

Track Files in Visual Studio

By default, Visual Studio’s Solution Explorer will update its selected item based on the currently active document. This is extremely annoying as it keeps expanding your projects and folders until your solution explorer becomes unmanageable and unusable, unless you collapse all Projects (Only available if you have Visual Studio Power Commands) installed) and even then, after collapsing the entire solution, the saga returns back. Turn off Active tracking 1. Turn your Active tracking off by going to Tools > Options 2. Select “Projects and Solutions” node 3. Uncheck the “Tack Active Item in Solution Explorer” Add a macro to do on-demand tracking 4. Tools > Marcos > Macro Explorer 5. You will see “MyMacros” Module (Node). Right mouse click on MyMacros and invoke “New Module…” 6. Name it anything you like. I Named it Utilities 7. Right mouse click on Utilizes and invoke “new Macro…” menu. The Macros IDE window opens. 8. Paste in the following into it within the Publ...

Google Instant search

Google Instant Search is the worst feature ever!!!. I could not for the life of me find a PERMANENT way to turn it off. Every time I turned it off using different means, it always came back. This is the only link I found useful so far, but the suggestion is not that great. It's OK. http://www.google.com/support/forum/p/Web%20Search/thread?tid=2a8bc9c3770bc11b&hl=en It is so annoying and so intrusive, every time I type a character it interrupts me and then I end up because of the time lag with a different string in the search box than the one I intended to type. Are they hiring a whole new set of STUPID generation at Google. This does not take a rocket scientist to figure out that this feature is useless. Even if they believe that is has some usefulness, let me (the customer, the user) decide. Anyone knows how to turn this stupid feature off?

Reduce Windows Folder Size

I just realized that my Windows directory has over 34 GB of stuff. What the heck!!! When you have Office, a couple of versions of Visual Studio, and few other Microsoft programs, you basically have already gobbled up about 80 GB of hard disk space. I found this online and found it to be useful and effective. It shaves off about 8 GB of your Windows folder. Still not what I had expected but I can definitely use 8 GB for other important documents. I'm just puzzled at what is Micros soft putting in an Operating system folder? huh? 28 GB of crap? Open a command prompt (make sure you either have Admin privileges). If you do not have Admin privileges, then open the command prompt as Admin. dism /online /cleanup-image /spsuperseded /hidesp