在窗口中运行的 bash 脚本如何提升/激活其窗口?

在窗口中运行的 bash 脚本如何提升/激活其窗口?

我进行了两次类似的实验。第一次成功,第二次失败。我做错了什么?两次实验的设置:我有两个并排的终端窗口 (urxvt)(i3 wm,ubuntu 18.04.4 LTS)

实验一:

在左侧窗口中输入:

$ wmctrl -r :ACTIVE: -T test                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                      

这会将左侧窗口标题更改为“测试”。
在右侧窗口中输入:

$ wmctrl -a test                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                     

这将激活(改变焦点)回到左侧窗口。
成功!

实验2:

我想做同样的事情,但使用窗口 ID 而不是窗口标题。所以...
在左侧窗口中输入:

$ echo $WINDOWID                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                     
31457300                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                             

在右侧窗口中输入:

$ wmctrl -i -a 31457300                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                              

什么也没发生。
失败!

好吧,这只是一个实验。我真正想做的是:

我有几个 bash 脚本,每个脚本都会运行,直到我将其终止或重新启动,每个脚本都在自己的窗口中,位于我很少查看的另一个桌面上。在极少数情况下,当脚本需要我的注意时,我希望它找出它在哪个窗口中运行,并将该窗口置于最前面。“找出它在哪个窗口中运行”我认为很简单 - 它是$WINDOWID。使用wmctrl来显示已知窗口 ID 的窗口也应该很简单,但我无法让它工作,如您在实验 2 中看到的那样。

问题的替代表述:

我也很乐意通过标题而不是 ID 来提升窗口。使用 wmctrl 通过标题提升窗口很容易 ( wmctrl -a <title-or-fragment-thereof>)。但我不知道我的 bash 脚本如何发现其窗口的标题。没有环境变量。

我知道有一种解决方案,对我来说很管用,但我不喜欢它。我知道如何从 bash 设置窗口标题,所以我不需要“发现”它,对吧?我可以直接设置它(wmctrl -r :ACTIVE: -T SomeUniqueWindowTitle)。为什么我不喜欢这个?因为我丢失了原始的窗口标题。

这是另一个我不喜欢的解决方案:几个 bash 脚本中的每一个都已经设置了其窗口标题,因此共享过程可能需要第二个参数 - 窗口标题。我可以这样做,但是......只是想知道是否有更好、更简单的方法。

提前致谢!

答案1

我找到了解决方法。我为我的代码道歉,因为 (a) 它是 perl 和 bash 的混合体,并且 (b) 我不是专家,我确​​信有更好、更简单、更优雅的方法来做到这一点。无论如何,这对我来说是可行的。您的情况可能会有所不同。

Bash 命令将其运行的窗口置于前台:

wmctrl -i -a $( my-window-id.pl )

my-window-id.pl 应该是可执行文件,并且位于 shell 的搜索路径中。或者,如果这太麻烦,您可以改为:

wmctrl -i -a $( perl /path/to/my-window-id.pl )

以下是源代码my-window-id.pl

#!/usr/bin/perl
use warnings;
use strict;

# Print window ID of the window in which this script is running
# and exit with exit status 0.
# If it is not running in a window, print a message to stderr and
# exit with exit status 1.

# Determine my window ID based on "pstree -ps $$" and "wmctrl -lp".
# The pstree gives process ID of me and all my ancestors.
# One of those ancestors is my window (the window in which I am running).
# The wmctrl command gives a table of info on each active window,
# including each window's window ID and process ID.
# So if there exists a process ID that appears in output of both
# commands, then bingo that's my window's process ID, and the wmctrl
# table allows me to map that to a window ID.

my %pid_to_winid = ();
foreach my $raw_window_line ( split /\n/, `wmctrl -lp` ) {
    my ( $winid, undef, $pid ) = split /\s+/, $raw_window_line;
    $pid_to_winid{$pid} = $winid;
}

my $raw_pstree_out = `pstree -ps $$`;
my @pstree_pids    = $raw_pstree_out =~ m{ \( ( \d+ ) \) }gx;
foreach my $pid ( @pstree_pids ) {
    my $winid = $pid_to_winid{$pid};
    if ( $winid ) {
        print "$winid\n";
        exit 0;
    }
}

print STDERR "No window ID found for this process.\n";
exit 1;

相关内容