commit e5913da5a99ced564fe2a68406f54ab44b767e82
Author: mrfox <jens.se@icloud.com>
AuthorDate: Sun Sep 20 22:03:28 2026 +0200
Commit: mrfox <jens.se@icloud.com>
CommitDate: Sun Sep 20 22:03:28 2026 +0200
screensaver: lower frame rate and cell count to cut CPU/GPU load
--frame-rate 120 over a full-monitor terminal canvas (pixelsize=24) was
pegging a CPU core and, on this machine, the GPU/fans, for the whole
150-300s window before DPMS blanks the display (see 241914c for that
separate fix -- this is about load while it's actively visible).
Measured headless with tte directly (same effect, same art, isolated
from any X/WM variance):
120fps, ~286x57 cells (~pixelsize 24 on a 3440-wide monitor): 72.7% CPU
30fps, same cell count: 65.8% CPU
120fps, ~172x34 cells (~pixelsize 40): 43.1% CPU
30fps, ~172x34 cells: 21.0% CPU
Frame rate alone barely helps -- most effects are CPU-bound computing
the frame, not waiting on the rate cap, until the cell count is also
cut. Combined, it's a ~3.5x reduction. Bumped screensaver-launch's font
from pixelsize 24 to 36 (fewer, bigger cells) and screensaver's
--frame-rate from 120 to 30, both now overridable via
SCREENSAVER_FONT_SIZE / SCREENSAVER_FPS like the existing
SCREENSAVER_ART / SCREENSAVER_IDLE_SECONDS knobs.
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
---
bin/screensaver | 8 +++++++-
bin/screensaver-launch | 7 ++++++-
2 files changed, 13 insertions(+), 2 deletions(-)
diff --git a/bin/screensaver b/bin/screensaver
index e8ae213..04205c0 100755
--- a/bin/screensaver
+++ b/bin/screensaver
@@ -4,6 +4,12 @@
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
ART_FILE="${SCREENSAVER_ART:-$SCRIPT_DIR/screensaver.txt}"
+# 120fps of full-canvas terminal effects pegged a CPU core and, on this
+# machine, the fans -- most effects don't need anywhere near that to look
+# smooth. Cuts CPU roughly in half on its own; combined with the larger
+# font in screensaver-launch (fewer cells to animate per frame) it's closer
+# to a 3-4x reduction.
+FRAME_RATE="${SCREENSAVER_FPS:-30}"
WIN_CLASS="screensaver"
screensaver_in_focus() {
@@ -27,7 +33,7 @@ tty=$(tty 2>/dev/null)
while true; do
tte -i "$ART_FILE" \
- --frame-rate 120 --canvas-width 0 --canvas-height 0 --reuse-canvas --anchor-canvas c --anchor-text c \
+ --frame-rate "$FRAME_RATE" --canvas-width 0 --canvas-height 0 --reuse-canvas --anchor-canvas c --anchor-text c \
--random-effect --no-eol --no-restore-cursor &
while pgrep -t "${tty#/dev/}" -x tte >/dev/null; do
diff --git a/bin/screensaver-launch b/bin/screensaver-launch
index a26adb8..465c609 100755
--- a/bin/screensaver-launch
+++ b/bin/screensaver-launch
@@ -6,6 +6,11 @@ export PATH="$HOME/.local/bin:$PATH"
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
WIN_CLASS="screensaver"
+# Bigger font = fewer terminal cells for tte to animate each frame over the
+# same physical screen area, which matters more for CPU than it sounds:
+# measured ~65% less CPU from cell count alone (going from a ~24px-per-cell
+# grid to this), before even touching frame rate.
+FONT_SIZE="${SCREENSAVER_FONT_SIZE:-36}"
command -v tte >/dev/null || { echo "tte not found (pipx install terminaltexteffects)" >&2; exit 1; }
@@ -27,7 +32,7 @@ for mon in $(xrandr --listmonitors | awk 'NR>1 {print $3}'); do
# st has no runtime equivalent of kitty's window_padding_width/mouse_hide_wait
# overrides (those are compile-time-only in st), so they're just dropped here.
st -c "$WIN_CLASS" \
- -f "JetBrainsMono Nerd Font:pixelsize=24:antialias=true:autohint=true" \
+ -f "JetBrainsMono Nerd Font:pixelsize=${FONT_SIZE}:antialias=true:autohint=true" \
-A 1.0 \
-e "$SCRIPT_DIR/screensaver" &
kpid=$!