resize() and resize_and_move() gain an animate flag — when True, skip the no_anim setprop so Hyprland's windowsIn/popin animation plays through. Popout passes animate=_first_fit_pending so the first fit after open animates; subsequent navigation fits still suppress anim to avoid resize flicker. behavior change: popout now animates in on open instead of snapping.
110 lines
3.7 KiB
Markdown
110 lines
3.7 KiB
Markdown
# Hyprland integration
|
|
|
|
I daily-drive booru-viewer on Hyprland and I've baked in my own opinions
|
|
on how the app should behave there. By default, a handful of `hyprctl`
|
|
dispatches run at runtime to:
|
|
|
|
- Restore the main window's last floating mode + dimensions on launch
|
|
- Restore the popout's position and keep it anchored to its configured
|
|
anchor point (center or any corner) as its content resizes during
|
|
navigation, and suppress F11 / fullscreen-transition flicker
|
|
- "Prime" Hyprland's per-window floating cache at startup so a mid-session
|
|
toggle to floating uses your saved dimensions
|
|
- Lock the popout's aspect ratio to its content so you can't accidentally
|
|
stretch mpv playback by dragging the popout corner
|
|
|
|
## Opting out
|
|
|
|
If you're a ricer with your own `windowrule`s targeting
|
|
`class:^(booru-viewer)$` and you'd rather the app keep its hands off your
|
|
setup, there are two independent opt-out env vars:
|
|
|
|
- **`BOORU_VIEWER_NO_HYPR_RULES=1`** — disables every in-code hyprctl
|
|
dispatch *except* the popout's `keep_aspect_ratio` lock. Use this if
|
|
you want app-side window management out of the way but you still want
|
|
the popout to size itself to its content.
|
|
- **`BOORU_VIEWER_NO_POPOUT_ASPECT_LOCK=1`** — independently disables
|
|
the popout's aspect ratio enforcement. Useful if you want to drag the
|
|
popout to whatever shape you like (square, panoramic, monitor-aspect,
|
|
whatever) and accept that mpv playback will letterbox or stretch to
|
|
match.
|
|
|
|
For the full hands-off experience, set both:
|
|
|
|
```ini
|
|
[Desktop Entry]
|
|
Name=booru-viewer
|
|
Exec=env BOORU_VIEWER_NO_HYPR_RULES=1 BOORU_VIEWER_NO_POPOUT_ASPECT_LOCK=1 /path/to/booru-viewer/.venv/bin/booru-viewer
|
|
Icon=/path/to/booru-viewer/icon.png
|
|
Type=Application
|
|
Categories=Graphics;
|
|
```
|
|
|
|
Or for one-off launches from a shell:
|
|
|
|
```bash
|
|
BOORU_VIEWER_NO_HYPR_RULES=1 booru-viewer
|
|
```
|
|
|
|
## Writing your own rules
|
|
|
|
If you're running with `BOORU_VIEWER_NO_HYPR_RULES=1` (or layering rules
|
|
on top of the defaults), here's the reference.
|
|
|
|
### Window identity
|
|
|
|
- Main window — class `booru-viewer`
|
|
- Popout — class `booru-viewer`, title `booru-viewer — Popout`
|
|
|
|
> ⚠ The popout title uses an em dash (`—`, U+2014), not a hyphen. A rule
|
|
> like `match:title = ^booru-viewer - Popout$` will silently match
|
|
> nothing. Either paste the em dash verbatim or match the tail:
|
|
> `match:title = Popout$`.
|
|
|
|
### Example rules
|
|
|
|
```ini
|
|
# Float the popout with aspect-locked resize and no animation flicker
|
|
windowrule {
|
|
match:class = ^(booru-viewer)$
|
|
match:title = Popout$
|
|
float = yes
|
|
keep_aspect_ratio = on
|
|
no_anim = on
|
|
}
|
|
|
|
# Per-window scroll factor if your global is too aggressive
|
|
windowrule {
|
|
match:class = ^(booru-viewer)$
|
|
match:title = Popout$
|
|
scroll_mouse = 0.65
|
|
}
|
|
```
|
|
|
|
### What the env vars actually disable
|
|
|
|
`BOORU_VIEWER_NO_HYPR_RULES=1` suppresses the in-code calls to:
|
|
|
|
- `dispatch resizeactive` / `moveactive` batches that restore saved
|
|
popout geometry
|
|
- `dispatch togglefloating` on the main window at launch
|
|
- `dispatch setprop address:<addr> no_anim 1` applied during popout
|
|
transitions (skipped on the first fit after open so Hyprland's
|
|
`windowsIn` / `popin` animation can play — subsequent navigation
|
|
fits still suppress anim to avoid resize flicker)
|
|
- The startup "prime" sequence that warms Hyprland's per-window
|
|
floating cache
|
|
|
|
`BOORU_VIEWER_NO_POPOUT_ASPECT_LOCK=1` suppresses only
|
|
`dispatch setprop address:<addr> keep_aspect_ratio 1` on the popout.
|
|
Everything else still runs.
|
|
|
|
Read-only queries (`hyprctl clients -j`, `hyprctl monitors -j`) always
|
|
run regardless — the app needs them to know where it is.
|
|
|
|
### Hyprland requirements
|
|
|
|
The `keep_aspect_ratio` windowrule and `dispatch setprop
|
|
keep_aspect_ratio` both require a recent Hyprland. On older builds the
|
|
aspect lock is silently a no-op.
|