Cockpit version: 225
OS: Windows 10
Page: Terminal
When using the terminal, trying to use CTRL + W pops up a window asking if I am sure I want to close the tab and does not pass the keystroke into the terminal.
Steps to reproduce
From testing, this applies to Chrome and Firefox.
Update: This also applies to other keystrokes such as CTRL + K and likely more
Technically, the ctrl+w isn't closing the tab (default behavior), but getting caught so that a native dialog gets in the way to prevent the tab from being closed via beforeUnload. Same applies to several other browser keystrokes.
@marusak: FWIW, I wrote a lot about this topic three years ago in https://github.com/cockpit-project/cockpit/issues/7956.
The result was implementing the beforeUnload event in https://github.com/cockpit-project/cockpit/pull/7985/files#diff-69d5f18370238cd010ba0c0230bcd1b3R171-R179
I suggested workarounds in the thread in the first link in this comment. Some options were sticky keys (usually an accessibility feature), chording with alt (and stripping out alt when it is sent), and so on. We could use one or more of these methods as work-arounds.
The big problem is that we're in a browser and browsers eat certain keypresses. Only some of them can be overridden. Many cannot. (Here's a list of common shortcuts: https://unboxhow.com/list-of-common-keyboard-shortcuts-that-work-in-all-web-browsers)
Once upon a time, over a decade ago, I did make a web-based terminal that proxied commands through a connector based on a Java applet and then, later, Flash to get around these restrictions. (Or was it Flash first, then Java? It doesn't matter though, both have been deprecated and are no longer possible to use.) I don't think there's a similar workaround these days.
I wonder if there might be a way to add a button on the terminal window in the browser, similar to how Android apps add a CTRL button via an option in terminal apps?
So, at the top of the window, maybe you click a button "hold CTRL" and then press your key. Then pass the fake CTRL + [key] into the terminal?
See mock up image

If I understand it correctly: That's similar to the sticky keys solution, but only works for control, and I guess is a 1-time toggle (so you have to switch to the mouse, click it, then switch back to the keyboard for your key combo)?
"Sticky Keys" is an accessibility feature of most OSes (some Linux desktops, like GNOME have this; macOS and Windows also have it). But it should work here as well.
From WikiPedia @ https://en.wikipedia.org/wiki/Sticky_keys:
Sticky keys is an accessibility feature of some graphical user interfaces to assist users who have physical disabilities or help users reduce repetitive strain injury (or a syndrome called the Emacs Pinky). It serializes keystrokes instead of pressing multiple keys at a time, allowing the user to press and release a modifier key, such as Shift, Ctrl, Alt, or the Windows key, and have it remain active until any other key is pressed.
For general sticky keys support, there should be:
Additionally, there should be:
The main idea is that you can use the keyboard for all of the input, instead of having to switch to the mouse and back to the keyboard for some of the keypresses.
If you do (out of habit) hit control-w or one of the other reserved keypresses, you could tap control, a status indicator shows up that you're pressing ctrl, and then you tap w.
and I guess is a 1-time toggle (so you have to switch to the mouse, click it, then switch back to the keyboard for your key combo)?
Yes, Not necessarily a great solution but an idea...
I tried using sticky keys on my Gnome desktop at home and win10 at work, but both still resulted in the browser catching the keystroke and it not getting into the web terminal.
Maybe there is an obvious way that I am missing here though. My thought with the "Hold CTRL" button is that it would allow you to completely avoid passing CTRL + [key] through the browser and instead using the button and letting the JS (Or otherwise) catch the next key you press, then send the CTRL + [key] using the Javascript instead, thus avoiding conflicting keystrokes in the browser itself.
For general sticky keys support, there should be:
- a UI toggle to enable it (on the right side of the terminal bar?)
- a status on what modifier keys are currently being "pressed" (on the left side of the terminal bar, as PF4 labels/badges?)
Additionally, there should be:
- auto-cancellation on a successful keystroke (so pressing chords still works as expected)
- toggling the keypress off (hitting control a second time would disable it)
You nailed it with this.
The main idea is that you can use the keyboard for all of the input, instead of having to switch to the mouse and back to the keyboard for some of the keypresses.
If you do (out of habit) hit control-w or one of the other reserved keypresses, you could tap control, a status indicator shows up that you're pressing ctrl, and then you tap w.
I do really like this idea, tapping control instead of holding it, if that is possible to catch in a browser that would be a much preferred solution over the button!
Is anyone working on this? We still wait till we decide what solution we want?
Is anyone working on this?
Not to my knowledge. But I don't like the 'click on the button to hold key'. It is barely usable. I would look through https://xtermjs.org/docs/ to see if there is no better way. For example https://xtermjs.org/docs/api/terminal/classes/terminal/#attachcustomkeyeventhandler might help us. But as mentioned above, not all keys combinations can be caught, some never reach us as browser keeps them for itself. I think we might go with ctrl+shift+ instead of ctrl+. But really no good ideas here.
When we go with button that is keyboard toggable, then it should be easily discoverable how it works.
I don't like the 'click on the button to hold key'.
Me neither. However I do like the tap ctrl then tap key approach as that could even work with hold ctrl and tap key for key combinations that aren't blocked by the browser.
I don't like the ctrl+shift+ as that will get blocked as well since browsers (generally) use it for enhanced functionaly. Eg. ctrl+shift+t opens previously closed tab, ctrl+shift+w closes the browser (firefox at least, not sure about others) itself.
Another idea is to use alt/alt gr instead of ctrl (or alt instead of shift in the ctrl+shift+ approach, but that might invoke OS functions instead)
I think we might go with
ctrl+shift+instead ofctrl+
That was what I was originally going to suggest before I went off trying to find another solution, but, in Chrome at least, ctrl+shift+ still does the same as ctrl+ in a lot of cases, such as crtl+shift+w as @DejfCold mentioned...
Another idea is to use
alt/alt grinstead ofctrl(oraltinstead ofshiftin thectrl+shift+approach, but that might invoke OS functions instead)
I can confirm that my system catches a lot of ctrl+alt+ as system commands... Not sure if Windows or Mac do this though.
alt/alt gr instead of ctrl
Which doesn't on many keyboards, including ANSI (EN-US) keyboards.
As mentioned before, I've researched all the solutions and the only one that really works as transparently as possible (without a plugin-based approach, which wouldn't be supported now in browsers anyway) is to use a form of Sticky Keys, as I suggested above.
We'd need to use keydown and keyup events:
With the sticky keys feature on:
This should transparently handle chords and not be noticed unless someone taps modifier keys.
We should probably consider having this on by default.
Note: keydown & keyup handle taps of modifier keys, whereas keypress and other key related JS does not (and are deprecated anyway).
Most helpful comment
As mentioned before, I've researched all the solutions and the only one that really works as transparently as possible (without a plugin-based approach, which wouldn't be supported now in browsers anyway) is to use a form of Sticky Keys, as I suggested above.
More detail on how Sticky Keys could be implemented
We'd need to use
keydownandkeyupevents:With the sticky keys feature on:
This should transparently handle chords and not be noticed unless someone taps modifier keys.
We should probably consider having this on by default.
Note: keydown & keyup handle taps of modifier keys, whereas keypress and other key related JS does not (and are deprecated anyway).