diff --git a/lyrathorpe/home/sway.nix b/lyrathorpe/home/sway.nix index 324640e..118a65f 100644 --- a/lyrathorpe/home/sway.nix +++ b/lyrathorpe/home/sway.nix @@ -19,6 +19,19 @@ let # where a consumer needs it -- Sway/i3status/dunst want "#", foot/swaylock do # not. ctp = import ../catppuccin-mocha.nix; + + # Focused-window screenshot -> swappy editor (the dotfiles' grimshot.sh logic). + # Full store paths so it needs nothing on PATH. + screenshotWindow = pkgs.writeShellScript "screenshot-window" '' + ${pkgs.grim}/bin/grim -g "$(${pkgs.sway}/bin/swaymsg -t get_tree \ + | ${pkgs.jq}/bin/jq -r '.. | select(.focused?) | .rect | "\(.x),\(.y) \(.width)x\(.height)"')" \ + - | ${pkgs.swappy}/bin/swappy -f - + ''; + + # Binding-mode names. The string is both the `modes` attr key and what the + # bar's mode indicator shows, so the keys are spelled out in the label. + layoutMode = "layout: [s]tacking [w]tabbed [e]split"; + systemMode = "system: [l]ock [e]xit [s]leep [r]eboot [Shift+s]shutdown"; in { wayland.windowManager.sway = { @@ -39,6 +52,15 @@ in xkb_layout = "us"; xkb_variant = "dvorak"; }; + # Touchpads (laptops): tap-to-click and natural scrolling. Inert on the + # desktop hosts, which have no touchpad. + input."type:touchpad" = { + tap = "enabled"; + natural_scroll = "enabled"; + }; + + # Solid Catppuccin Mocha base as the wallpaper (no image dependency). + output."*".bg = "#${ctp.base} solid_color"; # Window borders -- Catppuccin Mocha (blue accent on the focused window). colors = { @@ -79,6 +101,33 @@ in } ]; + # Binding modes (submenus). Entered from keybindings below; each action + # returns to the default mode. mkOptionDefault-merged with the module's + # built-in "resize" mode. + modes = { + # Layout submenu (Mod+y). Mirrors Sway's default s/w/e layout keys -- + # notably it restores split-toggle, which moved off Mod+e when that + # became the nemo launcher. + ${layoutMode} = { + "s" = "layout stacking, mode default"; + "w" = "layout tabbed, mode default"; + "e" = "layout toggle split, mode default"; + "Return" = "mode default"; + "Escape" = "mode default"; + }; + # Power menu (Mod+Shift+x). Lock reuses the themed swaylock; the rest go + # through systemd/logind (allowed for the active local session). + ${systemMode} = { + "l" = "exec ${pkgs.swaylock}/bin/swaylock -f, mode default"; + "e" = "exec ${pkgs.sway}/bin/swaymsg exit, mode default"; + "s" = "exec systemctl suspend, mode default"; + "r" = "exec systemctl reboot, mode default"; + "Shift+s" = "exec systemctl poweroff, mode default"; + "Return" = "mode default"; + "Escape" = "mode default"; + }; + }; + bars = [ { position = "top"; @@ -134,10 +183,39 @@ in # File manager. mkForce overrides the module default (layout toggle split). "${modifier}+e" = lib.mkForce "exec ${pkgs.nemo}/bin/nemo"; "${modifier}+l" = "exec ${pkgs.swaylock}/bin/swaylock -f"; - "Print" = "exec ${pkgs.grim}/bin/grim ~/screenshot-$(date +%F-%H%M%S).png"; + + # Cycle workspaces. + "${modifier}+z" = "workspace prev"; + "${modifier}+x" = "workspace next"; + + # focus mode_toggle (tiling <-> floating focus) -- re-homed off + # Mod+Space, which is now the launcher. + "${modifier}+Mod1+space" = "focus mode_toggle"; + + # Enter the binding-mode submenus defined above. + "${modifier}+y" = "mode \"${layoutMode}\""; + "${modifier}+Shift+x" = "mode \"${systemMode}\""; + + # Clipboard history: pick a past entry through fuzzel (clipman stores + # it -- see services.clipman below). + "${modifier}+c" = + "exec ${pkgs.clipman}/bin/clipman pick -t CUSTOM --tool-args=\"${pkgs.fuzzel}/bin/fuzzel --dmenu\""; + + # Screenshots -> swappy editor: Print = drag a region, Shift+Print = + # the focused window. + "Print" = + "exec ${pkgs.grim}/bin/grim -g \"$(${pkgs.slurp}/bin/slurp)\" - | ${pkgs.swappy}/bin/swappy -f -"; + "Shift+Print" = "exec ${screenshotWindow}"; + "XF86AudioRaiseVolume" = "exec ${pkgs.wireplumber}/bin/wpctl set-volume @DEFAULT_AUDIO_SINK@ 5%+"; "XF86AudioLowerVolume" = "exec ${pkgs.wireplumber}/bin/wpctl set-volume @DEFAULT_AUDIO_SINK@ 5%-"; "XF86AudioMute" = "exec ${pkgs.wireplumber}/bin/wpctl set-mute @DEFAULT_AUDIO_SINK@ toggle"; + "XF86AudioMicMute" = "exec ${pkgs.wireplumber}/bin/wpctl set-mute @DEFAULT_AUDIO_SOURCE@ toggle"; + + # Media keys (MPRIS via playerctl). + "XF86AudioPlay" = "exec ${pkgs.playerctl}/bin/playerctl play-pause"; + "XF86AudioNext" = "exec ${pkgs.playerctl}/bin/playerctl next"; + "XF86AudioPrev" = "exec ${pkgs.playerctl}/bin/playerctl previous"; } # Screen backlight: laptops only (no internal backlight on a desktop). // lib.optionalAttrs portable { @@ -158,6 +236,13 @@ in # " " (man foot.ini(5): "ff0000 00ff00" => green cursor, red # text). Only colors-dark is needed; we never set initial-color-theme=light. settings = { + main = { + # Advertise as xterm-256color so remote hosts without foot's terminfo + # still behave (tmux re-adds foot's RGB/sync/etc. features -- see + # shell.nix). The [main] section is the unheadered top of foot.ini. + term = "xterm-256color"; + }; + scrollback.lines = 100000; "colors-dark" = { background = ctp.base; foreground = ctp.text; @@ -184,6 +269,38 @@ in }; }; + # Clipboard history: a user service runs `wl-paste --watch clipman store`, + # bound to the Wayland session, so copies persist and Mod+c (above) can pick + # an old entry through fuzzel. + services.clipman.enable = true; + + # fuzzel: the dmenu picker used by clipman, themed Catppuccin Mocha to match + # (fuzzel colours are RRGGBBAA -- 8 hex digits). + programs.fuzzel = { + enable = true; + settings = { + main = { + font = "Noto Sans:size=12"; + prompt = "\"clipboard \""; + }; + border = { + width = 2; + radius = 8; + }; + colors = { + background = "${ctp.base}f0"; + text = "${ctp.text}ff"; + prompt = "${ctp.subtext0}ff"; + input = "${ctp.text}ff"; + match = "${ctp.blue}ff"; + selection = "${ctp.surface1}ff"; + selection-text = "${ctp.text}ff"; + selection-match = "${ctp.blue}ff"; + border = "${ctp.blue}ff"; + }; + }; + }; + programs.swaylock = { enable = true; # Catppuccin Mocha (swaylock colours are hex without "#"). diff --git a/lyrathorpe/swaywm.nix b/lyrathorpe/swaywm.nix index 3d9fcf2..9c5551b 100644 --- a/lyrathorpe/swaywm.nix +++ b/lyrathorpe/swaywm.nix @@ -37,6 +37,10 @@ in brightnessctl foot grim + slurp # region selection for screenshots + swappy # screenshot annotation/save + jq # used by the focused-window screenshot bind + playerctl # MPRIS media keys sway-launcher-desktop pavucontrol ];