0

I'm creating a WPF application and I have three windows ( MainWindow, SecondWindow and CameraWindow). I have added shortcut ("m") to set the camera to image mode. This works fine when CameraWindow is active.

private void Window_KeyDown(object sender, KeyEventArgs e)
{
    var key = e.Key.ToString().ToLower();
    if (key.Contains("m"))
    {              
       camera.SetImageMode();                
    }
}

I'm looking for the way to set the camera to image mode anywhere in my application. I mean I should be able to set the camera to image mode from anywhere even CameraWindow is not active.

Ctrl+M could be the key combination.

Any suggestions are welcome!

Uwe Keim
  • 39,551
  • 56
  • 175
  • 291
TestMan
  • 77
  • 1
  • 1
  • 15
  • If you want to adhere to MVVM you might want to use `ICommand`s and `CommandBinding` references on your viewmodel and view respectively. In you case you might want a `KeyBinding` on your `Window.InputBindings`. – Adwaenyth Jul 27 '17 at 10:44
  • @Adwaenyth Thanks for your comment. Could you show / link me an example of doing that because I'm quite new in wpf... – TestMan Jul 27 '17 at 11:22
  • Depending on how much you know, or rather on how much you don't know yet, this could be quit lengthy. However you might want to start [here](https://stackoverflow.com/questions/24304969/how-to-bind-keyboard-input-command-to-main-window). – Adwaenyth Jul 27 '17 at 11:36

2 Answers2

0
public class KeyboardHandler : IDisposable
    {
        private readonly int _modKey;
        private const int WmHotkey = 0x0312;
        private readonly WindowInteropHelper _host;

        [DllImport("user32.dll")]
        [return: MarshalAs(UnmanagedType.Bool)]
        private static extern bool RegisterHotKey(IntPtr hWnd, int id, int fsModifiers, int vlc);

        [DllImport("user32.dll")]
        [return: MarshalAs(UnmanagedType.Bool)]
        private static extern bool UnregisterHotKey(IntPtr hWnd, int id);


        private readonly ISubject<Unit> _hotKeyHandleSubject = new Subject<Unit>();
        public IObservable<Unit> WhenHotKeyHandled { get { return _hotKeyHandleSubject.AsObservable(); } }

        /// <summary>
        /// 
        /// </summary>
        /// <param name="mainWindow">the handle to the main window</param>
        /// <param name="vkKey">the virtual key you need to press -> https://msdn.microsoft.com/en-us/library/ms927178.aspx </param>
        /// <param name="modKey">the modifier key you need to press (2 is CTRL by Default) -> https://msdn.microsoft.com/it-it/library/windows/desktop/ms646279(v=vs.85).aspx </param>
        public KeyboardHandler(Window mainWindow, int vkKey, int modKey = 2)
        {
            _modKey = modKey;
            _host = new WindowInteropHelper(mainWindow);

            SetupHotKey(_host.Handle, vkKey);
            ComponentDispatcher.ThreadPreprocessMessage += ComponentDispatcher_ThreadPreprocessMessage;
        }

        private void ComponentDispatcher_ThreadPreprocessMessage(ref MSG msg, ref bool handled)
        {
            if (msg.message == WmHotkey)
            {
                _hotKeyHandleSubject.OnNext(Unit.Default);
            }
        }

        private void SetupHotKey(IntPtr handle, int vkKey)
        {
            RegisterHotKey(handle, GetType().GetHashCode(), _modKey, vkKey);
        }

        public void Dispose()
        {
            ComponentDispatcher.ThreadPreprocessMessage -= ComponentDispatcher_ThreadPreprocessMessage;
            UnregisterHotKey(_host.Handle, GetType().GetHashCode());
        }
    }

use it like this:

_keyboardHandler = new KeyboardHandler(this, 0x4D);
            _disposable = _keyboardHandler.WhenHotKeyHandled.ObserveOn(SynchronizationContext.Current).Subscribe(_ =>
            {
                TextBlock.Text += new Random().Next(10) + "_";
            });

kudos to https://stackoverflow.com/a/1960122/2159837, i just modified it a bit

This works also if your application doesn't have focus

Easly
  • 334
  • 2
  • 11
0

After a long search and experiment, a solution has finally been found https://stackoverflow.com/a/12676910/8152725

TestMan
  • 77
  • 1
  • 1
  • 15