Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion src/cascadia/TerminalApp/CommandPalette.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -385,7 +385,7 @@ namespace winrt::TerminalApp::implementation
// - Implements the Alt handler
// Return value:
// - whether the key was handled
bool CommandPalette::OnDirectKeyEvent(const uint32_t vkey, const uint8_t /*scanCode*/, const bool down)
bool CommandPalette::OnDirectKeyEvent(const uint32_t vkey, const uint8_t /*scanCode*/, const bool /*extended*/, const bool down)
{
auto handled = false;
if (_currentMode == CommandPaletteMode::TabSwitchMode)
Expand Down
2 changes: 1 addition & 1 deletion src/cascadia/TerminalApp/CommandPalette.h
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ namespace winrt::TerminalApp::implementation
void SetTabs(const Windows::Foundation::Collections::IObservableVector<winrt::TerminalApp::Tab>& tabs, const Windows::Foundation::Collections::IObservableVector<winrt::TerminalApp::Tab>& mruTabs);
void SetActionMap(const Microsoft::Terminal::Settings::Model::IActionMapView& actionMap);

bool OnDirectKeyEvent(const uint32_t vkey, const uint8_t scanCode, const bool down);
bool OnDirectKeyEvent(const uint32_t vkey, const uint8_t scanCode, const bool extended, const bool down);

void SelectNextItem(const bool moveDown);

Expand Down
2 changes: 1 addition & 1 deletion src/cascadia/TerminalApp/SuggestionsControl.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -460,7 +460,7 @@ namespace winrt::TerminalApp::implementation
// - Implements the Alt handler
// Return value:
// - whether the key was handled
bool SuggestionsControl::OnDirectKeyEvent(const uint32_t /*vkey*/, const uint8_t /*scanCode*/, const bool /*down*/)
bool SuggestionsControl::OnDirectKeyEvent(const uint32_t /*vkey*/, const uint8_t /*scanCode*/, const bool /*extended*/, const bool /*down*/)
{
auto handled = false;
return handled;
Expand Down
2 changes: 1 addition & 1 deletion src/cascadia/TerminalApp/SuggestionsControl.h
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ namespace winrt::TerminalApp::implementation

void SetCommands(const Windows::Foundation::Collections::IVector<Microsoft::Terminal::Settings::Model::Command>& actions);

bool OnDirectKeyEvent(const uint32_t vkey, const uint8_t scanCode, const bool down);
bool OnDirectKeyEvent(const uint32_t vkey, const uint8_t scanCode, const bool extended, const bool down);

void SelectNextItem(const bool moveDown);

Expand Down
2 changes: 1 addition & 1 deletion src/cascadia/TerminalApp/TerminalPage.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1890,7 +1890,7 @@ namespace winrt::TerminalApp::implementation
e.Handled(true);
}

bool TerminalPage::OnDirectKeyEvent(const uint32_t vkey, const uint8_t scanCode, const bool down)
bool TerminalPage::OnDirectKeyEvent(const uint32_t vkey, const uint8_t scanCode, const bool /*extended*/, const bool down)
{
const auto modifiers = _GetPressedModifierKeys();
if (vkey == VK_SPACE && modifiers.IsAltPressed() && down)
Expand Down
2 changes: 1 addition & 1 deletion src/cascadia/TerminalApp/TerminalPage.h
Original file line number Diff line number Diff line change
Expand Up @@ -222,7 +222,7 @@ namespace winrt::TerminalApp::implementation
void WindowActivated(const bool activated);
bool FocusTab(const winrt::TerminalApp::Tab& tab);

bool OnDirectKeyEvent(const uint32_t vkey, const uint8_t scanCode, const bool down);
bool OnDirectKeyEvent(const uint32_t vkey, const uint8_t scanCode, const bool extended, const bool down);

void AttachContent(Windows::Foundation::Collections::IVector<Microsoft::Terminal::Settings::Model::ActionAndArgs> args, uint32_t tabIndex);
void SendContentToOther(winrt::TerminalApp::RequestReceiveContentArgs args);
Expand Down
6 changes: 3 additions & 3 deletions src/cascadia/TerminalApp/TerminalWindow.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -910,7 +910,7 @@ namespace winrt::TerminalApp::implementation
// - Implements the Alt handler (per GH#6421)
// Return value:
// - whether the key was handled
bool TerminalWindow::OnDirectKeyEvent(const uint32_t vkey, const uint8_t scanCode, const bool down)
bool TerminalWindow::OnDirectKeyEvent(const uint32_t vkey, const uint8_t scanCode, const bool extended, const bool down)
{
if (_root)
{
Expand All @@ -926,7 +926,7 @@ namespace winrt::TerminalApp::implementation
{
if (auto keyListener{ focusedObject.try_as<UI::IDirectKeyListener>() })
{
if (keyListener.OnDirectKeyEvent(vkey, scanCode, down))
if (keyListener.OnDirectKeyEvent(vkey, scanCode, extended, down))
{
return true;
}
Expand Down Expand Up @@ -954,7 +954,7 @@ namespace winrt::TerminalApp::implementation
{
if (auto keyListener{ _root.try_as<UI::IDirectKeyListener>() })
{
return keyListener.OnDirectKeyEvent(vkey, scanCode, down);
return keyListener.OnDirectKeyEvent(vkey, scanCode, extended, down);
}
}
}
Expand Down
2 changes: 1 addition & 1 deletion src/cascadia/TerminalApp/TerminalWindow.h
Original file line number Diff line number Diff line change
Expand Up @@ -119,7 +119,7 @@ namespace winrt::TerminalApp::implementation

hstring Title();
void TitlebarClicked();
bool OnDirectKeyEvent(const uint32_t vkey, const uint8_t scanCode, const bool down);
bool OnDirectKeyEvent(const uint32_t vkey, const uint8_t scanCode, const bool extended, const bool down);

void CloseWindow();
void WindowVisibilityChanged(const bool showOrHide);
Expand Down
13 changes: 11 additions & 2 deletions src/cascadia/TerminalControl/TermControl.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1535,9 +1535,18 @@ namespace winrt::Microsoft::Terminal::Control::implementation
// normally. Namely, the keys we're concerned with are F7 down and Alt up.
// Return value:
// - Whether the key was handled.
bool TermControl::OnDirectKeyEvent(const uint32_t vkey, const uint8_t scanCode, const bool down)
bool TermControl::OnDirectKeyEvent(const uint32_t vkey, const uint8_t scanCode, const bool extended, const bool down)
{
const auto modifiers{ _GetPressedModifierKeys() };
auto modifiers{ _GetPressedModifierKeys() };

// GH#18120: Direct key events bypass the regular _KeyHandler path,
// which gets the extended-key state from CorePhysicalKeyStatus.
// Without this, releasing e.g. RightAlt loses its ENHANCED_KEY flag.
if (extended)
{
modifiers |= ControlKeyStates::EnhancedKey;
}

return _KeyHandler(gsl::narrow_cast<WORD>(vkey), gsl::narrow_cast<WORD>(scanCode), modifiers, down);
}

Expand Down
2 changes: 1 addition & 1 deletion src/cascadia/TerminalControl/TermControl.h
Original file line number Diff line number Diff line change
Expand Up @@ -144,7 +144,7 @@ namespace winrt::Microsoft::Terminal::Control::implementation

bool SearchBoxEditInFocus() const;

bool OnDirectKeyEvent(const uint32_t vkey, const uint8_t scanCode, const bool down);
bool OnDirectKeyEvent(const uint32_t vkey, const uint8_t scanCode, const bool extended, const bool down);

bool OnMouseWheel(const Windows::Foundation::Point location, const winrt::Microsoft::Terminal::Core::Point delta, const bool leftButtonDown, const bool midButtonDown, const bool rightButtonDown);

Expand Down
2 changes: 1 addition & 1 deletion src/cascadia/TerminalControl/TermControl.idl
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ namespace Microsoft.Terminal.Control
// WinRT is a trip.
[uuid("0ddf4edc-3fda-4dee-97ca-a417ee3dd510")]
interface IDirectKeyListener {
Boolean OnDirectKeyEvent(UInt32 vkey, UInt8 scanCode, Boolean down);
Boolean OnDirectKeyEvent(UInt32 vkey, UInt8 scanCode, Boolean extended, Boolean down);
}

enum CursorDisplayState
Expand Down
2 changes: 2 additions & 0 deletions src/cascadia/TerminalCore/Terminal.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,7 @@ namespace TerminalCoreUnitTests
class TerminalBufferTests;
class TerminalApiTest;
class ScrollTest;
class InputTest;
};
#endif

Expand Down Expand Up @@ -491,5 +492,6 @@ class Microsoft::Terminal::Core::Terminal final :
friend class TerminalCoreUnitTests::TerminalBufferTests;
friend class TerminalCoreUnitTests::TerminalApiTest;
friend class TerminalCoreUnitTests::ScrollTest;
friend class TerminalCoreUnitTests::InputTest;
#endif
};
2 changes: 1 addition & 1 deletion src/cascadia/UIHelpers/IDirectKeyListener.idl
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,6 @@ namespace Microsoft.Terminal.UI
{
[uuid("0ddf4edc-3fda-4dee-97ca-a417ee3dd510")]
interface IDirectKeyListener {
Boolean OnDirectKeyEvent(UInt32 vkey, UInt8 scanCode, Boolean down);
Boolean OnDirectKeyEvent(UInt32 vkey, UInt8 scanCode, Boolean extended, Boolean down);
}
}
26 changes: 26 additions & 0 deletions src/cascadia/UnitTests_TerminalCore/InputTest.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ namespace TerminalCoreUnitTests

TEST_METHOD(AltShiftKey);
TEST_METHOD(InvalidKeyEvent);
TEST_METHOD(Win32KeyEventsRetainEnhancedKey);

Terminal term{ Terminal::TestDummyMarker{} };
};
Expand All @@ -52,4 +53,29 @@ namespace TerminalCoreUnitTests
VERIFY_ARE_EQUAL(unhandled(), term.SendKeyEvent(0, 123, {}, true));
VERIFY_ARE_EQUAL(unhandled(), term.SendKeyEvent(255, 123, {}, true));
}

void InputTest::Win32KeyEventsRetainEnhancedKey()
{
// Tests GH#18120
// In win32-input-mode, both the press and the release of an extended
// key (e.g. RightAlt) must encode the ENHANCED_KEY flag (0x100) in the
// Cs parameter, so that the client can distinguish RightAlt from LeftAlt.
auto& input = term._getTerminalInput();
input.SetInputMode(Microsoft::Console::VirtualTerminal::TerminalInput::Mode::Win32, true);
const auto restore = wil::scope_exit([&]() {
input.SetInputMode(Microsoft::Console::VirtualTerminal::TerminalInput::Mode::Win32, false);
});

// RightAlt down: VK_MENU (18), scanCode 0x38 (56),
// Cs = RIGHT_ALT_PRESSED | ENHANCED_KEY = 0x0001 | 0x0100 = 257
const auto down = term.SendKeyEvent(VK_MENU, 0x38, ControlKeyStates::RightAltPressed | ControlKeyStates::EnhancedKey, true);
VERIFY_IS_TRUE(down.has_value());
VERIFY_ARE_EQUAL(L"\x1b[18;56;0;1;257;1_", *down);

// RightAlt up: the modifier itself is no longer pressed,
// but the key release must still carry ENHANCED_KEY = 0x0100 = 256.
const auto up = term.SendKeyEvent(VK_MENU, 0x38, ControlKeyStates::EnhancedKey, false);
VERIFY_IS_TRUE(up.has_value());
VERIFY_ARE_EQUAL(L"\x1b[18;56;0;0;256;1_", *up);
}
}
4 changes: 2 additions & 2 deletions src/cascadia/WindowsTerminal/AppHost.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -84,11 +84,11 @@ AppHost::AppHost(WindowEmperor* manager, const winrt::TerminalApp::AppLogic& log
QueryPerformanceCounter(&_lastActivatedTime);
}

bool AppHost::OnDirectKeyEvent(const uint32_t vkey, const uint8_t scanCode, const bool down)
bool AppHost::OnDirectKeyEvent(const uint32_t vkey, const uint8_t scanCode, const bool extended, const bool down)
{
if (_windowLogic)
{
return _windowLogic.OnDirectKeyEvent(vkey, scanCode, down);
return _windowLogic.OnDirectKeyEvent(vkey, scanCode, extended, down);
}
return false;
}
Expand Down
2 changes: 1 addition & 1 deletion src/cascadia/WindowsTerminal/AppHost.h
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ class AppHost : public std::enable_shared_from_this<AppHost>
IslandWindow* GetWindow() const noexcept;
winrt::TerminalApp::TerminalWindow Logic();

bool OnDirectKeyEvent(uint32_t vkey, uint8_t scanCode, bool down);
bool OnDirectKeyEvent(uint32_t vkey, uint8_t scanCode, bool extended, bool down);
void SetTaskbarProgress(const winrt::Windows::Foundation::IInspectable& sender, const winrt::Windows::Foundation::IInspectable& args);
safe_void_coroutine HandleSummon(winrt::TerminalApp::SummonWindowBehavior args) const;
void DispatchCommandline(winrt::TerminalApp::CommandlineArgs args);
Expand Down
6 changes: 5 additions & 1 deletion src/cascadia/WindowsTerminal/WindowEmperor.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -781,8 +781,12 @@ void WindowEmperor::_dispatchSpecialKey(const MSG& msg) const

const auto vkey = gsl::narrow_cast<uint32_t>(msg.wParam);
const auto scanCode = gsl::narrow_cast<uint8_t>(msg.lParam >> 16);
// Bit 24 of lParam indicates an extended key (e.g. RightAlt/RightCtrl).
// We need to forward it, so that the key event can be translated to an
// INPUT_RECORD with the ENHANCED_KEY flag set (GH#18120).
const bool extended = (msg.lParam & 0x01000000) != 0;
const bool keyDown = (msg.message & 1) == 0;
window->OnDirectKeyEvent(vkey, scanCode, keyDown);
window->OnDirectKeyEvent(vkey, scanCode, extended, keyDown);
}

void WindowEmperor::_dispatchCommandline(winrt::TerminalApp::CommandlineArgs args)
Expand Down