Skip to content
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

Enhancement: Dynamically select list of windows #159

Open
orestisfl opened this issue Feb 7, 2024 · 8 comments
Open

Enhancement: Dynamically select list of windows #159

orestisfl opened this issue Feb 7, 2024 · 8 comments

Comments

@orestisfl
Copy link

Current behavior

alttab initializes a window list using the initWinList function:

int initWinlist(void)

Desired behavior

alttab accepts a new argument, say -window_list_command which, when called, returns a list of windows to display. The command is called in each invocation of alttab.

There should be a pre-determined communication protocol between alttab and window_list_command. The simplest case would be to just return a list of window IDs. Then, alttab fetches needed information for each window ID and displays the window list with the given order.

Example use cases

  • Switch between windows of the same class
  • i3: always include scratchpad windows
  • i3: switch between a subset of windows (e.g. determined by marks)

Related

#77 is related as it also affects the selection logic of what to display. However, that ticket will require further UI changes while this one doesn't.

@sagb
Copy link
Owner

sagb commented Feb 7, 2024

This may seem like a nice feature, but the core essence of the alttab user experience is interactivity: it must render a dialog in approximately 30 milliseconds to be perceived as "immediate." Calling external programs could potentially undermine this critical feature. Since alttab has no control over external programs, it must not only perform numerous security and sanity checks and handle errors but also implement a timeout for waiting for input. Then arises the question: what should alttab do when the timeout elapses? Should it suddenly display all windows or none at all?

Instead, I suggest the following: the external program should prepare the window list in advance and place it into X objects, for example, by adding a window class or another property indicating "include this window in the list."

By the way, there is already a standard property that makes alttab skip a window: _NET_WM_STATE_SKIP_TASKBAR.

@orestisfl
Copy link
Author

it must render a dialog in approximately 30 milliseconds to be perceived as "immediate."

30 ms for calling a single process seems totally in the realm of possibility. Besides, this is an opt-in feature, the user should have an understanding that they are now responsible for the performance of alttab.

Since alttab has no control over external programs, it must not only perform numerous security and sanity checks

Not sure why this would be the case, the user controls the callback. Configuring a callback like that is typical in many programms for example i3, restic and git from the top of my mind. If a malicious actor can control the invocation of alttab, e.g. -window_list_command 'malicious_command' they would probably also have enough permissions to directly call malicious_command directly.

handle errors but also implement a timeout for waiting for input. Then arises the question: what should alttab do when the timeout elapses? Should it suddenly display all windows or none at all?

I would generally start with the simplest approach. Any error is non-recoverable (current invocation is skipped, error is logged in stderr), timeouts are the fault of the user.

Instead, I suggest the following: the external program should prepare the window list in advance and place it into X objects, for example, by adding a window class or another property indicating "include this window in the list."

Sure, that's also an option. It's also possible to accept window lists from stdin, e.g. in a jsonlines format. Downside is that the said program will need to always produce list of windows and react to events. Synchronization can also be a problem here as alttab might be called before the user program responds to new events that alter the window list.

@sagb
Copy link
Owner

sagb commented Feb 7, 2024

Users might download and execute a dubious script as a "callback," subsequently attributing any perceived sluggishness or unreliability to alttab.
Furthermore, should alttab be exploited, the capability to launch an arbitrary program could exacerbate the situation.
Additionally, if the "callback" itself is compromised or malicious from the outset, it may attempt to exploit alttab by stuffing it with harmful input.
The interaction with external programs expands the attack surface and necessitates security precautions. However, this problem isn't major.

The major problem is unpredictable delays caused by synchronous input. Alttab is designed to monitor various X11 events, maintaining a partially pre-constructed list to avoid the inefficiency of assembling everything at the moment the Alt-Tab keys are pressed.
A simple script might fail or lag in numerous edge cases, which might not be immediately apparent.

The only solution is asynchronous input: alttab should never be in a position where it is awaiting input. It needs to have instant access to at least some list at any given time. Contributions or patches that facilitate such a solution are welcomed.

@orestisfl
Copy link
Author

The only solution is asynchronous input: alttab should never be in a position where it is awaiting input. It needs to have instant access to at least some list at any given time. Contributions or patches that facilitate such a solution are welcomed.

So, to make sure we have the same understanding, the patch will modify alttab in the following way:

  1. Accept a new, disabled by default, flag that enables the new behavior
  2. When Alt-Tab is pressed, display only windows that have the ALTTAB_INCLUDE_WINDOW property
  3. Related docs

@sagb
Copy link
Owner

sagb commented Feb 7, 2024

Yes, such approach seems ok.

For alttab, the only justification for being small is being fast and reliable. If it's small AND slow or unreliable, it wouldn't be worth a penny.

@orestisfl
Copy link
Author

Actually, after some thought, one could achieve everything by setting the _NET_WM_STATE_SKIP_TASKBAR atom on the windows they'd like to hide and remove it from all others. So, it's somewhat possible, with the caveat that _NET_WM_STATE_SKIP_TASKBAR might already be set by the window for other reasons.

However, i found a bug that prevents that approach: #160

@orestisfl
Copy link
Author

Actually, after some thought, one could achieve everything by setting the _NET_WM_STATE_SKIP_TASKBAR atom on the windows they'd like to hide and remove it from all others. So, it's somewhat possible, with the caveat that _NET_WM_STATE_SKIP_TASKBAR might already be set by the window for other reasons.

However, i found a bug that prevents that approach: #160

The one added benefit of a new flag is that it would be possible to have for example multiple different instances of alttab that have different filters.

For example: super+grave to switch between instances of the same class and alt+tab to switch between the focused windows of each workspace.

That could be implemented by providing the name of the property alttab needs to check in each window. For example, alttab -mk Super_L -kk grave -f FOCUSED_CLASS and alttab -f FOCUSED_WORKSPACE

@sagb
Copy link
Owner

sagb commented Feb 9, 2024

This seems like a valid idea.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

2 participants