/// <inheritdoc /> protected override bool UpdatePlatform() { // Shift keys on windows tend to "stick" // When one key is held, the other doesn't receive down events, and an up event // is sent only to the latter one. To work around this manually query the status of both shift keys every tick. if (IsFocused) { KeyState lShift = User32.GetAsyncKeyState(VirtualKey.LSHIFT); UpdateKeyStatus(Key.LeftShift, lShift.IsPressed); KeyState rShift = User32.GetAsyncKeyState(VirtualKey.RSHIFT); UpdateKeyStatus(Key.RightShift, rShift.IsPressed); } while (User32.PeekMessage(out Message msg, IntPtr.Zero, 0, 0, PeekMessageFlags.PM_REMOVE)) { // Generated by task manager and stuff like that. // The WM_QUIT message is not associated with a window and therefore will never be received through a window's window procedure. if (msg.Value == WM.QUIT) { IsOpen = false; return(false); } User32.TranslateMessage(ref msg); User32.DispatchMessage(ref msg); } if (HostPaused) { User32.WaitMessage(); } return(true); }
private void CreateHelperWindow() { HelperWindowHandle = User32.CreateWindowEx( WindowExStyles.WS_EX_OVERLAPPEDWINDOW, CLASS_NAME, "Emotion Helper Window", WindowStyles.WS_CLIPSIBLINGS | WindowStyles.WS_CLIPCHILDREN, 0, 0, 100, 100, IntPtr.Zero, IntPtr.Zero, Kernel32.GetModuleHandle(null), IntPtr.Zero ); if (HelperWindowHandle == IntPtr.Zero) { CheckError("Win32: Failed to create helper window.", true); } // HACK: The command to the first ShowWindow call is ignored if the parent // process passed along a STARTUPINFO, so clear that with a no-op call User32.ShowWindow(HelperWindowHandle, ShowWindowCommands.SW_HIDE); // Register for HID device notifications var dbi = new DevBroadcastDeviceInterfaceW(); dbi.DbccSize = (uint)Marshal.SizeOf(dbi); dbi.DbccDeviceType = DeviceType.DeviceInterface; dbi.DbccClassGuid = User32Guids.GuidDevInterfaceHid; _deviceNotificationHandle = User32.RegisterDeviceNotificationW(HelperWindowHandle, ref dbi, DeviceNotificationFlags.WindowHandle); CheckError("Registering for device notifications."); while (User32.PeekMessage(out Message msg, HelperWindowHandle, 0, 0, PeekMessageFlags.PM_REMOVE)) { User32.TranslateMessage(ref msg); User32.DispatchMessage(ref msg); } Kernel32.SetLastError(0); CheckError("Creating helper window."); }
/// <inheritdoc /> protected override bool UpdatePlatform() { // Update input. // NOTE: Shift keys on Windows tend to "stick" when both are pressed as // no key up message is generated by the first key release // The other half of this is in the handling of WM_KEYUP // HACK: Query actual key state and synthesize release events as needed KeyState lShift = User32.GetAsyncKeyState(VirtualKey.LSHIFT); KeyState rShift = User32.GetAsyncKeyState(VirtualKey.RSHIFT); // Check if it was down, but no longer is. if (_keys[(short)Key.LeftShift] && lShift.Value != 0) { UpdateKeyStatus(Key.LeftShift, false); } if (_keys[(short)Key.RightShift] && rShift.Value != 0) { UpdateKeyStatus(Key.RightShift, false); } while (User32.PeekMessage(out Message msg, IntPtr.Zero, 0, 0, PeekMessageFlags.PM_REMOVE)) { // Things like the task manager will generate this message. if (msg.Value == WM.QUIT) { IsOpen = false; return(false); } User32.TranslateMessage(ref msg); User32.DispatchMessage(ref msg); } // Check if focused. if (!IsFocused && !Engine.Configuration.DebugMode) { User32.WaitMessage(); } return(true); }