@happyvertical/smrt-svelte 0.55.6 → 0.55.8
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/AGENTS.md +9 -31
- package/README.md +195 -5
- package/agents/browser-ai.md +47 -0
- package/agents/command-palette.md +85 -0
- package/agents/import-export.md +62 -0
- package/agents/overview-surfaces.md +255 -0
- package/agents/screens.md +57 -0
- package/agents/workspace.md +202 -5
- package/dist/browser-ai/adapters/stt/dictation-source.d.ts.map +1 -1
- package/dist/browser-ai/adapters/stt/dictation-source.js +8 -2
- package/dist/browser-ai/adapters/stt/factory.d.ts +6 -3
- package/dist/browser-ai/adapters/stt/factory.d.ts.map +1 -1
- package/dist/browser-ai/adapters/stt/factory.js +19 -9
- package/dist/browser-ai/adapters/stt/index.d.ts +3 -1
- package/dist/browser-ai/adapters/stt/index.d.ts.map +1 -1
- package/dist/browser-ai/adapters/stt/index.js +3 -1
- package/dist/browser-ai/adapters/stt/local-speech-model.d.ts +111 -0
- package/dist/browser-ai/adapters/stt/local-speech-model.d.ts.map +1 -0
- package/dist/browser-ai/adapters/stt/local-speech-model.js +377 -0
- package/dist/browser-ai/adapters/stt/local-speech.d.ts +82 -0
- package/dist/browser-ai/adapters/stt/local-speech.d.ts.map +1 -0
- package/dist/browser-ai/adapters/stt/local-speech.js +317 -0
- package/dist/browser-ai/adapters/stt/local-speech.worker.d.ts +2 -0
- package/dist/browser-ai/adapters/stt/local-speech.worker.d.ts.map +1 -0
- package/dist/browser-ai/adapters/stt/local-speech.worker.js +32 -0
- package/dist/browser-ai/adapters/stt/transformers-env.d.ts +8 -0
- package/dist/browser-ai/adapters/stt/transformers-env.d.ts.map +1 -0
- package/dist/browser-ai/adapters/stt/transformers-env.js +17 -0
- package/dist/browser-ai/adapters/stt/types.d.ts +54 -9
- package/dist/browser-ai/adapters/stt/types.d.ts.map +1 -1
- package/dist/browser-ai/adapters/tts/browser-synthesis.d.ts +5 -0
- package/dist/browser-ai/adapters/tts/browser-synthesis.d.ts.map +1 -1
- package/dist/browser-ai/adapters/tts/browser-synthesis.js +83 -55
- package/dist/browser-ai/capabilities/speech-probe.d.ts +29 -0
- package/dist/browser-ai/capabilities/speech-probe.d.ts.map +1 -0
- package/dist/browser-ai/capabilities/speech-probe.js +19 -0
- package/dist/browser-ai/core/errors.d.ts +9 -0
- package/dist/browser-ai/core/errors.d.ts.map +1 -1
- package/dist/browser-ai/core/errors.js +12 -0
- package/dist/browser-ai/index.d.ts +1 -0
- package/dist/browser-ai/index.d.ts.map +1 -1
- package/dist/browser-ai/index.js +1 -0
- package/dist/components/app/AppShell.svelte +587 -33
- package/dist/components/app/AppShell.svelte.d.ts +75 -4
- package/dist/components/app/AppShell.svelte.d.ts.map +1 -1
- package/dist/components/app/DockToggles.svelte +0 -1
- package/dist/components/app/dock-toggle.d.ts +7 -1
- package/dist/components/app/dock-toggle.d.ts.map +1 -1
- package/dist/components/app/index.d.ts +2 -1
- package/dist/components/app/index.d.ts.map +1 -1
- package/dist/components/app/slot-item.d.ts +21 -0
- package/dist/components/app/slot-item.d.ts.map +1 -0
- package/dist/components/app/slot-item.js +1 -0
- package/dist/components/command-palette/CommandPalette.svelte +75 -0
- package/dist/components/command-palette/CommandPalette.svelte.d.ts +22 -0
- package/dist/components/command-palette/CommandPalette.svelte.d.ts.map +1 -0
- package/dist/components/command-palette/CommandPaletteDialog.svelte +406 -0
- package/dist/components/command-palette/CommandPaletteDialog.svelte.d.ts +18 -0
- package/dist/components/command-palette/CommandPaletteDialog.svelte.d.ts.map +1 -0
- package/dist/components/command-palette/CommandPaletteTrigger.svelte +91 -0
- package/dist/components/command-palette/CommandPaletteTrigger.svelte.d.ts +17 -0
- package/dist/components/command-palette/CommandPaletteTrigger.svelte.d.ts.map +1 -0
- package/dist/components/command-palette/context.d.ts +18 -0
- package/dist/components/command-palette/context.d.ts.map +1 -0
- package/dist/components/command-palette/context.js +38 -0
- package/dist/components/command-palette/controller.svelte.d.ts +70 -0
- package/dist/components/command-palette/controller.svelte.d.ts.map +1 -0
- package/dist/components/command-palette/controller.svelte.js +379 -0
- package/dist/components/command-palette/hotkeys.d.ts +30 -0
- package/dist/components/command-palette/hotkeys.d.ts.map +1 -0
- package/dist/components/command-palette/hotkeys.js +161 -0
- package/dist/components/command-palette/index.d.ts +19 -0
- package/dist/components/command-palette/index.d.ts.map +1 -0
- package/dist/components/command-palette/index.js +17 -0
- package/dist/components/command-palette/match.d.ts +38 -0
- package/dist/components/command-palette/match.d.ts.map +1 -0
- package/dist/components/command-palette/match.js +172 -0
- package/dist/components/command-palette/providers.d.ts +159 -0
- package/dist/components/command-palette/providers.d.ts.map +1 -0
- package/dist/components/command-palette/providers.js +345 -0
- package/dist/components/command-palette/rank.d.ts +20 -0
- package/dist/components/command-palette/rank.d.ts.map +1 -0
- package/dist/components/command-palette/rank.js +74 -0
- package/dist/components/command-palette/types.d.ts +119 -0
- package/dist/components/command-palette/types.d.ts.map +1 -0
- package/dist/components/command-palette/types.js +10 -0
- package/dist/components/command-palette/use-provider.svelte.d.ts +14 -0
- package/dist/components/command-palette/use-provider.svelte.d.ts.map +1 -0
- package/dist/components/command-palette/use-provider.svelte.js +23 -0
- package/dist/components/forms/AddressInput.svelte +2 -15
- package/dist/components/forms/AddressInput.svelte.d.ts.map +1 -1
- package/dist/components/forms/DateRangeInput.svelte +2 -15
- package/dist/components/forms/DateRangeInput.svelte.d.ts.map +1 -1
- package/dist/components/forms/DateTimeInput.svelte +8 -15
- package/dist/components/forms/DateTimeInput.svelte.d.ts.map +1 -1
- package/dist/components/forms/MeasurementInput.svelte +2 -15
- package/dist/components/forms/MeasurementInput.svelte.d.ts.map +1 -1
- package/dist/components/forms/MoneyInput.svelte +8 -25
- package/dist/components/forms/MoneyInput.svelte.d.ts.map +1 -1
- package/dist/components/forms/NumberInput.svelte +7 -15
- package/dist/components/forms/NumberInput.svelte.d.ts.map +1 -1
- package/dist/components/forms/PhoneInput.svelte +7 -15
- package/dist/components/forms/PhoneInput.svelte.d.ts.map +1 -1
- package/dist/components/forms/SelectInput.svelte +34 -40
- package/dist/components/forms/SelectInput.svelte.d.ts.map +1 -1
- package/dist/components/forms/TextInput.svelte +20 -37
- package/dist/components/forms/TextInput.svelte.d.ts.map +1 -1
- package/dist/components/forms/TextareaInput.svelte +19 -35
- package/dist/components/forms/TextareaInput.svelte.d.ts.map +1 -1
- package/dist/components/import-export/ImportExport.svelte +678 -0
- package/dist/components/import-export/ImportExport.svelte.d.ts +5 -0
- package/dist/components/import-export/ImportExport.svelte.d.ts.map +1 -0
- package/dist/components/import-export/collection-adapter.d.ts +35 -0
- package/dist/components/import-export/collection-adapter.d.ts.map +1 -0
- package/dist/components/import-export/collection-adapter.js +42 -0
- package/dist/components/import-export/csv.d.ts +60 -0
- package/dist/components/import-export/csv.d.ts.map +1 -0
- package/dist/components/import-export/csv.js +192 -0
- package/dist/components/import-export/download.d.ts +4 -0
- package/dist/components/import-export/download.d.ts.map +1 -0
- package/dist/components/import-export/download.js +17 -0
- package/dist/components/import-export/export.d.ts +25 -0
- package/dist/components/import-export/export.d.ts.map +1 -0
- package/dist/components/import-export/export.js +68 -0
- package/dist/components/import-export/fields.d.ts +48 -0
- package/dist/components/import-export/fields.d.ts.map +1 -0
- package/dist/components/import-export/fields.js +103 -0
- package/dist/components/import-export/index.d.ts +12 -0
- package/dist/components/import-export/index.d.ts.map +1 -0
- package/dist/components/import-export/index.js +9 -0
- package/dist/components/import-export/mapping.d.ts +12 -0
- package/dist/components/import-export/mapping.d.ts.map +1 -0
- package/dist/components/import-export/mapping.js +38 -0
- package/dist/components/import-export/props.d.ts +34 -0
- package/dist/components/import-export/props.d.ts.map +1 -0
- package/dist/components/import-export/props.js +1 -0
- package/dist/components/import-export/report.d.ts +13 -0
- package/dist/components/import-export/report.d.ts.map +1 -0
- package/dist/components/import-export/report.js +50 -0
- package/dist/components/import-export/runner.d.ts +17 -0
- package/dist/components/import-export/runner.d.ts.map +1 -0
- package/dist/components/import-export/runner.js +39 -0
- package/dist/components/import-export/types.d.ts +100 -0
- package/dist/components/import-export/types.d.ts.map +1 -0
- package/dist/components/import-export/types.js +6 -0
- package/dist/components/import-export/validate.d.ts +39 -0
- package/dist/components/import-export/validate.d.ts.map +1 -0
- package/dist/components/import-export/validate.js +268 -0
- package/dist/components/overview/OverviewGrid.svelte +579 -0
- package/dist/components/overview/OverviewGrid.svelte.d.ts +5 -0
- package/dist/components/overview/OverviewGrid.svelte.d.ts.map +1 -0
- package/dist/components/overview/WidgetOptionsForm.svelte +193 -0
- package/dist/components/overview/WidgetOptionsForm.svelte.d.ts +5 -0
- package/dist/components/overview/WidgetOptionsForm.svelte.d.ts.map +1 -0
- package/dist/components/overview/controller.svelte.d.ts +92 -0
- package/dist/components/overview/controller.svelte.d.ts.map +1 -0
- package/dist/components/overview/controller.svelte.js +336 -0
- package/dist/components/overview/format.d.ts +13 -0
- package/dist/components/overview/format.d.ts.map +1 -0
- package/dist/components/overview/format.js +45 -0
- package/dist/components/overview/grid-types.d.ts +52 -0
- package/dist/components/overview/grid-types.d.ts.map +1 -0
- package/dist/components/overview/grid-types.js +1 -0
- package/dist/components/overview/index.d.ts +24 -0
- package/dist/components/overview/index.d.ts.map +1 -0
- package/dist/components/overview/index.js +22 -0
- package/dist/components/overview/load.d.ts +30 -0
- package/dist/components/overview/load.d.ts.map +1 -0
- package/dist/components/overview/load.js +92 -0
- package/dist/components/overview/markdown.d.ts +53 -0
- package/dist/components/overview/markdown.d.ts.map +1 -0
- package/dist/components/overview/markdown.js +203 -0
- package/dist/components/overview/model.d.ts +100 -0
- package/dist/components/overview/model.d.ts.map +1 -0
- package/dist/components/overview/model.js +460 -0
- package/dist/components/overview/recipe-widgets.d.ts +77 -0
- package/dist/components/overview/recipe-widgets.d.ts.map +1 -0
- package/dist/components/overview/recipe-widgets.js +151 -0
- package/dist/components/overview/registry.d.ts +45 -0
- package/dist/components/overview/registry.d.ts.map +1 -0
- package/dist/components/overview/registry.js +112 -0
- package/dist/components/overview/resize.d.ts +25 -0
- package/dist/components/overview/resize.d.ts.map +1 -0
- package/dist/components/overview/resize.js +41 -0
- package/dist/components/overview/schema.d.ts +34 -0
- package/dist/components/overview/schema.d.ts.map +1 -0
- package/dist/components/overview/schema.js +180 -0
- package/dist/components/overview/server.d.ts +14 -0
- package/dist/components/overview/server.d.ts.map +1 -0
- package/dist/components/overview/server.js +13 -0
- package/dist/components/overview/types.d.ts +235 -0
- package/dist/components/overview/types.d.ts.map +1 -0
- package/dist/components/overview/types.js +17 -0
- package/dist/components/overview/widgets/ChartWidget.svelte +111 -0
- package/dist/components/overview/widgets/ChartWidget.svelte.d.ts +6 -0
- package/dist/components/overview/widgets/ChartWidget.svelte.d.ts.map +1 -0
- package/dist/components/overview/widgets/MetricWidget.svelte +86 -0
- package/dist/components/overview/widgets/MetricWidget.svelte.d.ts +6 -0
- package/dist/components/overview/widgets/MetricWidget.svelte.d.ts.map +1 -0
- package/dist/components/overview/widgets/NoteWidget.svelte +61 -0
- package/dist/components/overview/widgets/NoteWidget.svelte.d.ts +5 -0
- package/dist/components/overview/widgets/NoteWidget.svelte.d.ts.map +1 -0
- package/dist/components/overview/widgets/RecordListWidget.svelte +91 -0
- package/dist/components/overview/widgets/RecordListWidget.svelte.d.ts +6 -0
- package/dist/components/overview/widgets/RecordListWidget.svelte.d.ts.map +1 -0
- package/dist/components/overview/widgets/ShortcutsWidget.svelte +80 -0
- package/dist/components/overview/widgets/ShortcutsWidget.svelte.d.ts +6 -0
- package/dist/components/overview/widgets/ShortcutsWidget.svelte.d.ts.map +1 -0
- package/dist/components/overview/widgets/core.d.ts +44 -0
- package/dist/components/overview/widgets/core.d.ts.map +1 -0
- package/dist/components/overview/widgets/core.js +222 -0
- package/dist/components/overview/widgets/data.d.ts +76 -0
- package/dist/components/overview/widgets/data.d.ts.map +1 -0
- package/dist/components/overview/widgets/data.js +40 -0
- package/dist/components/screens/DetailScreen.svelte +220 -0
- package/dist/components/screens/DetailScreen.svelte.d.ts +5 -0
- package/dist/components/screens/DetailScreen.svelte.d.ts.map +1 -0
- package/dist/components/screens/EditForm.svelte +313 -0
- package/dist/components/screens/EditForm.svelte.d.ts +5 -0
- package/dist/components/screens/EditForm.svelte.d.ts.map +1 -0
- package/dist/components/screens/ListScreen.svelte +191 -0
- package/dist/components/screens/ListScreen.svelte.d.ts +5 -0
- package/dist/components/screens/ListScreen.svelte.d.ts.map +1 -0
- package/dist/components/screens/RecipeScreens.svelte +237 -0
- package/dist/components/screens/RecipeScreens.svelte.d.ts +5 -0
- package/dist/components/screens/RecipeScreens.svelte.d.ts.map +1 -0
- package/dist/components/screens/fields.d.ts +54 -0
- package/dist/components/screens/fields.d.ts.map +1 -0
- package/dist/components/screens/fields.js +229 -0
- package/dist/components/screens/index.d.ts +8 -0
- package/dist/components/screens/index.d.ts.map +1 -0
- package/dist/components/screens/index.js +6 -0
- package/dist/components/screens/types.d.ts +215 -0
- package/dist/components/screens/types.d.ts.map +1 -0
- package/dist/components/screens/types.js +1 -0
- package/dist/components/screens/values.d.ts +62 -0
- package/dist/components/screens/values.d.ts.map +1 -0
- package/dist/components/screens/values.js +289 -0
- package/dist/components/sortable/Sortable.svelte +6 -33
- package/dist/components/sortable/Sortable.svelte.d.ts.map +1 -1
- package/dist/components/sortable/announce.d.ts +5 -0
- package/dist/components/sortable/announce.d.ts.map +1 -0
- package/dist/components/sortable/announce.js +33 -0
- package/dist/components/sortable/controller.svelte.d.ts +10 -0
- package/dist/components/sortable/controller.svelte.d.ts.map +1 -1
- package/dist/components/sortable/controller.svelte.js +29 -7
- package/dist/components/workspace/admin-shell/AdminShell.svelte +424 -58
- package/dist/components/workspace/admin-shell/AdminShell.svelte.d.ts +27 -2
- package/dist/components/workspace/admin-shell/AdminShell.svelte.d.ts.map +1 -1
- package/dist/components/workspace/admin-shell/ShellBrand.svelte +86 -0
- package/dist/components/workspace/admin-shell/ShellBrand.svelte.d.ts +18 -0
- package/dist/components/workspace/admin-shell/ShellBrand.svelte.d.ts.map +1 -0
- package/dist/components/workspace/admin-shell/ShellIconButton.svelte +77 -0
- package/dist/components/workspace/admin-shell/ShellIconButton.svelte.d.ts +26 -0
- package/dist/components/workspace/admin-shell/ShellIconButton.svelte.d.ts.map +1 -0
- package/dist/components/workspace/admin-shell/ShellLayoutEditor.svelte +88 -16
- package/dist/components/workspace/admin-shell/ShellLayoutEditor.svelte.d.ts.map +1 -1
- package/dist/components/workspace/admin-shell/ShellNavEditor.svelte +531 -0
- package/dist/components/workspace/admin-shell/ShellNavEditor.svelte.d.ts +26 -0
- package/dist/components/workspace/admin-shell/ShellNavEditor.svelte.d.ts.map +1 -0
- package/dist/components/workspace/admin-shell/ShellSectionIcon.svelte +57 -0
- package/dist/components/workspace/admin-shell/ShellSectionIcon.svelte.d.ts +22 -0
- package/dist/components/workspace/admin-shell/ShellSectionIcon.svelte.d.ts.map +1 -0
- package/dist/components/workspace/admin-shell/ShellSectionMenu.svelte +290 -0
- package/dist/components/workspace/admin-shell/ShellSectionMenu.svelte.d.ts +32 -0
- package/dist/components/workspace/admin-shell/ShellSectionMenu.svelte.d.ts.map +1 -0
- package/dist/components/workspace/admin-shell/TenantNav.svelte +67 -2
- package/dist/components/workspace/admin-shell/TenantNav.svelte.d.ts +8 -0
- package/dist/components/workspace/admin-shell/TenantNav.svelte.d.ts.map +1 -1
- package/dist/components/workspace/admin-shell/layout-controller.svelte.d.ts +67 -0
- package/dist/components/workspace/admin-shell/layout-controller.svelte.d.ts.map +1 -1
- package/dist/components/workspace/admin-shell/layout-controller.svelte.js +129 -1
- package/dist/components/workspace/admin-shell/layout.d.ts +122 -0
- package/dist/components/workspace/admin-shell/layout.d.ts.map +1 -1
- package/dist/components/workspace/admin-shell/layout.js +410 -10
- package/dist/components/workspace/admin-shell/settings.js +4 -4
- package/dist/components/workspace/admin-shell/shell-icons.d.ts +45 -0
- package/dist/components/workspace/admin-shell/shell-icons.d.ts.map +1 -0
- package/dist/components/workspace/admin-shell/shell-icons.js +66 -0
- package/dist/components/workspace/admin-shell/slot-labels.d.ts +33 -0
- package/dist/components/workspace/admin-shell/slot-labels.d.ts.map +1 -0
- package/dist/components/workspace/admin-shell/slot-labels.js +33 -0
- package/dist/components/workspace/admin-shell/slots.d.ts +50 -0
- package/dist/components/workspace/admin-shell/slots.d.ts.map +1 -0
- package/dist/components/workspace/admin-shell/slots.js +77 -0
- package/dist/components/workspace/admin-shell/state.svelte.d.ts +35 -0
- package/dist/components/workspace/admin-shell/state.svelte.d.ts.map +1 -1
- package/dist/components/workspace/admin-shell/state.svelte.js +111 -0
- package/dist/components/workspace/admin-shell/types.d.ts +101 -1
- package/dist/components/workspace/admin-shell/types.d.ts.map +1 -1
- package/dist/components/workspace/index.d.ts +9 -2
- package/dist/components/workspace/index.d.ts.map +1 -1
- package/dist/components/workspace/index.js +6 -0
- package/dist/components/workspace/manifest-nav.d.ts +20 -0
- package/dist/components/workspace/manifest-nav.d.ts.map +1 -1
- package/dist/components/workspace/manifest-nav.js +42 -13
- package/dist/i18n/server.d.ts +6 -0
- package/dist/i18n/server.d.ts.map +1 -1
- package/dist/i18n/server.js +6 -0
- package/dist/i18n/strings.import-export.d.ts +88 -0
- package/dist/i18n/strings.import-export.d.ts.map +1 -0
- package/dist/i18n/strings.import-export.js +88 -0
- package/dist/i18n/strings.overview.d.ts +100 -0
- package/dist/i18n/strings.overview.d.ts.map +1 -0
- package/dist/i18n/strings.overview.js +107 -0
- package/dist/i18n/strings.palette.d.ts +18 -0
- package/dist/i18n/strings.palette.d.ts.map +1 -0
- package/dist/i18n/strings.palette.js +18 -0
- package/dist/i18n/strings.screens.d.ts +31 -0
- package/dist/i18n/strings.screens.d.ts.map +1 -0
- package/dist/i18n/strings.screens.js +31 -0
- package/dist/i18n/strings.workspace.d.ts +49 -0
- package/dist/i18n/strings.workspace.d.ts.map +1 -1
- package/dist/i18n/strings.workspace.js +49 -0
- package/package.json +59 -19
- package/dist/browser-ai/adapters/stt/whisper-wasm.d.ts +0 -51
- package/dist/browser-ai/adapters/stt/whisper-wasm.d.ts.map +0 -1
- package/dist/browser-ai/adapters/stt/whisper-wasm.js +0 -380
|
@@ -14,8 +14,12 @@ export class BrowserSynthesisTTSAdapter {
|
|
|
14
14
|
synthesis = null;
|
|
15
15
|
options;
|
|
16
16
|
voices = [];
|
|
17
|
-
// biome-ignore lint/correctness/noUnusedPrivateClassMembers: Used in speak/stop/pause
|
|
18
17
|
currentUtterance = null;
|
|
18
|
+
operationGeneration = 0;
|
|
19
|
+
initializationGeneration = 0;
|
|
20
|
+
initialization = null;
|
|
21
|
+
cancelVoiceLoad = null;
|
|
22
|
+
settleCurrentSpeech = null;
|
|
19
23
|
// Event listeners
|
|
20
24
|
startListeners = new Set();
|
|
21
25
|
endListeners = new Set();
|
|
@@ -36,58 +40,60 @@ export class BrowserSynthesisTTSAdapter {
|
|
|
36
40
|
async ensureInitialized(_onProgress) {
|
|
37
41
|
if (this._initState === 'ready')
|
|
38
42
|
return;
|
|
39
|
-
if (this.
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
const check = () => {
|
|
43
|
-
if (this._initState === 'ready')
|
|
44
|
-
resolve();
|
|
45
|
-
else if (this._initState === 'error')
|
|
46
|
-
reject(new Error('Initialization failed'));
|
|
47
|
-
else
|
|
48
|
-
setTimeout(check, 50);
|
|
49
|
-
};
|
|
50
|
-
check();
|
|
51
|
-
});
|
|
52
|
-
}
|
|
43
|
+
if (this.initialization)
|
|
44
|
+
return this.initialization;
|
|
45
|
+
const generation = this.initializationGeneration;
|
|
53
46
|
this._initState = 'initializing';
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
47
|
+
const initialization = (async () => {
|
|
48
|
+
try {
|
|
49
|
+
if (typeof window === 'undefined' || !window.speechSynthesis) {
|
|
50
|
+
throw new CapabilityNotAvailableError('Web Speech Synthesis API', 'browser-synthesis');
|
|
51
|
+
}
|
|
52
|
+
this.synthesis = window.speechSynthesis;
|
|
53
|
+
await this.loadVoices(this.synthesis);
|
|
54
|
+
if (generation === this.initializationGeneration) {
|
|
55
|
+
this._initState = 'ready';
|
|
56
|
+
}
|
|
57
|
+
}
|
|
58
|
+
catch (error) {
|
|
59
|
+
if (generation === this.initializationGeneration) {
|
|
60
|
+
this._initState = 'error';
|
|
61
|
+
}
|
|
62
|
+
throw error;
|
|
57
63
|
}
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
64
|
+
})();
|
|
65
|
+
this.initialization = initialization;
|
|
66
|
+
try {
|
|
67
|
+
await initialization;
|
|
62
68
|
}
|
|
63
|
-
|
|
64
|
-
this.
|
|
65
|
-
|
|
69
|
+
finally {
|
|
70
|
+
if (this.initialization === initialization)
|
|
71
|
+
this.initialization = null;
|
|
66
72
|
}
|
|
67
73
|
}
|
|
68
|
-
async loadVoices() {
|
|
69
|
-
|
|
74
|
+
async loadVoices(synthesis) {
|
|
75
|
+
this.voices = synthesis.getVoices();
|
|
76
|
+
if (this.voices.length > 0)
|
|
70
77
|
return;
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
}
|
|
78
|
+
await new Promise((resolve) => {
|
|
79
|
+
const finish = () => {
|
|
80
|
+
clearTimeout(timeout);
|
|
81
|
+
synthesis.removeEventListener('voiceschanged', handleVoicesChanged);
|
|
82
|
+
this.cancelVoiceLoad = null;
|
|
83
|
+
resolve();
|
|
84
|
+
};
|
|
85
|
+
const handleVoicesChanged = () => {
|
|
86
|
+
this.voices = synthesis.getVoices();
|
|
87
|
+
if (this.voices.length > 0)
|
|
88
|
+
finish();
|
|
89
|
+
};
|
|
90
|
+
const timeout = setTimeout(() => {
|
|
91
|
+
this.voices = synthesis.getVoices();
|
|
92
|
+
finish();
|
|
93
|
+
}, 2000);
|
|
94
|
+
this.cancelVoiceLoad = finish;
|
|
95
|
+
synthesis.addEventListener('voiceschanged', handleVoicesChanged);
|
|
96
|
+
});
|
|
91
97
|
}
|
|
92
98
|
getCapabilities() {
|
|
93
99
|
return {
|
|
@@ -133,12 +139,15 @@ export class BrowserSynthesisTTSAdapter {
|
|
|
133
139
|
return this.voices.find((v) => v.default) || this.voices[0];
|
|
134
140
|
}
|
|
135
141
|
async speak(text, options = {}) {
|
|
142
|
+
// Invalidate previous requests before the asynchronous voices wait.
|
|
143
|
+
this.stop();
|
|
144
|
+
const generation = this.operationGeneration;
|
|
136
145
|
await this.ensureInitialized();
|
|
146
|
+
if (generation !== this.operationGeneration)
|
|
147
|
+
return;
|
|
137
148
|
if (!this.synthesis) {
|
|
138
149
|
throw new Error('Synthesis not initialized');
|
|
139
150
|
}
|
|
140
|
-
// Cancel any current speech
|
|
141
|
-
this.stop();
|
|
142
151
|
return new Promise((resolve, reject) => {
|
|
143
152
|
const utterance = new SpeechSynthesisUtterance(text);
|
|
144
153
|
// Set voice
|
|
@@ -154,21 +163,34 @@ export class BrowserSynthesisTTSAdapter {
|
|
|
154
163
|
utterance.rate = options.rate ?? this.options.defaultRate ?? 1;
|
|
155
164
|
utterance.pitch = options.pitch ?? this.options.defaultPitch ?? 1;
|
|
156
165
|
utterance.volume = options.volume ?? this.options.defaultVolume ?? 1;
|
|
166
|
+
const isCurrent = () => generation === this.operationGeneration &&
|
|
167
|
+
this.currentUtterance === utterance;
|
|
168
|
+
const settle = () => {
|
|
169
|
+
this.currentUtterance = null;
|
|
170
|
+
this.settleCurrentSpeech = null;
|
|
171
|
+
resolve();
|
|
172
|
+
};
|
|
157
173
|
// Set up event handlers
|
|
158
174
|
utterance.onstart = () => {
|
|
175
|
+
if (!isCurrent())
|
|
176
|
+
return;
|
|
159
177
|
for (const cb of this.startListeners) {
|
|
160
178
|
cb();
|
|
161
179
|
}
|
|
162
180
|
};
|
|
163
181
|
utterance.onend = () => {
|
|
164
|
-
|
|
182
|
+
if (!isCurrent())
|
|
183
|
+
return;
|
|
184
|
+
settle();
|
|
165
185
|
for (const cb of this.endListeners) {
|
|
166
186
|
cb();
|
|
167
187
|
}
|
|
168
|
-
resolve();
|
|
169
188
|
};
|
|
170
189
|
utterance.onerror = (event) => {
|
|
190
|
+
if (!isCurrent())
|
|
191
|
+
return;
|
|
171
192
|
this.currentUtterance = null;
|
|
193
|
+
this.settleCurrentSpeech = null;
|
|
172
194
|
const error = new Error(`Speech synthesis error: ${event.error}`);
|
|
173
195
|
for (const cb of this.errorListeners) {
|
|
174
196
|
cb(error);
|
|
@@ -176,19 +198,22 @@ export class BrowserSynthesisTTSAdapter {
|
|
|
176
198
|
reject(error);
|
|
177
199
|
};
|
|
178
200
|
utterance.onboundary = (event) => {
|
|
201
|
+
if (!isCurrent())
|
|
202
|
+
return;
|
|
179
203
|
for (const cb of this.boundaryListeners) {
|
|
180
204
|
cb(event.charIndex, event.charLength || 1);
|
|
181
205
|
}
|
|
182
206
|
};
|
|
183
207
|
this.currentUtterance = utterance;
|
|
208
|
+
this.settleCurrentSpeech = settle;
|
|
184
209
|
this.synthesis?.speak(utterance);
|
|
185
210
|
});
|
|
186
211
|
}
|
|
187
212
|
stop() {
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
213
|
+
++this.operationGeneration;
|
|
214
|
+
// Settle before native cancel: it may emit synchronous callbacks or none.
|
|
215
|
+
this.settleCurrentSpeech?.();
|
|
216
|
+
this.synthesis?.cancel();
|
|
192
217
|
}
|
|
193
218
|
pause() {
|
|
194
219
|
if (this.synthesis) {
|
|
@@ -224,6 +249,9 @@ export class BrowserSynthesisTTSAdapter {
|
|
|
224
249
|
}
|
|
225
250
|
async dispose() {
|
|
226
251
|
this.stop();
|
|
252
|
+
++this.initializationGeneration;
|
|
253
|
+
this.cancelVoiceLoad?.();
|
|
254
|
+
this.initialization = null;
|
|
227
255
|
this.synthesis = null;
|
|
228
256
|
this.voices = [];
|
|
229
257
|
this.startListeners.clear();
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Should a host offer local (downloadable) speech recognition?
|
|
3
|
+
*
|
|
4
|
+
* The browser's own speech recognition (`SpeechRecognition`) is a thin
|
|
5
|
+
* client for a vendor speech service, so "the API exists" does not mean it
|
|
6
|
+
* works. This looks only at what the browser exposes: it makes no network
|
|
7
|
+
* request and never opens the microphone (so there is no permission prompt).
|
|
8
|
+
*
|
|
9
|
+
* - `'works'`: Chrome-family browsers with the API (Chrome, Edge, Safari).
|
|
10
|
+
* - `'missing'`: no `SpeechRecognition` at all (Firefox).
|
|
11
|
+
* - `'unreliable'`: the API is there but has no speech service behind it:
|
|
12
|
+
* Brave (it ends instantly or fails with `network`), or an embedded
|
|
13
|
+
* Chromium (Electron) with no vendor speech key.
|
|
14
|
+
*
|
|
15
|
+
* Anything but `'works'` is a reason to offer the local model. A recogniser
|
|
16
|
+
* that still turns out to end instantly is caught later by smrt-ui's
|
|
17
|
+
* dictation state machine, which reports it as an error.
|
|
18
|
+
*/
|
|
19
|
+
export type BrowserSpeechSupport = 'works' | 'missing' | 'unreliable';
|
|
20
|
+
/** The browser objects the probe reads; injectable for tests. */
|
|
21
|
+
export interface BrowserSpeechProbeEnv {
|
|
22
|
+
window?: Record<string, unknown>;
|
|
23
|
+
navigator?: {
|
|
24
|
+
userAgent?: string;
|
|
25
|
+
brave?: unknown;
|
|
26
|
+
};
|
|
27
|
+
}
|
|
28
|
+
export declare function probeBrowserSpeech(env?: BrowserSpeechProbeEnv): Promise<BrowserSpeechSupport>;
|
|
29
|
+
//# sourceMappingURL=speech-probe.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"speech-probe.d.ts","sourceRoot":"","sources":["../../../src/browser-ai/capabilities/speech-probe.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;GAiBG;AACH,MAAM,MAAM,oBAAoB,GAAG,OAAO,GAAG,SAAS,GAAG,YAAY,CAAC;AAEtE,iEAAiE;AACjE,MAAM,WAAW,qBAAqB;IACpC,MAAM,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IACjC,SAAS,CAAC,EAAE;QAAE,SAAS,CAAC,EAAE,MAAM,CAAC;QAAC,KAAK,CAAC,EAAE,OAAO,CAAA;KAAE,CAAC;CACrD;AAED,wBAAsB,kBAAkB,CACtC,GAAG,GAAE,qBAA0B,GAC9B,OAAO,CAAC,oBAAoB,CAAC,CAiB/B"}
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
export async function probeBrowserSpeech(env = {}) {
|
|
2
|
+
const win = env.window ??
|
|
3
|
+
(typeof window !== 'undefined'
|
|
4
|
+
? window
|
|
5
|
+
: undefined);
|
|
6
|
+
const nav = env.navigator ?? (typeof navigator !== 'undefined' ? navigator : undefined);
|
|
7
|
+
if (!win)
|
|
8
|
+
return 'missing';
|
|
9
|
+
if (!('SpeechRecognition' in win) && !('webkitSpeechRecognition' in win)) {
|
|
10
|
+
return 'missing';
|
|
11
|
+
}
|
|
12
|
+
// Brave defines `navigator.brave`; its recogniser has no service behind it.
|
|
13
|
+
if (nav && 'brave' in nav && nav.brave)
|
|
14
|
+
return 'unreliable';
|
|
15
|
+
// Electron ships the API without the vendor speech key.
|
|
16
|
+
if (/\bElectron\//.test(nav?.userAgent ?? ''))
|
|
17
|
+
return 'unreliable';
|
|
18
|
+
return 'works';
|
|
19
|
+
}
|
|
@@ -21,6 +21,15 @@ export declare class InitializationError extends BrowserAIError {
|
|
|
21
21
|
export declare class CapabilityNotAvailableError extends BrowserAIError {
|
|
22
22
|
constructor(capability: string, adapter?: string);
|
|
23
23
|
}
|
|
24
|
+
/**
|
|
25
|
+
* Thrown when something needs an on-device model that is not stored on this
|
|
26
|
+
* device yet and was asked not to download it. `dictationKind` lets smrt-ui's
|
|
27
|
+
* `Dictation` show "The speech model isn't downloaded yet".
|
|
28
|
+
*/
|
|
29
|
+
export declare class ModelNotDownloadedError extends BrowserAIError {
|
|
30
|
+
readonly dictationKind = "model-missing";
|
|
31
|
+
constructor(model: string, adapter?: string);
|
|
32
|
+
}
|
|
24
33
|
/**
|
|
25
34
|
* Thrown when a model download fails
|
|
26
35
|
*/
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"errors.d.ts","sourceRoot":"","sources":["../../../src/browser-ai/core/errors.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH;;GAEG;AACH,qBAAa,cAAe,SAAQ,KAAK;IAG9B,IAAI,EAAE,MAAM;IACZ,OAAO,CAAC,EAAE,MAAM;gBAFvB,OAAO,EAAE,MAAM,EACR,IAAI,EAAE,MAAM,EACZ,OAAO,CAAC,EAAE,MAAM,YAAA;CAK1B;AAED;;GAEG;AACH,qBAAa,mBAAoB,SAAQ,cAAc;gBACzC,OAAO,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,MAAM;CAQ7C;AAED;;GAEG;AACH,qBAAa,2BAA4B,SAAQ,cAAc;gBACjD,UAAU,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,MAAM;CAQjD;AAED;;GAEG;AACH,qBAAa,aAAc,SAAQ,cAAc;IAEtC,GAAG,EAAE,MAAM;gBAAX,GAAG,EAAE,MAAM,EAClB,MAAM,CAAC,EAAE,MAAM,EACf,OAAO,CAAC,EAAE,MAAM;CASnB;AAED;;GAEG;AACH,qBAAa,cAAe,SAAQ,cAAc;IAEvC,KAAK,EAAE,MAAM;gBAAb,KAAK,EAAE,MAAM,EACpB,MAAM,CAAC,EAAE,MAAM,EACf,OAAO,CAAC,EAAE,MAAM;CASnB;AAED;;GAEG;AACH,qBAAa,YAAa,SAAQ,cAAc;gBAClC,SAAS,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,MAAM;CAQnE;AAED;;GAEG;AACH,qBAAa,qBAAsB,SAAQ,cAAc;gBAC3C,UAAU,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,MAAM;CAIjD;AAED;;GAEG;AACH,qBAAa,iBAAkB,SAAQ,cAAc;gBACvC,aAAa,EAAE,MAAM,EAAE,WAAW,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,MAAM;CAQzE;AAED;;GAEG;AACH,qBAAa,uBAAwB,SAAQ,cAAc;gBAC7C,WAAW,EAAE,MAAM,EAAE,cAAc,EAAE,MAAM,EAAE;CAO1D"}
|
|
1
|
+
{"version":3,"file":"errors.d.ts","sourceRoot":"","sources":["../../../src/browser-ai/core/errors.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH;;GAEG;AACH,qBAAa,cAAe,SAAQ,KAAK;IAG9B,IAAI,EAAE,MAAM;IACZ,OAAO,CAAC,EAAE,MAAM;gBAFvB,OAAO,EAAE,MAAM,EACR,IAAI,EAAE,MAAM,EACZ,OAAO,CAAC,EAAE,MAAM,YAAA;CAK1B;AAED;;GAEG;AACH,qBAAa,mBAAoB,SAAQ,cAAc;gBACzC,OAAO,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,MAAM;CAQ7C;AAED;;GAEG;AACH,qBAAa,2BAA4B,SAAQ,cAAc;gBACjD,UAAU,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,MAAM;CAQjD;AAED;;;;GAIG;AACH,qBAAa,uBAAwB,SAAQ,cAAc;IACzD,QAAQ,CAAC,aAAa,mBAAmB;gBAC7B,KAAK,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,MAAM;CAQ5C;AAED;;GAEG;AACH,qBAAa,aAAc,SAAQ,cAAc;IAEtC,GAAG,EAAE,MAAM;gBAAX,GAAG,EAAE,MAAM,EAClB,MAAM,CAAC,EAAE,MAAM,EACf,OAAO,CAAC,EAAE,MAAM;CASnB;AAED;;GAEG;AACH,qBAAa,cAAe,SAAQ,cAAc;IAEvC,KAAK,EAAE,MAAM;gBAAb,KAAK,EAAE,MAAM,EACpB,MAAM,CAAC,EAAE,MAAM,EACf,OAAO,CAAC,EAAE,MAAM;CASnB;AAED;;GAEG;AACH,qBAAa,YAAa,SAAQ,cAAc;gBAClC,SAAS,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,MAAM;CAQnE;AAED;;GAEG;AACH,qBAAa,qBAAsB,SAAQ,cAAc;gBAC3C,UAAU,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,MAAM;CAIjD;AAED;;GAEG;AACH,qBAAa,iBAAkB,SAAQ,cAAc;gBACvC,aAAa,EAAE,MAAM,EAAE,WAAW,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,MAAM;CAQzE;AAED;;GAEG;AACH,qBAAa,uBAAwB,SAAQ,cAAc;gBAC7C,WAAW,EAAE,MAAM,EAAE,cAAc,EAAE,MAAM,EAAE;CAO1D"}
|
|
@@ -32,6 +32,18 @@ export class CapabilityNotAvailableError extends BrowserAIError {
|
|
|
32
32
|
this.name = 'CapabilityNotAvailableError';
|
|
33
33
|
}
|
|
34
34
|
}
|
|
35
|
+
/**
|
|
36
|
+
* Thrown when something needs an on-device model that is not stored on this
|
|
37
|
+
* device yet and was asked not to download it. `dictationKind` lets smrt-ui's
|
|
38
|
+
* `Dictation` show "The speech model isn't downloaded yet".
|
|
39
|
+
*/
|
|
40
|
+
export class ModelNotDownloadedError extends BrowserAIError {
|
|
41
|
+
dictationKind = 'model-missing';
|
|
42
|
+
constructor(model, adapter) {
|
|
43
|
+
super(`The speech model isn't downloaded yet (${model})`, 'MODEL_NOT_DOWNLOADED', adapter);
|
|
44
|
+
this.name = 'ModelNotDownloadedError';
|
|
45
|
+
}
|
|
46
|
+
}
|
|
35
47
|
/**
|
|
36
48
|
* Thrown when a model download fails
|
|
37
49
|
*/
|
|
@@ -8,5 +8,6 @@ export * from './adapters/llm/index.js';
|
|
|
8
8
|
export * from './adapters/stt/index.js';
|
|
9
9
|
export * from './adapters/tts/index.js';
|
|
10
10
|
export * from './capabilities/detector.js';
|
|
11
|
+
export * from './capabilities/speech-probe.js';
|
|
11
12
|
export * from './core/index.js';
|
|
12
13
|
//# sourceMappingURL=index.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/browser-ai/index.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAGH,cAAc,yBAAyB,CAAC;AAExC,cAAc,yBAAyB,CAAC;AAExC,cAAc,yBAAyB,CAAC;AAExC,cAAc,4BAA4B,CAAC;
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/browser-ai/index.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAGH,cAAc,yBAAyB,CAAC;AAExC,cAAc,yBAAyB,CAAC;AAExC,cAAc,yBAAyB,CAAC;AAExC,cAAc,4BAA4B,CAAC;AAC3C,cAAc,gCAAgC,CAAC;AAE/C,cAAc,iBAAiB,CAAC"}
|
package/dist/browser-ai/index.js
CHANGED
|
@@ -12,5 +12,6 @@ export * from './adapters/stt/index.js';
|
|
|
12
12
|
export * from './adapters/tts/index.js';
|
|
13
13
|
// Capability detection
|
|
14
14
|
export * from './capabilities/detector.js';
|
|
15
|
+
export * from './capabilities/speech-probe.js';
|
|
15
16
|
// Core types and errors
|
|
16
17
|
export * from './core/index.js';
|