@arach/lattices 0.1.0 → 0.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (39) hide show
  1. package/README.md +28 -28
  2. package/app/Sources/ActionRow.swift +61 -0
  3. package/app/Sources/App.swift +1 -40
  4. package/app/Sources/AppDelegate.swift +154 -24
  5. package/app/Sources/CheatSheetHUD.swift +1 -0
  6. package/app/Sources/CommandModeState.swift +40 -19
  7. package/app/Sources/CommandModeView.swift +27 -2
  8. package/app/Sources/DaemonServer.swift +8 -0
  9. package/app/Sources/DiagnosticLog.swift +19 -1
  10. package/app/Sources/EventBus.swift +1 -0
  11. package/app/Sources/HotkeyManager.swift +1 -0
  12. package/app/Sources/HotkeyStore.swift +9 -1
  13. package/app/Sources/LatticesApi.swift +210 -0
  14. package/app/Sources/MainView.swift +46 -86
  15. package/app/Sources/MainWindow.swift +13 -0
  16. package/app/Sources/OcrModel.swift +309 -0
  17. package/app/Sources/OcrStore.swift +295 -0
  18. package/app/Sources/OmniSearchState.swift +283 -0
  19. package/app/Sources/OmniSearchView.swift +288 -0
  20. package/app/Sources/OmniSearchWindow.swift +105 -0
  21. package/app/Sources/PaletteCommand.swift +11 -1
  22. package/app/Sources/PermissionChecker.swift +12 -2
  23. package/app/Sources/Preferences.swift +44 -0
  24. package/app/Sources/ScreenMapState.swift +7 -17
  25. package/app/Sources/ScreenMapView.swift +3 -0
  26. package/app/Sources/SettingsView.swift +534 -122
  27. package/app/Sources/Theme.swift +39 -0
  28. package/app/Sources/WindowTiler.swift +59 -56
  29. package/bin/lattices-app.js +23 -7
  30. package/bin/lattices.js +123 -0
  31. package/docs/api.md +390 -249
  32. package/docs/app.md +75 -28
  33. package/docs/concepts.md +45 -136
  34. package/docs/config.md +8 -7
  35. package/docs/layers.md +16 -18
  36. package/docs/ocr.md +185 -0
  37. package/docs/overview.md +39 -34
  38. package/docs/quickstart.md +34 -35
  39. package/package.json +6 -2
package/docs/ocr.md ADDED
@@ -0,0 +1,185 @@
1
+ ---
2
+ title: Screen OCR & Search
3
+ description: Vision-powered screen reading with full-text search for agents
4
+ order: 3.5
5
+ ---
6
+
7
+ The menu bar app reads text from visible windows using Apple's Vision
8
+ framework and stores results in a local SQLite database with FTS5
9
+ full-text search. Agents can use this to "see" what's on screen.
10
+
11
+ ## Enabling OCR
12
+
13
+ Open **Settings** (via command palette or gear icon) and toggle
14
+ **Search & OCR** on. OCR is disabled by default.
15
+
16
+ ### Accuracy modes
17
+
18
+ | Mode | Description |
19
+ |------|-------------|
20
+ | **Accurate** (default) | Higher quality recognition, slower processing |
21
+ | **Fast** | Lower latency, reduced accuracy |
22
+
23
+ Both modes use `VNRecognizeTextRequest` with language correction enabled.
24
+
25
+ ## How scanning works
26
+
27
+ The app runs two scan schedules:
28
+
29
+ | Schedule | Interval | Window limit | Purpose |
30
+ |----------|----------|-------------|---------|
31
+ | **Quick scan** | 60 seconds | Top 5 windows | Keep recent content fresh |
32
+ | **Deep scan** | 2 hours | Up to 15 windows | Catch less-active windows |
33
+
34
+ Both intervals and limits are configurable in Settings.
35
+
36
+ ### Change detection
37
+
38
+ Before running OCR on a window, the app captures the window image and
39
+ computes a SHA-256 hash of the pixel data. If the hash matches the
40
+ previous scan, the cached result is reused. No Vision processing needed.
41
+
42
+ This keeps CPU usage low when windows haven't changed. A 100ms throttle
43
+ between windows further limits processing bursts.
44
+
45
+ ## Browsing results
46
+
47
+ The **Recent Captures** section in Settings shows OCR results grouped by
48
+ app. Each entry displays the window title, recognized text preview, and
49
+ timestamp.
50
+
51
+ ## Searching
52
+
53
+ ### From the command palette
54
+
55
+ The OmniSearch bar (Cmd+Shift+M) searches OCR content alongside windows,
56
+ projects, and sessions. Matches show as "Screen Text" results with
57
+ contextual snippets.
58
+
59
+ ### From the CLI
60
+
61
+ ```bash
62
+ # View current OCR snapshot
63
+ lattices ocr
64
+
65
+ # Search OCR history
66
+ lattices ocr search "error OR failed"
67
+
68
+ # Trigger an immediate deep scan
69
+ lattices ocr scan
70
+
71
+ # View OCR history for a specific window ID
72
+ lattices ocr history 12345
73
+ ```
74
+
75
+ ### From the daemon API
76
+
77
+ Agents can query OCR data through four daemon methods:
78
+
79
+ | Method | Description |
80
+ |--------|-------------|
81
+ | `ocr.snapshot` | Current OCR results for all visible windows |
82
+ | `ocr.search` | Full-text search across history (FTS5 syntax) |
83
+ | `ocr.history` | Timeline of OCR results for a specific window |
84
+ | `ocr.scan` | Trigger an immediate deep scan |
85
+
86
+ #### `ocr.snapshot`
87
+
88
+ Returns the latest OCR results for all on-screen windows.
89
+
90
+ ```js
91
+ import { daemonCall } from '@arach/lattices/daemon-client'
92
+
93
+ const snapshot = await daemonCall('ocr.snapshot')
94
+ // [{ wid, app, title, frame, fullText, blocks, timestamp }, ...]
95
+ ```
96
+
97
+ Each result includes:
98
+ - `wid` — window ID
99
+ - `app` — application name
100
+ - `title` — window title
101
+ - `frame` — `{ x, y, w, h }` screen position
102
+ - `fullText` — all recognized text concatenated
103
+ - `blocks` — individual text blocks with `{ text, confidence, x, y, w, h }`
104
+ - `timestamp` — Unix timestamp of the scan
105
+
106
+ #### `ocr.search`
107
+
108
+ Full-text search across OCR history using FTS5 query syntax.
109
+
110
+ ```js
111
+ const results = await daemonCall('ocr.search', {
112
+ query: 'error OR failed', // FTS5 query (required)
113
+ app: 'Terminal', // filter by app name (optional)
114
+ limit: 50, // max results (optional, default 50)
115
+ live: false // search in-memory snapshot instead of history (optional)
116
+ })
117
+ // [{ id, wid, app, title, frame, fullText, snippet, timestamp }, ...]
118
+ ```
119
+
120
+ The `snippet` field contains FTS5-highlighted text with `«` and `»`
121
+ delimiters around matched terms.
122
+
123
+ #### `ocr.history`
124
+
125
+ Get the OCR content timeline for a specific window.
126
+
127
+ ```js
128
+ const history = await daemonCall('ocr.history', {
129
+ wid: 12345, // window ID (required)
130
+ limit: 50 // max results (optional, default 50)
131
+ })
132
+ ```
133
+
134
+ #### `ocr.scan`
135
+
136
+ Trigger an immediate deep scan (all visible windows up to the deep limit).
137
+
138
+ ```js
139
+ await daemonCall('ocr.scan')
140
+ // { ok: true }
141
+ ```
142
+
143
+ ## Storage
144
+
145
+ OCR data is stored in `~/.lattices/ocr.db`, a SQLite database in WAL
146
+ (Write-Ahead Logging) mode for safe concurrent reads.
147
+
148
+ The schema uses two tables:
149
+ - `ocr_entry` — stores window ID, app, title, frame, full text, and timestamp
150
+ - `ocr_fts` — FTS5 virtual table indexing `full_text`, `app`, and `title`
151
+
152
+ Triggers keep the FTS index in sync with inserts, updates, and deletes.
153
+
154
+ Entries older than 3 days are automatically deleted.
155
+
156
+ ## Agent usage
157
+
158
+ A typical agent workflow: trigger a scan, then search for relevant content.
159
+
160
+ ```js
161
+ import { daemonCall } from '@arach/lattices/daemon-client'
162
+
163
+ // Trigger a fresh scan
164
+ await daemonCall('ocr.scan')
165
+
166
+ // Search for compilation errors across all windows
167
+ const errors = await daemonCall('ocr.search', { query: 'error OR warning' })
168
+
169
+ for (const result of errors) {
170
+ console.log(`[${result.app}] ${result.title}`)
171
+ console.log(result.snippet)
172
+ }
173
+
174
+ // Read everything currently visible
175
+ const snapshot = await daemonCall('ocr.snapshot')
176
+ for (const win of snapshot) {
177
+ console.log(`${win.app}: ${win.fullText.slice(0, 200)}`)
178
+ }
179
+ ```
180
+
181
+ ## Requirements
182
+
183
+ - **Screen Recording** permission — required to capture window images
184
+ - Grant via System Settings > Privacy & Security > Screen Recording
185
+ - Add the lattices menu bar app to the allowed list
package/docs/overview.md CHANGED
@@ -4,71 +4,76 @@ description: What lattices is and who it's for
4
4
  order: 0
5
5
  ---
6
6
 
7
- # Overview
8
-
9
- lattices is a macOS developer workspace manager. It pairs tmux sessions
10
- with a native menu bar app to give you — and your AI coding agents —
11
- full control over terminal layouts, window tiling, and project navigation.
7
+ lattices is a macOS developer workspace manager. A native menu bar app
8
+ handles window tiling, project navigation, on-screen OCR, and optionally
9
+ tmux-powered terminal sessions. Your AI coding agents can use it too.
12
10
 
13
11
  ## The problem
14
12
 
15
- Modern development means juggling multiple terminal windows: a coding
16
- agent in one, a dev server in another, tests in a third. Setting this up
17
- every morning is tedious. AI agents can't do it at all — they're trapped
18
- inside a single shell with no way to manage windows or switch contexts.
13
+ I kept losing track of windows. Terminal here, dev server there, browser
14
+ somewhere on the second monitor, three other projects buried under it all.
15
+ Every morning I'd rebuild the same layout. Half my context-switching was
16
+ just hunting for the right window.
17
+
18
+ AI agents have it worse. They're stuck inside a single shell with no way
19
+ to see what's on screen, arrange windows, or jump between projects.
19
20
 
20
21
  ## The solution
21
22
 
22
- lattices solves both sides:
23
+ lattices fixes both sides:
23
24
 
24
- - **For you** run `lattices` in any project to get a pre-configured
25
- tmux session. Use the menu bar app to launch, tile, and navigate
26
- sessions with a command palette.
27
- - **For agents** — the daemon API exposes 20 RPC methods over WebSocket.
28
- Agents can discover projects, launch sessions, tile windows, and
29
- switch workspace layers programmatically.
25
+ - The menu bar app tiles windows, navigates projects, and manages
26
+ workspace layers through a command palette. Add tmux if you want
27
+ persistent terminal sessions with auto-layout.
28
+ - The daemon API exposes 30 RPC methods over WebSocket. Agents can
29
+ discover projects, tile windows, switch layers, read on-screen text
30
+ via OCR, and launch sessions programmatically.
30
31
 
31
32
  ## What's included
32
33
 
33
34
  | Component | Description |
34
35
  |-----------|-------------|
35
- | **CLI** (`lattices`) | Create, manage, and tile tmux sessions from the terminal |
36
- | **Menu bar app** | Native macOS companion with command palette, tiling, and project discovery |
37
- | **Daemon API** | WebSocket server on `ws://127.0.0.1:9399` 20 methods, 3 real-time events |
36
+ | **CLI** | The `lattices` command. Tile windows, manage sessions, control the workspace from your terminal |
37
+ | **Menu bar app** | Native macOS companion. Command palette, window tiling, project discovery |
38
+ | **Daemon API** | WebSocket server on `ws://127.0.0.1:9399`. 30 methods, 5 real-time events |
39
+ | **OCR engine** | Reads text from visible windows using Apple Vision, indexes it with FTS5 |
38
40
  | **Node.js client** | Zero-dependency `daemonCall()` helper for scripting |
39
41
 
40
- ## Quick taste
42
+ ## Example
41
43
 
42
44
  ```bash
43
- # Launch a workspace (auto-detects your project)
44
45
  cd ~/my-project && lattices
45
-
46
- # Or give agents programmatic control
47
46
  ```
48
47
 
49
- ```js
50
- import { daemonCall } from 'lattices/daemon-client'
48
+ Agents get the same control programmatically:
51
49
 
50
+ ```js
51
+ import { daemonCall } from '@arach/lattices/daemon-client'
52
52
  await daemonCall('session.launch', { path: '/Users/you/dev/frontend' })
53
53
  await daemonCall('window.tile', { session: 'frontend-a1b2c3', position: 'left' })
54
54
  ```
55
55
 
56
56
  ## Who it's for
57
57
 
58
- - **Developers** who use tmux and want faster project switching
59
- - **AI agent builders** who need their agents to control the workspace
60
- - **Power users** who manage multiple projects across macOS Spaces
58
+ - Developers who juggle multiple projects and want faster window management
59
+ - People building AI agents that need to control the desktop
60
+ - Power users who work across multiple macOS Spaces
61
+ - tmux users who want persistent, auto-configured terminal sessions
61
62
 
62
63
  ## Requirements
63
64
 
64
65
  - macOS 13.0+
65
- - tmux (`brew install tmux`)
66
66
  - Node.js 18+
67
- - Swift 5.9+ (only needed to build the menu bar app from source)
67
+
68
+ ### Dev dependencies
69
+
70
+ - Swift 5.9+ — only to build the menu bar app from source
71
+ - tmux — needed for persistent terminal sessions (`brew install tmux`)
68
72
 
69
73
  ## Next steps
70
74
 
71
- - [Quickstart](/docs/quickstart) install and run your first session in 2 minutes
72
- - [Concepts](/docs/concepts) architecture, glossary, and how it all works
73
- - [Configuration](/docs/config) `.lattices.json` format and CLI commands
74
- - [Daemon API](/docs/api) full RPC method reference for agents and scripts
75
+ - [Quickstart](/docs/quickstart): install and run your first session in 2 minutes
76
+ - [Configuration](/docs/config): `.lattices.json` format and CLI commands
77
+ - [Screen OCR](/docs/ocr): Vision-powered screen reading and full-text search
78
+ - [Concepts](/docs/concepts): architecture, glossary, and how it all works
79
+ - [Daemon API](/docs/api): RPC method reference for agents and scripts
@@ -4,56 +4,46 @@ description: Install lattices and launch your first workspace in 2 minutes
4
4
  order: 0.5
5
5
  ---
6
6
 
7
- # Quickstart
7
+ Four steps to a running workspace.
8
8
 
9
- Get from zero to a running workspace in five steps.
10
-
11
- ## 1. Install tmux
9
+ ## 1. Install lattices
12
10
 
13
11
  ```bash
14
- brew install tmux
12
+ npm install -g @arach/lattices
15
13
  ```
16
14
 
17
- Skip if you already have it (`tmux -V` to check).
18
-
19
- ## 2. Install lattices
15
+ Or install from source:
20
16
 
21
17
  ```bash
22
- # Clone and link
23
18
  git clone https://github.com/arach/lattices
24
- cd lattices
25
- bun link
19
+ cd lattices && npm link
26
20
  ```
27
21
 
28
22
  Verify: `lattices help` should print usage info.
29
23
 
30
- ## 3. Launch a workspace
24
+ ## 2. Launch the menu bar app
31
25
 
32
26
  ```bash
33
- cd ~/your-project
34
- lattices
27
+ lattices app
35
28
  ```
36
29
 
37
- This creates a tmux session with two panes side by side:
38
- - Left pane (60%): `claude` (AI coding agent)
39
- - Right pane (40%): your dev command (auto-detected from `package.json`)
40
-
41
- No config file needed — lattices auto-detects your package manager
42
- and dev script.
30
+ This builds (or downloads) and launches the native macOS companion.
31
+ Open the command palette with **Cmd+Shift+M** to search and launch
32
+ any project, tile windows, or switch workspace layers.
43
33
 
44
- ## 4. Customize with .lattices.json
34
+ ## 3. Add a project config
45
35
 
46
- For more control, add a config to your project:
36
+ Drop a `.lattices.json` in your project root:
47
37
 
48
38
  ```bash
39
+ cd ~/your-project
49
40
  lattices init
50
41
  ```
51
42
 
52
- This generates a `.lattices.json` like:
43
+ This generates a config like:
53
44
 
54
45
  ```json
55
46
  {
56
- "ensure": true,
57
47
  "panes": [
58
48
  { "name": "claude", "cmd": "claude", "size": 60 },
59
49
  { "name": "server", "cmd": "bun dev" }
@@ -61,22 +51,31 @@ This generates a `.lattices.json` like:
61
51
  }
62
52
  ```
63
53
 
64
- Edit it to match your workflow, then run `lattices` again to apply.
54
+ The menu bar app discovers projects with `.lattices.json` files
55
+ automatically — they show up in the command palette.
56
+
57
+ ## 4. (Optional) Add tmux for persistent sessions
65
58
 
66
- ## 5. Launch the menu bar app
59
+ If you want terminal sessions that survive disconnects and auto-restore
60
+ your pane layout:
67
61
 
68
62
  ```bash
69
- lattices app
63
+ brew install tmux
64
+ cd ~/your-project && lattices
70
65
  ```
71
66
 
72
- This builds (or downloads) and launches the native macOS companion.
73
- Open the command palette with **Cmd+Shift+M** to search and launch
74
- any project, tile windows, or switch workspace layers.
67
+ This creates a tmux session with your configured panes side by side.
68
+ The session persists in the background close your terminal, reopen it,
69
+ run `lattices` again, and everything is still there.
70
+
71
+ > **Without tmux**, you still get the menu bar app, command palette,
72
+ > window tiling, workspace layers, OCR, and the full daemon API.
75
73
 
76
74
  ## What's next
77
75
 
78
- - [Concepts](/docs/concepts) understand sessions, panes, and the architecture
79
- - [Configuration](/docs/config) full `.lattices.json` reference and CLI commands
80
- - [Menu Bar App](/docs/app) command palette, tiling, and settings
81
- - [Daemon API](/docs/api) programmatic control for agents and scripts
82
- - [Layers & Groups](/docs/layers) organize projects into switchable contexts
76
+ - [Configuration](/docs/config): `.lattices.json` reference and CLI commands
77
+ - [Menu Bar App](/docs/app): command palette, tiling, and settings
78
+ - [Layers & Groups](/docs/layers): organize projects into switchable contexts
79
+ - [Screen OCR](/docs/ocr): let agents read what's on screen
80
+ - [Concepts](/docs/concepts): sessions, panes, and the architecture
81
+ - [Daemon API](/docs/api): programmatic control for agents and scripts
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@arach/lattices",
3
- "version": "0.1.0",
4
- "description": "Tmux sessions with Claude Code + dev server, side by side",
3
+ "version": "0.2.0",
4
+ "description": "macOS workspace manager with window tiling, OCR, and a 30-method daemon API for AI agents",
5
5
  "bin": {
6
6
  "lattices": "./bin/lattices.js",
7
7
  "lattices-app": "./bin/lattices-app.js"
@@ -20,6 +20,10 @@
20
20
  "url": "https://github.com/arach/lattices"
21
21
  },
22
22
  "license": "MIT",
23
+ "exports": {
24
+ ".": "./bin/lattices.js",
25
+ "./daemon-client": "./bin/daemon-client.js"
26
+ },
23
27
  "scripts": {
24
28
  "dev": "bun --cwd docs-site dev"
25
29
  },