Skip to content

Keprun/YeelightBar

Repository files navigation

YeelightBar

macOS 13+ Swift 5.9 SwiftUI License MIT LAN only Stars

English · Русский · 中文 · فارسی · Español · العربية

A native macOS app for Yeelight LAN lamps and Keychron keyboards — screen-sync ambilight
(multi-display + per-segment addressable strips), music reactivity, scenes, and multi-lamp groups.
Built for the Screen Light Bar Pro, it drives plain RGB strips & bulbs too.

No cloud · no account · everything over your LAN.

Screenshots

Keychron keyboard ambilight
Keychron keyboard ambilight — any Keychron QMK/VIA keyboard lights up in the colour of a chosen screen zone, over USB.

Screen-sync ambilight
Screen-sync ambilight — each lamp samples its own display & region; addressable strips map per-segment, all over a live monitor map.

Themes & settings Gamer-brand themes
Themes, appearance & language — four palettes, Light / Dark / Auto, 7 languages. Four dynamic themes — Venom · Crimson · Forge · Solar, each day/night.
Light & ambient Device groups
Light & ambient — independent front-white & ambient-RGB channels. Device groups — multi-select lamps, controlled together.
Scene editor About
Scenes — ready-made presets plus custom scenes you save, apply & delete. About — version, features & links to the project on GitHub.

Menu-bar quick controls
Menu-bar quick controls — power, brightness, ambient & effects without opening the window.

UI mockups rendered to scale from the app's actual layout & theme.

Features

  • Full control — power, front white (brightness + colour temperature), ambient RGB, ready-made scenes.
  • Group / "mix" control — select several lamps and drive them together; each lamp speaks its own protocol dialect (the bar has a separate ambient bg channel, strips don't).
  • Screen-sync ambilight — ScreenCaptureKit samples your screen and streams the colour to the lamp's ambient channel at ~20 Hz over a UDP session.
    • Per-lamp display + region: in a multi-monitor setup, each lamp can sample a different display and a different region of it (top / bottom / left / right / full) — e.g. the bar takes the top of your main screen while an under-desk strip takes the bottom of another.
    • Resolution-independent capture (works on 16:9, 4K, portrait, and 32:9 ultrawides alike).
    • Live preview: a screen-shaped panel per display showing exactly which region each lamp samples, in its live colour.
  • Music reactivity — captures system audio (no microphone), splits it into bass/mid/treble with IIR filters.
    • Beat mode pumps brightness on the kick; Spectrum mode maps bass→red / mid→green / treble→blue.
  • Keychron keyboard ambilight — drives the RGB matrix of any Keychron QMK/VIA keyboard (over USB) from the same screen-sync or music engine, choosing which screen zone it samples. Model is auto-detected (matched by raw-HID, not a hard-coded PID), colour goes to both the per-key matrix and underglow channels, and nothing is written to EEPROM (no wear). Reads battery % over the cable on firmware that reports it.
  • Scenes — save the current lamp colour as a named scene and re-apply it in one tap; ready-made presets plus a custom "My scenes" grid that persists across restarts.
  • Quality-of-life — an eyedropper to pick any on-screen colour as the ambient, idle dimming that fades the lamps when you step away and restores the running effect when you're back, launch at login, a scene-cut snap and letterbox (black-bar) skip for the ambilight.
  • Gamer-brand themes — Venom (green) · Crimson (red) · Forge (amber) · Solar (orange), each with full light + dark variants that follow the macOS day/night switch. Live in-app theme, appearance (Light / Dark / Auto) and language (7 languages) pickers in Settings.
  • Two surfaces — a compact menu-bar panel for quick tweaks and a full resizable borderless window (NavigationSplitView with a custom chrome) for setup.
  • Robust on a real network — auto-discovery (SSDP + active subnet scan), reconnect on DHCP IP changes, and serialized control so the lamp never drops a command from concurrent connections.

Requirements

  • macOS 13 (Ventura) or newer, Apple Silicon or Intel.
  • Yeelight device(s) with LAN Control enabled (Yeelight app → device → LAN Control).
  • Screen Recording permission (System Settings → Privacy & Security) for screen-sync and music modes.

Build & run

Xcode

Open YeelightBar.xcodeproj and run the YeelightBar scheme (⌘R). The project is generated from project.yml with XcodeGen; run xcodegen generate after editing the spec.

Swift Package Manager (no Xcode needed)

swift build
./scripts/bundle.sh          # assembles + signs build/YeelightBar.app
open build/YeelightBar.app

scripts/setup-signing.sh creates a stable self-signed code-signing identity so the Screen-Recording grant survives rebuilds (an ad-hoc signature changes every build and would re-trigger the permission prompt).

yeectl — command-line tool

A small CLI for testing and scripting the protocol:

swift run yeectl discover                 # SSDP
swift run yeectl auto                      # SSDP, fall back to active subnet scan
swift run yeectl state   <ip>
swift run yeectl on|off  <ip>
swift run yeectl bright  <ip> <0-100>
swift run yeectl ct      <ip> <1700-6500>
swift run yeectl rgb     <ip> <hex e.g. FF8800>   # ambient / bg channel
swift run yeectl rainbow <ip> [seconds]           # UDP 20 Hz streaming test

Architecture

Sources/
  YeelightKit/            # transport-only library, no UI
    Yeelight.swift        # TCP 55443 JSON control + UDP 55444 streaming session
    Discovery.swift       # SSDP multicast discovery
    Scan.swift            # active subnet scan + manual-IP validation
  yeectl/                 # CLI
  YeelightBarApp/         # SwiftUI app
    LampController.swift   # @MainActor store: discovery, group control, sync orchestration
    ScreenSyncEngine.swift # multi-display capture → per-(display,region) colour → UDP fan-out
    MusicSyncEngine.swift  # system-audio capture → beat/spectrum → UDP fan-out
    FullView.swift / MenuPanelView.swift

The Yeelight LAN protocol (TCP control, the UDP streaming handshake, the bar's quirky main_power/bg_power channels) is documented in PROTOCOL.md.

Notes on the Screen Light Bar Pro

This lamp has two independent channels — front white (set_power / main_power) and ambient RGB (bg_set_power / bg_set_rgb) — so you can run "ambient only". Its power property is unreliable (sticks at on even when the front is dark); the app reads main_power instead. Plain strips have a single channel and reject the bar-only dev_toggle, so control is dispatched per device type.

License

MIT — not affiliated with or endorsed by Yeelight / Xiaomi.

About

Native macOS app for Yeelight LAN lamps — screen-sync ambilight (multi-display + per-segment addressable strips), music reactivity, multi-lamp groups. Razer-styled SwiftUI.

Topics

Resources

License

Stars

0 stars

Watchers

0 watching

Forks

Packages

 
 
 

Contributors