diff --git a/modules/lib/maintainers.nix b/modules/lib/maintainers.nix
index dd4bb9e24..5c2136a24 100644
--- a/modules/lib/maintainers.nix
+++ b/modules/lib/maintainers.nix
@@ -454,4 +454,10 @@
github = "wcarlsen";
githubId = 17003032;
};
+ "9p4" = {
+ name = "9p4";
+ email = "vcs@ersei.net";
+ github = "9p4";
+ githubId = 17993169;
+ };
}
diff --git a/modules/modules.nix b/modules/modules.nix
index 02f4ae07a..12163edc7 100644
--- a/modules/modules.nix
+++ b/modules/modules.nix
@@ -201,6 +201,7 @@ let
./programs/ssh.nix
./programs/starship.nix
./programs/swaylock.nix
+ ./programs/swayr.nix
./programs/taskwarrior.nix
./programs/tealdeer.nix
./programs/terminator.nix
diff --git a/modules/programs/swayr.nix b/modules/programs/swayr.nix
new file mode 100644
index 000000000..250a3e01f
--- /dev/null
+++ b/modules/programs/swayr.nix
@@ -0,0 +1,135 @@
+{ config, lib, pkgs, ... }:
+
+with lib;
+
+let
+ cfg = config.programs.swayr;
+ tomlFormat = pkgs.formats.toml { };
+ configFile = tomlFormat.generate "config.toml" cfg.settings;
+ finalConfig = pkgs.writeText "swayr.toml"
+ ((builtins.readFile configFile) + cfg.extraConfig);
+in {
+ meta.maintainers = [ lib.hm.maintainers."9p4" ];
+
+ options.programs.swayr = {
+ enable = mkEnableOption "the swayr service";
+
+ settings = mkOption {
+ type = types.nullOr tomlFormat.type;
+ default = { };
+ example = literalExpression ''
+ menu = {
+ executable = "${pkgs.wofi}/bin/wofi";
+ args = [
+ "--show=dmenu"
+ "--allow-markup"
+ "--allow-images"
+ "--insensitive"
+ "--cache-file=/dev/null"
+ "--parse-search"
+ "--height=40%"
+ "--prompt={prompt}"
+ ];
+ };
+
+ format = {
+ output_format = "{indent}Output {name} ({id})";
+ workspace_format = "{indent}Workspace {name} [{layout}] on output {output_name} ({id})";
+ container_format = "{indent}Container [{layout}] {marks} on workspace {workspace_name} ({id})";
+ window_format = "img:{app_icon}:text:{indent}{app_name} — {urgency_start}“{title}”{urgency_end} {marks} on workspace {workspace_name} / {output_name} ({id})";
+ indent = " ";
+ urgency_start = "";
+ urgency_end = "";
+ html_escape = true;
+ };
+
+ layout = {
+ auto_tile = false;
+ auto_tile_min_window_width_per_output_width = [
+ [ 800 400 ]
+ [ 1024 500 ]
+ [ 1280 600 ]
+ [ 1400 680 ]
+ [ 1440 700 ]
+ [ 1600 780 ]
+ [ 1680 780 ]
+ [ 1920 920 ]
+ [ 2048 980 ]
+ [ 2560 1000 ]
+ [ 3440 1200 ]
+ [ 3840 1280 ]
+ [ 4096 1400 ]
+ [ 4480 1600 ]
+ [ 7680 2400 ]
+ ];
+ };
+
+ focus = {
+ lockin_delay = 750;
+ };
+
+ misc = {
+ seq_inhibit = false;
+ };
+ '';
+ description = ''
+ Configuration included in `config.toml`.
+ For available options see
+ '';
+ };
+
+ extraConfig = mkOption {
+ type = types.lines;
+ default = "";
+ description = ''
+ Extra configuration lines to append to the swayr
+ configuration file.
+ '';
+ };
+
+ systemd.enable = mkEnableOption "swayr systemd integration";
+ systemd.target = mkOption {
+ type = types.str;
+ default = "graphical-session.target";
+ description = ''
+ Systemd target to bind to.
+ '';
+ };
+
+ package = mkOption {
+ type = types.package;
+ default = pkgs.swayr;
+ defaultText = literalExpression "pkgs.swayr";
+ description = "swayr package to use.";
+ };
+ };
+
+ config = mkIf cfg.enable (mkMerge [
+ {
+ home.packages = [ cfg.package ];
+
+ # Creating an empty file on empty configuration is desirable, otherwise swayrd will create the file on startup.
+ xdg.configFile."swayr/config.toml" =
+ mkIf (cfg.settings != { }) { source = finalConfig; };
+ }
+
+ (mkIf cfg.systemd.enable {
+ systemd.user.services.swayrd = {
+ Unit = {
+ Description = "A window-switcher & more for sway";
+ Documentation = "https://sr.ht/~tsdh/swayr";
+ After = [ cfg.systemd.target ];
+ PartOf = [ cfg.systemd.target ];
+ X-Restart-Triggers = mkIf (cfg.settings != { })
+ [ "${config.xdg.configFile."swayr/config.toml".source}" ];
+ };
+ Service = {
+ Environment = [ "RUST_BACKTRACE=1" ];
+ ExecStart = "${cfg.package}/bin/swayrd";
+ Restart = "on-failure";
+ };
+ Install.WantedBy = [ cfg.systemd.target ];
+ };
+ })
+ ]);
+}
diff --git a/tests/default.nix b/tests/default.nix
index 23dd36ccd..db4e1d05f 100644
--- a/tests/default.nix
+++ b/tests/default.nix
@@ -195,6 +195,7 @@ import nmt {
./modules/programs/rofi
./modules/programs/rofi-pass
./modules/programs/swaylock
+ ./modules/programs/swayr
./modules/programs/terminator
./modules/programs/thunderbird
./modules/programs/waybar
diff --git a/tests/modules/programs/swayr/basic-configuration.nix b/tests/modules/programs/swayr/basic-configuration.nix
new file mode 100644
index 000000000..47648e828
--- /dev/null
+++ b/tests/modules/programs/swayr/basic-configuration.nix
@@ -0,0 +1,82 @@
+{ config, pkgs, ... }:
+
+{
+ config = {
+ programs.swayr = {
+ enable = true;
+ package = config.lib.test.mkStubPackage { };
+ systemd.enable = true;
+ settings = {
+ menu = {
+ executable = "wofi";
+ args = [
+ "--show=dmenu"
+ "--allow-markup"
+ "--allow-images"
+ "--insensitive"
+ "--cache-file=/dev/null"
+ "--parse-search"
+ "--height=40%"
+ "--prompt={prompt}"
+ ];
+ };
+
+ format = {
+ output_format = ''
+ {indent}Output {name} ({id})'';
+ workspace_format = ''
+ {indent}Workspace {name} [{layout}] on output {output_name} ({id})'';
+ container_format = ''
+ {indent}Container [{layout}] {marks} on workspace {workspace_name} ({id})'';
+ window_format = ''
+ img:{app_icon}:text:{indent}{app_name} — {urgency_start}“{title}”{urgency_end} {marks} on workspace {workspace_name} / {output_name} ({id})'';
+ indent = " ";
+ urgency_start = '''';
+ urgency_end = "";
+ html_escape = true;
+ };
+
+ layout = {
+ auto_tile = false;
+ auto_tile_min_window_width_per_output_width = [
+ [ 800 400 ]
+ [ 1024 500 ]
+ [ 1280 600 ]
+ [ 1400 680 ]
+ [ 1440 700 ]
+ [ 1600 780 ]
+ [ 1680 780 ]
+ [ 1920 920 ]
+ [ 2048 980 ]
+ [ 2560 1000 ]
+ [ 3440 1200 ]
+ [ 3840 1280 ]
+ [ 4096 1400 ]
+ [ 4480 1600 ]
+ [ 7680 2400 ]
+ ];
+ };
+
+ focus = { lockin_delay = 750; };
+
+ misc = { seq_inhibit = false; };
+ };
+ extraConfig = ''
+ [extra]
+ foo = "\ubar"
+ '';
+ };
+
+ nmt.script = ''
+ serviceFile=home-files/.config/systemd/user/swayrd.service
+
+ assertFileExists $serviceFile
+ assertFileRegex $serviceFile 'ExecStart=.*/bin/swayrd'
+ assertFileRegex $serviceFile 'Environment=RUST_BACKTRACE=1'
+
+ assertFileExists home-files/.config/swayr/config.toml
+ assertFileContent home-files/.config/swayr/config.toml \
+ ${./basic-configuration.toml}
+ '';
+ };
+}
diff --git a/tests/modules/programs/swayr/basic-configuration.toml b/tests/modules/programs/swayr/basic-configuration.toml
new file mode 100644
index 000000000..3252a632a
--- /dev/null
+++ b/tests/modules/programs/swayr/basic-configuration.toml
@@ -0,0 +1,25 @@
+[focus]
+lockin_delay = 750
+
+[format]
+container_format = "{indent}Container [{layout}] {marks} on workspace {workspace_name} ({id})"
+html_escape = true
+indent = " "
+output_format = "{indent}Output {name} ({id})"
+urgency_end = ""
+urgency_start = ""
+window_format = "img:{app_icon}:text:{indent}{app_name} — {urgency_start}“{title}”{urgency_end} {marks} on workspace {workspace_name} / {output_name} ({id})"
+workspace_format = "{indent}Workspace {name} [{layout}] on output {output_name} ({id})"
+
+[layout]
+auto_tile = false
+auto_tile_min_window_width_per_output_width = [[800, 400], [1024, 500], [1280, 600], [1400, 680], [1440, 700], [1600, 780], [1680, 780], [1920, 920], [2048, 980], [2560, 1000], [3440, 1200], [3840, 1280], [4096, 1400], [4480, 1600], [7680, 2400]]
+
+[menu]
+args = ["--show=dmenu", "--allow-markup", "--allow-images", "--insensitive", "--cache-file=/dev/null", "--parse-search", "--height=40%", "--prompt={prompt}"]
+executable = "wofi"
+
+[misc]
+seq_inhibit = false
+[extra]
+foo = "\ubar"
diff --git a/tests/modules/programs/swayr/default.nix b/tests/modules/programs/swayr/default.nix
new file mode 100644
index 000000000..ed2908e90
--- /dev/null
+++ b/tests/modules/programs/swayr/default.nix
@@ -0,0 +1,4 @@
+{
+ swayr-basic-configuration = ./basic-configuration.nix;
+ swayr-empty-configuration = ./empty-configuration.nix;
+}
diff --git a/tests/modules/programs/swayr/empty-configuration.nix b/tests/modules/programs/swayr/empty-configuration.nix
new file mode 100644
index 000000000..f1b4d6298
--- /dev/null
+++ b/tests/modules/programs/swayr/empty-configuration.nix
@@ -0,0 +1,21 @@
+{ config, pkgs, ... }:
+
+{
+ config = {
+ programs.swayr = {
+ enable = true;
+ package = config.lib.test.mkStubPackage { };
+ systemd.enable = true;
+ };
+
+ nmt.script = ''
+ serviceFile=home-files/.config/systemd/user/swayrd.service
+
+ assertFileExists $serviceFile
+ assertFileRegex $serviceFile 'ExecStart=.*/bin/swayrd'
+ assertFileRegex $serviceFile 'Environment=RUST_BACKTRACE=1'
+
+ assertPathNotExists home-files/.config/swayr/config.toml
+ '';
+ };
+}