如何在打开 GUI 应用程序(pdf、jpg 等)时隐藏终端,并在关闭时使其重新出现?

如何在打开 GUI 应用程序(pdf、jpg 等)时隐藏终端,并在关闭时使其重新出现?

我使用平铺 WM (AwesomeWM)alacritty作为我的默认 shell。当我(从终端)打开文件时,它会在终端旁边的新窗口中打开它。

这很烦人,不是我想要的。如果我关闭终端,PDF ( zathura) 也会关闭。我可以最小化终端,但我正在寻找更优雅的解决方案。

我记得有一种叫做“静音模式”的东西,尽管我不确定它的名字。这个想法是,当打开 PDF(或图像或其他什么)时,终端会“消失”并保持原样,直到我关闭 PDF,在这种情况下,终端会重新出现。

不知道它是如何工作的,我似乎找不到它。如果有人有任何想法,我将不胜感激。

答案1

这可以通过 来完成xdotools。旁“最小化”终端我们可以取消映射它使其对窗口管理器隐藏。

清理并评论了我多年前为这个项目编写的脚本,老实说我很少使用它,但应该适合。

xdotools使用(只要运行X)的好处是可以进行控制并可以进行调整等。它是制作自定义窗口工具的一个有价值的工具。如果有一个错误或一个需要的功能,那么处理起来很容易。

除了隐藏终端模拟器之外,该脚本还有一些选项:

  • -p将子项定位在与终端相同的坐标处(取消映射之前)。
  • -r不要隐藏终端,而是将其作为终端的子项。 (相当实验性,如果要与各种应用程序很好地配合工作,需要更多的工作。)
  • -v一些详细的打印
  • -h帮助

如果没有设置任何选项,它只需启动程序并取消映射终端即可。

重新映射时它还会恢复终端位置 - 因为这可能会在各种窗口管理器中丢失。

没有经过广泛的测试,但在我使用过的一小段时间里效果很好。

如果将其用于正在运行且不会产生新实例的应用程序,例如qalculate,需要使用-n标志或其他内容(如果存在),以便应用程序启动新会话。

当然可以实施最小化代替/除了取消映射ETC。

注意!:由于站点/SE通过替换选项卡的空格来破坏代码,或者通过单击复制编辑或粘贴到编辑器后驻留。 (这适用于<<-EOF下面的)

#! /bin/sh -

# Print various information, option: -v
verbose=0
# Position spawned window at X Y of terminal, option: -p
poschild=0
# Reparent to terminal
reparent=0

# ENABLE JOB CONTROL
set -m

print_help() {
    cat<<-EOF
    Usage: $(basename "$0") [OPTION] program [args ...]
      Hide terminal window by unmapping until program exits.
      Do Ctrl+C when using -r / -p if program fails.
    OPTIONS
      -p  Position child at X Y of terminal.
      -r  Reparent. Set it as child of terminal.
      -v  Verbose. Print geometry.
      -h  This help.
    EOF
}
print_geom() {
    cat<<-EOF
    WIN-ID  $WINDOW
    POS     $X $Y
    SIZE    $WIDTH $HEIGHT
    EOF
}
# DEFINES by Evil Eval
#   WINDOW (window id)
#   X Y
#   WIDTH HEIGHT
#   SCREEN
get_win_geom() {
    eval "$(xdotool getactivewindow getwindowgeometry --shell)"
}
# RESTORE Terminal Geom
set_win_geom() {
    xdotool windowmove "$WINDOW" "$X" "$Y"
    xdotool windowsize "$WINDOW" "$WIDTH" "$HEIGHT"
}
# HIDE current terminal
term_hide() {
    xdotool windowunmap "$WINDOW"
}
# RESTORE Terminal
term_show() {
    xdotool windowmap "$WINDOW"
    # On remapping window can loose original position
    # Restore to pre-unmap values
    set_win_geom
}
# Position program at X Y of terminal
# Using -sync has two effects:
#   1. Need to wait for window to appear
#   2. If command fails it hangs, and we can
#      abort with Ctrl+C
# Use --onlyvisible as windows can have a range of sub-windows.
# This could likely be done better.
pos_child() {
    wid="$(xdotool search --sync --pid "$1" --onlyvisible --limit 1 --all)"
    xdotool windowmove "$wid" "$X" "$Y"
}
# Adopt the child process's window
win_reparent() {
    wid="$(xdotool search --sync --pid "$1" --onlyvisible --limit 1 --all)"
    xdotool windowreparent "$wid" "$WINDOW"
}
# Bring process to foreground after mapping, moving etc.
fg_cpid() {
    if ! kill -0 "$cpid" 2>/dev/null || ! fg %1 >/dev/null; then
        printf 'Failed\n' >&2
        return 1
    fi
}
while [ -n "$1" ]; do
    case "$1" in
    '-h'|--help) print_help >&2 ; exit 1 ;;
    '-v') verbose=1 ;;
    '-p') poschild=1 ;;
    '-r') reparent=1 ;;
    *) break ;;
    esac
    shift
done
get_win_geom
[ $verbose -eq 1 ] && print_geom >&2

# Order of operation can be of importance here.
# Start child before unmap
command "$@" &
cpid="$!"

[ $poschild -eq 1 ] && pos_child "$cpid"
[ $verbose -eq 1 ] && jobs -l
if [ $reparent -eq 1 ]; then
    win_reparent "$cpid"
    fg_cpid || exit 1
else
    term_hide
    fg_cpid || exit 1
    # Restore when child departs
    term_show
fi

答案2

你的 shell 会产生像 Zarathura 这样的进程子流程当母进程被杀死时,它们也会被杀死。您的终端模拟器将 shell 本身作为子进程启动。

所以,最简单的解决方案是不是在子进程中打开事物,但作为一个单独的进程。

你可以这样做任何过程使用

 nohup programname parameters..

但就你而言,它更容易:

 xdg-open yourfile.pdf

打开应该打开 application/pdf 文件的应用程序,作为一个单独的进程。这也适用于其他文件类型。

答案3

我想我可能已经找到了我在说什么,所以我会考虑结束这个话题。感觉有点傻,但我有一段时间找不到它,而且比我问的还要多。随机地,我后来很快就找到了它。

但感谢您的帮助!

(如果有人有兴趣https://www.youtube.com/watch?v=mBNLzHcUtTo抱歉视频的名字很俗气。)

干杯。

相关内容