static HWND() { NULL = new HWND(IntPtr.Zero); BROADCAST = new HWND(new IntPtr(0xffff)); MESSAGE = new HWND(new IntPtr(-3)); DESKTOP = new HWND(new IntPtr(0)); TOP = new HWND(new IntPtr(0)); BOTTOM = new HWND(new IntPtr(1)); TOPMOST = new HWND(new IntPtr(-1)); NOTOPMOST = new HWND(new IntPtr(-2)); }
/// <summary> /// Hooks into the stream of messages that are dispatched to the /// specified window. /// </summary> /// <remarks> /// The window must be owned by the calling thread. /// </remarks> public WindowSubclass(HWND hwnd) { if (!IsCorrectThread(hwnd)) { throw new InvalidOperationException("May not hook a window created by a different thread."); } _hwnd = hwnd; _wndproc = WndProcStub; _wndprocPtr = Marshal.GetFunctionPointerForDelegate(_wndproc); // Because our window proc is an instance method, it is connected // to this instance of WindowSubclass, where we can store state. // We do not need to store any extra state in native memory. NativeMethods.SetWindowSubclass(hwnd, _wndproc, IntPtr.Zero, IntPtr.Zero); }
public static extern int SetClassLong(HWND hwnd, GCL nIndex, int dwNewLong);
private IntPtr WndProc(HWND hwnd, WM msg, IntPtr wParam, IntPtr lParam, IntPtr id, IntPtr data) { IntPtr retval = IntPtr.Zero; try { retval = WndProcOverride(hwnd, msg, wParam, lParam, id, data); } finally { if (_hwnd != HWND.NULL) { Debug.Assert(_hwnd == hwnd); if (msg == WM.NCDESTROY) { Dispose(); } else if (msg == _disposeMessage && wParam == _wndprocPtr) { DisposeHelper(lParam == IntPtr.Zero ? false : true); } } } return retval; }
protected virtual IntPtr WndProcOverride(HWND hwnd, WM msg, IntPtr wParam, IntPtr lParam, IntPtr id, IntPtr data) { // Call the next window proc in the subclass chain. return NativeMethods.DefSubclassProc(hwnd, msg, wParam, lParam); }
public bool Equals(HWND other) { if (Object.ReferenceEquals(other, null)) { return handle == IntPtr.Zero; } else { return other.handle == handle; } }
public static extern IntPtr DefWindowProc(HWND hWnd, WM Msg, IntPtr wParam, IntPtr lParam);
public static extern HWND CreateWindowEx(WS_EX dwExStyle, string lpClassName, string lpWindowName, WS dwStyle, int x, int y, int nWidth, int nHeight, HWND hWndParent, IntPtr hMenu, IntPtr hInstance, IntPtr lpParam);
public static extern int SetWindowLong(HWND hwnd, GWL nIndex, int dwNewLong);
public static extern IntPtr SetTimer(HWND hWnd, IntPtr nIDEvent, int uElapse, TIMERPROC lpTimerFunc);
public static extern HWND SetParent(HWND hwndChild, HWND hwndNewParent);
public static extern bool SetLayeredWindowAttributes(HWND hwnd, uint crKey, byte bAlpha, LWA dwFlags);
public static extern IntPtr SetCoalescableTimer(HWND hwnd, IntPtr nIDEvent, int uElapse, TIMERPROC lpTimerFunc, int uToleranceDelay);
public static extern bool ClientToScreen(HWND hwnd, ref POINT lpPoint);
public static extern short SetClassWord(HWND hwnd, GCW nIndex, short dwNewLong);
private static extern IntPtr _SetClassLongPtr(HWND hwnd, GCL nIndex, IntPtr dwNewLong);
private static extern IntPtr _SetWindowLongPtr(HWND hwnd, GWL nIndex, IntPtr dwNewLong);
public static IntPtr SetWindowLongPtr(HWND hwnd, GWL nIndex, IntPtr dwNewLong) { if (IntPtr.Size == 4) { // The SetWindowLongPtr entrypoint may not exist on 32-bit // OSes, so use the legacy SetWindowLong function instead. return new IntPtr(SetWindowLong(hwnd, nIndex, dwNewLong.ToInt32())); } else { return _SetWindowLongPtr(hwnd, nIndex, dwNewLong); } }
public static extern IntPtr DefSubclassProc(HWND hwnd, WM msg, IntPtr wParam, IntPtr lParam);
public static extern bool SetWindowPos(HWND hwnd, HWND hWndInsertAfter, int X, int Y, int cx, int cy, SWP uFlags);
public static extern bool DestroyWindow(HWND hwnd);
public static extern bool SetWindowSubclass(HWND hwnd, SUBCLASSPROC callback, IntPtr id, IntPtr data);
public static extern bool ShowWindow(HWND hWnd, SW nCmdShow);
private static extern IntPtr _GetClassLongPtr(HWND hwnd, GCL nIndex);
private bool IsCorrectThread(HWND hwnd) { int processId; int threadId = NativeMethods.GetWindowThreadProcessId(hwnd, out processId); return (processId == NativeMethods.GetCurrentProcessId() && threadId == NativeMethods.GetCurrentThreadId()); }
private static extern int _GetClassName(HWND hWnd, StringBuilder lpClassName, int nMaxCount);
private IntPtr WndProcStub(IntPtr hwnd, int msg, IntPtr wParam, IntPtr lParam, IntPtr id, IntPtr data) { HWND hwnd2 = new HWND(hwnd); return WndProc(hwnd2, (WM)msg, wParam, lParam, id, data); }
private static extern IntPtr _GetWindowLongPtr(HWND hwnd, GWL nIndex);
protected virtual void Dispose(bool disposing) { if(_hwnd == null || !IsCorrectThread(_hwnd)) { throw new InvalidOperationException("Dispose virtual should only be called by WindowSubclass once on the correct thread."); } NativeMethods.RemoveWindowSubclass(_hwnd, _wndproc, IntPtr.Zero); _hwnd = null; }
public static extern IntPtr SendMessage(HWND hwnd, WM msg, IntPtr wParam, IntPtr lParam);