| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217 |
- #pragma warning disable 0618
- using System;
- using System.Text;
- using System.Runtime.InteropServices;
- using System.Security.Permissions;
- [assembly: SecurityPermission(SecurityAction.RequestMinimum, UnmanagedCode = true)]
- namespace System.Windows
- {
- public class MessageBoxManager
- {
- private delegate IntPtr HookProc(int nCode, IntPtr wParam, IntPtr lParam);
- private delegate bool EnumChildProc(IntPtr hWnd, IntPtr lParam);
- private const int WH_CALLWNDPROCRET = 12;
- private const int WM_DESTROY = 0x0002;
- private const int WM_INITDIALOG = 0x0110;
- private const int WM_TIMER = 0x0113;
- private const int WM_USER = 0x400;
- private const int DM_GETDEFID = WM_USER + 0;
- private const int MBOK = 1;
- private const int MBCancel = 2;
- private const int MBAbort = 3;
- private const int MBRetry = 4;
- private const int MBIgnore = 5;
- private const int MBYes = 6;
- private const int MBNo = 7;
- [DllImport("user32.dll")]
- private static extern IntPtr SendMessage(IntPtr hWnd, int Msg, IntPtr wParam, IntPtr lParam);
- [DllImport("user32.dll")]
- private static extern IntPtr SetWindowsHookEx(int idHook, HookProc lpfn, IntPtr hInstance, int threadId);
- [DllImport("user32.dll")]
- private static extern int UnhookWindowsHookEx(IntPtr idHook);
-
- [DllImport("user32.dll")]
- private static extern IntPtr CallNextHookEx(IntPtr idHook, int nCode, IntPtr wParam, IntPtr lParam);
- [DllImport("user32.dll", EntryPoint = "GetWindowTextLengthW", CharSet = CharSet.Unicode)]
- private static extern int GetWindowTextLength(IntPtr hWnd);
- [DllImport("user32.dll", EntryPoint = "GetWindowTextW", CharSet = CharSet.Unicode)]
- private static extern int GetWindowText(IntPtr hWnd, StringBuilder text, int maxLength);
- [DllImport("user32.dll")]
- private static extern int EndDialog(IntPtr hDlg, IntPtr nResult);
- [DllImport("user32.dll")]
- private static extern bool EnumChildWindows(IntPtr hWndParent, EnumChildProc lpEnumFunc, IntPtr lParam);
- [DllImport("user32.dll", EntryPoint = "GetClassNameW", CharSet = CharSet.Unicode)]
- private static extern int GetClassName(IntPtr hWnd, StringBuilder lpClassName, int nMaxCount);
- [DllImport("user32.dll")]
- private static extern int GetDlgCtrlID(IntPtr hwndCtl);
- [DllImport("user32.dll")]
- private static extern IntPtr GetDlgItem(IntPtr hDlg, int nIDDlgItem);
- [DllImport("user32.dll", EntryPoint = "SetWindowTextW", CharSet = CharSet.Unicode)]
- private static extern bool SetWindowText(IntPtr hWnd, string lpString);
- [StructLayout(LayoutKind.Sequential)]
- public struct CWPRETSTRUCT
- {
- public IntPtr lResult;
- public IntPtr lParam;
- public IntPtr wParam;
- public uint message;
- public IntPtr hwnd;
- };
- private static HookProc hookProc;
- private static EnumChildProc enumProc;
- [ThreadStatic]
- private static IntPtr hHook;
- [ThreadStatic]
- private static int nButton;
- /// <summary>
- /// OK text
- /// </summary>
- public static string OK = "&OK";
- /// <summary>
- /// Cancel text
- /// </summary>
- public static string Cancel = "&Cancel";
- /// <summary>
- /// Abort text
- /// </summary>
- public static string Abort = "&Abort";
- /// <summary>
- /// Retry text
- /// </summary>
- public static string Retry = "&Retry";
- /// <summary>
- /// Ignore text
- /// </summary>
- public static string Ignore = "&Ignore";
- /// <summary>
- /// Yes text
- /// </summary>
- public static string Yes = "&Yes";
- /// <summary>
- /// No text
- /// </summary>
- public static string No = "&No";
- static MessageBoxManager()
- {
- hookProc = new HookProc(MessageBoxHookProc);
- enumProc = new EnumChildProc(MessageBoxEnumProc);
- hHook = IntPtr.Zero;
- }
-
- /// <summary>
- /// Enables MessageBoxManager functionality
- /// </summary>
- /// <remarks>
- /// MessageBoxManager functionality is enabled on current thread only.
- /// Each thread that needs MessageBoxManager functionality has to call this method.
- /// </remarks>
- public static void Register()
- {
- if (hHook != IntPtr.Zero)
- throw new NotSupportedException("One hook per thread allowed.");
- hHook = SetWindowsHookEx(WH_CALLWNDPROCRET, hookProc, IntPtr.Zero, AppDomain.GetCurrentThreadId());
- }
- /// <summary>
- /// Disables MessageBoxManager functionality
- /// </summary>
- /// <remarks>
- /// Disables MessageBoxManager functionality on current thread only.
- /// </remarks>
- public static void Unregister()
- {
- if (hHook != IntPtr.Zero)
- {
- UnhookWindowsHookEx(hHook);
- hHook = IntPtr.Zero;
- }
- }
-
- private static IntPtr MessageBoxHookProc(int nCode, IntPtr wParam, IntPtr lParam)
- {
- if (nCode < 0)
- return CallNextHookEx(hHook, nCode, wParam, lParam);
- CWPRETSTRUCT msg = (CWPRETSTRUCT)Marshal.PtrToStructure(lParam, typeof(CWPRETSTRUCT));
- IntPtr hook = hHook;
- if (msg.message == WM_INITDIALOG)
- {
- int nLength = GetWindowTextLength(msg.hwnd);
- StringBuilder className = new StringBuilder(10);
- GetClassName(msg.hwnd, className, className.Capacity);
- if (className.ToString() == "#32770")
- {
- nButton = 0;
- EnumChildWindows(msg.hwnd, enumProc, IntPtr.Zero);
- if (nButton == 1)
- {
- IntPtr hButton = GetDlgItem(msg.hwnd, MBCancel);
- if (hButton != IntPtr.Zero)
- SetWindowText(hButton, OK);
- }
- }
- }
- return CallNextHookEx(hook, nCode, wParam, lParam);
- }
- private static bool MessageBoxEnumProc(IntPtr hWnd, IntPtr lParam)
- {
- StringBuilder className = new StringBuilder(10);
- GetClassName(hWnd, className, className.Capacity);
- if (className.ToString() == "Button")
- {
- int ctlId = GetDlgCtrlID(hWnd);
- switch (ctlId)
- {
- case MBOK:
- SetWindowText(hWnd, OK);
- break;
- case MBCancel:
- SetWindowText(hWnd, Cancel);
- break;
- case MBAbort:
- SetWindowText(hWnd, Abort);
- break;
- case MBRetry:
- SetWindowText(hWnd, Retry);
- break;
- case MBIgnore:
- SetWindowText(hWnd, Ignore);
- break;
- case MBYes:
- SetWindowText(hWnd, Yes);
- break;
- case MBNo:
- SetWindowText(hWnd, No);
- break;
- }
- nButton++;
- }
- return true;
- }
- }
- }
|