【问题标题】:how can i disable windows + d combination keys in windows forms如何在 Windows 窗体中禁用 windows + d 组合键
【发布时间】:2013-02-23 07:13:52
【问题描述】:

我有一个看起来像小部件的窗体

我必须禁用组合键,如 alt+f4 win+d 。因为小部件没有使用快捷键最小化关闭的属性。

我已禁用小部件中的 win+d 键,但它禁用了所有应用程序的快捷方式

我要做的就是只禁用我的应用程序的快捷键,比如小部件。

当 some1 按任意 win+d 时,Internet Explorer(如果打开)等后台应用程序将被最小化或最大化。

知道我该怎么做吗?

像雨量计或像 xwidget 一样具有相同的属性!知道他们怎么能做到这一点?

【问题讨论】:

  • 为什么要禁用 Win+X 和 Win+D?我理解为什么要使用 Alt+F4,但我认为不需要为“小部件”禁用这两者。
  • @AlvinWong win+x 是示例,对于 win+d,我希望我的 win 形式与小部件相同,并且我越来越接近它,我不想创建小部件项目,因为我的小部件将有处理不同的操作系统和规范,
  • 我相信你把一个简单的问题复杂化了。你可以解释你在你的程序中所期望的行为,因为我认为你可能想错了。
  • 只是我想要那个。我不希望我的表单被最小化,但应用程序(如果像音乐播放器一样打开)将被最小化或最大化
  • 所以重点是防止表单被最小化,但禁用这些组合键。

标签: c# winforms forms c#-4.0 keyboard-shortcuts


【解决方案1】:

你不能在 Winforms 中这样做

您必须创建一个Widget Project

【讨论】:

  • 虽然“小部件项目”可以解决问题,但您不应该说它绝对不能在 WinForms 中完成。
  • 那么,我可以看看你的答案:)
  • 从技术上讲,它可以做到,但出于实际目的,说它不能做到已经足够接近了。无论如何都不应该这样做。
  • @user1693655 我认为您误解了这个答案。您不是在创建小部件。您正在创建一个表单,然后查看它与小部件的不同之处,并一次更改所有这些内容。你甚至不应该那样尝试。如果你想要一个小部件,为什么不直接创建一个小部件?这样您就不必禁用任何全局快捷键,因为全局快捷键已经在做正确的事情了。
  • @user1693655 我不知道,我只知道您所问问题的答案对您没有帮助。禁用 Win+D 是错误的做法,如果您在其他应用程序处于活动状态时启用它,它会最小化您的窗口。找出要问的正确问题,你会得到更有用的答案。我认为正确的问题是“如何防止我的窗口被最小化”,但我不确定这是否不会遗漏一些其他细节。
【解决方案2】:

你可以使用全局键盘钩子,你可以看一个例子here, 然后在你的钩子中听 win + d 组合,在这种情况下不要传递呼叫转移

【讨论】:

    【解决方案3】:
    public partial class MainForm : Form
    {
            readonly KeyboardFilter kbFilter = new KeyboardFilter(new Keys[] 
            { 
                Keys.LWin | Keys.D,
                Keys.RWin | Keys.D, 
                Keys.LWin | Keys.X, 
                Keys.RWin | Keys.X,
                Keys.Alt | Keys.F4
            });
    }
    

    请务必在Form_Closing 事件中使用KeyboardFilter.Dispose()

    KeyboardFilter 类取自 Here

    class KeyboardFilter : IDisposable
    {
        private Keys[] mFilter;
        private IntPtr mHook;
        private readonly LowLevelKeyboardProc mProc;
    
        public KeyboardFilter(Keys[] keysToFilter)
        {
            // Install hook
            mFilter = keysToFilter;
            ProcessModule mod = Process.GetCurrentProcess().MainModule;
            mProc = KeyboardProc;   // Avoid garbage collector problems
            mHook = SetWindowsHookEx(13, mProc, GetModuleHandle(mod.ModuleName), 0);
            if (mHook == IntPtr.Zero) throw new Win32Exception(Marshal.GetLastWin32Error(), "Failed to set hook");
        }
        public void Dispose()
        {
            Dispose(true);
            GC.SuppressFinalize(this);
        }
        protected virtual void Dispose(bool disposing)
        {
            if (disposing)
            {
                // Release hook
                if (mHook != IntPtr.Zero)
                {
                    UnhookWindowsHookEx(mHook);
                    mHook = IntPtr.Zero;
                }
            }
        }
        ~KeyboardFilter()
        {
            Dispose(false);
        }
        private IntPtr KeyboardProc(int nCode, IntPtr wp, IntPtr lp)
        {
            // Callback, filter key
            if (nCode >= 0)
            {
                KBDLLHOOKSTRUCT info = (KBDLLHOOKSTRUCT)Marshal.PtrToStructure(lp, typeof(KBDLLHOOKSTRUCT));
                foreach (Keys key in mFilter)
                    if ((key & Keys.KeyCode) == info.key && CheckModifier(key)) return (IntPtr)1;
            }
            return CallNextHookEx(mHook, nCode, wp, lp);
        }
        private static bool CheckModifier(Keys key)
        {
            // Check if modifier key in required state
            if ((key & Keys.Control) == Keys.Control &&
              GetAsyncKeyState(Keys.LControlKey) == 0 && GetAsyncKeyState(Keys.RControlKey) == 0) return false;
            if ((key & Keys.Shift) == Keys.Shift &&
              GetAsyncKeyState(Keys.LShiftKey) == 0 && GetAsyncKeyState(Keys.RShiftKey) == 0) return false;
            if ((key & Keys.Alt) == Keys.Alt &&
              GetAsyncKeyState(Keys.LMenu) == 0 && GetAsyncKeyState(Keys.RMenu) == 0) return false;
            return true;
        }
    
        // P/Invoke declarations
        [StructLayout(LayoutKind.Sequential)]
        private struct KBDLLHOOKSTRUCT
        {
            public Keys key;
            public int scanCode;
            public int flags;
            public int time;
            public IntPtr extra;
        }
        private delegate IntPtr LowLevelKeyboardProc(int nCode, IntPtr wParam, IntPtr lParam);
        [DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = true)]
        private static extern IntPtr SetWindowsHookEx(int id, LowLevelKeyboardProc callback, IntPtr hMod, uint dwThreadId);
        [DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = true)]
        private static extern bool UnhookWindowsHookEx(IntPtr hook);
        [DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = true)]
        private static extern IntPtr CallNextHookEx(IntPtr hook, int nCode, IntPtr wp, IntPtr lp);
        [DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
        private static extern IntPtr GetModuleHandle(string name);
        [DllImport("user32.dll", CharSet = CharSet.Auto)]
        private static extern short GetAsyncKeyState(Keys key); 
    }
    

    【讨论】:

    • 好吧,你说“你在网上某个地方找到了这个”,那么你也应该参考出处并注明出处。
    • @AppDeveloper 它将禁用我的表单的 win 键,并且它会被启用?就像运行我的表单和 sm1 按 win+d 那么它不应该最小化我的应用程序,而是最小化背景应用程序,如 i.e 或音乐播放器?
    • @AppDeveloper 它适用于全球。将在所有应用程序中完成!我不想为所有人禁用它
    • 好吧,扩展KeyBoardFilter,添加一个布尔属性,仅当form为Normal时才抑制键|最大化!
    • 你能提供一些代码吗,因为上面的代码会破坏密钥并禁用它@AppDeveloper
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-07-31
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-02-10
    相关资源
    最近更新 更多