-
Notifications
You must be signed in to change notification settings - Fork 8.4k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Implement Keyboard Selection #10824
Implement Keyboard Selection #10824
Conversation
Discussion
|
1df76e6
to
841cd2a
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I guess I'm blocking only for the GenerateName
thing? And update the docs? But I suppose the second can wait for the naming discussions to be finalized. Code looks great though.
Already looking forward to 1.12!
{ "command": {"action": "updateSelection", "direction": "down", "mode": "view" }, "keys": "shift+pgdn" }, | ||
{ "command": {"action": "updateSelection", "direction": "up", "mode": "buffer" }, "keys": "ctrl+shift+home" }, | ||
{ "command": {"action": "updateSelection", "direction": "down", "mode": "buffer" }, "keys": "ctrl+shift+end" }, | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
ah ohkay, we'll need a separate action for selectAll
. That's fine.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yeah, that can be a separate PR too
// 4. Scroll (if necessary) | ||
if (const auto viewport = _GetVisibleViewport(); !viewport.IsInBounds(targetPos)) | ||
{ | ||
if (const auto amtAboveView = viewport.Top() - targetPos.Y; amtAboveView > 0) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
little surprised that spellbot didn't complain about amt
here.
this is the only change I feel is necessary.
please no god no. IMO, bad text editors behave this way. Code editors generally don't.
Yea, the mutable bottom is more reasonable. The "scroll forward" doesn't exist for all intents and purposes. |
This comment has been minimized.
This comment has been minimized.
shh bot |
Updated |
5b4dd33
to
b2a7a19
Compare
It looks like Terminal.hpp can't find |
5297b80
to
0cc9bd0
Compare
That's so bizarre that this works locally, but not in CI. My guess is related to this bit at the top of Terminal.hpp: // You have to forward decl the ICoreSettings here, instead of including the header.
// If you include the header, there will be compilation errors with other
// headers that include Terminal.hpp
namespace winrt::Microsoft::Terminal::Core
{
struct ICoreSettings;
struct ICoreAppearance;
} OH I know why, it's because you're not building |
ad99008 might work to fix this. It certainly did locally. Take it or leave it :P |
95967ec
to
7179804
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I hate the duplicated enums, but I understand the world we live in
This comment has been minimized.
This comment has been minimized.
e498dea
to
118d1cd
Compare
Dismissing Mike's review because this iteration was a major design change and I wanna make sure he's on board.
Assigning @DHowett because he has some very passionate thoughts on keyboard selection haha |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
// Return Value: | ||
// - pos - The COORD for the last cell of the current glyph (exclusive) | ||
const til::point TextBuffer::GetGlyphEnd(const til::point pos, std::optional<til::point> limitOptional) const | ||
const til::point TextBuffer::GetGlyphEnd(const til::point pos, bool accessibilityMode, std::optional<til::point> limitOptional) const |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
(The amount of arguments our TextBuffer
member functions have is worrying ngl. 😄)
Why does "accessibility mode" mean "become exclusive" here? Don't you mean "bool exclusivePosition"?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yeeeeaaaaah. So, a11y and selection have a lot of similarities and very small/important differences. Some highlights include...
Selection | A11y | |
---|---|---|
endpoint representation | both endpoints are inclusive; start <= end | inclusive start; exclusive end; start <= end |
definition of a word | a run of legible characters | run of legible characters + run of whitespace after it (until next word starts) |
I just chose to name the parameter accessibilityMode
to make it clear what and when we're only doing some extra work for a11y.
// GH#8522, GH#3758 - Only dismiss the selection on key _down_. If we | ||
// dismiss on key up, then there's chance that we'll immediately dismiss | ||
// GH#8522, GH#3758 - Only modify the selection on key _down_. If we | ||
// modify on key up, then there's chance that we'll immediately dismiss |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
<showerthought>
If we could handle this modification on key up, then could we do something like bind markMode
to shift+left
, and have the shift+left
keydown enter mark mode, and the keyup extend the selection to the left? Essentially getting quickedit-like selection?
This is of course, crazy, but something to think about
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
HECK IT DOESN"T EVEN MATTER
a user could just bind markmost to shift+left, and that would start a selection at the cursor, and the subsequent keypresses would extend it without hitting the keybinding, which is actually just like conhost. Brilliant 🥂
🎉 Handy links: |
## Summary of the Pull Request 1.14 port of #13318 Introduced in #10824, this fixes a bug where you could use keyboard selection to move below the scroll area. Instead, we now clamp movement to the mutable viewport (aka the scrollable area). Specifically, we only clamp the y-coordinate to make the experience similar to that of mouse selection. ## Validation Steps Performed ✅ (no output) try to move past bottom of viewport ✅ (with output, at bottom of scroll area) try to move past viewport ✅ (with output, NOT at bottom of scroll area) try to move past viewport ✅ try to move past top of viewport
## Summary of the Pull Request Introduced in #10824, this fixes a bug where you could use keyboard selection to move below the scroll area. Instead, we now clamp movement to the mutable viewport (aka the scrollable area). Specifically, we clamp to the corners (i.e. 0,0 or bottom right cell of scroll area). ## Validation Steps Performed ✅ (no output) try to move past bottom of viewport ✅ (with output, at bottom of scroll area) try to move past viewport ✅ (with output, NOT at bottom of scroll area) try to move past viewport ✅ try to move past top of viewport
Summary of the Pull Request
Implements the following keyboard selection non-configurable key bindings:
This was purposefully done in the ControlCore layer to make keyboard selection an innate part of how the terminal functions (aka a shared component across terminal consumers).
References
#715 - Keyboard Selection
#2840 - Spec
Detailed Description of the Pull Request / Additional comments
The most relevant section is
TerminalSelection.cpp
, where we define how each movement operates. It's basically a giant embedded switch-case statement. We leverage a lot of the work done in a11y to perform the movements.Validation Steps Performed
char
: wide glyph supportword
: move towards, away, and across the selection pivot