The studio's signature Texas Hill Country dusk, living on your desktop. A fully animated wallpaper that follows the real sun and the real moon — golden afternoon → signature dusk → near-black starry night with fireflies and the Milky Way → rose dawn — plus a complete Windows brand kit: transparent taskbar, dark + gold accent theme, terminal colors, notification chimes, icons, and an optional keyboard-driven search/navigation stack.
| Dusk | Night | Day |
|---|---|---|
![]() |
![]() |
![]() |
git clone https://github.com/trimmdev/lhs-desktop-theme
cd lhs-desktop-theme
.\install.ps1 # wallpaper + taskbar + theme + terminal + chimes (opt-in)
.\install.ps1 -AutoAdjust # ...and keep the wallpaper fitted as monitors change
.\install.ps1 -NavStack # ...plus Everything, PowerToys FancyZones, Flow LauncherThere is a macOS port in macos/ — the same wallpaper file, so the sun
and the moon behave identically. It is wallpaper-first: the default install changes
exactly one thing, the desktop picture. Terminal schemes, launcher themes, the gold
accent and the studio icon are each behind their own opt-in flag.
cd macos
./install.sh --dry-run # prints every action, changes nothing — start here
./install.sh
./install.sh --auto-adjust # ...and keep it fitted as displays changeOptional extras: macos/screensaver/ runs the same living
scene as the screen saver, so an idle or locked Mac shows the animated dusk.
The macOS side was written without a Mac to test on. The wallpaper itself is a self-contained web page and is genuinely cross-platform; anything that touches system settings is best-effort and is documented as such. Run
--dry-runfirst.
Everything is user-level and reversible. One or two UAC prompts may appear for app installers. See the end-of-install output for the three optional manual finishing touches (avatar, gold pointer, lock screen).
An animated walkthrough of every feature and shortcut lives at docs/guide.html —
open it in any browser after cloning.
macos/— the macOS port. Shares this exact wallpaper file rather than copying it, so the two platforms cannot drift. Wallpaper-first installer, per-display exact fitting and a display watcher (macos/tools/), Liberty Hill Dusk schemes for six terminal emulators, Raycast + Alfred themes, an.icns, and an optional animated screen saver. Seemacos/README.md.wallpaper/lhs-dusk.html— the living wallpaper. Self-contained single file (Sora font embedded, zero network calls). Canvas-rendered at native resolution on any monitor: noise-generated ridgelines, dithered sky gradient, aerially-shaded hills, backlit cloud decks, god-rays, drifting valley mist, rising embers that become fireflies at night, a dense star field + Milky Way + shooting stars, film grain, and the Lone Star + wordmark lockup. 30fps capped, ~0.2% of one CPU core per monitor (measured), auto-pauses under fullscreen apps (via Lively).stills/— pixel-perfect PNG renders covering every standard aspect family (16:9 1280×720 → 8K, 16:10, 4:3, 5:4, 3:2, 21:9 and 32:9 ultrawides, 5K, portrait)- dawn/day/night variants at common sizes. Use as static wallpapers or lock screens. These are the offline fallback ladder — see Fits any monitor, which renders exact matches for resolutions that aren't in the ladder at all.
tools/— the resolution machinery:Set-LhsWallpaper.ps1(fit the scene to the attached monitors),Watch-LhsDisplays.ps1+Register-LhsDisplayWatcher.ps1(react to layout changes),LhsRender.psm1(render a still at any size with no dependencies),LhsDisplay.psm1(physical-pixel monitor enumeration), andstandard-resolutions.json(the shared catalog).terminal/liberty-hill-dusk.json— Windows Terminal scheme (ink background, parchment text, gold cursor, ember/verdant/sky/plum ANSI ramp).flow-launcher/Liberty Hill Dusk.xaml— Flow Launcher theme (translucent ink glass, gold caret + selection).fancyzones/— PowerToys FancyZones config: gold snap highlights + three studio layouts (LHS Ultrawide 30-40-30, LHS Quad, LHS Halves).icons/— multi-sizelhs.ico(Lone Star mark), account avatar, OEM logo.sounds/— two short studio chimes (finish + attention), wired to the Windows sound eventsSystemAsterisk,SystemExclamation, andNotification.Default.
The wallpaper is a canvas scene, not a photograph, so there is no reason to ever show you a stretched one. Every monitor gets a still rendered at its own native resolution — including resolutions nobody has ever pre-baked. Both platforms, with the same guarantee and no shared limitation.
# Windows
.\install.ps1 -AutoAdjust # install + watch for changes
.\tools\Set-LhsWallpaper.ps1 # re-fit right now
.\tools\Set-LhsWallpaper.ps1 -Mood night # ...in a different mood
.\tools\Register-LhsDisplayWatcher.ps1 -Remove # stop watching# macOS — see macos/README.md for the detail
./install.sh --auto-adjust
./tools/lhs-fit-wallpaper.sh
./tools/install-display-watcher.sh --remove| Windows | macOS | |
|---|---|---|
| Exact native render per monitor | ✅ | ✅ |
| Renders resolutions never pre-baked | ✅ | ✅ |
| Re-fits on resolution / hotplug change | ✅ logon task | ✅ LaunchAgent |
| Renderer dependency | Edge (ships with Windows) | /usr/bin/perl + any Chromium-family browser |
| Multi-monitor method | one span bitmap at physical origins | per-display (setDesktopImageURL:forScreen:) |
| No-browser fallback | aspect-scored cover-crop | aspect-scored shipped still |
What the watcher reacts to. Change a resolution, rotate a screen, plug in a
projector, dock or undock a laptop, or swap monitors entirely — the wallpaper is rebuilt
for the new layout within a few seconds. It runs as a hidden per-user logon task
(Liberty Hill Display Watcher), logging to
%LOCALAPPDATA%\Liberty Hill Studios\display-watcher.log.
How a new resolution gets a wallpaper. Cache → shipped stills/ ladder → render it
natively → (only if the machine has no Chromium-family browser at all) cover-crop the
nearest shipped still. The renderer drives Edge — which ships with Windows — over the
DevTools Protocol, so no node, npm or Playwright is required on the target machine.
A fresh 4K bake takes about three seconds and is cached forever after. macOS does the
same thing through macos/tools/lhs-render-still.pl, using only /usr/bin/perl and core
modules.
The one-shot
msedge --headless --screenshotswitch is not used, and can't be: it fires at the load event, before the scene has painted a frame, and reliably produces a black PNG. The scene raiseswindow.__readyonce its deterministic frame is on the canvas, and the renderer waits for that.
Multi-monitor. Each monitor gets its own complete composition — its own sun, its own
lockup — and they are composed into one span image laid out at the monitors' real
physical origins, negative ones included. Mixed resolutions, mixed refresh rates and
mixed DPI all work; monitors are enumerated in physical pixels via
EnumDisplaySettings, because Screen.AllScreens reports logical ones and would quietly
bake a 2560×1440 still for a 4K panel running at 150%.
The static image tracks the real sun too. -Mood auto (the default) asks the scene
what the sky is doing right now and bakes that. This matters because the static image is
what you actually see whenever the living wallpaper isn't drawing — Lively pauses under
fullscreen apps, and it hasn't started yet at logon. Before this, that fallback was frozen
at dusk forever, so a midday game session dropped you onto a sunset. The mood comes from
the page's own solarAltitude() / moodWeights() over CDP; the solar maths is deliberately
not reimplemented in PowerShell, because a second copy would drift from the verified
one. The watcher re-checks every 20 minutes, and a check that finds nothing new writes
nothing. Pin it with -Mood dusk (or dawn/day/night) if you'd rather it never moved.
Pre-baking (optional). install.ps1 -PreRenderStandard, or
.\tools\Set-LhsWallpaper.ps1 -PreRender standard, renders every resolution in
tools/standard-resolutions.json into the local cache
so even the first paint on a brand-new monitor is instant. It is not required — the
watcher renders on demand.
To regenerate the committed ladder after changing the scene:
node tools/bake-stills.mjs --shipped (or --all, or 3440x1440 --moods dusk,dawn).
The scene doesn't just interpolate between times of day — it solves for where the sun and moon actually are.
- Sun — altitude from the USNO/NOAA low-precision solar equations. Sunrise, golden hour, civil twilight and night follow the true sun for the date, so they drift with the seasons instead of firing at hardcoded clock times. The disc is clipped to the sky, so the ridge genuinely occludes it as it rises and sets.
- Moon — position and phase from abridged lunar theory (Meeus ch. 47, with the evection, variation and annual-equation terms). Verified at 0.38 minutes of error per lunation across 618 lunations / 50 years. The terminator is a real projected ellipse, the unlit limb carries earthshine, the maria rotate with the parallactic angle, and the disc grows and shrinks with true perigee/apogee distance.
- Sunrise ≠ sunset — dawn gets its own cooler, rosier palette. Overnight the air settles, so morning runs violet → rose → peach where evening runs ember.
- Late-hour comfort — after ~22:30 the finished frame is eased down and warmed, deepest through the small hours, lifting before dawn.
Set your own location — the site is a single constant near the top of
wallpaper/lhs-dusk.html:
const SITE = { lat: 30.6624, lon: -97.9247, name: "Liberty Hill, Texas" };One deliberate stylization: the sun is pinned to the centre of the frame rather than placed at its true azimuth, because the composition nests it in a dip baked into the far ridge, under the wordmark. The moon does use its true azimuth. So each body's own position is real, but the on-screen distance between them is not — at a first quarter they are 97° apart in the real sky while appearing close together here.
| Param | Effect |
|---|---|
?mood=day|dusk|dawn|night |
Pin a mood instead of following the real sun |
?at=2026-07-21T21:30 |
Run the scene at another moment (local time) |
?at=+9 / ?at=-3.5 |
...or a signed hour offset from now |
?speed=1440 |
Run the clock N× faster — 1440 puts a full day in one minute, with a time/sun/moon readout |
?still=1 |
One deterministic frame, for baking PNGs |
Gold #E8A13A is an accent, never a background: cursors, highlights, selection,
icons — small elements only. Surfaces stay translucent ink (#0A0807). Standard system
affordances (drive icons, capacity bars) are never reskinned.
Lively Wallpaper · TranslucentTB · PowerToys · Everything · Flow Launcher — all free, all excellent. Wordmark font: Sora (SIL Open Font License), embedded as base64.
| Token | Hex | Token | Hex | |
|---|---|---|---|---|
| ink-950 | #0a0807 |
gold-400 | #e8a13a |
|
| parchment | #f5ecd9 |
gold-300 | #ecbe5b |
|
| ember-400 | #d4542b |
gold-600 | #b3661f |
Mirrors liberty-hill-studios/src/lib/palette.ts — change them together or the dusk
drifts from the site.
Built with care at Liberty Hill Studios. 🌵⭐



