diff --git a/hosts/desktop/shared-configuration.nix b/hosts/desktop/shared-configuration.nix index 1efd598..066c5e7 100644 --- a/hosts/desktop/shared-configuration.nix +++ b/hosts/desktop/shared-configuration.nix @@ -12,6 +12,13 @@ sops.defaultSopsFile = ../../secrets/desktop-secrets.yaml; sops.defaultSopsFormat = "yaml"; + sops.secrets.lon = { + owner = config.users.users.guz.name; + }; + sops.secrets.lat = { + owner = config.users.users.guz.name; + }; + sops.age.keyFile = "/home/guz/.config/sops/age/keys.txt"; programs.hyprland = { diff --git a/hosts/desktop/shared-home.nix b/hosts/desktop/shared-home.nix index bbb6d3d..456496a 100644 --- a/hosts/desktop/shared-home.nix +++ b/hosts/desktop/shared-home.nix @@ -26,7 +26,6 @@ home.packages = with pkgs; [ ## Programs firefox - eww-wayland # (pkgs.writeShellScriptBin "my-hello" '' # echo "Hello, ${config.home.username}!" diff --git a/hosts/desktop/wm.nix b/hosts/desktop/wm.nix index 6a37d05..b35910e 100644 --- a/hosts/desktop/wm.nix +++ b/hosts/desktop/wm.nix @@ -1,15 +1,20 @@ -{ pkgs, ... }: +{ config, lib, pkgs, ... }: +let + cfg = config.wm; +in { imports = [ ../../modules/home-manager/programs/hyprland.nix ../../modules/home-manager/programs/eww ]; - options.wm = { }; + options.wm = with lib; with lib.types; { }; config = { + eww.enable = true; hyprland.enable = true; + hyprland.monitors = [ { name = "monitor1"; @@ -52,5 +57,4 @@ } ]; }; - } diff --git a/modules/home-manager/programs/eww/default.nix b/modules/home-manager/programs/eww/default.nix index 9091ae7..4f8e10e 100644 --- a/modules/home-manager/programs/eww/default.nix +++ b/modules/home-manager/programs/eww/default.nix @@ -3,6 +3,77 @@ let cfg = config.eww; ewwDir = "${config.xdg.configHome}/eww"; + + eww-get-active-workspace = pkgs.writeShellScriptBin "eww-get-active-workspace" '' + hyprctl="${pkgs.hyprland}/bin/hyprctl" + jq="${pkgs.jq}/bin/jq" + socat="${pkgs.socat}/bin/socat" + + $hyprctl monitors -j | + $jq '.[] | select(.focused) | .activeWorkspace.id' + + $socat -u UNIX-CONNECT:/tmp/hypr/$HYPRLAND_INSTANCE_SIGNATURE/.socket2.sock - | + stdbuf -o0 awk -F '>>|,' -e '/^workspace>>/ {print $2}' -e '/^focusedmon>>/ {print $3}' + ''; + + eww-volume = pkgs.writeShellScriptBin "eww-volume" '' + pulsemixer="${pkgs.pulsemixer}/bin/pulsemixer" + + sink="$(echo $($pulsemixer -l | grep 'Default' | grep 'sink-' | awk '{print $3}') | rev | cut -c 2- | rev)" + function="$1" + value="$2" + + if [[ "$function" == "set" ]]; then + $pulsemixer --id "$sink" --set-volume "$value" + echo "0" + elif [[ "$function" == "get" ]]; then + echo "$($pulsemixer --id "$sink" --get-volume | awk '{print $1}')" + elif [[ "$function" == "label" ]]; then + echo "$($pulsemixer --id "$sink" --get-mute | awk '{if($1>0) print "󰖁"; else print "󰕾"}')" + fi + ''; + + eww-weather = pkgs.writeShellScriptBin "eww-weather" '' + curl="${pkgs.curl}/bin/curl" + jq="${pkgs.jq}/bin/jq" + + lat="$(cat /run/secrets/lat)" + lon="$(cat /run/secrets/lon)" + + res="$($curl -s "https://api.open-meteo.com/v1/forecast?latitude=$lat&longitude=$lon¤t=temperature_2m,precipitation,wind_speed_10m,rain")" + + temperature="$(echo $res | $jq .current.temperature_2m)" + wind="$(echo $res | $jq .current.wind_speed_10m)" + precipitation="$(echo $res | $jq .current.precipitation)" + rain="$(echo $res | $jq .current.rain)" + + if [[ "$1" == "--temperature" ]]; then + echo $temperature + elif [[ "$1" == "--wind" ]]; then + echo $wind + elif [[ "$1" == "--precipitation" ]]; then + echo $precipitation + elif [[ "$1" == "--rain" ]]; then + echo $rain + fi + ''; + + eww-boot = pkgs.writeShellScriptBin "eww-boot" '' + eww="${pkgs.eww-wayland}/bin/eww" + + ping="$($eww ping)" + if [[ "$ping" == "pong" ]]; then + $eww reload + $eww close-all + else + $eww daemon + $eww close-all + fi + + $eww open bar + $eww open bar-2 + + ''; in { imports = [ ]; @@ -11,16 +82,43 @@ in }; config = lib.mkIf cfg.enable { + home.packages = with pkgs; [ + eww-wayland + ]; + home.activation = { + eww-boot = "${eww-boot}/bin/eww-boot"; + }; + home.file."${ewwDir}/eww.yuck".source = ./eww.yuck; home.file."${ewwDir}/eww.scss".source = ./eww.scss; home.file."${ewwDir}/vars.yuck".text = '' + (deflisten active-workspace :initial "1" + "${eww-get-active-workspace}/bin/eww-get-active-workspace") + + (defpoll volume :interval "1s" + "${eww-volume}/bin/eww-volume get") + + (defpoll volume-label :interval "1s" + "${eww-volume}/bin/eww-volume label") + + (defvar volume-set "${eww-volume}/bin/eww-volume set {}") + (defvar volume-toggle "${pkgs.pulsemixer}/bin/pulsemixer --toggle-mute") + + (defpoll temperature :interval "15m" :initial "00.0" + "${eww-weather}/bin/eww-weather --temperature") + (defpoll wind :interval "15m" :initial "00.0" + "${eww-weather}/bin/eww-weather --wind") + (defpoll precipitation :interval "15m" :initial "00.0" + "${eww-weather}/bin/eww-weather --precipitation") + (defpoll rain :interval "15m" :initial "00.0" + "${eww-weather}/bin/eww-weather --rain") ''; home.file."${ewwDir}/vars.scss".text = '' $color-accent: #${config.theme.accent}; $foreground: rgba(#${config.colorScheme.colors.base03}, 1); - $background: rgba(#${config.colorScheme.colors.base00}, 1); + $background: rgba(#${config.colorScheme.colors.base00} , 1); $shadow: 2px 2px 2px rgba(0, 0, 0, 0.2); $border-radius: 5px; @@ -28,9 +126,10 @@ in @mixin box-style { border-radius: $border-radius; box-shadow: $shadow; - background-color: $color-background; + background-color: $background; } ''; }; } + diff --git a/modules/home-manager/programs/eww/eww.scss b/modules/home-manager/programs/eww/eww.scss index 1457eba..e047bc5 100644 --- a/modules/home-manager/programs/eww/eww.scss +++ b/modules/home-manager/programs/eww/eww.scss @@ -2,8 +2,18 @@ * { background-color: transparent; + all: unset; } +tooltip { + @include box-style(); + + background-color: $foreground; + color: $color-accent; + font-weight: bold; +} + + .bar { @include box-style(); @@ -20,9 +30,39 @@ .middlestuff { // background-color: green; + font-size: small; } .leftstuff { // background-color: red; } } + +.temperature, .rain, .season { + margin: 0 4px; +} + +.metric { + .label { + font-size: small; + margin: 0; + padding: 0; + color: $color-accent; + margin-right: 5px; + } + margin-right: 5px; + + scale trough { + all: unset; + background: $foreground; + border-radius: 50px; + min-height: 5px; + min-width: 50px; + + highlight { + all: unset; + background-color: $color-accent; + border-radius: 10px; + } + } +} diff --git a/modules/home-manager/programs/eww/eww.yuck b/modules/home-manager/programs/eww/eww.yuck index 7ef0d22..5fe2a99 100644 --- a/modules/home-manager/programs/eww/eww.yuck +++ b/modules/home-manager/programs/eww/eww.yuck @@ -1,19 +1,59 @@ (include "/home/guz/.config/eww/vars.yuck"); +(defpoll week-day :interval "1m" + :initial "1" + `date +%w`) + +(defpoll quarter :interval "24h" + :initial "1" + `date +%q`) + (defpoll time :interval "10s" - :initial "00:00:00" + :initial "00:00" `date +%H:%M`) (defpoll date :interval "1m" - :initial "00:00:00" + :initial "00/00" `date +%d/%m`) (defwidget empty [] "") -(defwidget date [] +(defwidget day [] (box :orientation "h" - "${date}  ${time}")) + ; Sun, Moon, Mars, Mercury, Jupiter, Venus, Saturn + "${[" Sun", " Mon", " Tue", "󰬸 Wed", "󱡓 Thu", " Fri", " Sat"][week-day]} ${date} ${time}")) + +(defwidget season [] + (box :orientation "h" + "${["", "󰖨 Summer", "󰌪 Autumn", " Winter", "󰉊 Spring"][quarter]}")) + +(defwidget metric [label value ?value-text ?onchange ?onclick] + (box :orientation "h" + :tooltip "${value-text != "" ? value-text : value}" + :space-evenly false + :class "metric" + (box :orientation "h" + :class "label" + (eventbox :active {onclick != ""} + :width 15 + :cursor "pointer" + :onclick onclick + label)) + (scale :min 0 + :max 101 + :active {onchange != ""} + :onchange onchange + :value value))) + +(defwidget system-stats [] + (box :class "system-stats" + "")) + +(defwidget workspaces [workspace] + (box :class "workspace" + :orientation "h" + "${workspace == 1 ? '' : ''} ${workspace == 2 ? '' : ''} ${workspace == 3 ? '' : ''}")) (defwindow bar :monitor 0 @@ -29,22 +69,69 @@ :exclusive true (centerbox :orientation "h" :class "bar" - (centerbox :orientation "h" + (box :orientation "h" :halign "start" :class "rightstuff" - (empty) + (workspaces :workspace active-workspace) (empty) (empty)) - (centerbox :orientation "h" + (box :orientation "h" :halign "center" :class "middlestuff" - (empty) + (day)) + (box :orientation "h" + :halign "end" + :class "leftstuff" + :space-evenly false + (metric :label volume-label + :value volume + :value-text "${volume-label} Volume ${volume}%" + :onclick volume-toggle + :onchange volume-set)))) + +(defwindow bar-2 + :monitor 1 + :geometry (geometry :x "0%" + :y "5px" + :width "99.2%" + :height "20px" + :anchor "top center") + :stacking "fg" + :reserve (struts :distance "40px" :side "top") + :windowtype "dock" + :wm-ignore false + :exclusive true + (centerbox :orientation "h" + :class "bar" + (box :orientation "h" + :halign "start" + :class "rightstuff" + (metric :label "" + :value "${EWW_RAM.used_mem_perc}" + :value-text " Ram ${round(EWW_RAM.used_mem_perc, 2)}%") + (metric :label "" + :value "${EWW_CPU.avg}" + :value-text " CPU ${round(EWW_CPU.avg, 2)}%") + (metric :label "󰨣" + :value "${EWW_DISK["/"].used_perc}" + :value-text "󰨣 Disk ${round(EWW_DISK["/"].used_perc, 2)}%") (empty) (empty)) - (centerbox :orientation "h" + (box :orientation "h" + :halign "center" + :class "middlestuff" + :space-evenly false + (box :class "season" + (season)) + (label :tooltip "󱣖 ${temperature}°C -  ${wind}km/h" + :class "temperature" + :text "${round(temperature, 0)}󰔄") + (label :tooltip "󰖗 ${rain}mm - 󰖌 ${precipitation}mm" + :class "rain" + :text "${round(precipitation, 2)}mm")) + (box :orientation "h" :halign "end" :class "leftstuff" (empty) - (empty) - (date)))) + (workspaces :workspace "${active-workspace - 3}")))) diff --git a/modules/home-manager/programs/hyprland.nix b/modules/home-manager/programs/hyprland.nix index 1e20817..58c9d41 100644 --- a/modules/home-manager/programs/hyprland.nix +++ b/modules/home-manager/programs/hyprland.nix @@ -17,6 +17,10 @@ in scale = lib.types.nullOr lib.types.int; }; */ }; + exec = mkOption { + default = [ ]; + type = listOf str; + }; env = mkOption { default = { }; type = attrsOf str; @@ -145,6 +149,8 @@ in cfg.monitors ); + exec-once = cfg.exec; + # "Hack" to transform attributes sets to lists (because I didn't know other way to do it) # Transform { "envName" = "value" } to [ "envName,value" ] env = builtins.attrValues