Show HN: I reverse engineered Apple's video wallpapers
Summary
An open-source macOS app that uses Apple's private WallpaperExtensionKit to allow custom video wallpapers, featuring gapless looping, multi-display support, and power-aware playback.
View Cached Full Text
Cached at: 05/21/26, 06:23 AM
kageroumado/phosphene
Source: https://github.com/kageroumado/phosphene
Phosphene
A video wallpaper engine for macOS Tahoe.
Phosphene is a menu bar app + wallpaper extension that plays your own video files as the macOS desktop and lock-screen wallpaper. It plugs into the system’s native wallpaper picker, so videos appear alongside Apple’s built-in Aerials in System Settings → Wallpaper.
It is built on top of Apple’s private WallpaperExtensionKit framework — the same one Apple’s own Aerials use — which means playback runs out-of-process, survives app quits, and integrates with the OS-level lock-screen / idle / sleep lifecycle.
⚠️ Private framework. Phosphene loads
WallpaperExtensionKitviadlopenand uses Mirror-based runtime introspection to talk to its XPC types. Apple could change this at any major OS release. The project tracks macOS 26 (Tahoe).
Features
- Bring your own videos. Import MP4 / MOV / any AVFoundation-readable file. They show up in the system wallpaper picker.
- Gapless looping. Frame-accurate loops by offsetting PTS/DTS across loop boundaries — no flush, no stutter.
- Multi-display + per-Space selections. Different wallpapers per display, persisted by macOS.
- Power-aware playback. A graduated
PlaybackPolicyreduces work or pauses entirely based on thermal state, battery level, on-battery vs AC, Game Mode, and presentation mode (active / locked / idle). - Smooth lock-screen ramp. When Only on Lock Screen is enabled, the wallpaper eases in/out with a cubic curve as you lock and unlock, matching Apple’s own Aerials behavior.
- Pause when occluded. Detects when every display is fully covered by windows and pauses rendering until the desktop is visible again.
- Adaptive variants. Optionally pre-render lower-resolution / lower-fps variants of a video; the renderer swaps to the cheapest variant that satisfies the current policy at each loop boundary.
- Menu bar control. Preview the current wallpaper, toggle pause, switch displays, configure behavior, launch at login.
Requirements
- macOS Tahoe (26.0+). Phosphene depends on the Wallpaper extension point introduced in macOS 14 but uses Tahoe-only SwiftUI and
glassEffect()APIs. - Apple Silicon. Targets
arm64-apple-macos26.0. - Xcode 17+ to build, with Swift 6 strict concurrency enabled.
Building
git clone https://github.com/<you>/phosphene
cd phosphene
open Phosphene.xcodeproj
In Xcode, select the Phosphene scheme and Run. The project uses synchronized filesystem groups, so adding/removing files in Phosphene/ or PhospheneExtension/ requires no pbxproj edits.
You’ll need to set a development team for code signing. The wallpaper extension is embedded into the app bundle and registered with the system when the app launches.
Using a video wallpaper
- Launch Phosphene. Use the menu bar icon to Manage Library and add one or more videos.
- Open System Settings → Wallpaper. Phosphene’s videos appear under their own collection.
- Pick a video. macOS handles the actual wallpaper assignment — Phosphene’s extension provides the frames.
Architecture
┌─────────────────────────┐ ┌──────────────────────────────┐
│ Phosphene.app │ │ PhospheneExtension.appex │
│ (menu bar UI) │ │ (host: WallpaperAgent) │
│ │ │ │
│ • Library management │ Darwin │ • XPC handler │
│ • Per-video metadata │ ──────▶ │ • AVSampleBufferDisplayLayer │
│ • Optimization (HEVC) │ notif. │ • Power / thermal monitor │
│ • Preferences │ │ • Snapshot generator │
└─────────────────────────┘ └──────────────────────────────┘
│ │
└──────────────┬───────────────┘
▼
Shared App Group container
(~/Library/Group Containers/glass.kagerou.phosphene)
• Video library + variants
• WallpaperPrefs.plist
• BMP snapshot cache
App side (Phosphene/) — SwiftUI menu-bar app. Manages the on-disk video library, transcodes optional lower-resolution variants via VideoOptimizationService, exposes preferences, and posts a Darwin notification when the library changes.
Extension side (PhospheneExtension/) — runs inside the system WallpaperAgent process when a Phosphene wallpaper is active. Loads WallpaperExtensionKit.framework at runtime, registers as a wallpaper provider, and renders frames into a remote CAContext via AVSampleBufferDisplayLayer. It receives XPC acquire / update / invalidate / snapshot calls from WallpaperAgent and routes presentation-mode changes through PlaybackPolicy.
PlaybackPolicy is the single source of truth for playback behavior. Inputs (thermal state, battery, presentation mode, user pause, occlusion, etc.) collapse to one of full / reduced / minimal / paused. The renderer applies the policy on every state change.
VideoRenderer owns the decode pipeline. Instead of AVPlayerLayer — which silently fails inside a remote CAContext — it drives AVSampleBufferDisplayLayer manually: one AVAssetReader for the current loop, a preloaded one for the next, and a PTS offset that grows across loops to keep the timeline monotonically increasing. Result is glitch-free looping without flushing the renderer.
Quirks worth knowing
WallpaperSnapshotXPCswizzle. The system’s snapshot encoder checkstype(of: coder) == NSXPCCoder.self, but the real coder is a subclass. Without the runtime swizzle inPhospheneExtension.swift, snapshots silently encode to nothing and you get a grey lock screen during transitions.- Mirror-based XPC parsing. Apple’s request types (
WallpaperCreationRequestXPCetc.) aren’t part of any public SDK header. The extension reads them viaMirrorreflection. If Apple renames fields, expect surgical breakage. - Variants are advisory. A “1080p@30” variant won’t be selected if Power-Monitor thinks we’re on AC and idle —
PlaybackPolicyalways picks the highest tier that’s still allowed.
License
MIT. Do whatever you want, no warranty.
Acknowledgements
Built by @kageroumado. Phosphene was originally a commercial project; it’s open-source now because the market for “video wallpaper apps on macOS” turned out to be more crowded than it looked.
Similar Articles
Watching sunsets
Fabien Sanglard describes his attempt to recreate the Horizon live wallpaper after migrating to a Pixel 7, using a simple WallpaperService that swaps screen captures based on battery level.
Show HN: Davit, a Apple Containers UI
Davit is a free, open-source native macOS app built with SwiftUI that provides a UI for Apple's container platform on Apple silicon, allowing users to run Linux containers without Docker Desktop.
Show HN: Inkwash, a watercolor sketching app and explanation
Inkwash is a WebGL2-based watercolor sketching app that simulates pigment flow and paper interaction, generated with Claude Fable 5. The article explains the technical pipeline of floating-point textures and shaders behind the realistic watercolor effect.
@emilkowalski: New skill: /apple-design Apple’s WWDC videos are a goldmine of knowledge. I’ve combed through my favorite ones and came…
A curated set of 17 design and motion principles distilled from Apple's WWDC videos, packaged as a reusable skill for design engineers to review and improve UI animations and interfaces.
Show HN: We missed Winamp, so we built an audio player for macOS
A new macOS audio player called 180db is launched, inspired by Winamp and designed for musicians and DJs, with features like pitch change and layout customization.