插入外接显示器时自动应用 RandR 配置的工具

插入外接显示器时自动应用 RandR 配置的工具

有没有一种工具可以让人们:

  • 记住每个显示器的当前 RandR 配置(位置、方向、分辨率等),
  • 一旦插入显示器,就会自动应用最后一次正确的配置,而无需使用小程序或 xrandr(1) 进行处理?

这些配置必须针对每个用户、每个显示器进行应用。

如果没有这样的工具,我想自己组装一个,但据我所知,没有办法知道监视器已插入。我是否必须使用 xrandr -q 进行轮询偶尔找出输出已连接或断开,或者是否有更有效的方法来做到这一点? udev 可以调整来做到这一点吗?

答案1

关于可以按用户和每个显示器存储显示器配置配置文件的工具,自动排序就会这么做。

我的笔记本电脑有 NVIDIA 卡,所以我使用分散后端而不是 xrandr。如果您将其称为 ,Autorandr 将使用 分散 作为后端来管理您的监视器autodisper。不过,在本文的其余部分中,为了保持一致性,我将其称为“autorandr一致性”。

您可以使用 保存配置文件autorandr --save profile_nameautorandr然后,单独运行将为您提供一份配置文件列表,并确定哪个配置文件被检测为当前配置。

例如:

$ autorandr
laptop
syncmaster19 (detected)

您可以告诉它自动加载当前配置的适当配置文件autorandr --change。该命令与 udev 规则配对以在热插拔时运行它,将执行您所请求的操作。

作为额外的预防措施,我已附加--default laptop到该命令,如果没有与当前配置匹配的已保存配置文件,这将使其默认为笔记本电脑的显示。所以我用来切换显示的完整命令是:

autorandr --change --default laptop

不幸的是,当我热插拔显示器时,我的机器没有给出任何 udev 输出。我使用的是 NVIDIA 专有驱动程序,所以这并不奇怪。所以我现在将它绑定到 XF68Display 键(Fn-F8),这几乎一样好。

答案2

我正在使用这个简单的(自制)脚本,当 VGA 连接/断开连接时,它会不断轮询 RandR 并在 LVDS1 和 VGA1 之间切换。 (为了HDMI输出,在以下脚本文件中,将所有更改VGA1HDMI1)

这是一个肮脏的解决方案,但它工作得很好。

它是为我的设置定制的:您很可能需要更改 RandR 输出名称 (LVDS1VGA1) 和不像我您可能对 VGA 的 RandR 默认模式感到满意。

#!/bin/bash

# setting up new mode for my VGA
xrandr --newmode "1920x1080" 148.5 1920 2008 2052 2200 1080 1089 1095 1125 +hsync +vsync
xrandr --addmode VGA1 1920x1080

# default monitor is LVDS1
MONITOR=LVDS1

# functions to switch from LVDS1 to VGA and vice versa
function ActivateVGA {
    echo "Switching to VGA1"
    xrandr --output VGA1 --mode 1920x1080 --dpi 160 --output LVDS1 --off
    MONITOR=VGA1
}
function DeactivateVGA {
    echo "Switching to LVDS1"
    xrandr --output VGA1 --off --output LVDS1 --auto
    MONITOR=LVDS1
}

# functions to check if VGA is connected and in use
function VGAActive {
    [ $MONITOR = "VGA1" ]
}
function VGAConnected {
    ! xrandr | grep "^VGA1" | grep disconnected
}

# actual script
while true
do
    if ! VGAActive && VGAConnected
    then
        ActivateVGA
    fi

    if VGAActive && ! VGAConnected
    then
        DeactivateVGA
    fi

    sleep 1s
done

完整步骤:

  1. 将上面的脚本 ( homemadeMonitor.sh) 放入您首选的目录中

  2. 通过在终端中键入以下命令使 .sh 文件可执行

    chmod +x homemadeMonitor.sh

  3. 运行.sh文件

    ./homemadeMonitor.sh

答案3

回答问题的“判断显示器已插入的[一种]方法”部分:

支持仍然有很大差异,但最近的内核支持在发生显示热插拔时生成 udev 事件。对于内核 2.6.38 和 ATI X1400 硬件,我在第一次连接 VGA 显示器时收到一个事件,但在随后断开或重新连接显示器时没有事件。Intel硬件可能有更好的支持。NVIDIA专有驱动目前不支持KMS;我还没有尝试过在 NVIDIA 硬件上寻找热插拔事件,但我怀疑它是否有效。

如果您想尝试 udev,可以尝试以下步骤:

  • 更新到最新的内核
  • 确保内核模式设置 (KMS) 已启用。如果启用,它应该在您的内核输出中报告。我的说[drm] radeon kernel modesetting enabled[drm] initializing kernel modesetting
  • 运行udevadm monitor --property并查看当您(断开)连接显示器时是否报告事件

如果您在显示器热插拔上收到 udev 事件,则可以使用 udev 规则触发脚本,例如:

ACTION=="change", SUBSYSTEM=="drm", HOTPLUG=="1", RUN+="/path/to/hotplug.sh"

笔记:这会不是如果您使用带有专有二进制驱动程序的 nVIDIA GPU,则可以工作,因为它不使用 KMS。你会不是获取任何 udev 事件。

答案4

我使用了上面建议的 udev 规则以及一个如下所示的 shell 脚本

#!/bin/sh

dmode="$(cat /sys/class/drm/card0-VGA-1/status)"
export DISPLAY=:0
export XAUTHORITY=/home/yourusername/.Xauthority

if [ "${dmode}" = disconnected ]; then
     /usr/bin/xrandr --auto
elif [ "${dmode}" = connected ];then
     /usr/bin/xrandr --output VGA1 --auto --right-of LVDS1
else /usr/bin/xrandr --auto
fi

Xauthority 部分和导出一样重要DISPLAY,您可以使用 echo$DISPLAY来查看它等于哪个数字。用于xrandr -q查看您拥有的外部显示器。最后的 else 语句只是为了确保您永远不会在没有显示的情况下陷入困境。

相关内容