From 400402329771251b35237889a305b03d08db99cc Mon Sep 17 00:00:00 2001 From: Felitendo Date: Sun, 16 Aug 2026 20:44:19 +0200 Subject: [PATCH] Make the second menu entry an action instead of a report "Apply now" had nothing to do in the normal case. Enabling applies, the watcher handles everything installed afterwards, and the settings and applications screens apply on their way out - so pressing it answered "already applied to 14 applications" and that was the whole interaction. It is now "Re-apply everything": the state is taken back and written again from scratch. That is the answer to the question the status block can raise but nothing could act on - Steam showing as not patched after a client update, an application that drifted, a flag file edited by hand. Uninstalling an application used to leave the entry shadowing it behind, in the user home where the package manager cannot see it, offering to start a program that is gone. A plain apply only looks at what exists now, so the watcher never noticed either. Those are removed on every apply now, not just when rebuilding. --- Makefile | 2 +- README.md | 3 ++- doc/middleclick-autoscroll.1.scd | 9 ++++++++- po/de.po | 12 ++++++++--- po/middleclick-autoscroll.pot | 10 ++++++++-- src/lib/apply.sh | 2 ++ src/lib/menu.sh | 14 +++++++++---- src/lib/patch.sh | 34 ++++++++++++++++++++++++++++++++ src/middleclick-autoscroll | 24 ++++++++++++++-------- 9 files changed, 90 insertions(+), 20 deletions(-) diff --git a/Makefile b/Makefile index 52b6a50..ea04302 100644 --- a/Makefile +++ b/Makefile @@ -8,7 +8,7 @@ # Overridable so a packager can pass the version it is actually building # (`make VERSION=$pkgver`). The literal below is the fallback for builds # straight from a checkout, and is what a release tag has to carry. -VERSION ?= 1.0.2 +VERSION ?= 1.0.3 PREFIX ?= /usr DESTDIR ?= diff --git a/README.md b/README.md index e73ff94..8a58d41 100644 --- a/README.md +++ b/README.md @@ -59,7 +59,7 @@ all of them, in a way that survives the next package upgrade, is not: Applications pick this up the next time they are started. [1] Turn autoscroll on or off - [2] Apply now + [2] Re-apply everything [3] Applications [4] Settings [q] Quit @@ -170,6 +170,7 @@ Run this before uninstalling the package. | `… enable` | turn it on, apply, start watching | | `… disable` | turn it off and put everything back | | `… apply` | apply to anything new (this is what the watcher calls) | +| `… apply --rebuild` | take everything back and apply it again, to repair a mess | | `… status` | what is covered | | `… list` | every application that was found and how it is handled | diff --git a/doc/middleclick-autoscroll.1.scd b/doc/middleclick-autoscroll.1.scd index 569d3a8..9118368 100644 --- a/doc/middleclick-autoscroll.1.scd +++ b/doc/middleclick-autoscroll.1.scd @@ -36,10 +36,17 @@ is refused. *disable* Turn it off and put every file that was changed back the way it was. -*apply* +*apply* [*--rebuild*] Apply to anything that has appeared since the last run. This is what the watcher calls; running it by hand is only needed when the watcher is off. + Entries left behind by an application that has since been uninstalled are + removed here too - the entry shadowing it lives in the user's home, where + the package manager that removed the application cannot see it. + + With *--rebuild* everything is taken back first and written again from + scratch. That is the repair: it does not care what looks correct already. + *status* How many applications are covered, whether Steam is patched, and when the last run was. diff --git a/po/de.po b/po/de.po index bbe24b9..e10d616 100644 --- a/po/de.po +++ b/po/de.po @@ -4,7 +4,7 @@ # msgid "" msgstr "" -"Project-Id-Version: middleclick-autoscroll 1.0.2\n" +"Project-Id-Version: middleclick-autoscroll 1.0.3\n" "Report-Msgid-Bugs-To: https://github.com/Felitendo/middleclick-autoscroll/issues\n" "POT-Creation-Date: 2026-08-16 00:00+0200\n" "PO-Revision-Date: 2026-08-16 00:00+0200\n" @@ -77,8 +77,8 @@ msgstr "Anwendungen übernehmen das beim nächsten Start." msgid "Turn autoscroll on or off" msgstr "Autoscroll ein- oder ausschalten" -msgid "Apply now" -msgstr "Jetzt anwenden" +msgid "Re-apply everything" +msgstr "Alles neu anwenden" msgid "Applications" msgstr "Anwendungen" @@ -164,6 +164,9 @@ msgstr "Autoscroll ist aus, alle Änderungen wurden zurückgenommen." msgid "Autoscroll is off. Turn it on first." msgstr "Autoscroll ist aus. Erst einschalten." +msgid "Applied again to %d applications." +msgstr "Erneut auf %d Anwendungen angewendet." + msgid "Applied to %d applications." msgstr "Auf %d Anwendungen angewendet." @@ -190,6 +193,9 @@ msgstr "Ausschalten und alles zurücknehmen" msgid "Apply to anything installed since the last run" msgstr "Auf alles anwenden, was seit dem letzten Lauf dazugekommen ist" +msgid "Take everything back and apply it again" +msgstr "Alles zurücknehmen und neu anwenden" + msgid "Show what is covered" msgstr "Anzeigen, was abgedeckt ist" diff --git a/po/middleclick-autoscroll.pot b/po/middleclick-autoscroll.pot index 073f15a..0cab8d1 100644 --- a/po/middleclick-autoscroll.pot +++ b/po/middleclick-autoscroll.pot @@ -4,7 +4,7 @@ # msgid "" msgstr "" -"Project-Id-Version: middleclick-autoscroll 1.0.2\n" +"Project-Id-Version: middleclick-autoscroll 1.0.3\n" "Report-Msgid-Bugs-To: https://github.com/Felitendo/middleclick-autoscroll/issues\n" "POT-Creation-Date: 2026-08-16 00:00+0200\n" "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" @@ -77,7 +77,7 @@ msgstr "" msgid "Turn autoscroll on or off" msgstr "" -msgid "Apply now" +msgid "Re-apply everything" msgstr "" msgid "Applications" @@ -164,6 +164,9 @@ msgstr "" msgid "Autoscroll is off. Turn it on first." msgstr "" +msgid "Applied again to %d applications." +msgstr "" + msgid "Applied to %d applications." msgstr "" @@ -190,6 +193,9 @@ msgstr "" msgid "Apply to anything installed since the last run" msgstr "" +msgid "Take everything back and apply it again" +msgstr "" + msgid "Show what is covered" msgstr "" diff --git a/src/lib/apply.sh b/src/lib/apply.sh index 8ecea29..fa58873 100644 --- a/src/lib/apply.sh +++ b/src/lib/apply.sh @@ -110,6 +110,8 @@ mca_apply() { [[ $CFG_AUTOSTART == yes ]] && mca_autostart_apply [[ $CFG_SPOTIFY == yes ]] && mca_spotify_apply + mca_prune_orphans + if (( MCA_CHANGES )) && mca_have update-desktop-database; then update-desktop-database "$MCA_APPDIR" 2>/dev/null || true fi diff --git a/src/lib/menu.sh b/src/lib/menu.sh index 5e39aaf..d55da2a 100644 --- a/src/lib/menu.sh +++ b/src/lib/menu.sh @@ -495,7 +495,7 @@ mca_ui_menu() { mca_ui_status printf '\n' printf ' [1] %s\n' "$(mca_msg "Turn autoscroll on or off")" - printf ' [2] %s\n' "$(mca_msg "Apply now")" + printf ' [2] %s\n' "$(mca_msg "Re-apply everything")" printf ' [3] %s\n' "$(mca_msg "Applications")" printf ' [4] %s\n' "$(mca_msg "Settings")" printf ' [q] %s\n' "$(mca_msg "Quit")" @@ -519,18 +519,24 @@ mca_ui_menu() { fi [[ -n $MCA_UI_NEEDS_ACK ]] && mca_pause ;; + # Not a plain apply: with the watcher running there is never + # anything left for one to do, and a menu entry that answers + # "already done" every time is not an action. This is the repair - + # everything is taken back and written again from scratch, which is + # what fixes an application that drifted, a flag file somebody + # edited, or Steam after it restored its own script. 2) - mca_ui_cooked mca_do_apply + mca_ui_cooked mca_do_apply --rebuild mca_pause ;; 3) if mca_ui_apps; then - [[ $CFG_ENABLED == yes ]] && mca_ui_cooked mca_do_apply --changed + [[ $CFG_ENABLED == yes ]] && mca_ui_cooked mca_do_apply --rebuild fi ;; 4) if mca_ui_settings; then - [[ $CFG_ENABLED == yes ]] && mca_ui_cooked mca_do_apply --changed + [[ $CFG_ENABLED == yes ]] && mca_ui_cooked mca_do_apply --rebuild fi ;; q|Q) mca_ui_term_restore; trap - EXIT INT TERM; return 0 ;; diff --git a/src/lib/patch.sh b/src/lib/patch.sh index d510a95..1597698 100644 --- a/src/lib/patch.sh +++ b/src/lib/patch.sh @@ -418,6 +418,40 @@ mca_spotify_apply() { return 0 } +# --------------------------------------------------------------------------- +# Leftovers +# --------------------------------------------------------------------------- + +# mca_prune_orphans +# Removes generated entries whose application is gone. +# +# Uninstalling something deletes its entry from /usr/share/applications, but the +# copy shadowing it is in the user's home and pacman knows nothing about it. It +# would sit in the menu forever, offering to start a program that is no longer +# installed - and the watcher would not notice, because a plain apply only ever +# looks at what is there now. +mca_prune_orphans() { + local kind path source line + local -a lines=() + + [[ -f $MCA_LEDGER ]] || return 0 + mapfile -t lines < "$MCA_LEDGER" + + for line in "${lines[@]}"; do + IFS=$'\t' read -r kind path source <<< "$line" + [[ $kind == shadow && -n $source ]] || continue + [[ -e $source ]] && continue + + # Only ever remove something still recognisably ours. + if [[ -f $path ]] && grep -q "^$MCA_MARK_SHADOW=" "$path" 2>/dev/null; then + rm -f -- "$path" + MCA_CHANGES=$(( MCA_CHANGES + 1 )) + fi + mca_ledger_forget "$path" + done + return 0 +} + # --------------------------------------------------------------------------- # Undo # --------------------------------------------------------------------------- diff --git a/src/middleclick-autoscroll b/src/middleclick-autoscroll index 49ab08e..845cc08 100644 --- a/src/middleclick-autoscroll +++ b/src/middleclick-autoscroll @@ -76,11 +76,11 @@ mca_do_disable() { } mca_do_apply() { - local changed=0 arg + local rebuild=0 arg for arg in "$@"; do case "$arg" in - --changed) changed=1 ;; + --rebuild) rebuild=1 ;; --quiet) MCA_QUIET=1 ;; esac done @@ -95,17 +95,24 @@ mca_do_apply() { return 1 fi - # A settings change can take an application out of scope as well as bring - # one in, and only a full undo can tell the difference, so that path starts - # from a clean slate. The watcher never does this: rewriting files that are - # already correct would make it trigger itself. - if (( changed )); then + # Start from a clean slate. Needed after a settings change, which can take + # an application out of scope as well as bring one in and where only a full + # undo can tell the difference, and it is what makes the repair a repair: + # whatever drifted is written again rather than left because it is "already + # applied". + # + # The watcher never does this. Rewriting files that are already correct + # would change their timestamps, and it is watching those directories. + if (( rebuild )); then mca_revert fi mca_apply - if (( MCA_CHANGES )); then + if (( rebuild )); then + mca_ok "$(mca_msg "Applied again to %d applications." "$MCA_N_ON")" + mca_say " $(mca_msg "Applications that are already running pick this up when they are restarted.")" + elif (( MCA_CHANGES )); then mca_ok "$(mca_msg "Applied to %d applications." "$MCA_N_ON")" mca_say " $(mca_msg "Applications that are already running pick this up when they are restarted.")" else @@ -160,6 +167,7 @@ mca_do_help() { enable $(mca_msg "Turn autoscroll on") disable $(mca_msg "Turn it off and put everything back") apply $(mca_msg "Apply to anything installed since the last run") + apply --rebuild $(mca_msg "Take everything back and apply it again") status $(mca_msg "Show what is covered") list $(mca_msg "List every application that was found") -h, --help $(mca_msg "Show this help")