Swift CLI to control iPhone via macOS iPhone Mirroring. See also AGENTS.md for cross-agent instructions.
swift build # debug
swift build -c release # release
swift test # tests
Sources/IPhoneBaseCore/— library: WindowManager, ScreenCapture, OCREngine, InputInjector, HIDKeyMap, ActionResultSources/iphonebase/— CLI entry point + Commands/skills/iphonebase/— OpenClaw skill (SKILL.md)
- Create
Sources/iphonebase/Commands/XxxCommand.swift - Implement
AsyncParsableCommand(orParsableCommandfor sync-only) - Add
XxxCommand.selfto subcommands array inIPhoneBase.swift - Include
--jsonflag for structured output - Update
skills/iphonebase/SKILL.md
- Import order: ArgumentParser, IPhoneBaseCore, Foundation
- All commands support
--jsonvia sharedActionResult<T>envelope - Results to stdout, debug/verbose to stderr
- InputInjector pattern:
connect()thendefer { disconnect() }; setwindowBoundsfor coordinate validation - Call
wm.bringToFront()before any input injection - Errors: typed enums with
CustomStringConvertible; throwExitCode.failurefor user errors
- Perceive → Reason → Act:
perceivegives AI eyes, action commands are hands, AI does all reasoning - No OCR-based decision-making in action commands — agent provides coordinates from
perceive - Action commands are "dumb executors":
tap x y,swipe up,type "text"
- ScreenCapture captures at 2x retina resolution
- OCR (Vision) returns normalized coords with bottom-left origin — must invert Y
perceivescales all coordinates to window-relative screen pointstap x yexpects window-relative screen points — coordinates fromperceiveflow directly- All InputInjector operations use absolute screen coordinates (
window.bounds.origin + offset)
- iPhone Mirroring blocks CGEvent clicks — only Karabiner virtual HID works
- Tap sequence: CGWarp cursor → nudge-sync (3x 1px/-1px) → click via HID
- Timing delays (
usleep) are tuned values, not arbitrary - Karabiner daemon must be running (not just installed)
- Imperative mood ("Add feature" not "Added feature")
- First line under 72 characters