Skip to content

Instantly share code, notes, and snippets.

@ammmze
Last active June 20, 2026 05:12
Show Gist options
  • Select an option

  • Save ammmze/b2099fee4fb5fea7977e9a21799c8e55 to your computer and use it in GitHub Desktop.

Select an option

Save ammmze/b2099fee4fb5fea7977e9a21799c8e55 to your computer and use it in GitHub Desktop.
xrandr scripts to toggle 1080i broadcast mode on X11 (auto-detects connected HDMI output)

1080i Broadcast Toggle (X11 / xrandr)

Two shell scripts to toggle a connected display in and out of a 1920x1080 interlaced broadcast mode on X11. Useful when a capture card, hardware encoder, or downstream broadcast workflow demands a true 1080i signal that the desktop normally won't produce.

The custom modeline uses SMPTE 274M timing (74.25 MHz pixel clock, 1080i60).

What they do

set_1080i.sh

  1. Runs xrandr --query and finds every connected output.
  2. If only one is connected, uses it.
  3. If multiple are connected, prompts you to pick one (select menu).
  4. Registers the 1080i_broadcast modeline if it isn't already known to X.
  5. Attaches the mode to the chosen output and switches to it.

reset_display.sh

  1. Scans xrandr --query for whichever output is currently running 1080i_broadcast (the mode line marked with *).
  2. Runs xrandr --output <that one> --auto to restore its native progressive mode.
  3. Detaches and removes the custom modeline.

No hard-coded output names — both scripts work whether the display is on HDMI-1, HDMI-2, DP-1, etc.

Install

curl -O https://gist.githubusercontent.com/ammmze/b2099fee4fb5fea7977e9a21799c8e55/raw/set_1080i.sh
curl -O https://gist.githubusercontent.com/ammmze/b2099fee4fb5fea7977e9a21799c8e55/raw/reset_display.sh
chmod +x set_1080i.sh reset_display.sh

Move them anywhere on your $PATH if you'd like (e.g. ~/.local/bin/).

Usage

./set_1080i.sh       # switch into 1080i broadcast mode
./reset_display.sh   # restore normal display mode

Bind to hotkeys

In your desktop environment's keyboard settings, add custom shortcuts pointing at the absolute path of each script. Suggested bindings:

Action Suggested key
set_1080i.sh Ctrl + Alt + B (Broadcast)
reset_display.sh Ctrl + Alt + P (Progressive)

Requirements

  • X11 (will not work under Wayland — xrandr cannot inject modelines on Wayland sessions)
  • xrandr, awk, bash
  • A GPU driver / display that accepts custom modelines (most Intel/AMD/NVIDIA drivers do; some HDMI sinks reject non-EDID modes)

Ubuntu 26.04 Setup (fresh install)

Ubuntu 26.04's default GNOME desktop is Wayland-only, and Wayland does not support custom xrandr modelines. To use these scripts on a fresh install, switch to an X11-supported desktop session.

1. Install an X11 desktop

XFCE (via Xubuntu) is the lightest option:

sudo apt update
sudo apt install xubuntu-desktop

During installation you'll be prompted to pick a default display manager. Choose gdm3 (not lightdm) — it handles session switching cleanly and works well alongside the default Ubuntu stack.

KDE works too if you prefer it (sudo apt install kubuntu-desktop).

2. Log into an X11 session

Reboot. At the login screen:

  1. Click your username.
  2. Click the gear / session-picker icon (usually bottom-right).
  3. Select Xfce Session (or any entry explicitly labeled X11 / on Xorg).
  4. Log in.

Confirm you're on X11 from a terminal:

pgrep -al Xorg

If a real Xorg process is listed, you're on X11 — these scripts will work.

Note: $XDG_SESSION_TYPE and loginctl show-session ... -p Type both frequently report wayland on Ubuntu 26.04 even when the actual server is Xorg (gdm3 mis-tags the session). They are unreliable for this check. The only ground truth is which server process is running — Xorg vs Xwayland. If only Xwayland shows up, you logged into a Wayland session; log out and pick the Xfce / Xorg one.

3. Install the scripts

See Install above. From there, set_1080i.sh handles modeline registration, output detection, and switching; you don't need to run any xrandr commands by hand.

Optional: apply on login

If you want 1080i active every time you log in, add a line to ~/.xprofile:

~/path/to/set_1080i.sh

Notes

  • The custom modeline is not persistent across reboots. The set script re-registers it on each invocation, so this is fine for normal use.
  • If your workflow needs 1080i50 (PAL) instead of 1080i60, swap the modeline in set_1080i.sh — same pixel clock, different horizontal/vertical totals.
  • If xrandr --addmode fails with BadMatch, your driver or sink is rejecting the mode; that's a hardware/driver issue, not a script bug.
#!/bin/bash
# Reset any display currently running 1080i_broadcast back to its auto mode.
set -euo pipefail
MODE_NAME="1080i_broadcast"
mapfile -t targets < <(
xrandr --query | awk -v mode="$MODE_NAME" '
/ connected/ { output=$1 }
$1==mode && $0 ~ /\*/ { print output }
'
)
if [[ ${#targets[@]} -eq 0 ]]; then
echo "No display currently using $MODE_NAME."
exit 0
fi
for output in "${targets[@]}"; do
echo "Resetting $output to auto..."
xrandr --output "$output" --auto
xrandr --delmode "$output" "$MODE_NAME" 2>/dev/null || true
done
xrandr --rmmode "$MODE_NAME" 2>/dev/null || true
echo "Done."
#!/bin/bash
# Switch a connected display into 1080i broadcast mode.
# Detects connected outputs via xrandr; prompts if more than one is connected.
set -euo pipefail
MODE_NAME="1080i_broadcast"
MODELINE=(74.250 1920 2008 2052 2200 1080 1084 1094 1125 +hsync +vsync Interlace)
mapfile -t connected < <(xrandr --query | awk '/ connected/ {print $1}')
if [[ ${#connected[@]} -eq 0 ]]; then
echo "No connected displays found." >&2
exit 1
elif [[ ${#connected[@]} -eq 1 ]]; then
output="${connected[0]}"
else
echo "Multiple displays connected. Select target:"
select choice in "${connected[@]}"; do
if [[ -n "${choice:-}" ]]; then
output="$choice"
break
fi
echo "Invalid selection."
done
fi
echo "Configuring $output for $MODE_NAME..."
if ! xrandr | grep -q "$MODE_NAME"; then
xrandr --newmode "$MODE_NAME" "${MODELINE[@]}"
fi
xrandr --addmode "$output" "$MODE_NAME" 2>/dev/null || true
xrandr --output "$output" --mode "$MODE_NAME"
echo "$output now running $MODE_NAME."
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment