Refactor DMS configuration and enhance Obsidian integration
- Replaced legacy Obsidian snippet directory options with a unified `obsidianVaults` option for better management. - Updated DMS configuration to streamline widget handling and removed deprecated options. - Introduced new templates for Hyprland colors and Obsidian themes to improve user customization. - Added scripts for SwiftShare upload functionality, enhancing screenshot capabilities within the DMS environment.
This commit is contained in:
@@ -6,20 +6,11 @@
|
|||||||
default = true;
|
default = true;
|
||||||
description = "GPU temp in DMS bar.";
|
description = "GPU temp in DMS bar.";
|
||||||
};
|
};
|
||||||
obsidianSnippetsDir = lib.mkOption {
|
obsidianVaults = lib.mkOption {
|
||||||
type = lib.types.nullOr lib.types.str;
|
|
||||||
default = null;
|
|
||||||
description = "Legacy single Obsidian snippets dir for matugen.";
|
|
||||||
};
|
|
||||||
obsidianConfigDirs = lib.mkOption {
|
|
||||||
type = lib.types.listOf lib.types.str;
|
type = lib.types.listOf lib.types.str;
|
||||||
default = [ ];
|
default = [ ];
|
||||||
description = "Vault `.obsidian/` paths for matugen.";
|
example = [ "/mnt/zimaos/Obsidian/Home/.obsidian" ];
|
||||||
};
|
description = "Vault `.obsidian/` dirs; matugen writes `<vault>/snippets/matugen.css`.";
|
||||||
obsidianSnippetsDirs = lib.mkOption {
|
|
||||||
type = lib.types.listOf lib.types.str;
|
|
||||||
default = [ ];
|
|
||||||
description = "Explicit `.obsidian/snippets` paths.";
|
|
||||||
};
|
};
|
||||||
extraRightBarWidgets = lib.mkOption {
|
extraRightBarWidgets = lib.mkOption {
|
||||||
type = lib.types.listOf lib.types.attrs;
|
type = lib.types.listOf lib.types.attrs;
|
||||||
@@ -81,29 +72,7 @@
|
|||||||
];
|
];
|
||||||
|
|
||||||
config = lib.mkIf dmsEnabled {
|
config = lib.mkIf dmsEnabled {
|
||||||
dms.enable = true;
|
|
||||||
dms.enableGpuTemp = cfg.enableGpuTemp or true;
|
|
||||||
dms.obsidianSnippetsDir = cfg.obsidianSnippetsDir or null;
|
|
||||||
dms.obsidianConfigDirs = cfg.obsidianConfigDirs or [ ];
|
|
||||||
dms.obsidianSnippetsDirs = cfg.obsidianSnippetsDirs or [ ];
|
|
||||||
dms.enableWvkbdToggle = cfg.enableWvkbdToggle or false;
|
|
||||||
dms.enableRbwLockToggle = cfg.enableRbwLockToggle or false;
|
|
||||||
dms.extraRightBarWidgets =
|
|
||||||
(lib.optionals (cfg.enableWvkbdToggle or false) [
|
|
||||||
{
|
|
||||||
id = "wvkbdToggle";
|
|
||||||
enabled = true;
|
|
||||||
}
|
|
||||||
])
|
|
||||||
++ (lib.optionals (cfg.enableRbwLockToggle or false) [
|
|
||||||
{
|
|
||||||
id = "rbwLockToggle";
|
|
||||||
enabled = true;
|
|
||||||
}
|
|
||||||
])
|
|
||||||
++ (cfg.extraRightBarWidgets or [ ]);
|
|
||||||
programs.nix-monitor.rebuildCommand = rebuildCommand;
|
programs.nix-monitor.rebuildCommand = rebuildCommand;
|
||||||
dms.bundleThirdPartyPlugins = cfg.bundleThirdPartyPlugins or true;
|
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,21 @@
|
|||||||
...
|
...
|
||||||
}: let
|
}: let
|
||||||
home = config.home.homeDirectory;
|
home = config.home.homeDirectory;
|
||||||
cfg = config.dms;
|
dmsEnabled = lib.attrByPath [ "chiasson" "desktop" "shell" ] null osConfig == "dms";
|
||||||
gpuTempEnabled = cfg.enableGpuTemp;
|
dmsOs = lib.attrByPath [ "chiasson" "desktop" "shells" "dms" ] { } osConfig;
|
||||||
|
gpuTempEnabled = dmsOs.enableGpuTemp or true;
|
||||||
hyprlandEnabled = lib.attrByPath [ "chiasson" "desktop" "hyprland" "enable" ] false osConfig;
|
hyprlandEnabled = lib.attrByPath [ "chiasson" "desktop" "hyprland" "enable" ] false osConfig;
|
||||||
discordEnabled = lib.attrByPath [ "chiasson" "home" "apps" "discord" "enable" ] false config;
|
discordEnabled = lib.attrByPath [ "chiasson" "home" "apps" "discord" "enable" ] false config;
|
||||||
ohMyPoshEnabled = config.programs.oh-my-posh.enable or false;
|
ohMyPoshEnabled = config.programs.oh-my-posh.enable or false;
|
||||||
|
obsidianSnippetDirs = map (v: v + "/snippets") (dmsOs.obsidianVaults or [ ]);
|
||||||
|
seedBarWidgets =
|
||||||
|
lib.optionals (dmsOs.enableWvkbdToggle or false) [
|
||||||
|
{ id = "wvkbdToggle"; enabled = true; }
|
||||||
|
]
|
||||||
|
++ lib.optionals (dmsOs.enableRbwLockToggle or false) [
|
||||||
|
{ id = "rbwLockToggle"; enabled = true; }
|
||||||
|
]
|
||||||
|
++ (dmsOs.extraRightBarWidgets or [ ]);
|
||||||
matugenOutputDirs =
|
matugenOutputDirs =
|
||||||
lib.optionals hyprlandEnabled [ "${home}/.config/hypr" ]
|
lib.optionals hyprlandEnabled [ "${home}/.config/hypr" ]
|
||||||
++ lib.optionals ohMyPoshEnabled [ "${home}/.config/oh-my-posh" ]
|
++ lib.optionals ohMyPoshEnabled [ "${home}/.config/oh-my-posh" ]
|
||||||
@@ -23,29 +33,28 @@
|
|||||||
ensureMatugenOutputDirsScript = pkgs.writeShellScript "dms-ensure-matugen-output-dirs" ''
|
ensureMatugenOutputDirsScript = pkgs.writeShellScript "dms-ensure-matugen-output-dirs" ''
|
||||||
set -euo pipefail
|
set -euo pipefail
|
||||||
${lib.concatStringsSep "\n" (map (dir: "mkdir -p ${lib.escapeShellArg dir}") matugenOutputDirs)}
|
${lib.concatStringsSep "\n" (map (dir: "mkdir -p ${lib.escapeShellArg dir}") matugenOutputDirs)}
|
||||||
|
${lib.concatStringsSep "\n" (map (dir: ''
|
||||||
|
snippetDir=${lib.escapeShellArg dir}
|
||||||
|
parentDir="$(dirname "$snippetDir")"
|
||||||
|
if [ -d "$snippetDir" ]; then
|
||||||
|
:
|
||||||
|
elif [ ! -d "$parentDir" ] || [ ! -w "$parentDir" ]; then
|
||||||
|
echo "dms: skipping Obsidian snippet dir '$snippetDir' (parent missing or not writable)" >&2
|
||||||
|
else
|
||||||
|
mkdir -p "$snippetDir"
|
||||||
|
fi
|
||||||
|
'') obsidianSnippetDirs)}
|
||||||
${lib.optionalString ohMyPoshEnabled ''
|
${lib.optionalString ohMyPoshEnabled ''
|
||||||
dest="$HOME/.config/oh-my-posh/theme.omp.json"
|
dest="$HOME/.config/oh-my-posh/theme.omp.json"
|
||||||
template="$HOME/.config/matugen/templates/ohmyposh-theme.omp.json"
|
template="$HOME/.config/matugen/templates/ohmyposh-theme.omp.json"
|
||||||
# matugen writes output_path in place; HM symlinks into the store are read-only and go stale.
|
|
||||||
if [ -L "$dest" ] || { [ -e "$dest" ] && ! [ -f "$dest" ]; }; then
|
if [ -L "$dest" ] || { [ -e "$dest" ] && ! [ -f "$dest" ]; }; then
|
||||||
rm -f "$dest"
|
rm -f "$dest"
|
||||||
fi
|
fi
|
||||||
if [ ! -f "$dest" ]; then
|
if [ ! -f "$dest" ]; then
|
||||||
# Seed from our matugen template (same generation closure), not programs.oh-my-posh.package
|
|
||||||
# which can reference a GC'd store path after profile churn.
|
|
||||||
cp -L "$template" "$dest"
|
cp -L "$template" "$dest"
|
||||||
fi
|
fi
|
||||||
''}
|
''}
|
||||||
'';
|
'';
|
||||||
obsidianSnippetsDir = cfg.obsidianSnippetsDir; # legacy single path
|
|
||||||
obsidianSnippetDirs =
|
|
||||||
let
|
|
||||||
snippetsFromConfigDirs = map (d: "${d}/snippets") cfg.obsidianConfigDirs;
|
|
||||||
explicitSnippetsDirs =
|
|
||||||
cfg.obsidianSnippetsDirs
|
|
||||||
++ lib.optionals (obsidianSnippetsDir != null) [obsidianSnippetsDir];
|
|
||||||
in
|
|
||||||
lib.unique (snippetsFromConfigDirs ++ explicitSnippetsDirs);
|
|
||||||
|
|
||||||
# Clears Quickshell QML bytecode cache so bar plugins reload (stale *.qmlc keeps old UI).
|
# Clears Quickshell QML bytecode cache so bar plugins reload (stale *.qmlc keeps old UI).
|
||||||
dmsRestartOnceScript = pkgs.writeShellScript "dms-rbw-plugin-restart-once" ''
|
dmsRestartOnceScript = pkgs.writeShellScript "dms-rbw-plugin-restart-once" ''
|
||||||
@@ -75,7 +84,7 @@
|
|||||||
"settings.json" = jsonFormat.generate "dms-settings-seed.json" (
|
"settings.json" = jsonFormat.generate "dms-settings-seed.json" (
|
||||||
import ../_private/default-settings.nix {
|
import ../_private/default-settings.nix {
|
||||||
inherit lib gpuTempEnabled;
|
inherit lib gpuTempEnabled;
|
||||||
extraRightBarWidgets = cfg.extraRightBarWidgets;
|
extraRightBarWidgets = seedBarWidgets;
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
@@ -108,83 +117,13 @@
|
|||||||
};
|
};
|
||||||
|
|
||||||
in {
|
in {
|
||||||
options = {
|
|
||||||
dms.enable = lib.mkOption {
|
|
||||||
type = lib.types.bool;
|
|
||||||
default = false;
|
|
||||||
description = "DMS Home Manager config from this flake.";
|
|
||||||
};
|
|
||||||
|
|
||||||
dms.enableGpuTemp = lib.mkOption {
|
|
||||||
type = lib.types.bool;
|
|
||||||
default = true;
|
|
||||||
description = "GPU temp widget in the bar.";
|
|
||||||
};
|
|
||||||
|
|
||||||
# <vault>/.obsidian/snippets — unset skips Obsidian matugen output
|
|
||||||
dms.obsidianSnippetsDir = lib.mkOption {
|
|
||||||
type = lib.types.nullOr lib.types.str;
|
|
||||||
default = null;
|
|
||||||
example = "/home/olivier/Documents/Notes/.obsidian/snippets";
|
|
||||||
description = "Snippet dir for `matugen.css` (legacy; prefer `obsidianConfigDirs`).";
|
|
||||||
};
|
|
||||||
|
|
||||||
# Each path is a vault’s `.obsidian/` — we write `<path>/snippets/matugen.css`.
|
|
||||||
dms.obsidianConfigDirs = lib.mkOption {
|
|
||||||
type = lib.types.listOf lib.types.str;
|
|
||||||
default = [];
|
|
||||||
example = [
|
|
||||||
"/mnt/zimaos/Obsidian/Home/.obsidian"
|
|
||||||
];
|
|
||||||
description = "Vault `.obsidian` dirs for matugen CSS.";
|
|
||||||
};
|
|
||||||
|
|
||||||
# Or pass `.obsidian/snippets` paths yourself.
|
|
||||||
dms.obsidianSnippetsDirs = lib.mkOption {
|
|
||||||
type = lib.types.listOf lib.types.str;
|
|
||||||
default = [];
|
|
||||||
example = [
|
|
||||||
"/mnt/zimaos/Obsidian/Home/.obsidian/snippets"
|
|
||||||
];
|
|
||||||
description = "Explicit snippet directories for matugen CSS.";
|
|
||||||
};
|
|
||||||
|
|
||||||
# Prepended to the bar’s rightWidgets (shows first).
|
|
||||||
dms.extraRightBarWidgets = lib.mkOption {
|
|
||||||
type = lib.types.listOf lib.types.attrs;
|
|
||||||
default = [];
|
|
||||||
example = [
|
|
||||||
{ id = "wvkbdToggle"; enabled = true; }
|
|
||||||
{ id = "rbwLockToggle"; enabled = true; }
|
|
||||||
];
|
|
||||||
description = "Extra `{ id, enabled, … }` widgets merged into the first-run settings seed.";
|
|
||||||
};
|
|
||||||
|
|
||||||
dms.enableWvkbdToggle = lib.mkEnableOption ''
|
|
||||||
Ship wvkbd-toggle plugin into `~/.config/DankMaterialShell/plugins/` (toggle from NixOS `desktop.shells.dms`).
|
|
||||||
'';
|
|
||||||
|
|
||||||
dms.enableRbwLockToggle = lib.mkEnableOption ''
|
|
||||||
Ship rbw-lock-toggle into `~/.config/DankMaterialShell/plugins/rbwLockToggle/` (directory name matches plugin id; Bitwarden vault lock/unlock in the bar).
|
|
||||||
'';
|
|
||||||
|
|
||||||
dms.bundleThirdPartyPlugins = lib.mkOption {
|
|
||||||
type = lib.types.bool;
|
|
||||||
default = true;
|
|
||||||
description = ''
|
|
||||||
Install bundled third-party DMS plugins (DankVault, Calculator, Home Assistant, …)
|
|
||||||
into `~/.config/DankMaterialShell/plugins/` from flake inputs.
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
imports = [
|
imports = [
|
||||||
inputs.dms.homeModules.dank-material-shell
|
inputs.dms.homeModules.dank-material-shell
|
||||||
inputs.nix-monitor.homeManagerModules.default
|
inputs.nix-monitor.homeManagerModules.default
|
||||||
];
|
];
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable (lib.mkMerge [
|
config = lib.mkIf dmsEnabled (lib.mkMerge [
|
||||||
(lib.mkIf cfg.enableWvkbdToggle {
|
(lib.mkIf (dmsOs.enableWvkbdToggle or false) {
|
||||||
xdg.configFile."DankMaterialShell/plugins/wvkbd-toggle/plugin.json".source =
|
xdg.configFile."DankMaterialShell/plugins/wvkbd-toggle/plugin.json".source =
|
||||||
../plugins/wvkbd-toggle/plugin.json;
|
../plugins/wvkbd-toggle/plugin.json;
|
||||||
xdg.configFile."DankMaterialShell/plugins/wvkbd-toggle/WvkbdToggle.qml".source =
|
xdg.configFile."DankMaterialShell/plugins/wvkbd-toggle/WvkbdToggle.qml".source =
|
||||||
@@ -192,7 +131,7 @@ in {
|
|||||||
xdg.configFile."DankMaterialShell/plugins/wvkbd-toggle/WvkbdToggleSettings.qml".source =
|
xdg.configFile."DankMaterialShell/plugins/wvkbd-toggle/WvkbdToggleSettings.qml".source =
|
||||||
../plugins/wvkbd-toggle/WvkbdToggleSettings.qml;
|
../plugins/wvkbd-toggle/WvkbdToggleSettings.qml;
|
||||||
})
|
})
|
||||||
(lib.mkIf cfg.enableRbwLockToggle {
|
(lib.mkIf (dmsOs.enableRbwLockToggle or false) {
|
||||||
# Directory name matches plugin id (same idea as NixMonitor / ideapad wvkbdToggle).
|
# Directory name matches plugin id (same idea as NixMonitor / ideapad wvkbdToggle).
|
||||||
xdg.configFile."DankMaterialShell/plugins/rbwLockToggle/plugin.json" = {
|
xdg.configFile."DankMaterialShell/plugins/rbwLockToggle/plugin.json" = {
|
||||||
source = ../plugins/rbw-lock-toggle/plugin.json;
|
source = ../plugins/rbw-lock-toggle/plugin.json;
|
||||||
@@ -207,7 +146,7 @@ in {
|
|||||||
onChange = "${dmsRestartOnceScript}";
|
onChange = "${dmsRestartOnceScript}";
|
||||||
};
|
};
|
||||||
})
|
})
|
||||||
(lib.mkIf cfg.bundleThirdPartyPlugins {
|
(lib.mkIf (dmsOs.bundleThirdPartyPlugins or true) {
|
||||||
xdg.configFile =
|
xdg.configFile =
|
||||||
lib.mapAttrs (id: src: shipThirdPartyPlugin id src) thirdPartyPlugins;
|
lib.mapAttrs (id: src: shipThirdPartyPlugin id src) thirdPartyPlugins;
|
||||||
})
|
})
|
||||||
@@ -332,445 +271,11 @@ in {
|
|||||||
)
|
)
|
||||||
;
|
;
|
||||||
|
|
||||||
# Obsidian snippet dirs for matugen: mkdir here instead of tmpfiles (no chmod fights on weird mounts).
|
|
||||||
home.activation.dmsEnsureObsidianSnippetDirs = lib.hm.dag.entryAfter ["writeBoundary"] (
|
|
||||||
let
|
|
||||||
snippetDirs = lib.unique obsidianSnippetDirs;
|
|
||||||
escapedSnippetDirs = map lib.escapeShellArg snippetDirs;
|
|
||||||
in
|
|
||||||
''
|
|
||||||
for snippetDir in ${lib.concatStringsSep " " escapedSnippetDirs}; do
|
|
||||||
parentDir="$(dirname "$snippetDir")"
|
|
||||||
|
|
||||||
if [ -d "$snippetDir" ]; then
|
|
||||||
continue
|
|
||||||
fi
|
|
||||||
|
|
||||||
if [ ! -d "$parentDir" ] || [ ! -w "$parentDir" ]; then
|
|
||||||
echo "dms: skipping Obsidian snippet dir '$snippetDir' (parent missing or not writable)" >&2
|
|
||||||
continue
|
|
||||||
fi
|
|
||||||
|
|
||||||
mkdir -p "$snippetDir"
|
|
||||||
done
|
|
||||||
''
|
|
||||||
);
|
|
||||||
|
|
||||||
xdg.configFile."matugen/templates/dank-discord.css".source = ../templates/dank-discord.css;
|
xdg.configFile."matugen/templates/dank-discord.css".source = ../templates/dank-discord.css;
|
||||||
|
xdg.configFile."matugen/templates/hyprland-colors.conf".source = ../templates/hyprland-colors.conf;
|
||||||
# matugen template → Hyprland colors file sourced at runtime.
|
xdg.configFile."matugen/templates/ohmyposh-theme.omp.json".source = ../templates/ohmyposh-theme.omp.json;
|
||||||
# Your Hyprland module includes: `source = ~/.config/hypr/colors.conf`
|
xdg.configFile."matugen/templates/obsidian-minimal-matugen-colors.css".source =
|
||||||
# (see `modules/desktop/hyprland/home-manager/appearance.nix`).
|
../templates/obsidian-minimal-matugen-colors.css;
|
||||||
xdg.configFile."matugen/templates/hyprland-colors.conf".text = ''
|
|
||||||
# Hyprland colors generated by DMS/matugen
|
|
||||||
# Keep `.default` so DMS can swap to `.dark` when "Always use Dark Theme" is enabled.
|
|
||||||
|
|
||||||
general {
|
|
||||||
col.active_border = rgb({{colors.primary.default.hex_stripped}}) rgb({{colors.secondary.default.hex_stripped}}) rgb({{colors.tertiary.default.hex_stripped}})
|
|
||||||
col.inactive_border = rgba({{colors.surface_variant.default.hex_stripped}}ee)
|
|
||||||
}
|
|
||||||
|
|
||||||
decoration {
|
|
||||||
shadow {
|
|
||||||
color = rgba({{colors.shadow.default.hex_stripped}}cc)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
# Hyprbars colors
|
|
||||||
plugin {
|
|
||||||
hyprbars {
|
|
||||||
bar_color = rgba({{colors.surface.default.hex_stripped}}ff)
|
|
||||||
col.text = rgba({{colors.on_surface.default.hex_stripped}}ff)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
'';
|
|
||||||
|
|
||||||
# matugen → Oh My Posh JSON; hex in the base theme swapped for matugen tokens.
|
|
||||||
xdg.configFile."matugen/templates/ohmyposh-theme.omp.json".text = ''
|
|
||||||
{
|
|
||||||
"$schema": "https://raw.githubusercontent.com/JanDeDobbeleer/oh-my-posh/main/themes/schema.json",
|
|
||||||
"blocks": [
|
|
||||||
{
|
|
||||||
"alignment": "left",
|
|
||||||
"segments": [
|
|
||||||
{
|
|
||||||
"background": "#3A456E",
|
|
||||||
"foreground": "#ffbebc",
|
|
||||||
"leading_diamond": "\ue0b6",
|
|
||||||
"style": "diamond",
|
|
||||||
"template": "\u007B\u007B .UserName \u007D\u007D@\u007B\u007B .HostName \u007D\u007D <#ffffff>on</>",
|
|
||||||
"type": "session"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"type": "os",
|
|
||||||
"style": "diamond",
|
|
||||||
"background": "#3A456E",
|
|
||||||
"foreground": "#ffffff",
|
|
||||||
"trailing_diamond": "\ue0b4",
|
|
||||||
"template": " \u007B\u007B .Icon \u007D\u007D "
|
|
||||||
},
|
|
||||||
{"type": "session",
|
|
||||||
"style": "diamond",
|
|
||||||
"background": "#3A456E",
|
|
||||||
"foreground": "#ffbebc",
|
|
||||||
"template": "\u007B\u007B if .SSHSession \u007D\u007Dvia SSH\u007B\u007B end \u007D\u007D",
|
|
||||||
"trailing_diamond": "\ue0b4",
|
|
||||||
"type": "session"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"type": "text",
|
|
||||||
"style": "diamond",
|
|
||||||
"background": "#3A456E",
|
|
||||||
"foreground": "#ffbebc",
|
|
||||||
"template": "\u007B\u007B if .Env.IN_NIX_SHELL \u007D\u007Din nix-shell\u007B\u007B end \u007D\u007D",
|
|
||||||
"trailing_diamond": "\ue0b4"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"background": "#3A456E",
|
|
||||||
"foreground": "#bc93ff",
|
|
||||||
"leading_diamond": "\ue0b6",
|
|
||||||
"properties": {
|
|
||||||
"time_format": "Monday <#ffffff>at</> 3:04 PM"
|
|
||||||
},
|
|
||||||
"style": "diamond",
|
|
||||||
"trailing_diamond": "\ue0b4",
|
|
||||||
"template": "\u007B\u007B .CurrentDate | date .Format \u007D\u007D",
|
|
||||||
"type": "time"
|
|
||||||
},
|
|
||||||
|
|
||||||
|
|
||||||
{
|
|
||||||
"background": "#3A456E",
|
|
||||||
"foreground": "#43CCEA",
|
|
||||||
"foreground_templates": [
|
|
||||||
"\u007B\u007B if or (.Working.Changed) (.Staging.Changed) \u007D\u007D#FF9248\u007B\u007B end \u007D\u007D",
|
|
||||||
"\u007B\u007B if and (gt .Ahead 0) (gt .Behind 0) \u007D\u007D#ff4500\u007B\u007B end \u007D\u007D",
|
|
||||||
"\u007B\u007B if gt .Ahead 0 \u007D\u007D#B388FF\u007B\u007B end \u007D\u007D",
|
|
||||||
"\u007B\u007B if gt .Behind 0 \u007D\u007D#B388FF\u007B\u007B end \u007D\u007D"
|
|
||||||
],
|
|
||||||
"leading_diamond": " \ue0b6",
|
|
||||||
"options": {
|
|
||||||
"branch_template": "\u007B\u007B trunc 25 .Branch \u007D\u007D",
|
|
||||||
"fetch_status": true,
|
|
||||||
"fetch_upstream_icon": true
|
|
||||||
},
|
|
||||||
"style": "diamond",
|
|
||||||
"template": " \u007B\u007B .UpstreamIcon \u007D\u007D\u007B\u007B .HEAD \u007D\u007D\u007B\u007Bif .BranchStatus \u007D\u007D \u007B\u007B .BranchStatus \u007D\u007D\u007B\u007B end \u007D\u007D\u007B\u007B if .Working.Changed \u007D\u007D \uf044 \u007B\u007B .Working.String \u007D\u007D\u007B\u007B end \u007D\u007D\u007B\u007B if and (.Working.Changed) (.Staging.Changed) \u007D\u007D |\u007B\u007B end \u007D\u007D\u007B\u007B if .Staging.Changed \u007D\u007D \uf046 \u007B\u007B .Staging.String \u007D\u007D\u007B\u007B end \u007D\u007D\u007B\u007B if gt .StashCount 0 \u007D\u007D \ueb4b \u007B\u007B .StashCount \u007D\u007D\u007B\u007B end \u007D\u007D ",
|
|
||||||
"trailing_diamond": "\ue0b4",
|
|
||||||
"type": "git"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"background": "#3A456E",
|
|
||||||
"foreground": "#E4F34A",
|
|
||||||
"leading_diamond": " \ue0b6",
|
|
||||||
"options": {
|
|
||||||
"fetch_version": false
|
|
||||||
},
|
|
||||||
"style": "diamond",
|
|
||||||
"template": "\ue235 \u007B\u007B if .Error \u007D\u007D\u007B\u007B .Error \u007D\u007D\u007B\u007B else \u007D\u007D\u007B\u007B if .Venv \u007D\u007D\u007B\u007B .Venv \u007D\u007D \u007B\u007B end \u007D\u007D\u007B\u007B .Full \u007D\u007D\u007B\u007B end \u007D\u007D",
|
|
||||||
"trailing_diamond": "\ue0b4",
|
|
||||||
"type": "python"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"background": "#3A456E",
|
|
||||||
"foreground": "#7FD5EA",
|
|
||||||
"leading_diamond": " \ue0b6",
|
|
||||||
"options": {
|
|
||||||
"fetch_version": false
|
|
||||||
},
|
|
||||||
"style": "diamond",
|
|
||||||
"template": "\ue626\u007B\u007B if .Error \u007D\u007D\u007B\u007B .Error \u007D\u007D\u007B\u007B else \u007D\u007D\u007B\u007B .Full \u007D\u007D\u007B\u007B end \u007D\u007D",
|
|
||||||
"trailing_diamond": "\ue0b4",
|
|
||||||
"type": "go"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"background": "#3A456E",
|
|
||||||
"foreground": "#42E66C",
|
|
||||||
"leading_diamond": " \ue0b6",
|
|
||||||
"options": {
|
|
||||||
"fetch_version": false
|
|
||||||
},
|
|
||||||
"style": "diamond",
|
|
||||||
"template": "\ue718\u007B\u007B if .PackageManagerIcon \u007D\u007D\u007B\u007B .PackageManagerIcon \u007D\u007D \u007B\u007B end \u007D\u007D\u007B\u007B .Full \u007D\u007D",
|
|
||||||
"trailing_diamond": "\ue0b4",
|
|
||||||
"type": "node"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"background": "#3A456E",
|
|
||||||
"foreground": "#E64747",
|
|
||||||
"leading_diamond": " \ue0b6",
|
|
||||||
"options": {
|
|
||||||
"fetch_version": false
|
|
||||||
},
|
|
||||||
"style": "diamond",
|
|
||||||
"template": "\ue791\u007B\u007B if .Error \u007D\u007D\u007B\u007B .Error \u007D\u007D\u007B\u007B else \u007D\u007D\u007B\u007B .Full \u007D\u007D\u007B\u007B end \u007D\u007D",
|
|
||||||
"trailing_diamond": "\ue0b4",
|
|
||||||
"type": "ruby"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"background": "#3A456E",
|
|
||||||
"foreground": "#E64747",
|
|
||||||
"leading_diamond": " \ue0b6",
|
|
||||||
"options": {
|
|
||||||
"fetch_version": false
|
|
||||||
},
|
|
||||||
"style": "diamond",
|
|
||||||
"template": "\ue738\u007B\u007B if .Error \u007D\u007D\u007B\u007B .Error \u007D\u007D\u007B\u007B else \u007D\u007D\u007B\u007B .Full \u007D\u007D\u007B\u007B end \u007D\u007D",
|
|
||||||
"trailing_diamond": "\ue0b4",
|
|
||||||
"type": "java"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"background": "#3A456E",
|
|
||||||
"foreground": "#9B6BDF",
|
|
||||||
"leading_diamond": " \ue0b6",
|
|
||||||
"options": {
|
|
||||||
"fetch_version": false
|
|
||||||
},
|
|
||||||
"style": "diamond",
|
|
||||||
"template": "\ue624\u007B\u007B if .Error \u007D\u007D\u007B\u007B .Error \u007D\u007D\u007B\u007B else \u007D\u007D\u007B\u007B .Full \u007D\u007D\u007B\u007B end \u007D\u007D ",
|
|
||||||
"trailing_diamond": "\ue0b4",
|
|
||||||
"type": "julia"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"type": "php",
|
|
||||||
"style": "diamond",
|
|
||||||
"foreground": "#ffffff",
|
|
||||||
"background": "#4063D8",
|
|
||||||
"leading_diamond": " \ue0b6",
|
|
||||||
"options": {
|
|
||||||
"fetch_version": false
|
|
||||||
},
|
|
||||||
"template": "\ue73d \u007B\u007B .Full \u007D\u007D ",
|
|
||||||
"trailing_diamond": "\ue0b4"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"background": "#3A456E",
|
|
||||||
"foreground": "#9B6BDF",
|
|
||||||
"foreground_templates": [
|
|
||||||
"\u007B\u007Bif eq \"Charging\" .State.String\u007D\u007D#40c4ff\u007B\u007Bend\u007D\u007D",
|
|
||||||
"\u007B\u007Bif eq \"Discharging\" .State.String\u007D\u007D#ff5722\u007B\u007Bend\u007D\u007D",
|
|
||||||
"\u007B\u007Bif eq \"Full\" .State.String\u007D\u007D#4caf50\u007B\u007Bend\u007D\u007D"
|
|
||||||
],
|
|
||||||
"leading_diamond": " \ue0b6",
|
|
||||||
"options": {
|
|
||||||
"charged_icon": " ",
|
|
||||||
"charging_icon": "\u21e1 ",
|
|
||||||
"discharging_icon": "\u21e3 "
|
|
||||||
},
|
|
||||||
"style": "diamond",
|
|
||||||
"template": "\u007B\u007B if not .Error \u007D\u007D\u007B\u007B .Icon \u007D\u007D\u007B\u007B .Percentage \u007D\u007D\u007B\u007B end \u007D\u007D\u007B\u007B .Error \u007D\u007D",
|
|
||||||
"trailing_diamond": "\ue0b4",
|
|
||||||
"type": "battery"
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"type": "prompt"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"alignment": "right",
|
|
||||||
"segments": [
|
|
||||||
{
|
|
||||||
"background": "#3A456E",
|
|
||||||
"foreground": "#AEA4BF",
|
|
||||||
"leading_diamond": "\ue0b6",
|
|
||||||
"options": {
|
|
||||||
"style": "austin",
|
|
||||||
"threshold": 150
|
|
||||||
},
|
|
||||||
"style": "diamond",
|
|
||||||
"template": "\u007B\u007B .FormattedMs \u007D\u007D",
|
|
||||||
"trailing_diamond": "\ue0b4 ",
|
|
||||||
"type": "executiontime"
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"type": "prompt"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"alignment": "left",
|
|
||||||
"newline": true,
|
|
||||||
"segments": [
|
|
||||||
{
|
|
||||||
"background": "#3A456E",
|
|
||||||
"foreground": "#3EC669",
|
|
||||||
"leading_diamond": "\ue0b6",
|
|
||||||
"properties": {
|
|
||||||
"style": "agnoster_full",
|
|
||||||
"cycle": [
|
|
||||||
"#3EC669,#3A456E",
|
|
||||||
"#43CCEA,#3A456E",
|
|
||||||
"#E4F34A,#3A456E",
|
|
||||||
"#9B6BDF,#3A456E"
|
|
||||||
],
|
|
||||||
"cycle_folder_separator": true
|
|
||||||
},
|
|
||||||
"style": "diamond",
|
|
||||||
"template": "\ue5ff \u007B\u007B .Path \u007D\u007D",
|
|
||||||
"trailing_diamond": "\ue0b4",
|
|
||||||
"type": "path"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"background": "#3A456E",
|
|
||||||
"foreground": "#ffbebc",
|
|
||||||
"leading_diamond": "\ue0b6",
|
|
||||||
"style": "diamond",
|
|
||||||
"template": "\ue602",
|
|
||||||
"trailing_diamond": "\ue0b4",
|
|
||||||
"type": "text"
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"type": "prompt"
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"final_space": true,
|
|
||||||
"version": 4
|
|
||||||
}
|
|
||||||
'';
|
|
||||||
|
|
||||||
# matugen template → Obsidian CSS snippet (Minimal-compatible variables).
|
|
||||||
#
|
|
||||||
# Upstream template:
|
|
||||||
# https://raw.githubusercontent.com/Simorg2002/obsidian-matugen-template/refs/heads/main/obsidian-minimal-matugen-colors.css
|
|
||||||
xdg.configFile."matugen/templates/obsidian-minimal-matugen-colors.css".text = ''
|
|
||||||
.theme-dark {
|
|
||||||
--accent-h:calc({{colors.primary.dark.hue}}/255*360);
|
|
||||||
--accent-s:calc({{colors.primary.dark.saturation}}/255*100%);
|
|
||||||
--accent-l:calc({{colors.primary.dark.lightness}}/255*100%);
|
|
||||||
|
|
||||||
--text-normal:{{colors.on_surface.dark.hex}};
|
|
||||||
--text-muted:{{colors.on_surface_variant.dark.hex}};
|
|
||||||
--text-faint:{{colors.outline.dark.hex}};
|
|
||||||
|
|
||||||
--background-primary:{{colors.surface.dark.hex}}; /* editor and right ribbon */
|
|
||||||
--background-secondary:{{colors.surface_dim.dark.hex}}; /* left ribbon */
|
|
||||||
--background-modifier-hover:{{colors.secondary_container.dark.hex}};
|
|
||||||
--background-modifier-active-hover:{{colors.secondary.dark.hex}};
|
|
||||||
--background-modifier-message:{{colors.surface_dim.dark.hex}};
|
|
||||||
--background-modifier-form-field:{{colors.primary_container.dark.hex}};
|
|
||||||
|
|
||||||
--ribbon-background:{{colors.surface.dark.hex}};
|
|
||||||
--divider-color:{{colors.secondary_container.dark.hex}};
|
|
||||||
--scrollbar-thumb-bg:{{colors.on_secondary_container.dark.hex}};
|
|
||||||
--status-bar-border-color:{{colors.secondary_container.dark.hex}};
|
|
||||||
--status-bar-background:{{colors.surface.dark.hex}};
|
|
||||||
--titlebar-background:{{colors.surface.dark.hex}};
|
|
||||||
--titlebar-text-color:{{colors.on_surface.dark.hex}};
|
|
||||||
|
|
||||||
--nav-item-color:{{colors.on_surface_variant.dark.hex}};
|
|
||||||
--nav-item-color-active:{{colors.on_primary_container.dark.hex}};
|
|
||||||
--nav-item-background-active:{{colors.primary_container.dark.hex}};
|
|
||||||
--nav-item-color-hover:{{colors.on_secondary_container.dark.hex}};
|
|
||||||
--nav-item-background-hover:{{colors.secondary_container.dark.hex}};
|
|
||||||
|
|
||||||
--tab-background-active:{{colors.primary_container.dark.hex}};
|
|
||||||
--tab-text-color-active:{{colors.on_primary_container.dark.hex}};
|
|
||||||
--tab-text-color:{{colors.on_surface_variant.dark.hex}};
|
|
||||||
|
|
||||||
--icon-color:{{colors.on_surface.dark.hex}};
|
|
||||||
|
|
||||||
--h1-color:{{colors.primary.dark.hex}};
|
|
||||||
--h2-color: color-mix(in srgb, {{colors.primary.dark.hex}}, {{colors.tertiary.dark.hex}});
|
|
||||||
--h3-color:{{colors.tertiary.dark.hex}};
|
|
||||||
--h4-color: color-mix(in srgb, {{colors.primary.dark.hex}}, {{colors.secondary.dark.hex}});
|
|
||||||
--h5-color:{{colors.secondary.dark.hex}};
|
|
||||||
--h6-color: color-mix(in srgb, {{colors.tertiary.dark.hex}}, {{colors.secondary.dark.hex}});
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* add parts not accessible without specific selector?*/
|
|
||||||
.theme-dark .sidebar-toggle-button.mod-left {
|
|
||||||
color:{{colors.on_surface.dark.hex}};
|
|
||||||
background:{{colors.surface.dark.hex}};
|
|
||||||
}
|
|
||||||
.theme-dark .sidebar-toggle-button.mod-right {
|
|
||||||
color:{{colors.on_surface.dark.hex}};
|
|
||||||
background:{{colors.surface.dark.hex}};
|
|
||||||
}
|
|
||||||
|
|
||||||
.theme-dark .workspace-tab-header-container{
|
|
||||||
background:{{colors.surface.dark.hex}};
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* copy for light mode */
|
|
||||||
.theme-light {
|
|
||||||
--accent-h:calc({{colors.primary.light.hue}}/255*360);
|
|
||||||
--accent-s:calc({{colors.primary.light.saturation}}/255*100%);
|
|
||||||
--accent-l:calc({{colors.primary.light.lightness}}/255*100%);
|
|
||||||
|
|
||||||
--text-normal:{{colors.on_surface.light.hex}};
|
|
||||||
--text-muted:{{colors.on_surface_variant.light.hex}};
|
|
||||||
--text-faint:{{colors.outline.light.hex}};
|
|
||||||
|
|
||||||
--background-primary:{{colors.surface.light.hex}}; /* editor and right ribbon */
|
|
||||||
--background-secondary:{{colors.surface_dim.light.hex}}; /* left ribbon */
|
|
||||||
--background-modifier-hover:{{colors.secondary_container.light.hex}};
|
|
||||||
--background-modifier-active-hover:{{colors.secondary.light.hex}};
|
|
||||||
--background-modifier-message:{{colors.surface_dim.light.hex}};
|
|
||||||
--background-modifier-form-field:{{colors.primary_container.light.hex}};
|
|
||||||
|
|
||||||
--ribbon-background:{{colors.surface.light.hex}};
|
|
||||||
--divider-color:{{colors.secondary_container.light.hex}};
|
|
||||||
--scrollbar-thumb-bg:{{colors.on_secondary_container.light.hex}};
|
|
||||||
--status-bar-border-color:{{colors.secondary_container.light.hex}};
|
|
||||||
--status-bar-background:{{colors.surface.light.hex}};
|
|
||||||
--titlebar-background:{{colors.surface.light.hex}};
|
|
||||||
--titlebar-text-color:{{colors.on_surface.light.hex}};
|
|
||||||
|
|
||||||
--nav-item-color:{{colors.on_surface_variant.light.hex}};
|
|
||||||
--nav-item-color-active:{{colors.on_primary_container.light.hex}};
|
|
||||||
--nav-item-background-active:{{colors.primary_container.light.hex}};
|
|
||||||
--nav-item-color-hover:{{colors.on_secondary_container.light.hex}};
|
|
||||||
--nav-item-background-hover:{{colors.secondary_container.light.hex}};
|
|
||||||
|
|
||||||
--tab-background-active:{{colors.primary_container.light.hex}};
|
|
||||||
--tab-text-color-active:{{colors.on_primary_container.light.hex}};
|
|
||||||
--tab-text-color:{{colors.on_surface_variant.light.hex}};
|
|
||||||
|
|
||||||
--icon-color:{{colors.on_surface.light.hex}};
|
|
||||||
|
|
||||||
--h1-color:{{colors.primary.light.hex}};
|
|
||||||
--h2-color: color-mix(in srgb, {{colors.primary.light.hex}}, {{colors.tertiary.light.hex}});
|
|
||||||
--h3-color:{{colors.tertiary.light.hex}};
|
|
||||||
--h4-color: color-mix(in srgb, {{colors.primary.light.hex}}, {{colors.secondary.light.hex}});
|
|
||||||
--h5-color:{{colors.secondary.light.hex}};
|
|
||||||
--h6-color: color-mix(in srgb, {{colors.tertiary.light.hex}}, {{colors.secondary.light.hex}});
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* add parts not accessible without specific selector?*/
|
|
||||||
.theme-light .sidebar-toggle-button.mod-left {
|
|
||||||
color:{{colors.on_surface.light.hex}};
|
|
||||||
background:{{colors.surface.light.hex}};
|
|
||||||
}
|
|
||||||
.theme-light .sidebar-toggle-button.mod-right {
|
|
||||||
color:{{colors.on_surface.light.hex}};
|
|
||||||
background:{{colors.surface.light.hex}};
|
|
||||||
}
|
|
||||||
|
|
||||||
.theme-light .workspace-tab-header-container{
|
|
||||||
background:{{colors.surface.light.hex}};
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Hide window controls (frameless titlebar buttons) */
|
|
||||||
div[aria-label="Close window"],
|
|
||||||
div[aria-label="Minimize"],
|
|
||||||
div[aria-label="Restore down"],
|
|
||||||
div[aria-label="Maximize"]{
|
|
||||||
display: none !important;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Remove the extra right-side spacing reserved for those buttons */
|
|
||||||
.is-hidden-frameless:not(.is-fullscreen) .workspace-tabs.mod-top-right-space .workspace-tab-header-container{
|
|
||||||
padding-right: 0px !important;
|
|
||||||
}
|
|
||||||
|
|
||||||
.is-hidden-frameless:not(.is-fullscreen) .workspace-tabs.mod-top-right-space .workspace-tab-header-container:after{
|
|
||||||
display: none !important;
|
|
||||||
}
|
|
||||||
'';
|
|
||||||
}
|
}
|
||||||
(lib.mkIf ohMyPoshEnabled {
|
(lib.mkIf ohMyPoshEnabled {
|
||||||
# Same path as matugen `[templates.ohmyposh]`; seeded as a real file by `ensureMatugenOutputDirsScript`.
|
# Same path as matugen `[templates.ohmyposh]`; seeded as a real file by `ensureMatugenOutputDirsScript`.
|
||||||
|
|||||||
@@ -0,0 +1,21 @@
|
|||||||
|
# Hyprland colors generated by DMS/matugen
|
||||||
|
# Keep `.default` so DMS can swap to `.dark` when "Always use Dark Theme" is enabled.
|
||||||
|
|
||||||
|
general {
|
||||||
|
col.active_border = rgb({{colors.primary.default.hex_stripped}}) rgb({{colors.secondary.default.hex_stripped}}) rgb({{colors.tertiary.default.hex_stripped}})
|
||||||
|
col.inactive_border = rgba({{colors.surface_variant.default.hex_stripped}}ee)
|
||||||
|
}
|
||||||
|
|
||||||
|
decoration {
|
||||||
|
shadow {
|
||||||
|
color = rgba({{colors.shadow.default.hex_stripped}}cc)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
# Hyprbars colors
|
||||||
|
plugin {
|
||||||
|
hyprbars {
|
||||||
|
bar_color = rgba({{colors.surface.default.hex_stripped}}ff)
|
||||||
|
col.text = rgba({{colors.on_surface.default.hex_stripped}}ff)
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,140 @@
|
|||||||
|
.theme-dark {
|
||||||
|
--accent-h:calc({{colors.primary.dark.hue}}/255*360);
|
||||||
|
--accent-s:calc({{colors.primary.dark.saturation}}/255*100%);
|
||||||
|
--accent-l:calc({{colors.primary.dark.lightness}}/255*100%);
|
||||||
|
|
||||||
|
--text-normal:{{colors.on_surface.dark.hex}};
|
||||||
|
--text-muted:{{colors.on_surface_variant.dark.hex}};
|
||||||
|
--text-faint:{{colors.outline.dark.hex}};
|
||||||
|
|
||||||
|
--background-primary:{{colors.surface.dark.hex}}; /* editor and right ribbon */
|
||||||
|
--background-secondary:{{colors.surface_dim.dark.hex}}; /* left ribbon */
|
||||||
|
--background-modifier-hover:{{colors.secondary_container.dark.hex}};
|
||||||
|
--background-modifier-active-hover:{{colors.secondary.dark.hex}};
|
||||||
|
--background-modifier-message:{{colors.surface_dim.dark.hex}};
|
||||||
|
--background-modifier-form-field:{{colors.primary_container.dark.hex}};
|
||||||
|
|
||||||
|
--ribbon-background:{{colors.surface.dark.hex}};
|
||||||
|
--divider-color:{{colors.secondary_container.dark.hex}};
|
||||||
|
--scrollbar-thumb-bg:{{colors.on_secondary_container.dark.hex}};
|
||||||
|
--status-bar-border-color:{{colors.secondary_container.dark.hex}};
|
||||||
|
--status-bar-background:{{colors.surface.dark.hex}};
|
||||||
|
--titlebar-background:{{colors.surface.dark.hex}};
|
||||||
|
--titlebar-text-color:{{colors.on_surface.dark.hex}};
|
||||||
|
|
||||||
|
--nav-item-color:{{colors.on_surface_variant.dark.hex}};
|
||||||
|
--nav-item-color-active:{{colors.on_primary_container.dark.hex}};
|
||||||
|
--nav-item-background-active:{{colors.primary_container.dark.hex}};
|
||||||
|
--nav-item-color-hover:{{colors.on_secondary_container.dark.hex}};
|
||||||
|
--nav-item-background-hover:{{colors.secondary_container.dark.hex}};
|
||||||
|
|
||||||
|
--tab-background-active:{{colors.primary_container.dark.hex}};
|
||||||
|
--tab-text-color-active:{{colors.on_primary_container.dark.hex}};
|
||||||
|
--tab-text-color:{{colors.on_surface_variant.dark.hex}};
|
||||||
|
|
||||||
|
--icon-color:{{colors.on_surface.dark.hex}};
|
||||||
|
|
||||||
|
--h1-color:{{colors.primary.dark.hex}};
|
||||||
|
--h2-color: color-mix(in srgb, {{colors.primary.dark.hex}}, {{colors.tertiary.dark.hex}});
|
||||||
|
--h3-color:{{colors.tertiary.dark.hex}};
|
||||||
|
--h4-color: color-mix(in srgb, {{colors.primary.dark.hex}}, {{colors.secondary.dark.hex}});
|
||||||
|
--h5-color:{{colors.secondary.dark.hex}};
|
||||||
|
--h6-color: color-mix(in srgb, {{colors.tertiary.dark.hex}}, {{colors.secondary.dark.hex}});
|
||||||
|
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* add parts not accessible without specific selector?*/
|
||||||
|
.theme-dark .sidebar-toggle-button.mod-left {
|
||||||
|
color:{{colors.on_surface.dark.hex}};
|
||||||
|
background:{{colors.surface.dark.hex}};
|
||||||
|
}
|
||||||
|
.theme-dark .sidebar-toggle-button.mod-right {
|
||||||
|
color:{{colors.on_surface.dark.hex}};
|
||||||
|
background:{{colors.surface.dark.hex}};
|
||||||
|
}
|
||||||
|
|
||||||
|
.theme-dark .workspace-tab-header-container{
|
||||||
|
background:{{colors.surface.dark.hex}};
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* copy for light mode */
|
||||||
|
.theme-light {
|
||||||
|
--accent-h:calc({{colors.primary.light.hue}}/255*360);
|
||||||
|
--accent-s:calc({{colors.primary.light.saturation}}/255*100%);
|
||||||
|
--accent-l:calc({{colors.primary.light.lightness}}/255*100%);
|
||||||
|
|
||||||
|
--text-normal:{{colors.on_surface.light.hex}};
|
||||||
|
--text-muted:{{colors.on_surface_variant.light.hex}};
|
||||||
|
--text-faint:{{colors.outline.light.hex}};
|
||||||
|
|
||||||
|
--background-primary:{{colors.surface.light.hex}}; /* editor and right ribbon */
|
||||||
|
--background-secondary:{{colors.surface_dim.light.hex}}; /* left ribbon */
|
||||||
|
--background-modifier-hover:{{colors.secondary_container.light.hex}};
|
||||||
|
--background-modifier-active-hover:{{colors.secondary.light.hex}};
|
||||||
|
--background-modifier-message:{{colors.surface_dim.light.hex}};
|
||||||
|
--background-modifier-form-field:{{colors.primary_container.light.hex}};
|
||||||
|
|
||||||
|
--ribbon-background:{{colors.surface.light.hex}};
|
||||||
|
--divider-color:{{colors.secondary_container.light.hex}};
|
||||||
|
--scrollbar-thumb-bg:{{colors.on_secondary_container.light.hex}};
|
||||||
|
--status-bar-border-color:{{colors.secondary_container.light.hex}};
|
||||||
|
--status-bar-background:{{colors.surface.light.hex}};
|
||||||
|
--titlebar-background:{{colors.surface.light.hex}};
|
||||||
|
--titlebar-text-color:{{colors.on_surface.light.hex}};
|
||||||
|
|
||||||
|
--nav-item-color:{{colors.on_surface_variant.light.hex}};
|
||||||
|
--nav-item-color-active:{{colors.on_primary_container.light.hex}};
|
||||||
|
--nav-item-background-active:{{colors.primary_container.light.hex}};
|
||||||
|
--nav-item-color-hover:{{colors.on_secondary_container.light.hex}};
|
||||||
|
--nav-item-background-hover:{{colors.secondary_container.light.hex}};
|
||||||
|
|
||||||
|
--tab-background-active:{{colors.primary_container.light.hex}};
|
||||||
|
--tab-text-color-active:{{colors.on_primary_container.light.hex}};
|
||||||
|
--tab-text-color:{{colors.on_surface_variant.light.hex}};
|
||||||
|
|
||||||
|
--icon-color:{{colors.on_surface.light.hex}};
|
||||||
|
|
||||||
|
--h1-color:{{colors.primary.light.hex}};
|
||||||
|
--h2-color: color-mix(in srgb, {{colors.primary.light.hex}}, {{colors.tertiary.light.hex}});
|
||||||
|
--h3-color:{{colors.tertiary.light.hex}};
|
||||||
|
--h4-color: color-mix(in srgb, {{colors.primary.light.hex}}, {{colors.secondary.light.hex}});
|
||||||
|
--h5-color:{{colors.secondary.light.hex}};
|
||||||
|
--h6-color: color-mix(in srgb, {{colors.tertiary.light.hex}}, {{colors.secondary.light.hex}});
|
||||||
|
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* add parts not accessible without specific selector?*/
|
||||||
|
.theme-light .sidebar-toggle-button.mod-left {
|
||||||
|
color:{{colors.on_surface.light.hex}};
|
||||||
|
background:{{colors.surface.light.hex}};
|
||||||
|
}
|
||||||
|
.theme-light .sidebar-toggle-button.mod-right {
|
||||||
|
color:{{colors.on_surface.light.hex}};
|
||||||
|
background:{{colors.surface.light.hex}};
|
||||||
|
}
|
||||||
|
|
||||||
|
.theme-light .workspace-tab-header-container{
|
||||||
|
background:{{colors.surface.light.hex}};
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Hide window controls (frameless titlebar buttons) */
|
||||||
|
div[aria-label="Close window"],
|
||||||
|
div[aria-label="Minimize"],
|
||||||
|
div[aria-label="Restore down"],
|
||||||
|
div[aria-label="Maximize"]{
|
||||||
|
display: none !important;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Remove the extra right-side spacing reserved for those buttons */
|
||||||
|
.is-hidden-frameless:not(.is-fullscreen) .workspace-tabs.mod-top-right-space .workspace-tab-header-container{
|
||||||
|
padding-right: 0px !important;
|
||||||
|
}
|
||||||
|
|
||||||
|
.is-hidden-frameless:not(.is-fullscreen) .workspace-tabs.mod-top-right-space .workspace-tab-header-container:after{
|
||||||
|
display: none !important;
|
||||||
|
}
|
||||||
@@ -0,0 +1,236 @@
|
|||||||
|
{
|
||||||
|
"$schema": "https://raw.githubusercontent.com/JanDeDobbeleer/oh-my-posh/main/themes/schema.json",
|
||||||
|
"blocks": [
|
||||||
|
{
|
||||||
|
"alignment": "left",
|
||||||
|
"segments": [
|
||||||
|
{
|
||||||
|
"background": "#3A456E",
|
||||||
|
"foreground": "#ffbebc",
|
||||||
|
"leading_diamond": "\ue0b6",
|
||||||
|
"style": "diamond",
|
||||||
|
"template": "\u007B\u007B .UserName \u007D\u007D@\u007B\u007B .HostName \u007D\u007D <#ffffff>on</>",
|
||||||
|
"type": "session"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"type": "os",
|
||||||
|
"style": "diamond",
|
||||||
|
"background": "#3A456E",
|
||||||
|
"foreground": "#ffffff",
|
||||||
|
"trailing_diamond": "\ue0b4",
|
||||||
|
"template": " \u007B\u007B .Icon \u007D\u007D "
|
||||||
|
},
|
||||||
|
{"type": "session",
|
||||||
|
"style": "diamond",
|
||||||
|
"background": "#3A456E",
|
||||||
|
"foreground": "#ffbebc",
|
||||||
|
"template": "\u007B\u007B if .SSHSession \u007D\u007Dvia SSH\u007B\u007B end \u007D\u007D",
|
||||||
|
"trailing_diamond": "\ue0b4",
|
||||||
|
"type": "session"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"type": "text",
|
||||||
|
"style": "diamond",
|
||||||
|
"background": "#3A456E",
|
||||||
|
"foreground": "#ffbebc",
|
||||||
|
"template": "\u007B\u007B if .Env.IN_NIX_SHELL \u007D\u007Din nix-shell\u007B\u007B end \u007D\u007D",
|
||||||
|
"trailing_diamond": "\ue0b4"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"background": "#3A456E",
|
||||||
|
"foreground": "#bc93ff",
|
||||||
|
"leading_diamond": "\ue0b6",
|
||||||
|
"properties": {
|
||||||
|
"time_format": "Monday <#ffffff>at</> 3:04 PM"
|
||||||
|
},
|
||||||
|
"style": "diamond",
|
||||||
|
"trailing_diamond": "\ue0b4",
|
||||||
|
"template": "\u007B\u007B .CurrentDate | date .Format \u007D\u007D",
|
||||||
|
"type": "time"
|
||||||
|
},
|
||||||
|
|
||||||
|
|
||||||
|
{
|
||||||
|
"background": "#3A456E",
|
||||||
|
"foreground": "#43CCEA",
|
||||||
|
"foreground_templates": [
|
||||||
|
"\u007B\u007B if or (.Working.Changed) (.Staging.Changed) \u007D\u007D#FF9248\u007B\u007B end \u007D\u007D",
|
||||||
|
"\u007B\u007B if and (gt .Ahead 0) (gt .Behind 0) \u007D\u007D#ff4500\u007B\u007B end \u007D\u007D",
|
||||||
|
"\u007B\u007B if gt .Ahead 0 \u007D\u007D#B388FF\u007B\u007B end \u007D\u007D",
|
||||||
|
"\u007B\u007B if gt .Behind 0 \u007D\u007D#B388FF\u007B\u007B end \u007D\u007D"
|
||||||
|
],
|
||||||
|
"leading_diamond": " \ue0b6",
|
||||||
|
"options": {
|
||||||
|
"branch_template": "\u007B\u007B trunc 25 .Branch \u007D\u007D",
|
||||||
|
"fetch_status": true,
|
||||||
|
"fetch_upstream_icon": true
|
||||||
|
},
|
||||||
|
"style": "diamond",
|
||||||
|
"template": " \u007B\u007B .UpstreamIcon \u007D\u007D\u007B\u007B .HEAD \u007D\u007D\u007B\u007Bif .BranchStatus \u007D\u007D \u007B\u007B .BranchStatus \u007D\u007D\u007B\u007B end \u007D\u007D\u007B\u007B if .Working.Changed \u007D\u007D \uf044 \u007B\u007B .Working.String \u007D\u007D\u007B\u007B end \u007D\u007D\u007B\u007B if and (.Working.Changed) (.Staging.Changed) \u007D\u007D |\u007B\u007B end \u007D\u007D\u007B\u007B if .Staging.Changed \u007D\u007D \uf046 \u007B\u007B .Staging.String \u007D\u007D\u007B\u007B end \u007D\u007D\u007B\u007B if gt .StashCount 0 \u007D\u007D \ueb4b \u007B\u007B .StashCount \u007D\u007D\u007B\u007B end \u007D\u007D ",
|
||||||
|
"trailing_diamond": "\ue0b4",
|
||||||
|
"type": "git"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"background": "#3A456E",
|
||||||
|
"foreground": "#E4F34A",
|
||||||
|
"leading_diamond": " \ue0b6",
|
||||||
|
"options": {
|
||||||
|
"fetch_version": false
|
||||||
|
},
|
||||||
|
"style": "diamond",
|
||||||
|
"template": "\ue235 \u007B\u007B if .Error \u007D\u007D\u007B\u007B .Error \u007D\u007D\u007B\u007B else \u007D\u007D\u007B\u007B if .Venv \u007D\u007D\u007B\u007B .Venv \u007D\u007D \u007B\u007B end \u007D\u007D\u007B\u007B .Full \u007D\u007D\u007B\u007B end \u007D\u007D",
|
||||||
|
"trailing_diamond": "\ue0b4",
|
||||||
|
"type": "python"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"background": "#3A456E",
|
||||||
|
"foreground": "#7FD5EA",
|
||||||
|
"leading_diamond": " \ue0b6",
|
||||||
|
"options": {
|
||||||
|
"fetch_version": false
|
||||||
|
},
|
||||||
|
"style": "diamond",
|
||||||
|
"template": "\ue626\u007B\u007B if .Error \u007D\u007D\u007B\u007B .Error \u007D\u007D\u007B\u007B else \u007D\u007D\u007B\u007B .Full \u007D\u007D\u007B\u007B end \u007D\u007D",
|
||||||
|
"trailing_diamond": "\ue0b4",
|
||||||
|
"type": "go"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"background": "#3A456E",
|
||||||
|
"foreground": "#42E66C",
|
||||||
|
"leading_diamond": " \ue0b6",
|
||||||
|
"options": {
|
||||||
|
"fetch_version": false
|
||||||
|
},
|
||||||
|
"style": "diamond",
|
||||||
|
"template": "\ue718\u007B\u007B if .PackageManagerIcon \u007D\u007D\u007B\u007B .PackageManagerIcon \u007D\u007D \u007B\u007B end \u007D\u007D\u007B\u007B .Full \u007D\u007D",
|
||||||
|
"trailing_diamond": "\ue0b4",
|
||||||
|
"type": "node"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"background": "#3A456E",
|
||||||
|
"foreground": "#E64747",
|
||||||
|
"leading_diamond": " \ue0b6",
|
||||||
|
"options": {
|
||||||
|
"fetch_version": false
|
||||||
|
},
|
||||||
|
"style": "diamond",
|
||||||
|
"template": "\ue791\u007B\u007B if .Error \u007D\u007D\u007B\u007B .Error \u007D\u007D\u007B\u007B else \u007D\u007D\u007B\u007B .Full \u007D\u007D\u007B\u007B end \u007D\u007D",
|
||||||
|
"trailing_diamond": "\ue0b4",
|
||||||
|
"type": "ruby"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"background": "#3A456E",
|
||||||
|
"foreground": "#E64747",
|
||||||
|
"leading_diamond": " \ue0b6",
|
||||||
|
"options": {
|
||||||
|
"fetch_version": false
|
||||||
|
},
|
||||||
|
"style": "diamond",
|
||||||
|
"template": "\ue738\u007B\u007B if .Error \u007D\u007D\u007B\u007B .Error \u007D\u007D\u007B\u007B else \u007D\u007D\u007B\u007B .Full \u007D\u007D\u007B\u007B end \u007D\u007D",
|
||||||
|
"trailing_diamond": "\ue0b4",
|
||||||
|
"type": "java"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"background": "#3A456E",
|
||||||
|
"foreground": "#9B6BDF",
|
||||||
|
"leading_diamond": " \ue0b6",
|
||||||
|
"options": {
|
||||||
|
"fetch_version": false
|
||||||
|
},
|
||||||
|
"style": "diamond",
|
||||||
|
"template": "\ue624\u007B\u007B if .Error \u007D\u007D\u007B\u007B .Error \u007D\u007D\u007B\u007B else \u007D\u007D\u007B\u007B .Full \u007D\u007D\u007B\u007B end \u007D\u007D ",
|
||||||
|
"trailing_diamond": "\ue0b4",
|
||||||
|
"type": "julia"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"type": "php",
|
||||||
|
"style": "diamond",
|
||||||
|
"foreground": "#ffffff",
|
||||||
|
"background": "#4063D8",
|
||||||
|
"leading_diamond": " \ue0b6",
|
||||||
|
"options": {
|
||||||
|
"fetch_version": false
|
||||||
|
},
|
||||||
|
"template": "\ue73d \u007B\u007B .Full \u007D\u007D ",
|
||||||
|
"trailing_diamond": "\ue0b4"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"background": "#3A456E",
|
||||||
|
"foreground": "#9B6BDF",
|
||||||
|
"foreground_templates": [
|
||||||
|
"\u007B\u007Bif eq \"Charging\" .State.String\u007D\u007D#40c4ff\u007B\u007Bend\u007D\u007D",
|
||||||
|
"\u007B\u007Bif eq \"Discharging\" .State.String\u007D\u007D#ff5722\u007B\u007Bend\u007D\u007D",
|
||||||
|
"\u007B\u007Bif eq \"Full\" .State.String\u007D\u007D#4caf50\u007B\u007Bend\u007D\u007D"
|
||||||
|
],
|
||||||
|
"leading_diamond": " \ue0b6",
|
||||||
|
"options": {
|
||||||
|
"charged_icon": " ",
|
||||||
|
"charging_icon": "\u21e1 ",
|
||||||
|
"discharging_icon": "\u21e3 "
|
||||||
|
},
|
||||||
|
"style": "diamond",
|
||||||
|
"template": "\u007B\u007B if not .Error \u007D\u007D\u007B\u007B .Icon \u007D\u007D\u007B\u007B .Percentage \u007D\u007D\u007B\u007B end \u007D\u007D\u007B\u007B .Error \u007D\u007D",
|
||||||
|
"trailing_diamond": "\ue0b4",
|
||||||
|
"type": "battery"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"type": "prompt"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alignment": "right",
|
||||||
|
"segments": [
|
||||||
|
{
|
||||||
|
"background": "#3A456E",
|
||||||
|
"foreground": "#AEA4BF",
|
||||||
|
"leading_diamond": "\ue0b6",
|
||||||
|
"options": {
|
||||||
|
"style": "austin",
|
||||||
|
"threshold": 150
|
||||||
|
},
|
||||||
|
"style": "diamond",
|
||||||
|
"template": "\u007B\u007B .FormattedMs \u007D\u007D",
|
||||||
|
"trailing_diamond": "\ue0b4 ",
|
||||||
|
"type": "executiontime"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"type": "prompt"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alignment": "left",
|
||||||
|
"newline": true,
|
||||||
|
"segments": [
|
||||||
|
{
|
||||||
|
"background": "#3A456E",
|
||||||
|
"foreground": "#3EC669",
|
||||||
|
"leading_diamond": "\ue0b6",
|
||||||
|
"properties": {
|
||||||
|
"style": "agnoster_full",
|
||||||
|
"cycle": [
|
||||||
|
"#3EC669,#3A456E",
|
||||||
|
"#43CCEA,#3A456E",
|
||||||
|
"#E4F34A,#3A456E",
|
||||||
|
"#9B6BDF,#3A456E"
|
||||||
|
],
|
||||||
|
"cycle_folder_separator": true
|
||||||
|
},
|
||||||
|
"style": "diamond",
|
||||||
|
"template": "\ue5ff \u007B\u007B .Path \u007D\u007D",
|
||||||
|
"trailing_diamond": "\ue0b4",
|
||||||
|
"type": "path"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"background": "#3A456E",
|
||||||
|
"foreground": "#ffbebc",
|
||||||
|
"leading_diamond": "\ue0b6",
|
||||||
|
"style": "diamond",
|
||||||
|
"template": "\ue602",
|
||||||
|
"trailing_diamond": "\ue0b4",
|
||||||
|
"type": "text"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"type": "prompt"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"final_space": true,
|
||||||
|
"version": 4
|
||||||
|
}
|
||||||
@@ -1,15 +1,5 @@
|
|||||||
# HM side of the flake; option tree is `chiasson.home.*` (docs/conventions.md).
|
# HM side of the flake; option tree is `chiasson.home.*` (docs/conventions.md).
|
||||||
{ self, inputs, ... }: {
|
{ self, inputs, ... }: {
|
||||||
imports = [
|
|
||||||
./apps/discord.nix
|
|
||||||
./apps/localsend.nix
|
|
||||||
./apps/pokeclicker
|
|
||||||
./apps/spotify.nix
|
|
||||||
./browsers/orion.nix
|
|
||||||
./desktop/screenshot.nix
|
|
||||||
./hardware/uconsole-gamepad.nix
|
|
||||||
];
|
|
||||||
|
|
||||||
# Root module: chiasson.home.enable + bash. Other `wisdom*` slices auto-wire via
|
# Root module: chiasson.home.enable + bash. Other `wisdom*` slices auto-wire via
|
||||||
# `lib.wisdomCatalogExtraModules`; hosts flip `chiasson.home.*.enable` rather than re-importing.
|
# `lib.wisdomCatalogExtraModules`; hosts flip `chiasson.home.*.enable` rather than re-importing.
|
||||||
flake.homeManagerModules.wisdom =
|
flake.homeManagerModules.wisdom =
|
||||||
|
|||||||
@@ -7,6 +7,8 @@
|
|||||||
hyprlandHm = lib.attrByPath [ "wayland" "windowManager" "hyprland" ] { } config;
|
hyprlandHm = lib.attrByPath [ "wayland" "windowManager" "hyprland" ] { } config;
|
||||||
hyprlandHmEnabled = hyprlandHm.enable or false;
|
hyprlandHmEnabled = hyprlandHm.enable or false;
|
||||||
keyOk = cfg.swiftshareApiKeyFile != null && cfg.swiftshareApiKeyFile != "";
|
keyOk = cfg.swiftshareApiKeyFile != null && cfg.swiftshareApiKeyFile != "";
|
||||||
|
uploadScript = builtins.readFile ./scripts/swiftshare-upload.sh;
|
||||||
|
screenshotScript = builtins.readFile ./scripts/swiftshare-screenshot.sh;
|
||||||
in
|
in
|
||||||
{
|
{
|
||||||
options.chiasson.home.desktop.screenshot.enable = lib.mkEnableOption ''
|
options.chiasson.home.desktop.screenshot.enable = lib.mkEnableOption ''
|
||||||
@@ -33,171 +35,23 @@
|
|||||||
(lib.mkIf (root.enable && cfg.enable && keyOk) (
|
(lib.mkIf (root.enable && cfg.enable && keyOk) (
|
||||||
let
|
let
|
||||||
apiKeyFile = cfg.swiftshareApiKeyFile;
|
apiKeyFile = cfg.swiftshareApiKeyFile;
|
||||||
|
swiftshareUpload = pkgs.writeShellScriptBin "swiftshare-upload" (
|
||||||
|
builtins.replaceStrings [ "@API_KEY_FILE@" ] [ apiKeyFile ] uploadScript
|
||||||
|
);
|
||||||
|
swiftshareScreenshot = pkgs.writeShellScriptBin "swiftshare-screenshot" screenshotScript;
|
||||||
in
|
in
|
||||||
lib.mkMerge [
|
lib.mkMerge [
|
||||||
{
|
{
|
||||||
home.packages = with pkgs; [
|
home.packages = with pkgs; [
|
||||||
grim
|
grim
|
||||||
slurp
|
slurp
|
||||||
swappy
|
swappy
|
||||||
wl-clipboard
|
wl-clipboard
|
||||||
libnotify
|
libnotify
|
||||||
(writeShellScriptBin "swiftshare-upload" ''
|
curl
|
||||||
#!${pkgs.bash}/bin/bash
|
jq
|
||||||
set -euo pipefail
|
swiftshareUpload
|
||||||
|
swiftshareScreenshot
|
||||||
COPY_URL=0
|
|
||||||
if [ "$#" -ge 1 ] && [ "$1" = "--copy-url" ]; then
|
|
||||||
COPY_URL=1
|
|
||||||
shift
|
|
||||||
fi
|
|
||||||
|
|
||||||
APP_NAME=""
|
|
||||||
if [ "$#" -ge 2 ] && [ "$1" = "--app-name" ]; then
|
|
||||||
APP_NAME="$2"
|
|
||||||
shift 2
|
|
||||||
fi
|
|
||||||
|
|
||||||
API_KEY_FILE=${lib.escapeShellArg apiKeyFile}
|
|
||||||
if [ -r "$API_KEY_FILE" ]; then
|
|
||||||
SWIFTSHARE_API_KEY="$(tr -d '\n' < "$API_KEY_FILE")"
|
|
||||||
fi
|
|
||||||
|
|
||||||
if [ -z "''${SWIFTSHARE_API_KEY:-}" ]; then
|
|
||||||
${pkgs.libnotify}/bin/notify-send "SwiftShare upload" "SwiftShare API key missing (expected readable: $API_KEY_FILE)"
|
|
||||||
echo "Error: SwiftShare API key missing (expected readable: $API_KEY_FILE)" >&2
|
|
||||||
exit 1
|
|
||||||
fi
|
|
||||||
|
|
||||||
IMAGE_FILE=""
|
|
||||||
RESPONSE_FILE=""
|
|
||||||
cleanup() {
|
|
||||||
if [ -n "$RESPONSE_FILE" ] && [ -f "$RESPONSE_FILE" ]; then
|
|
||||||
rm -f "$RESPONSE_FILE"
|
|
||||||
fi
|
|
||||||
}
|
|
||||||
trap cleanup EXIT
|
|
||||||
|
|
||||||
if [ "$#" -ge 1 ] && [ "$1" != "-" ]; then
|
|
||||||
IMAGE_FILE="$1"
|
|
||||||
if [ "''${IMAGE_FILE#'/'}" = "''${IMAGE_FILE}" ]; then
|
|
||||||
IMAGE_FILE="$(${pkgs.coreutils}/bin/readlink -f "''${IMAGE_FILE}")"
|
|
||||||
fi
|
|
||||||
if [ ! -f "$IMAGE_FILE" ]; then
|
|
||||||
echo "Error: file not found: $IMAGE_FILE" >&2
|
|
||||||
exit 1
|
|
||||||
fi
|
|
||||||
else
|
|
||||||
APP_NAME="''${APP_NAME:-screenshot}"
|
|
||||||
APP_NAME="''${APP_NAME%% *}"
|
|
||||||
APP_NAME="''${APP_NAME//[^A-Za-z0-9]/}"
|
|
||||||
APP_NAME="''${APP_NAME,,}"
|
|
||||||
if [ -z "$APP_NAME" ]; then
|
|
||||||
APP_NAME="screenshot"
|
|
||||||
fi
|
|
||||||
|
|
||||||
IMAGE_FILE="$(${pkgs.coreutils}/bin/mktemp --suffix=.png "''${TMPDIR:-/tmp}/''${APP_NAME}_XXXXXX")"
|
|
||||||
cat > "$IMAGE_FILE"
|
|
||||||
fi
|
|
||||||
|
|
||||||
if [ ! -s "$IMAGE_FILE" ]; then
|
|
||||||
${pkgs.libnotify}/bin/notify-send "SwiftShare" "Empty capture (maybe canceled) – not uploading"
|
|
||||||
echo "Empty image file, not uploading." >&2
|
|
||||||
exit 0
|
|
||||||
fi
|
|
||||||
|
|
||||||
RESPONSE_FILE="$(mktemp)"
|
|
||||||
set +e
|
|
||||||
HTTP_STATUS="$(${pkgs.curl}/bin/curl -sS -o "''${RESPONSE_FILE}" -w '%{http_code}' \
|
|
||||||
-X POST "https://swiftshare.cloud/api/upload/sharex" \
|
|
||||||
-F "upload=@''${IMAGE_FILE}" \
|
|
||||||
-F "apiKey=''${SWIFTSHARE_API_KEY}")"
|
|
||||||
CURL_EXIT=$?
|
|
||||||
set -e
|
|
||||||
|
|
||||||
RESPONSE="$(cat "''${RESPONSE_FILE}")"
|
|
||||||
|
|
||||||
if [ "''${CURL_EXIT}" -ne 0 ]; then
|
|
||||||
${pkgs.libnotify}/bin/notify-send "SwiftShare upload failed" "Network or HTTP error (curl exit ''${CURL_EXIT})"
|
|
||||||
echo "SwiftShare upload failed (curl exit ''${CURL_EXIT})." >&2
|
|
||||||
echo "Response body:" >&2
|
|
||||||
echo "''${RESPONSE}" >&2
|
|
||||||
exit 1
|
|
||||||
fi
|
|
||||||
|
|
||||||
if ! echo "''${HTTP_STATUS}" | grep -qE '^2[0-9][0-9]$'; then
|
|
||||||
ERROR_MSG="$(${pkgs.jq}/bin/jq -r '.error // empty' <<< "''${RESPONSE}")"
|
|
||||||
if [ -z "''${ERROR_MSG}" ] || [ "''${ERROR_MSG}" = "null" ]; then
|
|
||||||
ERROR_MSG="Failed to upload file"
|
|
||||||
fi
|
|
||||||
${pkgs.libnotify}/bin/notify-send "SwiftShare upload failed (''${HTTP_STATUS})" "''${ERROR_MSG}"
|
|
||||||
echo "SwiftShare upload failed (HTTP ''${HTTP_STATUS}): ''${ERROR_MSG}" >&2
|
|
||||||
exit 1
|
|
||||||
fi
|
|
||||||
|
|
||||||
URL="$(${pkgs.jq}/bin/jq -r '.url // empty' <<< "''${RESPONSE}")"
|
|
||||||
THUMBNAIL="$(${pkgs.jq}/bin/jq -r '.thumbnail // empty' <<< "''${RESPONSE}")"
|
|
||||||
|
|
||||||
if [ -z "$URL" ] || [ "$URL" = "null" ]; then
|
|
||||||
${pkgs.libnotify}/bin/notify-send "SwiftShare upload failed" "Could not parse URL from response"
|
|
||||||
echo "Upload failed. Raw response:" >&2
|
|
||||||
echo "''${RESPONSE}" >&2
|
|
||||||
exit 1
|
|
||||||
fi
|
|
||||||
|
|
||||||
echo "$URL"
|
|
||||||
if [ -n "$THUMBNAIL" ] && [ "$THUMBNAIL" != "null" ]; then
|
|
||||||
echo "$THUMBNAIL"
|
|
||||||
fi
|
|
||||||
|
|
||||||
if [ "$COPY_URL" = "1" ]; then
|
|
||||||
${pkgs.wl-clipboard}/bin/wl-copy <<< "$URL"
|
|
||||||
fi
|
|
||||||
|
|
||||||
if [ -n "$IMAGE_FILE" ] && [ -f "$IMAGE_FILE" ]; then
|
|
||||||
${pkgs.libnotify}/bin/notify-send \
|
|
||||||
-a "SwiftShare" \
|
|
||||||
-i "$IMAGE_FILE" \
|
|
||||||
-h string:image-path:"$IMAGE_FILE" \
|
|
||||||
"SwiftShare upload" "Uploaded image: $URL"
|
|
||||||
else
|
|
||||||
${pkgs.libnotify}/bin/notify-send "SwiftShare upload" "Uploaded image: $URL"
|
|
||||||
fi
|
|
||||||
'')
|
|
||||||
|
|
||||||
(writeShellScriptBin "swiftshare-screenshot" ''
|
|
||||||
#!${pkgs.bash}/bin/bash
|
|
||||||
set -euo pipefail
|
|
||||||
|
|
||||||
LOG_DIR="$HOME/.local/state/swiftshare"
|
|
||||||
mkdir -p "$LOG_DIR"
|
|
||||||
LOG_FILE="$LOG_DIR/screenshot.log"
|
|
||||||
|
|
||||||
APP_CLASS="$(${pkgs.hyprland}/bin/hyprctl activewindow -j 2>/dev/null | ${pkgs.jq}/bin/jq -r '.class // .initialClass // empty' 2>/dev/null || true)"
|
|
||||||
APP_CLASS="''${APP_CLASS%% *}"
|
|
||||||
APP_CLASS="''${APP_CLASS//[^A-Za-z0-9]/}"
|
|
||||||
APP_CLASS="''${APP_CLASS,,}"
|
|
||||||
if [ -z "$APP_CLASS" ]; then
|
|
||||||
APP_CLASS="screenshot"
|
|
||||||
fi
|
|
||||||
|
|
||||||
GEOM="$(${pkgs.slurp}/bin/slurp)"
|
|
||||||
SLURP_EXIT=$?
|
|
||||||
|
|
||||||
if [ "$SLURP_EXIT" -ne 0 ] || [ -z "$GEOM" ]; then
|
|
||||||
${pkgs.libnotify}/bin/notify-send "SwiftShare" "Capture canceled"
|
|
||||||
{
|
|
||||||
echo "==== $(date) ==== capture canceled (slurp exit $SLURP_EXIT, geom='$GEOM')"
|
|
||||||
} >>"$LOG_FILE" 2>&1
|
|
||||||
exit 0
|
|
||||||
fi
|
|
||||||
|
|
||||||
{
|
|
||||||
echo "==== $(date) ===="
|
|
||||||
echo "Geometry: $GEOM"
|
|
||||||
${pkgs.grim}/bin/grim -g "$GEOM" - | ${pkgs.swappy}/bin/swappy -f - -o - | swiftshare-upload --copy-url --app-name "$APP_CLASS"
|
|
||||||
} >>"$LOG_FILE" 2>&1
|
|
||||||
'')
|
|
||||||
];
|
];
|
||||||
}
|
}
|
||||||
(lib.mkIf hyprlandHmEnabled {
|
(lib.mkIf hyprlandHmEnabled {
|
||||||
|
|||||||
@@ -0,0 +1,31 @@
|
|||||||
|
#!/usr/bin/env bash
|
||||||
|
set -euo pipefail
|
||||||
|
|
||||||
|
LOG_DIR="$HOME/.local/state/swiftshare"
|
||||||
|
mkdir -p "$LOG_DIR"
|
||||||
|
LOG_FILE="$LOG_DIR/screenshot.log"
|
||||||
|
|
||||||
|
APP_CLASS="$(hyprctl activewindow -j 2>/dev/null | jq -r '.class // .initialClass // empty' 2>/dev/null || true)"
|
||||||
|
APP_CLASS="${APP_CLASS%% *}"
|
||||||
|
APP_CLASS="${APP_CLASS//[^A-Za-z0-9]/}"
|
||||||
|
APP_CLASS="${APP_CLASS,,}"
|
||||||
|
if [ -z "$APP_CLASS" ]; then
|
||||||
|
APP_CLASS="screenshot"
|
||||||
|
fi
|
||||||
|
|
||||||
|
GEOM="$(slurp)"
|
||||||
|
SLURP_EXIT=$?
|
||||||
|
|
||||||
|
if [ "$SLURP_EXIT" -ne 0 ] || [ -z "$GEOM" ]; then
|
||||||
|
notify-send "SwiftShare" "Capture canceled"
|
||||||
|
{
|
||||||
|
echo "==== $(date) ==== capture canceled (slurp exit $SLURP_EXIT, geom='$GEOM')"
|
||||||
|
} >>"$LOG_FILE" 2>&1
|
||||||
|
exit 0
|
||||||
|
fi
|
||||||
|
|
||||||
|
{
|
||||||
|
echo "==== $(date) ===="
|
||||||
|
echo "Geometry: $GEOM"
|
||||||
|
grim -g "$GEOM" - | swappy -f - -o - | swiftshare-upload --copy-url --app-name "$APP_CLASS"
|
||||||
|
} >>"$LOG_FILE" 2>&1
|
||||||
@@ -0,0 +1,121 @@
|
|||||||
|
#!/usr/bin/env bash
|
||||||
|
# API key path substituted at build time (@API_KEY_FILE@).
|
||||||
|
set -euo pipefail
|
||||||
|
|
||||||
|
COPY_URL=0
|
||||||
|
if [ "$#" -ge 1 ] && [ "$1" = "--copy-url" ]; then
|
||||||
|
COPY_URL=1
|
||||||
|
shift
|
||||||
|
fi
|
||||||
|
|
||||||
|
APP_NAME=""
|
||||||
|
if [ "$#" -ge 2 ] && [ "$1" = "--app-name" ]; then
|
||||||
|
APP_NAME="$2"
|
||||||
|
shift 2
|
||||||
|
fi
|
||||||
|
|
||||||
|
API_KEY_FILE=@API_KEY_FILE@
|
||||||
|
if [ -r "$API_KEY_FILE" ]; then
|
||||||
|
SWIFTSHARE_API_KEY="$(tr -d '\n' < "$API_KEY_FILE")"
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [ -z "${SWIFTSHARE_API_KEY:-}" ]; then
|
||||||
|
notify-send "SwiftShare upload" "SwiftShare API key missing (expected readable: $API_KEY_FILE)"
|
||||||
|
echo "Error: SwiftShare API key missing (expected readable: $API_KEY_FILE)" >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
IMAGE_FILE=""
|
||||||
|
RESPONSE_FILE=""
|
||||||
|
cleanup() {
|
||||||
|
if [ -n "$RESPONSE_FILE" ] && [ -f "$RESPONSE_FILE" ]; then
|
||||||
|
rm -f "$RESPONSE_FILE"
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
trap cleanup EXIT
|
||||||
|
|
||||||
|
if [ "$#" -ge 1 ] && [ "$1" != "-" ]; then
|
||||||
|
IMAGE_FILE="$1"
|
||||||
|
if [ "${IMAGE_FILE#/}" = "${IMAGE_FILE}" ]; then
|
||||||
|
IMAGE_FILE="$(readlink -f "${IMAGE_FILE}")"
|
||||||
|
fi
|
||||||
|
if [ ! -f "$IMAGE_FILE" ]; then
|
||||||
|
echo "Error: file not found: $IMAGE_FILE" >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
else
|
||||||
|
APP_NAME="${APP_NAME:-screenshot}"
|
||||||
|
APP_NAME="${APP_NAME%% *}"
|
||||||
|
APP_NAME="${APP_NAME//[^A-Za-z0-9]/}"
|
||||||
|
APP_NAME="${APP_NAME,,}"
|
||||||
|
if [ -z "$APP_NAME" ]; then
|
||||||
|
APP_NAME="screenshot"
|
||||||
|
fi
|
||||||
|
|
||||||
|
IMAGE_FILE="$(mktemp --suffix=.png "${TMPDIR:-/tmp}/${APP_NAME}_XXXXXX")"
|
||||||
|
cat > "$IMAGE_FILE"
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [ ! -s "$IMAGE_FILE" ]; then
|
||||||
|
notify-send "SwiftShare" "Empty capture (maybe canceled) – not uploading"
|
||||||
|
echo "Empty image file, not uploading." >&2
|
||||||
|
exit 0
|
||||||
|
fi
|
||||||
|
|
||||||
|
RESPONSE_FILE="$(mktemp)"
|
||||||
|
set +e
|
||||||
|
HTTP_STATUS="$(curl -sS -o "${RESPONSE_FILE}" -w '%{http_code}' \
|
||||||
|
-X POST "https://swiftshare.cloud/api/upload/sharex" \
|
||||||
|
-F "upload=${IMAGE_FILE}" \
|
||||||
|
-F "apiKey=${SWIFTSHARE_API_KEY}")"
|
||||||
|
CURL_EXIT=$?
|
||||||
|
set -e
|
||||||
|
|
||||||
|
RESPONSE="$(cat "${RESPONSE_FILE}")"
|
||||||
|
|
||||||
|
if [ "${CURL_EXIT}" -ne 0 ]; then
|
||||||
|
notify-send "SwiftShare upload failed" "Network or HTTP error (curl exit ${CURL_EXIT})"
|
||||||
|
echo "SwiftShare upload failed (curl exit ${CURL_EXIT})." >&2
|
||||||
|
echo "Response body:" >&2
|
||||||
|
echo "${RESPONSE}" >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
if ! echo "${HTTP_STATUS}" | grep -qE '^2[0-9][0-9]$'; then
|
||||||
|
ERROR_MSG="$(jq -r '.error // empty' <<< "${RESPONSE}")"
|
||||||
|
if [ -z "${ERROR_MSG}" ] || [ "${ERROR_MSG}" = "null" ]; then
|
||||||
|
ERROR_MSG="Failed to upload file"
|
||||||
|
fi
|
||||||
|
notify-send "SwiftShare upload failed (${HTTP_STATUS})" "${ERROR_MSG}"
|
||||||
|
echo "SwiftShare upload failed (HTTP ${HTTP_STATUS}): ${ERROR_MSG}" >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
URL="$(jq -r '.url // empty' <<< "${RESPONSE}")"
|
||||||
|
THUMBNAIL="$(jq -r '.thumbnail // empty' <<< "${RESPONSE}")"
|
||||||
|
|
||||||
|
if [ -z "$URL" ] || [ "$URL" = "null" ]; then
|
||||||
|
notify-send "SwiftShare upload failed" "Could not parse URL from response"
|
||||||
|
echo "Upload failed. Raw response:" >&2
|
||||||
|
echo "${RESPONSE}" >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
echo "$URL"
|
||||||
|
if [ -n "$THUMBNAIL" ] && [ "$THUMBNAIL" != "null" ]; then
|
||||||
|
echo "$THUMBNAIL"
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [ "$COPY_URL" = "1" ]; then
|
||||||
|
wl-copy <<< "$URL"
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [ -n "$IMAGE_FILE" ] && [ -f "$IMAGE_FILE" ]; then
|
||||||
|
notify-send \
|
||||||
|
-a "SwiftShare" \
|
||||||
|
-i "$IMAGE_FILE" \
|
||||||
|
-h string:image-path:"$IMAGE_FILE" \
|
||||||
|
"SwiftShare upload" "Uploaded image: $URL"
|
||||||
|
else
|
||||||
|
notify-send "SwiftShare upload" "Uploaded image: $URL"
|
||||||
|
fi
|
||||||
Reference in New Issue
Block a user