@sdata/web-vue 3.22.0 → 3.22.2

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.
@@ -12,7 +12,7 @@ interface UseSpeechOptions {
12
12
  export declare function useSpeech(allowSpeech: MaybeRefOrGetter<SenderAllowSpeech | undefined>, options: UseSpeechOptions): {
13
13
  available: import("vue").ComputedRef<boolean>;
14
14
  recording: import("vue").ComputedRef<boolean>;
15
- requesting: import("vue").ShallowRef<boolean, boolean>;
15
+ requesting: import("vue").ComputedRef<boolean>;
16
16
  statusText: import("vue").ComputedRef<string>;
17
17
  trigger: (breakRecording?: boolean) => Promise<void>;
18
18
  };
@@ -55,6 +55,7 @@ function useSpeech(allowSpeech, options) {
55
55
  const supported = shallowRef(false);
56
56
  const internalRecording = shallowRef(false);
57
57
  const requesting = shallowRef(false);
58
+ const stopping = shallowRef(false);
58
59
  const captureError = shallowRef();
59
60
  const stream = shallowRef();
60
61
  const audioContext = shallowRef();
@@ -66,6 +67,7 @@ function useSpeech(allowSpeech, options) {
66
67
  const sequence = shallowRef(0);
67
68
  let generatedWorkletUrl;
68
69
  let resolveWorkletFlush;
70
+ let workletReady = false;
69
71
  let disposed = false;
70
72
  const recording = computed(() => controlled.value && typeof config.value === "object" ? Boolean(config.value.recording) : internalRecording.value);
71
73
  const available = computed(() => Boolean(config.value) && (controlled.value || supported.value) && !(captureError.value && isPermissionDeniedError(captureError.value.error)));
@@ -138,51 +140,65 @@ function useSpeech(allowSpeech, options) {
138
140
  });
139
141
  const releaseResources = function() {
140
142
  var _ref = _asyncToGenerator(function* () {
141
- var _workletNode$value2, _sourceNode$value, _stream$value, _audioContext$value, _audioContext$value2;
143
+ var _workletNode$value2, _sourceNode$value, _stream$value, _audioContext$value;
142
144
  (_workletNode$value2 = workletNode.value) === null || _workletNode$value2 === void 0 || _workletNode$value2.disconnect();
143
145
  (_sourceNode$value = sourceNode.value) === null || _sourceNode$value === void 0 || _sourceNode$value.disconnect();
144
146
  (_stream$value = stream.value) === null || _stream$value === void 0 || _stream$value.getTracks().forEach((track) => track.stop());
145
- if (((_audioContext$value = audioContext.value) === null || _audioContext$value === void 0 ? void 0 : _audioContext$value.state) !== "closed") yield (_audioContext$value2 = audioContext.value) === null || _audioContext$value2 === void 0 ? void 0 : _audioContext$value2.close();
147
+ if (((_audioContext$value = audioContext.value) === null || _audioContext$value === void 0 ? void 0 : _audioContext$value.state) === "running") yield audioContext.value.suspend();
146
148
  if (socket.value && (socket.value.readyState === WebSocket.OPEN || socket.value.readyState === WebSocket.CONNECTING)) socket.value.close(1e3, "speech-ended");
147
149
  workletNode.value = void 0;
148
150
  sourceNode.value = void 0;
149
151
  stream.value = void 0;
150
- audioContext.value = void 0;
151
152
  socket.value = void 0;
152
153
  });
153
154
  return function releaseResources() {
154
155
  return _ref.apply(this, arguments);
155
156
  };
156
157
  }();
158
+ const closeAudioContext = function() {
159
+ var _ref2 = _asyncToGenerator(function* () {
160
+ if (audioContext.value && audioContext.value.state !== "closed") yield audioContext.value.close();
161
+ audioContext.value = void 0;
162
+ workletReady = false;
163
+ });
164
+ return function closeAudioContext() {
165
+ return _ref2.apply(this, arguments);
166
+ };
167
+ }();
157
168
  const stopCapture = function() {
158
- var _ref2 = _asyncToGenerator(function* (reason = "manual") {
159
- var _socket$value, _config$value$onRecor, _config$value;
160
- if (!internalRecording.value) return;
161
- yield flushWorklet();
162
- const endedAt = performance.now();
163
- internalRecording.value = false;
164
- if (((_socket$value = socket.value) === null || _socket$value === void 0 ? void 0 : _socket$value.readyState) === WebSocket.OPEN && typeof config.value === "object" && config.value.sendMetadata !== false) socket.value.send(JSON.stringify({
165
- type: "end",
166
- reason
167
- }));
168
- yield releaseResources();
169
- if (typeof config.value === "object") (_config$value$onRecor = (_config$value = config.value).onRecordingChange) === null || _config$value$onRecor === void 0 || _config$value$onRecor.call(_config$value, false);
170
- options.onEnd({
171
- source: "capture",
172
- reason,
173
- startedAt: startedAt.value,
174
- endedAt,
175
- duration: endedAt - startedAt.value,
176
- chunks: chunks.value
177
- });
169
+ var _ref3 = _asyncToGenerator(function* (reason = "manual") {
170
+ if (!internalRecording.value || stopping.value) return;
171
+ stopping.value = true;
172
+ try {
173
+ var _socket$value, _config$value$onRecor, _config$value;
174
+ yield flushWorklet();
175
+ const endedAt = performance.now();
176
+ internalRecording.value = false;
177
+ if (((_socket$value = socket.value) === null || _socket$value === void 0 ? void 0 : _socket$value.readyState) === WebSocket.OPEN && typeof config.value === "object" && config.value.sendMetadata !== false) socket.value.send(JSON.stringify({
178
+ type: "end",
179
+ reason
180
+ }));
181
+ yield releaseResources();
182
+ if (typeof config.value === "object") (_config$value$onRecor = (_config$value = config.value).onRecordingChange) === null || _config$value$onRecor === void 0 || _config$value$onRecor.call(_config$value, false);
183
+ options.onEnd({
184
+ source: "capture",
185
+ reason,
186
+ startedAt: startedAt.value,
187
+ endedAt,
188
+ duration: endedAt - startedAt.value,
189
+ chunks: chunks.value
190
+ });
191
+ } finally {
192
+ stopping.value = false;
193
+ }
178
194
  });
179
195
  return function stopCapture() {
180
- return _ref2.apply(this, arguments);
196
+ return _ref3.apply(this, arguments);
181
197
  };
182
198
  }();
183
199
  const startCapture = function() {
184
- var _ref3 = _asyncToGenerator(function* () {
185
- if (requesting.value || internalRecording.value || !available.value) return;
200
+ var _ref4 = _asyncToGenerator(function* () {
201
+ if (requesting.value || stopping.value || internalRecording.value || !available.value) return;
186
202
  requesting.value = true;
187
203
  captureError.value = void 0;
188
204
  let phase = "permission";
@@ -207,10 +223,18 @@ function useSpeech(allowSpeech, options) {
207
223
  }
208
224
  }
209
225
  phase = "audioContext";
210
- const nextAudioContext = resolveAudioContext();
211
- audioContext.value = nextAudioContext;
226
+ let nextAudioContext = audioContext.value;
227
+ if (!nextAudioContext) {
228
+ nextAudioContext = resolveAudioContext();
229
+ audioContext.value = nextAudioContext;
230
+ workletReady = false;
231
+ }
232
+ if (nextAudioContext.state === "suspended") yield nextAudioContext.resume();
212
233
  phase = "audioWorklet";
213
- yield nextAudioContext.audioWorklet.addModule(resolveWorkletUrl());
234
+ if (!workletReady) {
235
+ yield nextAudioContext.audioWorklet.addModule(resolveWorkletUrl());
236
+ workletReady = true;
237
+ }
214
238
  if (disposed) {
215
239
  yield releaseResources();
216
240
  return;
@@ -271,16 +295,18 @@ function useSpeech(allowSpeech, options) {
271
295
  captureError.value = errorEvent;
272
296
  options.onError(errorEvent);
273
297
  yield releaseResources();
298
+ yield closeAudioContext();
274
299
  } finally {
275
300
  requesting.value = false;
276
301
  }
277
302
  });
278
303
  return function startCapture() {
279
- return _ref3.apply(this, arguments);
304
+ return _ref4.apply(this, arguments);
280
305
  };
281
306
  }();
282
307
  const trigger = function() {
283
- var _ref4 = _asyncToGenerator(function* (breakRecording = false) {
308
+ var _ref5 = _asyncToGenerator(function* (breakRecording = false) {
309
+ if (requesting.value || stopping.value) return;
284
310
  if (breakRecording && !recording.value) return;
285
311
  if (controlled.value && typeof config.value === "object") {
286
312
  var _config$value$onRecor2, _config$value2;
@@ -307,7 +333,7 @@ function useSpeech(allowSpeech, options) {
307
333
  else yield startCapture();
308
334
  });
309
335
  return function trigger() {
310
- return _ref4.apply(this, arguments);
336
+ return _ref5.apply(this, arguments);
311
337
  };
312
338
  }();
313
339
  onMounted(() => {
@@ -324,12 +350,13 @@ function useSpeech(allowSpeech, options) {
324
350
  disposed = true;
325
351
  if (internalRecording.value) yield stopCapture("unmount");
326
352
  else yield releaseResources();
353
+ yield closeAudioContext();
327
354
  if (generatedWorkletUrl) URL.revokeObjectURL(generatedWorkletUrl);
328
355
  }));
329
356
  return {
330
357
  available,
331
358
  recording,
332
- requesting,
359
+ requesting: computed(() => requesting.value || stopping.value),
333
360
  statusText,
334
361
  trigger
335
362
  };
@@ -2,7 +2,7 @@
2
2
  "$schema": "https://raw.githubusercontent.com/JetBrains/web-types/master/schema/web-types.json",
3
3
  "framework": "vue",
4
4
  "name": "@sdata/web-vue",
5
- "version": "3.21.0",
5
+ "version": "3.22.1",
6
6
  "contributions": {
7
7
  "html": {
8
8
  "types-syntax": "typescript",
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@sdata/web-vue",
3
- "version": "3.22.0",
3
+ "version": "3.22.2",
4
4
  "description": "SD Design Vue: A Vue.js 3 UI Library",
5
5
  "keywords": [
6
6
  "sd",