hyprland: use builtin previous-workspace toggle
This commit is contained in:
@@ -444,10 +444,9 @@ bind = $mainMod CTRL, 8, workspace, 8
|
||||
bind = $mainMod CTRL, 9, movetoworkspacesilent, 9
|
||||
bind = $mainMod CTRL, 9, workspace, 9
|
||||
|
||||
# Workspace cycling with monitor-local history and commit-on-release semantics.
|
||||
bind = $mainMod, backslash, exec, ~/.config/hypr/scripts/workspace-back.sh cycle
|
||||
bindr = , SUPER_L, exec, ~/.config/hypr/scripts/workspace-back.sh finalize
|
||||
bindr = , SUPER_R, exec, ~/.config/hypr/scripts/workspace-back.sh finalize
|
||||
# Toggle to the previous workspace on the current monitor using Hyprland's
|
||||
# built-in per-monitor workspace history.
|
||||
bind = $mainMod, backslash, workspace, previous_per_monitor
|
||||
|
||||
# Swap current workspace with another (like XMonad's swapWithCurrent)
|
||||
bind = $hyper, 5, exec, ~/.config/hypr/scripts/swap-workspaces.sh
|
||||
@@ -556,7 +555,6 @@ exec-once = sh -lc 'export IMALISON_SESSION_TYPE=wayland; dbus-update-activation
|
||||
# Force a fresh daemon after compositor restarts so hyprscratch doesn't keep a stale socket.
|
||||
exec-once = systemctl --user restart hyprscratch.service
|
||||
exec-once = hypridle
|
||||
exec-once = ~/.config/hypr/scripts/workspace-history.sh
|
||||
|
||||
# Clipboard history daemon
|
||||
exec-once = wl-paste --type text --watch cliphist store
|
||||
|
||||
@@ -1,71 +0,0 @@
|
||||
#!/usr/bin/env bash
|
||||
set -euo pipefail
|
||||
|
||||
script_dir="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
||||
# shellcheck source=workspace-history-common.sh
|
||||
# shellcheck source-path=SCRIPTDIR
|
||||
source "${script_dir}/workspace-history-common.sh"
|
||||
|
||||
action="${1:-cycle}"
|
||||
|
||||
exec 9>"${lock_file}"
|
||||
flock 9
|
||||
|
||||
state="$(wh_load_state)"
|
||||
monitors_json="$(wh_monitors_json)"
|
||||
state="$(wh_refresh_state_json "${state}" "${monitors_json}")"
|
||||
|
||||
focused_monitor="$(
|
||||
jq -r '.[] | select(.focused == true) | .name // empty' <<<"${monitors_json}" | head -n 1
|
||||
)"
|
||||
|
||||
if [[ -z "${focused_monitor}" ]]; then
|
||||
wh_save_state "${state}"
|
||||
exit 0
|
||||
fi
|
||||
|
||||
current_workspace="$(jq -r --arg monitor "${focused_monitor}" '.monitorCurrent[$monitor] // empty' <<<"${state}")"
|
||||
|
||||
case "${action}" in
|
||||
cycle)
|
||||
next_workspace="$(
|
||||
jq -r \
|
||||
--arg monitor "${focused_monitor}" \
|
||||
--arg current "${current_workspace}" \
|
||||
'
|
||||
(.monitorHistory[$monitor] // []) as $history
|
||||
| if ($history | length) < 2 then
|
||||
""
|
||||
else
|
||||
($history | index($current)) as $idx
|
||||
| if $idx == null then
|
||||
""
|
||||
else
|
||||
$history[(($idx + 1) % ($history | length))]
|
||||
end
|
||||
end
|
||||
' <<<"${state}"
|
||||
)"
|
||||
|
||||
if [[ -z "${next_workspace}" || "${next_workspace}" == "${current_workspace}" ]]; then
|
||||
wh_save_state "${state}"
|
||||
exit 0
|
||||
fi
|
||||
|
||||
state="$(
|
||||
jq -c \
|
||||
--arg monitor "${focused_monitor}" \
|
||||
'.cycle = {"active": true, "monitor": $monitor}' <<<"${state}"
|
||||
)"
|
||||
wh_save_state "${state}"
|
||||
hyprctl dispatch workspace "${next_workspace}" >/dev/null 2>&1 || true
|
||||
;;
|
||||
finalize)
|
||||
state="$(wh_finalize_cycle_json "${state}")"
|
||||
wh_save_state "${state}"
|
||||
;;
|
||||
*)
|
||||
printf 'Unknown action: %s\n' "${action}" >&2
|
||||
exit 1
|
||||
;;
|
||||
esac
|
||||
@@ -1,127 +0,0 @@
|
||||
#!/usr/bin/env bash
|
||||
|
||||
max_ws="${HYPR_MAX_WORKSPACE:-9}"
|
||||
|
||||
runtime_dir="${XDG_RUNTIME_DIR:-/run/user/$(id -u)}"
|
||||
state_dir="${HYPR_WORKSPACE_STATE_DIR:-${runtime_dir}/hypr}"
|
||||
state_file="${state_dir}/workspace-history.json"
|
||||
# shellcheck disable=SC2034 # Sourced by sibling scripts that coordinate updates.
|
||||
lock_file="${state_dir}/workspace-history.lock"
|
||||
|
||||
mkdir -p "${state_dir}"
|
||||
|
||||
wh_default_state() {
|
||||
cat <<'EOF'
|
||||
{"monitorCurrent":{},"monitorHistory":{},"cycle":{"active":false}}
|
||||
EOF
|
||||
}
|
||||
|
||||
wh_load_state() {
|
||||
local state
|
||||
if [[ -s "${state_file}" ]] && state="$(jq -c '.' "${state_file}" 2>/dev/null)"; then
|
||||
printf '%s\n' "${state}"
|
||||
return
|
||||
fi
|
||||
|
||||
wh_default_state
|
||||
}
|
||||
|
||||
wh_save_state() {
|
||||
local state="$1"
|
||||
local tmp_file
|
||||
|
||||
tmp_file="$(mktemp "${state_file}.XXXXXX")"
|
||||
printf '%s\n' "${state}" >"${tmp_file}"
|
||||
mv "${tmp_file}" "${state_file}"
|
||||
}
|
||||
|
||||
wh_normalize_workspace() {
|
||||
local ws_id="${1:-}"
|
||||
local ws_name="${2:-}"
|
||||
|
||||
if [[ -n "${ws_name}" && "${ws_name}" != "null" && "${ws_name}" != special:* ]]; then
|
||||
printf '%s\n' "${ws_name}"
|
||||
return
|
||||
fi
|
||||
|
||||
if [[ -z "${ws_id}" || "${ws_id}" == "null" || "${ws_id}" =~ ^- ]]; then
|
||||
return
|
||||
fi
|
||||
|
||||
if [[ "${ws_id}" =~ ^[0-9]+$ ]] && ((ws_id >= 1 && ws_id <= max_ws)); then
|
||||
printf '%s\n' "${ws_id}"
|
||||
fi
|
||||
}
|
||||
|
||||
wh_monitors_json() {
|
||||
hyprctl -j monitors 2>/dev/null || printf '[]\n'
|
||||
}
|
||||
|
||||
wh_refresh_state_json() {
|
||||
local state="$1"
|
||||
local monitors_json="$2"
|
||||
local row
|
||||
local monitor
|
||||
local ws_id
|
||||
local ws_name
|
||||
local workspace
|
||||
|
||||
while IFS= read -r row; do
|
||||
[[ -z "${row}" ]] && continue
|
||||
|
||||
monitor="$(jq -r '.name // empty' <<<"${row}")"
|
||||
ws_id="$(jq -r '.activeWorkspace.id // empty' <<<"${row}")"
|
||||
ws_name="$(jq -r '.activeWorkspace.name // empty' <<<"${row}")"
|
||||
workspace="$(wh_normalize_workspace "${ws_id}" "${ws_name}")"
|
||||
|
||||
[[ -z "${monitor}" || -z "${workspace}" ]] && continue
|
||||
|
||||
state="$(
|
||||
jq -c \
|
||||
--arg monitor "${monitor}" \
|
||||
--arg workspace "${workspace}" \
|
||||
'
|
||||
.monitorCurrent[$monitor] = $workspace
|
||||
| if .cycle.active == true and .cycle.monitor == $monitor then
|
||||
.
|
||||
else
|
||||
.monitorHistory[$monitor] =
|
||||
([$workspace] + ((.monitorHistory[$monitor] // []) | map(select(. != $workspace))))
|
||||
end
|
||||
' <<<"${state}"
|
||||
)"
|
||||
done < <(jq -c '.[]' <<<"${monitors_json}")
|
||||
|
||||
printf '%s\n' "${state}"
|
||||
}
|
||||
|
||||
wh_finalize_cycle_json() {
|
||||
local state="$1"
|
||||
local monitor
|
||||
local current
|
||||
|
||||
if [[ "$(jq -r '.cycle.active // false' <<<"${state}")" != "true" ]]; then
|
||||
printf '%s\n' "${state}"
|
||||
return
|
||||
fi
|
||||
|
||||
monitor="$(jq -r '.cycle.monitor // empty' <<<"${state}")"
|
||||
current="$(jq -r --arg monitor "${monitor}" '.monitorCurrent[$monitor] // empty' <<<"${state}")"
|
||||
|
||||
if [[ -n "${monitor}" && -n "${current}" ]]; then
|
||||
state="$(
|
||||
jq -c \
|
||||
--arg monitor "${monitor}" \
|
||||
--arg current "${current}" \
|
||||
'
|
||||
.monitorHistory[$monitor] =
|
||||
([$current] + ((.monitorHistory[$monitor] // []) | map(select(. != $current))))
|
||||
| .cycle = {"active": false}
|
||||
' <<<"${state}"
|
||||
)"
|
||||
else
|
||||
state="$(jq -c '.cycle = {"active": false}' <<<"${state}")"
|
||||
fi
|
||||
|
||||
printf '%s\n' "${state}"
|
||||
}
|
||||
@@ -1,46 +0,0 @@
|
||||
#!/usr/bin/env bash
|
||||
set -euo pipefail
|
||||
|
||||
script_dir="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
||||
# shellcheck source=workspace-history-common.sh
|
||||
# shellcheck source-path=SCRIPTDIR
|
||||
source "${script_dir}/workspace-history-common.sh"
|
||||
|
||||
runtime_dir="${XDG_RUNTIME_DIR:-/run/user/$(id -u)}"
|
||||
sig="${HYPRLAND_INSTANCE_SIGNATURE:-}"
|
||||
if [[ -z "$sig" ]]; then
|
||||
exit 0
|
||||
fi
|
||||
|
||||
sock="${runtime_dir}/hypr/${sig}/.socket2.sock"
|
||||
|
||||
with_history_lock() {
|
||||
exec 9>"${lock_file}"
|
||||
flock 9
|
||||
"$@"
|
||||
}
|
||||
|
||||
refresh_history_state() {
|
||||
local state
|
||||
local monitors_json
|
||||
|
||||
state="$(wh_load_state)"
|
||||
monitors_json="$(wh_monitors_json)"
|
||||
state="$(wh_refresh_state_json "${state}" "${monitors_json}")"
|
||||
wh_save_state "${state}"
|
||||
}
|
||||
|
||||
with_history_lock refresh_history_state
|
||||
|
||||
# Wait for the event socket to be ready.
|
||||
while [[ ! -S "${sock}" ]]; do
|
||||
sleep 0.2
|
||||
done
|
||||
|
||||
nc -U "${sock}" | while read -r line; do
|
||||
case "${line}" in
|
||||
workspace*">>"*)
|
||||
with_history_lock refresh_history_state
|
||||
;;
|
||||
esac
|
||||
done
|
||||
Reference in New Issue
Block a user