zerg-ztc 0.1.10 → 0.1.12
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.
- package/bin/.gitkeep +0 -0
- package/bin/ztc-audio-darwin-arm64 +0 -0
- package/dist/App.d.ts.map +1 -1
- package/dist/App.js +63 -2
- package/dist/App.js.map +1 -1
- package/dist/agent/commands/dictation.d.ts +3 -0
- package/dist/agent/commands/dictation.d.ts.map +1 -0
- package/dist/agent/commands/dictation.js +10 -0
- package/dist/agent/commands/dictation.js.map +1 -0
- package/dist/agent/commands/index.d.ts.map +1 -1
- package/dist/agent/commands/index.js +2 -1
- package/dist/agent/commands/index.js.map +1 -1
- package/dist/agent/commands/types.d.ts +7 -0
- package/dist/agent/commands/types.d.ts.map +1 -1
- package/dist/components/InputArea.d.ts +1 -0
- package/dist/components/InputArea.d.ts.map +1 -1
- package/dist/components/InputArea.js +591 -43
- package/dist/components/InputArea.js.map +1 -1
- package/dist/components/SingleMessage.d.ts.map +1 -1
- package/dist/components/SingleMessage.js +157 -7
- package/dist/components/SingleMessage.js.map +1 -1
- package/dist/config/types.d.ts +6 -0
- package/dist/config/types.d.ts.map +1 -1
- package/dist/ui/views/status_bar.js +2 -2
- package/dist/ui/views/status_bar.js.map +1 -1
- package/dist/utils/dictation.d.ts +46 -0
- package/dist/utils/dictation.d.ts.map +1 -0
- package/dist/utils/dictation.js +409 -0
- package/dist/utils/dictation.js.map +1 -0
- package/dist/utils/dictation_native.d.ts +51 -0
- package/dist/utils/dictation_native.d.ts.map +1 -0
- package/dist/utils/dictation_native.js +236 -0
- package/dist/utils/dictation_native.js.map +1 -0
- package/dist/utils/path_format.d.ts +20 -0
- package/dist/utils/path_format.d.ts.map +1 -0
- package/dist/utils/path_format.js +90 -0
- package/dist/utils/path_format.js.map +1 -0
- package/dist/utils/table.d.ts +38 -0
- package/dist/utils/table.d.ts.map +1 -0
- package/dist/utils/table.js +133 -0
- package/dist/utils/table.js.map +1 -0
- package/dist/utils/tool_trace.d.ts +7 -2
- package/dist/utils/tool_trace.d.ts.map +1 -1
- package/dist/utils/tool_trace.js +156 -51
- package/dist/utils/tool_trace.js.map +1 -1
- package/package.json +5 -1
- package/src/App.tsx +0 -813
- package/src/agent/agent.ts +0 -534
- package/src/agent/backends/anthropic.ts +0 -86
- package/src/agent/backends/gemini.ts +0 -119
- package/src/agent/backends/inception.ts +0 -23
- package/src/agent/backends/index.ts +0 -17
- package/src/agent/backends/openai.ts +0 -23
- package/src/agent/backends/openai_compatible.ts +0 -143
- package/src/agent/backends/types.ts +0 -83
- package/src/agent/commands/clipboard.ts +0 -77
- package/src/agent/commands/config.ts +0 -204
- package/src/agent/commands/debug.ts +0 -23
- package/src/agent/commands/emulation.ts +0 -80
- package/src/agent/commands/execution.ts +0 -9
- package/src/agent/commands/help.ts +0 -20
- package/src/agent/commands/history.ts +0 -13
- package/src/agent/commands/index.ts +0 -46
- package/src/agent/commands/input_mode.ts +0 -22
- package/src/agent/commands/keybindings.ts +0 -40
- package/src/agent/commands/model.ts +0 -11
- package/src/agent/commands/models.ts +0 -116
- package/src/agent/commands/permissions.ts +0 -64
- package/src/agent/commands/retry.ts +0 -9
- package/src/agent/commands/shell.ts +0 -68
- package/src/agent/commands/skills.ts +0 -54
- package/src/agent/commands/status.ts +0 -19
- package/src/agent/commands/types.ts +0 -80
- package/src/agent/commands/update.ts +0 -32
- package/src/agent/factory.ts +0 -60
- package/src/agent/index.ts +0 -20
- package/src/agent/runtime/capabilities.ts +0 -7
- package/src/agent/runtime/memory.ts +0 -23
- package/src/agent/runtime/policy.ts +0 -48
- package/src/agent/runtime/session.ts +0 -18
- package/src/agent/runtime/tracing.ts +0 -23
- package/src/agent/tools/file.ts +0 -178
- package/src/agent/tools/index.ts +0 -52
- package/src/agent/tools/screenshot.ts +0 -821
- package/src/agent/tools/search.ts +0 -138
- package/src/agent/tools/shell.ts +0 -69
- package/src/agent/tools/skills.ts +0 -28
- package/src/agent/tools/types.ts +0 -14
- package/src/agent/tools/zerg.ts +0 -50
- package/src/cli.tsx +0 -163
- package/src/components/ActivityLine.tsx +0 -23
- package/src/components/FullScreen.tsx +0 -79
- package/src/components/Header.tsx +0 -27
- package/src/components/InputArea.tsx +0 -1096
- package/src/components/MessageList.tsx +0 -71
- package/src/components/SingleMessage.tsx +0 -59
- package/src/components/StatusBar.tsx +0 -55
- package/src/components/index.tsx +0 -8
- package/src/config/types.ts +0 -12
- package/src/config.ts +0 -186
- package/src/debug/logger.ts +0 -14
- package/src/emulation/README.md +0 -24
- package/src/emulation/catalog.ts +0 -82
- package/src/emulation/trace_style.ts +0 -8
- package/src/emulation/types.ts +0 -7
- package/src/skills/index.ts +0 -36
- package/src/skills/loader.ts +0 -135
- package/src/skills/registry.ts +0 -6
- package/src/skills/types.ts +0 -10
- package/src/types.ts +0 -84
- package/src/ui/README.md +0 -44
- package/src/ui/core/factory.ts +0 -9
- package/src/ui/core/index.ts +0 -4
- package/src/ui/core/input.ts +0 -38
- package/src/ui/core/input_segments.ts +0 -410
- package/src/ui/core/input_state.ts +0 -17
- package/src/ui/core/layout_yoga.ts +0 -122
- package/src/ui/core/style.ts +0 -38
- package/src/ui/core/types.ts +0 -54
- package/src/ui/ink/index.tsx +0 -1
- package/src/ui/ink/render.tsx +0 -60
- package/src/ui/views/activity_line.ts +0 -33
- package/src/ui/views/app.ts +0 -111
- package/src/ui/views/header.ts +0 -44
- package/src/ui/views/input_area.ts +0 -255
- package/src/ui/views/message_list.ts +0 -443
- package/src/ui/views/status_bar.ts +0 -114
- package/src/ui/vue/index.ts +0 -53
- package/src/ui/web/frame_render.tsx +0 -148
- package/src/ui/web/index.tsx +0 -1
- package/src/ui/web/render.tsx +0 -41
- package/src/utils/clipboard.ts +0 -39
- package/src/utils/clipboard_image.ts +0 -40
- package/src/utils/diff.ts +0 -52
- package/src/utils/image_preview.ts +0 -36
- package/src/utils/models.ts +0 -98
- package/src/utils/path_complete.ts +0 -173
- package/src/utils/shell.ts +0 -72
- package/src/utils/spinner_frames.ts +0 -1
- package/src/utils/spinner_verbs.ts +0 -23
- package/src/utils/tool_summary.ts +0 -56
- package/src/utils/tool_trace.ts +0 -216
- package/src/utils/update.ts +0 -44
- package/src/utils/version.ts +0 -15
- package/src/web/index.html +0 -352
- package/src/web/mirror-favicon.svg +0 -4
- package/src/web/mirror.html +0 -641
- package/src/web/mirror_hook.ts +0 -25
- package/src/web/mirror_server.ts +0 -204
- package/tsconfig.json +0 -22
- package/vite.config.ts +0 -363
|
@@ -0,0 +1,409 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Audio dictation with push-to-talk support
|
|
3
|
+
* Automatic provider fallback:
|
|
4
|
+
* 1. OpenAI Whisper API (if OPENAI_API_KEY available)
|
|
5
|
+
* 2. Local whisper (if installed)
|
|
6
|
+
* 3. macOS native (SFSpeechRecognizer)
|
|
7
|
+
*/
|
|
8
|
+
import { spawn, execSync, spawnSync } from 'child_process';
|
|
9
|
+
import { writeFile, readFile, unlink } from 'fs/promises';
|
|
10
|
+
import { existsSync } from 'fs';
|
|
11
|
+
import { join } from 'path';
|
|
12
|
+
import { tmpdir, homedir, platform } from 'os';
|
|
13
|
+
const RECORDING_DIR = join(tmpdir(), 'ztc-dictation');
|
|
14
|
+
const RECORDING_FILE = join(RECORDING_DIR, 'recording.wav');
|
|
15
|
+
// Global state for push-to-talk
|
|
16
|
+
let activeRecording = null;
|
|
17
|
+
let cachedRecordingTool = null;
|
|
18
|
+
let cachedProvider = null;
|
|
19
|
+
/**
|
|
20
|
+
* Check for available recording tool (cached)
|
|
21
|
+
*/
|
|
22
|
+
function getRecordingTool() {
|
|
23
|
+
if (cachedRecordingTool !== null)
|
|
24
|
+
return cachedRecordingTool;
|
|
25
|
+
const os = platform();
|
|
26
|
+
if (os === 'darwin' || os === 'linux') {
|
|
27
|
+
try {
|
|
28
|
+
execSync('which rec', { stdio: 'ignore' });
|
|
29
|
+
cachedRecordingTool = 'sox';
|
|
30
|
+
return 'sox';
|
|
31
|
+
}
|
|
32
|
+
catch { }
|
|
33
|
+
try {
|
|
34
|
+
execSync('which ffmpeg', { stdio: 'ignore' });
|
|
35
|
+
cachedRecordingTool = 'ffmpeg';
|
|
36
|
+
return 'ffmpeg';
|
|
37
|
+
}
|
|
38
|
+
catch { }
|
|
39
|
+
}
|
|
40
|
+
if (os === 'linux') {
|
|
41
|
+
try {
|
|
42
|
+
execSync('which arecord', { stdio: 'ignore' });
|
|
43
|
+
cachedRecordingTool = 'arecord';
|
|
44
|
+
return 'arecord';
|
|
45
|
+
}
|
|
46
|
+
catch { }
|
|
47
|
+
}
|
|
48
|
+
return null;
|
|
49
|
+
}
|
|
50
|
+
/**
|
|
51
|
+
* Get the best available transcription provider (cached)
|
|
52
|
+
*/
|
|
53
|
+
export function getBestProvider() {
|
|
54
|
+
if (cachedProvider !== null)
|
|
55
|
+
return cachedProvider;
|
|
56
|
+
// Check OpenAI first (best quality)
|
|
57
|
+
if (process.env.OPENAI_API_KEY) {
|
|
58
|
+
cachedProvider = 'openai';
|
|
59
|
+
return 'openai';
|
|
60
|
+
}
|
|
61
|
+
// Check local whisper
|
|
62
|
+
try {
|
|
63
|
+
execSync('which whisper', { stdio: 'ignore' });
|
|
64
|
+
cachedProvider = 'local';
|
|
65
|
+
return 'local';
|
|
66
|
+
}
|
|
67
|
+
catch { }
|
|
68
|
+
try {
|
|
69
|
+
execSync('which whisper-cpp', { stdio: 'ignore' });
|
|
70
|
+
cachedProvider = 'local';
|
|
71
|
+
return 'local';
|
|
72
|
+
}
|
|
73
|
+
catch { }
|
|
74
|
+
// macOS native as fallback
|
|
75
|
+
if (platform() === 'darwin') {
|
|
76
|
+
cachedProvider = 'macos';
|
|
77
|
+
return 'macos';
|
|
78
|
+
}
|
|
79
|
+
return null;
|
|
80
|
+
}
|
|
81
|
+
/**
|
|
82
|
+
* Check if dictation is available
|
|
83
|
+
*/
|
|
84
|
+
export function isDictationAvailable() {
|
|
85
|
+
return getRecordingTool() !== null && getBestProvider() !== null;
|
|
86
|
+
}
|
|
87
|
+
/**
|
|
88
|
+
* Check if currently recording
|
|
89
|
+
*/
|
|
90
|
+
export function isRecording() {
|
|
91
|
+
return activeRecording !== null;
|
|
92
|
+
}
|
|
93
|
+
/**
|
|
94
|
+
* Get the name of the recording device/tool being used
|
|
95
|
+
*/
|
|
96
|
+
export function getRecordingDeviceName() {
|
|
97
|
+
const tool = getRecordingTool();
|
|
98
|
+
if (!tool)
|
|
99
|
+
return null;
|
|
100
|
+
const os = platform();
|
|
101
|
+
if (tool === 'sox') {
|
|
102
|
+
// On macOS, sox uses coreaudio
|
|
103
|
+
if (os === 'darwin') {
|
|
104
|
+
return 'Default Input (sox)';
|
|
105
|
+
}
|
|
106
|
+
return 'Default Input (sox)';
|
|
107
|
+
}
|
|
108
|
+
if (tool === 'ffmpeg') {
|
|
109
|
+
if (os === 'darwin') {
|
|
110
|
+
return 'Default Input (avfoundation)';
|
|
111
|
+
}
|
|
112
|
+
return 'Default Input (alsa)';
|
|
113
|
+
}
|
|
114
|
+
if (tool === 'arecord') {
|
|
115
|
+
return 'Default Input (alsa)';
|
|
116
|
+
}
|
|
117
|
+
return tool;
|
|
118
|
+
}
|
|
119
|
+
/**
|
|
120
|
+
* Start recording (push-to-talk: press to start)
|
|
121
|
+
*/
|
|
122
|
+
export function startRecording() {
|
|
123
|
+
if (activeRecording) {
|
|
124
|
+
return false; // Already recording
|
|
125
|
+
}
|
|
126
|
+
const tool = getRecordingTool();
|
|
127
|
+
if (!tool) {
|
|
128
|
+
throw new Error('No recording tool available. Install sox: brew install sox');
|
|
129
|
+
}
|
|
130
|
+
// Ensure directory exists
|
|
131
|
+
if (!existsSync(RECORDING_DIR)) {
|
|
132
|
+
execSync(`mkdir -p "${RECORDING_DIR}"`);
|
|
133
|
+
}
|
|
134
|
+
const os = platform();
|
|
135
|
+
let proc;
|
|
136
|
+
if (tool === 'sox') {
|
|
137
|
+
proc = spawn('rec', [
|
|
138
|
+
'-q', // Quiet
|
|
139
|
+
'-r', '16000', // 16kHz (Whisper optimal)
|
|
140
|
+
'-c', '1', // Mono
|
|
141
|
+
'-b', '16', // 16-bit
|
|
142
|
+
RECORDING_FILE
|
|
143
|
+
], { stdio: 'ignore' });
|
|
144
|
+
}
|
|
145
|
+
else if (tool === 'ffmpeg') {
|
|
146
|
+
if (os === 'darwin') {
|
|
147
|
+
proc = spawn('ffmpeg', [
|
|
148
|
+
'-y', '-f', 'avfoundation', '-i', ':0',
|
|
149
|
+
'-ar', '16000', '-ac', '1', '-sample_fmt', 's16',
|
|
150
|
+
RECORDING_FILE
|
|
151
|
+
], { stdio: 'ignore' });
|
|
152
|
+
}
|
|
153
|
+
else {
|
|
154
|
+
proc = spawn('ffmpeg', [
|
|
155
|
+
'-y', '-f', 'alsa', '-i', 'default',
|
|
156
|
+
'-ar', '16000', '-ac', '1', '-sample_fmt', 's16',
|
|
157
|
+
RECORDING_FILE
|
|
158
|
+
], { stdio: 'ignore' });
|
|
159
|
+
}
|
|
160
|
+
}
|
|
161
|
+
else {
|
|
162
|
+
proc = spawn('arecord', [
|
|
163
|
+
'-f', 'S16_LE', '-r', '16000', '-c', '1',
|
|
164
|
+
RECORDING_FILE
|
|
165
|
+
], { stdio: 'ignore' });
|
|
166
|
+
}
|
|
167
|
+
activeRecording = {
|
|
168
|
+
process: proc,
|
|
169
|
+
startTime: Date.now()
|
|
170
|
+
};
|
|
171
|
+
return true;
|
|
172
|
+
}
|
|
173
|
+
/**
|
|
174
|
+
* Stop recording and transcribe (push-to-talk: release to stop)
|
|
175
|
+
*/
|
|
176
|
+
export async function stopRecordingAndTranscribe() {
|
|
177
|
+
if (!activeRecording) {
|
|
178
|
+
throw new Error('Not currently recording');
|
|
179
|
+
}
|
|
180
|
+
const { process: proc, startTime } = activeRecording;
|
|
181
|
+
activeRecording = null;
|
|
182
|
+
// Stop the recording process
|
|
183
|
+
await new Promise((resolve) => {
|
|
184
|
+
proc.on('close', () => resolve());
|
|
185
|
+
proc.on('error', () => resolve());
|
|
186
|
+
proc.kill('SIGINT');
|
|
187
|
+
// Fallback timeout
|
|
188
|
+
setTimeout(() => resolve(), 1000);
|
|
189
|
+
});
|
|
190
|
+
// Small delay to ensure file is written
|
|
191
|
+
await new Promise(resolve => setTimeout(resolve, 100));
|
|
192
|
+
if (!existsSync(RECORDING_FILE)) {
|
|
193
|
+
throw new Error('Recording file not created');
|
|
194
|
+
}
|
|
195
|
+
const recordingDuration = Date.now() - startTime;
|
|
196
|
+
const provider = getBestProvider();
|
|
197
|
+
if (!provider) {
|
|
198
|
+
throw new Error('No transcription provider available');
|
|
199
|
+
}
|
|
200
|
+
// Transcribe
|
|
201
|
+
const transcribeStart = Date.now();
|
|
202
|
+
let text;
|
|
203
|
+
try {
|
|
204
|
+
text = await transcribe(RECORDING_FILE, provider);
|
|
205
|
+
}
|
|
206
|
+
finally {
|
|
207
|
+
// Clean up recording file
|
|
208
|
+
try {
|
|
209
|
+
await unlink(RECORDING_FILE);
|
|
210
|
+
}
|
|
211
|
+
catch { }
|
|
212
|
+
}
|
|
213
|
+
return {
|
|
214
|
+
text: text.trim(),
|
|
215
|
+
duration: Date.now() - transcribeStart,
|
|
216
|
+
provider
|
|
217
|
+
};
|
|
218
|
+
}
|
|
219
|
+
/**
|
|
220
|
+
* Cancel active recording without transcribing
|
|
221
|
+
*/
|
|
222
|
+
export function cancelRecording() {
|
|
223
|
+
if (activeRecording) {
|
|
224
|
+
activeRecording.process.kill('SIGKILL');
|
|
225
|
+
activeRecording = null;
|
|
226
|
+
// Clean up file
|
|
227
|
+
try {
|
|
228
|
+
if (existsSync(RECORDING_FILE)) {
|
|
229
|
+
execSync(`rm -f "${RECORDING_FILE}"`);
|
|
230
|
+
}
|
|
231
|
+
}
|
|
232
|
+
catch { }
|
|
233
|
+
}
|
|
234
|
+
}
|
|
235
|
+
/**
|
|
236
|
+
* Transcribe audio file
|
|
237
|
+
*/
|
|
238
|
+
async function transcribe(audioPath, provider) {
|
|
239
|
+
switch (provider) {
|
|
240
|
+
case 'openai':
|
|
241
|
+
return transcribeOpenAI(audioPath);
|
|
242
|
+
case 'local':
|
|
243
|
+
return transcribeLocal(audioPath);
|
|
244
|
+
case 'macos':
|
|
245
|
+
return transcribeMacOS(audioPath);
|
|
246
|
+
default:
|
|
247
|
+
throw new Error(`Unknown provider: ${provider}`);
|
|
248
|
+
}
|
|
249
|
+
}
|
|
250
|
+
/**
|
|
251
|
+
* Transcribe using OpenAI Whisper API
|
|
252
|
+
*/
|
|
253
|
+
async function transcribeOpenAI(audioPath) {
|
|
254
|
+
const apiKey = process.env.OPENAI_API_KEY;
|
|
255
|
+
if (!apiKey) {
|
|
256
|
+
throw new Error('OPENAI_API_KEY not set');
|
|
257
|
+
}
|
|
258
|
+
const audioData = await readFile(audioPath);
|
|
259
|
+
const formData = new FormData();
|
|
260
|
+
formData.append('file', new Blob([audioData], { type: 'audio/wav' }), 'audio.wav');
|
|
261
|
+
formData.append('model', 'whisper-1');
|
|
262
|
+
const response = await fetch('https://api.openai.com/v1/audio/transcriptions', {
|
|
263
|
+
method: 'POST',
|
|
264
|
+
headers: { 'Authorization': `Bearer ${apiKey}` },
|
|
265
|
+
body: formData
|
|
266
|
+
});
|
|
267
|
+
if (!response.ok) {
|
|
268
|
+
const error = await response.text();
|
|
269
|
+
throw new Error(`Whisper API error: ${error}`);
|
|
270
|
+
}
|
|
271
|
+
const result = await response.json();
|
|
272
|
+
return result.text;
|
|
273
|
+
}
|
|
274
|
+
/**
|
|
275
|
+
* Transcribe using local whisper
|
|
276
|
+
*/
|
|
277
|
+
async function transcribeLocal(audioPath) {
|
|
278
|
+
// Try Python whisper first
|
|
279
|
+
try {
|
|
280
|
+
execSync('which whisper', { stdio: 'ignore' });
|
|
281
|
+
const result = spawnSync('whisper', [
|
|
282
|
+
audioPath,
|
|
283
|
+
'--model', 'base',
|
|
284
|
+
'--output_format', 'txt',
|
|
285
|
+
'--output_dir', RECORDING_DIR
|
|
286
|
+
], { encoding: 'utf-8', timeout: 60000 });
|
|
287
|
+
if (result.status === 0) {
|
|
288
|
+
const outputFile = audioPath.replace(/\.wav$/, '.txt');
|
|
289
|
+
if (existsSync(outputFile)) {
|
|
290
|
+
const text = await readFile(outputFile, 'utf-8');
|
|
291
|
+
await unlink(outputFile).catch(() => { });
|
|
292
|
+
return text.trim();
|
|
293
|
+
}
|
|
294
|
+
}
|
|
295
|
+
}
|
|
296
|
+
catch { }
|
|
297
|
+
// Try whisper.cpp
|
|
298
|
+
try {
|
|
299
|
+
execSync('which whisper-cpp', { stdio: 'ignore' });
|
|
300
|
+
const modelPath = join(homedir(), '.local/share/whisper/ggml-base.bin');
|
|
301
|
+
const result = spawnSync('whisper-cpp', [
|
|
302
|
+
'-m', modelPath,
|
|
303
|
+
'-f', audioPath
|
|
304
|
+
], { encoding: 'utf-8', timeout: 60000 });
|
|
305
|
+
if (result.status === 0) {
|
|
306
|
+
return result.stdout.trim();
|
|
307
|
+
}
|
|
308
|
+
}
|
|
309
|
+
catch { }
|
|
310
|
+
throw new Error('Local whisper transcription failed');
|
|
311
|
+
}
|
|
312
|
+
/**
|
|
313
|
+
* Transcribe using macOS native Speech Recognition
|
|
314
|
+
*/
|
|
315
|
+
async function transcribeMacOS(audioPath) {
|
|
316
|
+
const swiftCode = `
|
|
317
|
+
import Foundation
|
|
318
|
+
import Speech
|
|
319
|
+
|
|
320
|
+
let semaphore = DispatchSemaphore(value: 0)
|
|
321
|
+
var transcription = ""
|
|
322
|
+
var errorMsg = ""
|
|
323
|
+
|
|
324
|
+
SFSpeechRecognizer.requestAuthorization { status in
|
|
325
|
+
guard status == .authorized else {
|
|
326
|
+
errorMsg = "Speech recognition not authorized"
|
|
327
|
+
semaphore.signal()
|
|
328
|
+
return
|
|
329
|
+
}
|
|
330
|
+
|
|
331
|
+
guard let recognizer = SFSpeechRecognizer(locale: Locale(identifier: "en-US")),
|
|
332
|
+
recognizer.isAvailable else {
|
|
333
|
+
errorMsg = "Speech recognizer not available"
|
|
334
|
+
semaphore.signal()
|
|
335
|
+
return
|
|
336
|
+
}
|
|
337
|
+
|
|
338
|
+
let url = URL(fileURLWithPath: CommandLine.arguments[1])
|
|
339
|
+
let request = SFSpeechURLRecognitionRequest(url: url)
|
|
340
|
+
request.shouldReportPartialResults = false
|
|
341
|
+
|
|
342
|
+
recognizer.recognitionTask(with: request) { result, error in
|
|
343
|
+
if let error = error {
|
|
344
|
+
errorMsg = error.localizedDescription
|
|
345
|
+
semaphore.signal()
|
|
346
|
+
return
|
|
347
|
+
}
|
|
348
|
+
|
|
349
|
+
if let result = result, result.isFinal {
|
|
350
|
+
transcription = result.bestTranscription.formattedString
|
|
351
|
+
semaphore.signal()
|
|
352
|
+
}
|
|
353
|
+
}
|
|
354
|
+
}
|
|
355
|
+
|
|
356
|
+
_ = semaphore.wait(timeout: .now() + 30)
|
|
357
|
+
|
|
358
|
+
if !errorMsg.isEmpty {
|
|
359
|
+
fputs(errorMsg + "\\n", stderr)
|
|
360
|
+
exit(1)
|
|
361
|
+
}
|
|
362
|
+
print(transcription)
|
|
363
|
+
`;
|
|
364
|
+
const swiftFile = join(RECORDING_DIR, 'transcribe.swift');
|
|
365
|
+
await writeFile(swiftFile, swiftCode);
|
|
366
|
+
try {
|
|
367
|
+
const result = spawnSync('swift', [swiftFile, audioPath], {
|
|
368
|
+
encoding: 'utf-8',
|
|
369
|
+
timeout: 35000
|
|
370
|
+
});
|
|
371
|
+
if (result.status !== 0) {
|
|
372
|
+
throw new Error(result.stderr || 'macOS transcription failed');
|
|
373
|
+
}
|
|
374
|
+
return result.stdout.trim();
|
|
375
|
+
}
|
|
376
|
+
finally {
|
|
377
|
+
await unlink(swiftFile).catch(() => { });
|
|
378
|
+
}
|
|
379
|
+
}
|
|
380
|
+
/**
|
|
381
|
+
* Get status message for dictation availability
|
|
382
|
+
*/
|
|
383
|
+
export function getDictationStatus() {
|
|
384
|
+
const tool = getRecordingTool();
|
|
385
|
+
const provider = getBestProvider();
|
|
386
|
+
const parts = [];
|
|
387
|
+
if (tool) {
|
|
388
|
+
parts.push(`Recording: ${tool}`);
|
|
389
|
+
}
|
|
390
|
+
else {
|
|
391
|
+
parts.push('Recording: not available (install sox: brew install sox)');
|
|
392
|
+
}
|
|
393
|
+
if (provider) {
|
|
394
|
+
const providerNames = {
|
|
395
|
+
openai: 'OpenAI Whisper',
|
|
396
|
+
local: 'Local Whisper',
|
|
397
|
+
macos: 'macOS Native'
|
|
398
|
+
};
|
|
399
|
+
parts.push(`Transcription: ${providerNames[provider]}`);
|
|
400
|
+
}
|
|
401
|
+
else {
|
|
402
|
+
parts.push('Transcription: not available');
|
|
403
|
+
}
|
|
404
|
+
if (tool && provider) {
|
|
405
|
+
parts.push('\nPress Ctrl+T to start/stop recording');
|
|
406
|
+
}
|
|
407
|
+
return parts.join('\n');
|
|
408
|
+
}
|
|
409
|
+
//# sourceMappingURL=dictation.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"dictation.js","sourceRoot":"","sources":["../../src/utils/dictation.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Native real-time dictation using ztc-audio Rust binary
|
|
3
|
+
* Provides:
|
|
4
|
+
* - Real-time audio level metering (VU meter)
|
|
5
|
+
* - Real-time transcription via whisper
|
|
6
|
+
* - Cross-platform support
|
|
7
|
+
*/
|
|
8
|
+
export interface DictationEvent {
|
|
9
|
+
type: 'ready' | 'level' | 'text' | 'error' | 'stopped';
|
|
10
|
+
device?: string;
|
|
11
|
+
model?: string;
|
|
12
|
+
db?: number;
|
|
13
|
+
rms?: number;
|
|
14
|
+
content?: string;
|
|
15
|
+
partial?: boolean;
|
|
16
|
+
message?: string;
|
|
17
|
+
}
|
|
18
|
+
export type DictationEventHandler = (event: DictationEvent) => void;
|
|
19
|
+
/**
|
|
20
|
+
* Check if native dictation is available
|
|
21
|
+
*/
|
|
22
|
+
export declare function isNativeDictationAvailable(): boolean;
|
|
23
|
+
/**
|
|
24
|
+
* Check if currently recording
|
|
25
|
+
*/
|
|
26
|
+
export declare function isNativeRecording(): boolean;
|
|
27
|
+
/**
|
|
28
|
+
* Subscribe to dictation events
|
|
29
|
+
*/
|
|
30
|
+
export declare function onDictationEvent(handler: DictationEventHandler): () => void;
|
|
31
|
+
/**
|
|
32
|
+
* Start native recording with real-time transcription
|
|
33
|
+
*/
|
|
34
|
+
export declare function startNativeRecording(options?: {
|
|
35
|
+
model?: string;
|
|
36
|
+
device?: string;
|
|
37
|
+
}): boolean;
|
|
38
|
+
/**
|
|
39
|
+
* Stop native recording
|
|
40
|
+
* Returns the final transcription
|
|
41
|
+
*/
|
|
42
|
+
export declare function stopNativeRecording(): Promise<string>;
|
|
43
|
+
/**
|
|
44
|
+
* Cancel native recording without getting transcription
|
|
45
|
+
*/
|
|
46
|
+
export declare function cancelNativeRecording(): void;
|
|
47
|
+
/**
|
|
48
|
+
* Get recording status info
|
|
49
|
+
*/
|
|
50
|
+
export declare function getNativeDictationStatus(): string;
|
|
51
|
+
//# sourceMappingURL=dictation_native.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"dictation_native.d.ts","sourceRoot":"","sources":["../../src/utils/dictation_native.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAYH,MAAM,WAAW,cAAc;IAC7B,IAAI,EAAE,OAAO,GAAG,OAAO,GAAG,MAAM,GAAG,OAAO,GAAG,SAAS,CAAC;IACvD,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,EAAE,CAAC,EAAE,MAAM,CAAC;IACZ,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,OAAO,CAAC,EAAE,MAAM,CAAC;CAClB;AAED,MAAM,MAAM,qBAAqB,GAAG,CAAC,KAAK,EAAE,cAAc,KAAK,IAAI,CAAC;AAqEpE;;GAEG;AACH,wBAAgB,0BAA0B,IAAI,OAAO,CAEpD;AAED;;GAEG;AACH,wBAAgB,iBAAiB,IAAI,OAAO,CAE3C;AAED;;GAEG;AACH,wBAAgB,gBAAgB,CAAC,OAAO,EAAE,qBAAqB,GAAG,MAAM,IAAI,CAK3E;AAYD;;GAEG;AACH,wBAAgB,oBAAoB,CAAC,OAAO,GAAE;IAC5C,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,MAAM,CAAC,EAAE,MAAM,CAAC;CACZ,GAAG,OAAO,CAuEf;AAED;;;GAGG;AACH,wBAAsB,mBAAmB,IAAI,OAAO,CAAC,MAAM,CAAC,CAgC3D;AAED;;GAEG;AACH,wBAAgB,qBAAqB,IAAI,IAAI,CAK5C;AAED;;GAEG;AACH,wBAAgB,wBAAwB,IAAI,MAAM,CAmBjD"}
|