{ lib, pkgs, config, ... }: with lib; let cfg = config.eboskma.programs.sway; mod = "Mod4"; swaylockcmd = "${pkgs.swaylock}/bin/swaylock --ignore-empty-password --daemonize --show-failed-attempts --indicator-caps-lock --image ${cfg.lock-wallpaper} --scaling fill"; rofiPower = pkgs.writeShellScriptBin "rofi-power" ( builtins.replaceStrings [ "{WALLPAPER}" ] [ (builtins.toString cfg.lock-wallpaper) ] ( builtins.readFile ./powermenu.sh ) ); in { options.eboskma.programs.sway = { enable = mkEnableOption "sway"; wayvnc = mkEnableOption "wayvnc"; package = mkPackageOption pkgs "sway" { }; lock-wallpaper = mkOption { description = "Wallpaper to use for the lockscreen"; type = types.path; }; output = mkOption { description = "An attribute set that defines output modules. See the sway-output(5) manpage for options"; type = types.attrsOf (types.attrsOf types.str); default = { }; }; input = mkOption { description = "An attribute set that defines input modules. See the sway-input(5) manpage for options"; type = types.attrsOf (types.attrsOf types.str); default = { }; }; startup = mkOption { description = "Commands that should be executed at startup."; default = [ ]; type = types.listOf ( types.submodule { options = { command = mkOption { type = types.str; description = "Command that will be executed on startup."; }; always = mkOption { type = types.bool; default = false; description = "Whether to run command on each ${moduleName} restart."; }; }; } ); }; workspaceOutputs = mkOption { description = "Assign workspaces to outputs"; type = types.listOf ( types.submodule { options = { output = mkOption { description = "Name(s) of the output to assign"; type = with types; either str (listOf str); apply = lists.toList; default = ""; }; workspace = mkOption { description = "Name of the workspace to assign"; type = types.str; default = ""; }; }; } ); default = [ ]; }; extraKeybindings = mkOption { description = "Extra keybindings"; type = types.attrsOf types.str; default = { }; }; }; config = mkIf cfg.enable { wayland.windowManager.sway = { enable = true; package = cfg.package; checkConfig = false; # Why is this even here? config = { modifier = mod; bars = [ ]; # Dracula theme colors = { background = "#f8f8f2"; focused = { border = "#6272a4"; background = "#6272A4"; text = "#f8f8f2"; indicator = "#6272a4"; childBorder = "#6272a4"; }; focusedInactive = { border = "#44475a"; background = "#44475a"; text = "#f8f8f2"; indicator = "#44475a"; childBorder = "#44475a"; }; unfocused = { border = "#282a36"; background = "#282a36"; text = "#bfbfbf"; indicator = "#282a36"; childBorder = "#282a36"; }; urgent = { border = "#44475a"; background = "#ff5555"; text = "#f8f8f2"; indicator = "#ff5555"; childBorder = "#ff5555"; }; placeholder = { border = "#282a36"; background = "#282a36"; text = "#f8f8f2"; indicator = "#282a36"; childBorder = "#282a36"; }; }; defaultWorkspace = "workspace number 1"; workspaceOutputAssign = cfg.workspaceOutputs; left = "n"; down = "e"; up = "i"; right = "o"; floating = { criteria = [ { app_id = "gnome-calculator"; } ]; modifier = mod; }; fonts = { names = [ "Iosevka Nerd Font" ]; style = "Regular"; size = 12.0; }; gaps = { inner = 10; # outer = 5; smartBorders = "on"; }; input = cfg.input; output = cfg.output; # menu = "${pkgs.rofi}/bin/rofi -show drun -no-lazy-grab"; menu = "${config.programs.anyrun.package}/bin/anyrun"; keybindings = { "${mod}+Return" = "exec ${config.wayland.windowManager.sway.config.terminal}"; "${mod}+Shift+q" = "kill"; "${mod}+s" = "exec ${config.wayland.windowManager.sway.config.menu}"; # "${mod}+Shift+s" = "exec ${pkgs.wofi}/bin/wofi --show run | ${pkgs.findutils}/bin/xargs swaymsg exec --"; "${mod}+${config.wayland.windowManager.sway.config.left}" = "focus left"; "${mod}+${config.wayland.windowManager.sway.config.down}" = "focus down"; "${mod}+${config.wayland.windowManager.sway.config.up}" = "focus up"; "${mod}+${config.wayland.windowManager.sway.config.right}" = "focus right"; "${mod}+Left" = "focus left"; "${mod}+Down" = "focus down"; "${mod}+Up" = "focus up"; "${mod}+Right" = "focus right"; "${mod}+Shift+${config.wayland.windowManager.sway.config.left}" = "move left"; "${mod}+Shift+${config.wayland.windowManager.sway.config.down}" = "move down"; "${mod}+Shift+${config.wayland.windowManager.sway.config.up}" = "move up"; "${mod}+Shift+${config.wayland.windowManager.sway.config.right}" = "move right"; "${mod}+Shift+Left" = "move left"; "${mod}+Shift+Down" = "move down"; "${mod}+Shift+Up" = "move up"; "${mod}+Shift+Right" = "move right"; "${mod}+h" = "split h"; "${mod}+v" = "split v"; "${mod}+t" = "fullscreen toggle"; "${mod}+a" = "focus parent"; "${mod}+r" = "layout stacking"; "${mod}+w" = "layout tabbed"; "${mod}+f" = "layout toggle split"; "${mod}+Shift+space" = "floating toggle"; "${mod}+space" = "focus mode_toggle"; "${mod}+Shift+k" = "sticky toggle"; "${mod}+1" = "workspace number 1"; "${mod}+2" = "workspace number 2"; "${mod}+3" = "workspace number 3"; "${mod}+4" = "workspace number 4"; "${mod}+5" = "workspace number 5"; "${mod}+6" = "workspace number 6"; "${mod}+7" = "workspace number 7"; "${mod}+8" = "workspace number 8"; "${mod}+9" = "workspace number 9"; "${mod}+0" = "workspace number 10"; "${mod}+Shift+1" = "move container to workspace number 1"; "${mod}+Shift+2" = "move container to workspace number 2"; "${mod}+Shift+3" = "move container to workspace number 3"; "${mod}+Shift+4" = "move container to workspace number 4"; "${mod}+Shift+5" = "move container to workspace number 5"; "${mod}+Shift+6" = "move container to workspace number 6"; "${mod}+Shift+7" = "move container to workspace number 7"; "${mod}+Shift+8" = "move container to workspace number 8"; "${mod}+Shift+9" = "move container to workspace number 9"; "${mod}+Shift+0" = "move container to workspace number 10"; "${mod}+Shift+minus" = "move scratchpad"; "${mod}+minus" = "scratchpad show"; "${mod}+Shift+c" = "reload"; "${mod}+Shift+f" = "exec --no-startup-id ${rofiPower}/bin/rofi-power"; "${mod}+l" = "exec ${swaylockcmd}"; "${mod}+p" = "mode resize"; "${mod}+Pause" = "mode passthrough"; "${mod}+c" = mkIf config.eboskma.programs.emacs.enable "exec ${config.programs.emacs.package}/bin/emacsclient -c"; "${mod}+Print" = "exec ${pkgs.grim}/bin/grim -o $(${cfg.package}/bin/swaymsg -t get_outputs | ${pkgs.jaq}/bin/jaq -r '.[] | select(.focused) | .name')"; "${mod}+Shift+Print" = ''exec ${pkgs.grim}/bin/grim -o $(${cfg.package}/bin/swaymsg -t get_outputs | ${pkgs.jaq}/bin/jaq -r '.[] | select(.focused) | .name') - | ${pkgs.wl-clipboard}/bin/wl-copy -t "image/png" -f''; "${mod}+Shift+Ctrl+Print" = ''exec ${pkgs.grim}/bin/grim -g "$(${pkgs.slurp}/bin/slurp)" - | ${pkgs.wl-clipboard}/bin/wl-copy -t "image/png" -f''; "${mod}+Shift+Alt+Print" = ''exec ${pkgs.grim}/bin/grim -g "$(${pkgs.slurp}/bin/slurp)"''; "XF86AudioRaiseVolume" = "exec ${pkgs.pamedia}/bin/pamedia up"; "XF86AudioLowerVolume" = "exec ${pkgs.pamedia}/bin/pamedia down"; "XF86AudioMute" = "exec ${pkgs.pamedia}/bin/pamedia mute"; "XF86Calculator" = "exec ${pkgs.gnome-calculator}/bin/gnome-calculator"; "${mod}+d" = "exec ${pkgs.swaynotificationcenter}/bin/swaync-client --toggle-panel --skip-wait"; "${mod}+Shift+d" = "exec ${pkgs.swaynotificationcenter}/bin/swaync-client --toggle-dnd --skip-wait"; } // cfg.extraKeybindings; modes = { passthrough = { "${mod}+Pause" = "mode default"; }; }; terminal = "${pkgs.foot}/bin/foot"; window = { border = 1; titlebar = false; }; workspaceAutoBackAndForth = true; seat = { "seat0" = { hide_cursor = "when-typing enable"; }; }; startup = cfg.startup; }; extraConfig = builtins.concatStringsSep "\n" ( [ '' for_window [app_id="^.*"] inhibit_idle fullscreen for_window [class="^.*"] inhibit_idle fullscreen for_window [app_id="org.gnome.Calculator"] floating enable for_window [shell="xwayland"] title_format "%title [XWayland]" for_window [app_id="^.*iwgtk$"] floating enable include /etc/sway/config.d/* '' ] ++ lib.optional (cfg.package == pkgs.swayfx) '' blur enable blur_xray disable shadows enable default_dim_inactive 0.2 corner_radius 10 '' ); # exec --no-startup-id ${pkgs.swaynotificationcenter}/bin/swaync # exec --no-startup-id ${pkgs.networkmanagerapplet}/bin/nm-applet --indicator # exec --no-startup-id ${pkgs.swayidle}/bin/swayidle -w timeout 900 "${swaylockcmd}" # exec --no-startup-id ${pkgs.swayidle}/bin/swayidle -w timeout 1200 "${pkgs.sway}/bin/swaymsg 'output * dpms off'" resume "${pkgs.sway}/bin/swaymsg 'output * dpms on'" # exec_always --no-startup-id systemctl --user import-environment _JAVA_AWT_WM_NONREPARENTING MOZ_ENABLE_WAYLAND MOZ_DBUS_REMOTE QT_QPA_PLATFORM QT_WAYLAND_DISABLE_WINDOWDECORATION QT_QPA_PLATFORMTHEME SDL_VIDEODRIVER SSH_AUTH_SOCK # exec_always --no-startup-id dbus-update-activation-environment --systemd _JAVA_AWT_WM_NONREPARENTING MOZ_ENABLE_WAYLAND MOZ_DBUS_REMOTE QT_QPA_PLATFORM QT_WAYLAND_DISABLE_WINDOWDECORATION QT_QPA_PLATFORMTHEME SDL_VIDEODRIVER SSH_AUTH_SOCK # extraSessionCommands = # '' # export _JAVA_AWT_WM_NONREPARENTING=1 # export MOZ_ENABLE_WAYLAND=1 # export MOZ_DBUS_REMOTE=1 # export QT_QPA_PLATFORM=wayland # export QT_WAYLAND_DISABLE_WINDOWDECORATION="1" # export QT_QPA_PLATFORMTHEME=qt5ct # export SDL_VIDEODRIVER=wayland # export SSH_AUTH_SOCK="''${XDG_RUNTIME_DIR}/gnupg/S.gpg-agent.ssh" # ''; wrapperFeatures = { base = true; gtk = true; }; xwayland = true; systemd = { enable = true; xdgAutostart = true; }; }; services = { swayidle = { enable = true; events = [ { event = "lock"; command = swaylockcmd; } ]; timeouts = let poweroffOpts = builtins.concatStringsSep " " ( builtins.map (name: "--output ${name} --off") (builtins.attrNames cfg.output) ); resumeOpts = builtins.concatStringsSep " " ( builtins.map (name: "--output ${name} --on") (builtins.attrNames cfg.output) ); in [ { timeout = 900; command = swaylockcmd; } { timeout = 1200; command = "${pkgs.wlr-randr}/bin/wlr-randr ${poweroffOpts}"; resumeCommand = "${pkgs.wlr-randr}/bin/wlr-randr ${resumeOpts}"; } ]; }; }; systemd.user = { services = { wayvnc = mkIf cfg.wayvnc { Unit = { Description = "VNC server for wlroots based Wayland compositors"; After = [ "sway-session.target" ]; }; Service = { ExecStart = "${pkgs.wayvnc}/bin/wayvnc 0.0.0.0"; Restart = "always"; }; Install = { WantedBy = [ "graphical-session.target" ]; }; }; }; targets.tray = { Unit = { Description = "Home Manager System Tray"; Requires = [ "sway-session-pre.target" ]; }; }; }; }; }