Removed the bitmap.GetHbitmap call for every redraw of the gadget. This should reduce dynamic memory allocation and freeing and removes some of the page faults increasing.
     1.1 --- a/GUI/Gadget.cs	Sun Jun 19 14:14:00 2011 +0000
     1.2 +++ b/GUI/Gadget.cs	Wed Jun 22 22:36:17 2011 +0000
     1.3 @@ -16,7 +16,7 @@
     1.4  
     1.5    The Initial Developer of the Original Code is 
     1.6    Michael Möller <m.moeller@gmx.ch>.
     1.7 -  Portions created by the Initial Developer are Copyright (C) 2010
     1.8 +  Portions created by the Initial Developer are Copyright (C) 2010-2011
     1.9    the Initial Developer. All Rights Reserved.
    1.10  
    1.11    Contributor(s):
    1.12 @@ -37,25 +37,22 @@
    1.13  
    1.14  using System;
    1.15  using System.Drawing;
    1.16 -using System.Drawing.Drawing2D;
    1.17 -using System.Drawing.Imaging;
    1.18 -using System.Drawing.Text;
    1.19  using System.Windows.Forms;
    1.20  
    1.21  namespace OpenHardwareMonitor.GUI {
    1.22    public abstract class Gadget : IDisposable {
    1.23  
    1.24      private GadgetWindow window;
    1.25 -    private Bitmap buffer;
    1.26 -    private Graphics graphics;
    1.27  
    1.28      public Gadget() {
    1.29        this.window = new GadgetWindow();
    1.30 -      CreateBuffer();
    1.31 +      this.window.Paint += delegate(object sender, PaintEventArgs e) {
    1.32 +        OnPaint(e);
    1.33 +      };
    1.34      }
    1.35  
    1.36      public virtual void Dispose() {
    1.37 -      DisposeBuffer();
    1.38 +      window.Dispose();
    1.39      }
    1.40  
    1.41      public Point Location {
    1.42 @@ -148,27 +145,6 @@
    1.43        }
    1.44      }
    1.45  
    1.46 -    private void CreateBuffer() {
    1.47 -      this.buffer = new Bitmap(window.Size.Width, window.Size.Height, 
    1.48 -        PixelFormat.Format32bppArgb);
    1.49 -      this.graphics = Graphics.FromImage(this.buffer);
    1.50 -      if (Environment.OSVersion.Version.Major > 5) {
    1.51 -        this.graphics.TextRenderingHint = TextRenderingHint.SystemDefault;
    1.52 -        this.graphics.SmoothingMode = SmoothingMode.HighQuality;
    1.53 -      }
    1.54 -    }
    1.55 -
    1.56 -    private void DisposeBuffer() {
    1.57 -      if (buffer != null) {
    1.58 -        this.buffer.Dispose();
    1.59 -        this.buffer = null;
    1.60 -      }
    1.61 -      if (graphics != null) {
    1.62 -        this.graphics.Dispose();
    1.63 -        this.graphics = null;
    1.64 -      }
    1.65 -    }
    1.66 -
    1.67      public bool Visible {
    1.68        get {
    1.69          return window.Visible;
    1.70 @@ -187,17 +163,7 @@
    1.71      public event EventHandler VisibleChanged;
    1.72  
    1.73      public void Redraw() {
    1.74 -      if (!window.Visible)
    1.75 -        return;
    1.76 -      
    1.77 -      if (window.Size != buffer.Size) {
    1.78 -        DisposeBuffer();
    1.79 -        CreateBuffer();
    1.80 -      }
    1.81 -
    1.82 -      OnPaint(new PaintEventArgs(graphics, 
    1.83 -        new Rectangle(Point.Empty, window.Size)));
    1.84 -      window.Update(buffer);
    1.85 +      window.Redraw();
    1.86      }
    1.87  
    1.88      protected abstract void OnPaint(PaintEventArgs e);
     2.1 --- a/GUI/GadgetWindow.cs	Sun Jun 19 14:14:00 2011 +0000
     2.2 +++ b/GUI/GadgetWindow.cs	Wed Jun 22 22:36:17 2011 +0000
     2.3 @@ -16,7 +16,7 @@
     2.4  
     2.5    The Initial Developer of the Original Code is 
     2.6    Michael Möller <m.moeller@gmx.ch>.
     2.7 -  Portions created by the Initial Developer are Copyright (C) 2010
     2.8 +  Portions created by the Initial Developer are Copyright (C) 2010-2011
     2.9    the Initial Developer. All Rights Reserved.
    2.10  
    2.11    Contributor(s):
    2.12 @@ -37,13 +37,15 @@
    2.13  
    2.14  using System;
    2.15  using System.Drawing;
    2.16 +using System.Drawing.Drawing2D;
    2.17 +using System.Drawing.Text;
    2.18  using System.Reflection;
    2.19  using System.Runtime.InteropServices;
    2.20  using System.Windows.Forms;
    2.21  
    2.22  namespace OpenHardwareMonitor.GUI {
    2.23  
    2.24 -  public class GadgetWindow : NativeWindow {
    2.25 +  public class GadgetWindow : NativeWindow, IDisposable {
    2.26  
    2.27      private bool visible = false;
    2.28      private bool lockPositionAndSize = false;
    2.29 @@ -53,6 +55,9 @@
    2.30      private Size size = new Size(130, 84);
    2.31      private ContextMenu contextMenu = null;
    2.32      private MethodInfo commandDispatch;
    2.33 +    private IntPtr handleBitmapDC;
    2.34 +    private Size bufferSize;
    2.35 +    private Graphics graphics;
    2.36  
    2.37      public GadgetWindow() {
    2.38        Type commandType = 
    2.39 @@ -73,6 +78,8 @@
    2.40            WindowAttribute.DWMWA_EXCLUDED_FROM_PEEK, ref value,
    2.41            Marshal.SizeOf(value));
    2.42        } catch (DllNotFoundException) { } catch (EntryPointNotFoundException) { }
    2.43 +
    2.44 +      CreateBuffer();
    2.45      }
    2.46  
    2.47      private void ShowDesktopChanged(bool showDesktop) {
    2.48 @@ -223,35 +230,66 @@
    2.49        return blend;
    2.50      }
    2.51  
    2.52 -    public void Update(Bitmap bitmap) {
    2.53 -      IntPtr screen = NativeMethods.GetDC(IntPtr.Zero);
    2.54 -      IntPtr memory = NativeMethods.CreateCompatibleDC(screen);
    2.55 -      IntPtr newHBitmap = IntPtr.Zero;
    2.56 -      IntPtr oldHBitmap = IntPtr.Zero;
    2.57 +    private void CreateBuffer() {      
    2.58 +      IntPtr handleScreenDC = NativeMethods.GetDC(IntPtr.Zero);
    2.59 +      handleBitmapDC = NativeMethods.CreateCompatibleDC(handleScreenDC);
    2.60 +      NativeMethods.ReleaseDC(IntPtr.Zero, handleScreenDC);
    2.61 +      bufferSize = size;
    2.62  
    2.63 -      try {
    2.64 -        newHBitmap = bitmap.GetHbitmap(Color.Black);
    2.65 -        oldHBitmap = NativeMethods.SelectObject(memory, newHBitmap);
    2.66 +      BitmapInfo info = new BitmapInfo();
    2.67 +      info.Size = Marshal.SizeOf(info);
    2.68 +      info.Width = size.Width;
    2.69 +      info.Height = -size.Height;
    2.70 +      info.BitCount = 32;
    2.71 +      info.Planes = 1;
    2.72 +
    2.73 +      IntPtr ptr;
    2.74 +      IntPtr hBmp = NativeMethods.CreateDIBSection(handleBitmapDC, ref info, 0, 
    2.75 +        out ptr, IntPtr.Zero, 0);
    2.76 +      IntPtr hBmpOld = NativeMethods.SelectObject(handleBitmapDC, hBmp);
    2.77 +      NativeMethods.DeleteObject(hBmpOld);
    2.78 +      
    2.79 +      graphics = Graphics.FromHdc(handleBitmapDC);
    2.80 +
    2.81 +      if (Environment.OSVersion.Version.Major > 5) {
    2.82 +        this.graphics.TextRenderingHint = TextRenderingHint.SystemDefault;
    2.83 +        this.graphics.SmoothingMode = SmoothingMode.HighQuality;
    2.84 +      } 
    2.85 +    }
    2.86 +
    2.87 +    private void DisposeBuffer() {
    2.88 +      graphics.Dispose();
    2.89 +      NativeMethods.DeleteDC(handleBitmapDC);
    2.90 +    }
    2.91 +
    2.92 +    public virtual void Dispose() {
    2.93 +      DisposeBuffer();
    2.94 +    } 
    2.95 +
    2.96 +    public PaintEventHandler Paint; 
    2.97 +
    2.98 +    public void Redraw() {
    2.99 +      if (!visible || Paint == null)
   2.100 +        return;
   2.101 +
   2.102 +      if (size != bufferSize) {
   2.103 +        DisposeBuffer();
   2.104 +        CreateBuffer();
   2.105 +      }
   2.106 +
   2.107 +      Paint(this, 
   2.108 +        new PaintEventArgs(graphics, new Rectangle(Point.Empty, size))); 
   2.109  
   2.110          Point pointSource = Point.Empty;
   2.111          BlendFunction blend = CreateBlendFunction();
   2.112  
   2.113 -        NativeMethods.UpdateLayeredWindow(Handle, screen, IntPtr.Zero,
   2.114 -          ref size, memory, ref pointSource, 0, ref blend, ULW_ALPHA);
   2.115 +        NativeMethods.UpdateLayeredWindow(Handle, IntPtr.Zero, IntPtr.Zero,
   2.116 +          ref size, handleBitmapDC, ref pointSource, 0, ref blend, ULW_ALPHA);
   2.117  
   2.118          // make sure the window is at the right location
   2.119 -        NativeMethods.SetWindowPos(Handle, IntPtr.Zero, 
   2.120 -          location.X, location.Y, 0, 0, SWP_NOSIZE | SWP_NOACTIVATE | 
   2.121 +        NativeMethods.SetWindowPos(Handle, IntPtr.Zero,
   2.122 +          location.X, location.Y, 0, 0, SWP_NOSIZE | SWP_NOACTIVATE |
   2.123            SWP_NOZORDER | SWP_NOSENDCHANGING);
   2.124 -
   2.125 -      } finally {        
   2.126 -        if (newHBitmap != IntPtr.Zero) {
   2.127 -          NativeMethods.SelectObject(memory, oldHBitmap);
   2.128 -          NativeMethods.DeleteObject(newHBitmap);
   2.129 -        }
   2.130 -        NativeMethods.DeleteDC(memory);
   2.131 -        NativeMethods.ReleaseDC(IntPtr.Zero, screen);
   2.132 -      }
   2.133      }
   2.134  
   2.135      public byte Opacity {
   2.136 @@ -386,6 +424,22 @@
   2.137        public uint flags;
   2.138      }
   2.139  
   2.140 +    [StructLayout(LayoutKind.Sequential)]
   2.141 +    public struct BitmapInfo {
   2.142 +      public Int32 Size;
   2.143 +      public Int32 Width;
   2.144 +      public Int32 Height;
   2.145 +      public Int16 Planes;
   2.146 +      public Int16 BitCount;
   2.147 +      public Int32 Compression;
   2.148 +      public Int32 SizeImage;
   2.149 +      public Int32 XPelsPerMeter;
   2.150 +      public Int32 YPelsPerMeter;
   2.151 +      public Int32 ClrUsed;
   2.152 +      public Int32 ClrImportant;
   2.153 +      public Int32 Colors;
   2.154 +    }
   2.155 +
   2.156      public static readonly IntPtr HWND_BOTTOM = (IntPtr)1;
   2.157      public static readonly IntPtr HWND_TOPMOST = (IntPtr)(-1);
   2.158  
   2.159 @@ -501,6 +555,11 @@
   2.160        public static extern IntPtr CreateCompatibleDC(IntPtr hDC);
   2.161  
   2.162        [DllImport(GDI, CallingConvention = CallingConvention.Winapi)]
   2.163 +      public static extern IntPtr CreateDIBSection(IntPtr hdc, 
   2.164 +        [In] ref BitmapInfo pbmi, uint pila, out IntPtr ppvBits, 
   2.165 +        IntPtr hSection, uint dwOffset);
   2.166 +
   2.167 +      [DllImport(GDI, CallingConvention = CallingConvention.Winapi)]
   2.168        [return: MarshalAs(UnmanagedType.Bool)]
   2.169        public static extern bool DeleteDC(IntPtr hdc);
   2.170