Some checks failed
Check / eval (push) Has been cancelled
The machine flake's git-tracked settings file is system state, not "theme" only — rename it to state.json. CLI becomes nomarchy-state-sync with a nomarchy-theme-sync symlink for scripts and muscle memory. Eval (mkFlake, doctor, lifecycle) still accepts theme-state.json; the next write migrates to state.json and removes the legacy file. Documented in MIGRATION.md; drop the CLI alias after release notes.
208 lines
7.7 KiB
Markdown
208 lines
7.7 KiB
Markdown
# Overriding Nomarchy's defaults
|
||
|
||
You consume Nomarchy as a flake input and own two files: `system.nix` and
|
||
`home.nix`. Your config is **merged** with Nomarchy's modules, so changing a
|
||
default is just a matter of knowing which of three knobs to reach for. The
|
||
rule of thumb:
|
||
|
||
> **Appearance → the CLI. Behaviour → `home.nix`. Whole component → toggle it off.**
|
||
|
||
## 1. Appearance (gaps, colors, rounding, fonts, opacity) — use the CLI
|
||
|
||
Everything that defines the *look* flows from `state.json`, the single
|
||
source of truth. Change it with `nomarchy-state-sync`, which writes the JSON
|
||
and rebuilds — one generation, applied to Hyprland, Waybar, Kitty, btop and
|
||
Stylix at once:
|
||
|
||
```sh
|
||
nomarchy-state-sync set ui.gapsOut 16 # gaps, borders, rounding, opacity
|
||
nomarchy-state-sync set ui.rounding 0
|
||
nomarchy-state-sync set fonts.mono "FiraCode Nerd Font"
|
||
nomarchy-state-sync apply gruvbox # whole palette
|
||
```
|
||
|
||
### Icon pack
|
||
|
||
Icons follow the active theme's light/dark mode using **Papirus** — the only
|
||
icon pack shipped by default (Papirus alone is ~1 GiB, so extra packs are
|
||
opt-in rather than a cost every install pays). To switch to another pack:
|
||
|
||
```sh
|
||
nomarchy-state-sync set icons "Tela-dark" # or "" to return to Papirus-by-mode
|
||
```
|
||
|
||
Only the pack you name is pulled into your system (the first switch downloads
|
||
it). Known packs and an example theme name from each:
|
||
|
||
| Set `icons` to… | Pack |
|
||
|---|---|
|
||
| `Papirus`, `Papirus-Dark`, `Papirus-Light` | Papirus (default; `""` auto-picks Dark/Light by mode) |
|
||
| `Tela`, `Tela-dark`, `Tela-<color>[-dark]` | Tela (colors: blue, green, red, purple, nord, dracula, …) |
|
||
| `Qogir`, `Qogir-Dark`, `Qogir-Light` | Qogir (note the capital D/L) |
|
||
| `Reversal`, `Reversal-dark` | Reversal |
|
||
| `Numix-Circle`, `Numix-Circle-Light` | Numix Circle |
|
||
|
||
The choice is a **sticky global override** — it survives `apply <palette>`
|
||
switches (presets don't carry an icon field). To add a pack that isn't listed,
|
||
append a row to `iconPacks` in `modules/home/theme.nix`. Set `icons` to `""`
|
||
any time to drop back to Papirus with automatic Dark/Light.
|
||
|
||
### Auto theme (day/night)
|
||
|
||
Switch automatically between a light **day** theme and a dark **night** theme
|
||
on a schedule — the same one engine as a manual `apply`, no second pipeline.
|
||
Turn it on from **Look & Feel › Auto theme** (`SUPER+M`): toggle it, pick the
|
||
day and night themes, and set the sunrise/sunset times. The same from a shell:
|
||
|
||
```sh
|
||
nomarchy-state-sync set settings.autoTheme.day summer-day --no-switch
|
||
nomarchy-state-sync set settings.autoTheme.night summer-night --no-switch
|
||
nomarchy-state-sync set settings.autoTheme.sunset 20:00 --no-switch
|
||
nomarchy-state-sync set settings.autoTheme.enable true --no-switch
|
||
nomarchy-state-sync auto --force # one rebuild: installs the timer + applies now
|
||
```
|
||
|
||
State lives in `settings.autoTheme`:
|
||
|
||
| Field | Meaning |
|
||
|---|---|
|
||
| `enable` | on / off |
|
||
| `day` / `night` | theme slugs — e.g. `summer-day` / `summer-night` (see `nomarchy-state-sync list`) |
|
||
| `sunrise` / `sunset` | switch times, `"HH:MM"` (24-hour) |
|
||
|
||
A timer re-checks every ~15 minutes: the day theme applies around sunrise, the
|
||
night theme around sunset — but it only rebuilds when the active theme
|
||
actually needs to change, so most checks do nothing. Enabling rebuilds once
|
||
(to install the timer); disabling is instant. Preview the current decision
|
||
without switching with `nomarchy-state-sync auto --which`.
|
||
|
||
These values are deliberately kept at normal priority in the modules, so they
|
||
stay owned by the theme system. If you *insist* on pinning one in `home.nix`
|
||
regardless of the active theme, use `lib.mkForce` (see §4) — but then the CLI
|
||
can no longer change that knob.
|
||
|
||
## 2. Behaviour (input, misc, monitor, animations, terminal chrome) — `home.nix`
|
||
|
||
Non-appearance defaults are set with `lib.mkDefault`, so a **plain assignment**
|
||
in your `home.nix` wins — no `mkForce` needed:
|
||
|
||
```nix
|
||
# home.nix
|
||
{ ... }:
|
||
{
|
||
wayland.windowManager.hyprland.settings = {
|
||
input.follow_mouse = 0; # was 1
|
||
input.touchpad.natural_scroll = false;
|
||
misc.disable_splash_rendering = false;
|
||
monitor = [ "DP-1,2560x1440@144,0x0,1" ]; # raw rule — replaces the default
|
||
animations.enabled = false;
|
||
};
|
||
|
||
programs.kitty.settings = {
|
||
window_padding_width = 4; # was 12
|
||
};
|
||
}
|
||
```
|
||
|
||
For monitor layout, prefer the friendlier **`nomarchy.monitors`** (a list of
|
||
per-output submodules — resolution/position/scale/rotation — turned into
|
||
Hyprland rules and applied on hotplug; run `nwg-displays` to find the values
|
||
interactively). Assigning `settings.monitor` directly, as above, replaces it.
|
||
|
||
### Adding vs. overriding lists
|
||
|
||
`bind`, `bindel`, `bindl`, `bindm` and `exec-once` are lists kept at normal
|
||
priority, so anything you add **concatenates** with Nomarchy's — your binds and
|
||
autostarts run *alongside* the defaults:
|
||
|
||
```nix
|
||
{
|
||
wayland.windowManager.hyprland.settings = {
|
||
bind = [
|
||
"$mod, B, exec, firefox"
|
||
"$mod SHIFT, S, exec, grim -g \"$(slurp)\" - | satty --filename -"
|
||
];
|
||
exec-once = [ "nm-applet --indicator" ];
|
||
};
|
||
}
|
||
```
|
||
|
||
To **remove or replace** a default bind, override the whole `bind` list with
|
||
`lib.mkForce [ … ]` (you then own the full list), or rebind the key to
|
||
something else (last definition for a key wins in Hyprland).
|
||
|
||
You can also drop raw config that doesn't fit the Nix schema:
|
||
|
||
```nix
|
||
{ wayland.windowManager.hyprland.extraConfig = ''
|
||
bindl = , switch:Lid Switch, exec, hyprlock
|
||
'';
|
||
}
|
||
```
|
||
|
||
### Waybar
|
||
|
||
For a themed bar identity, ship whole-swap assets
|
||
(`themes/<slug>/waybar.jsonc` and `waybar.css`) — see the main README. To
|
||
replace the bar wholesale from `home.nix`, assign `programs.waybar.settings.
|
||
mainBar` / `programs.waybar.style` (both `mkDefault`, so a plain assignment
|
||
wins). For a one-off tweak of a single generated key, `lib.mkForce` it.
|
||
|
||
## 3. Whole component — toggle it off and bring your own
|
||
|
||
Each desktop piece has an enable flag (all default `true`). Turn one off and
|
||
Nomarchy contributes nothing for it, leaving the field clear for your own:
|
||
|
||
```nix
|
||
# home.nix
|
||
{
|
||
nomarchy.hyprland.enable = false; # then write your own wayland.windowManager.hyprland
|
||
nomarchy.waybar.enable = false;
|
||
nomarchy.swaync.enable = false;
|
||
nomarchy.idle.enable = false; # no hyprlock/hypridle
|
||
}
|
||
```
|
||
|
||
```nix
|
||
# system.nix
|
||
{
|
||
nomarchy.system.plymouth.enable = false;
|
||
nomarchy.system.greeter.enable = false; # bring your own login manager
|
||
}
|
||
```
|
||
|
||
See the option tables in the README for the full list.
|
||
|
||
## 4. Last resort: `lib.mkForce`
|
||
|
||
To override a value Nomarchy sets at normal priority (an appearance value, or
|
||
a whole list), raise your definition's priority:
|
||
|
||
```nix
|
||
{ lib, ... }:
|
||
{
|
||
# hardcode rounding against the theme (the CLI can no longer change it)
|
||
wayland.windowManager.hyprland.settings.decoration.rounding = lib.mkForce 0;
|
||
|
||
# own the entire keybind list
|
||
wayland.windowManager.hyprland.settings.bind = lib.mkForce [ "$mod, Return, exec, kitty" ];
|
||
}
|
||
```
|
||
|
||
If a plain assignment errors with *"has conflicting definition values"*, that
|
||
value is theme-owned at normal priority — either change it via the CLI (§1) or
|
||
`mkForce` it here.
|
||
|
||
## Quick reference
|
||
|
||
| You want to… | Do this |
|
||
|---|---|
|
||
| Change gaps / colors / rounding / fonts | `nomarchy-state-sync set …` or `apply` |
|
||
| Change input / misc / monitor / animations / terminal chrome | plain assignment in `home.nix` |
|
||
| Arrange monitors declaratively | `nomarchy.monitors` (values via `nwg-displays`) |
|
||
| Add keybinds / autostarts | add to the `bind` / `exec-once` list (concatenates) |
|
||
| Replace all keybinds | `bind = lib.mkForce [ … ]` |
|
||
| Hardcode an appearance value against the theme | `lib.mkForce` in `home.nix` |
|
||
| Drop a whole component | `nomarchy.<component>.enable = false` |
|
||
| Raw Hyprland lines | `wayland.windowManager.hyprland.extraConfig` |
|