@wcstack/speech 1.22.6 → 1.24.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.
package/README.ja.md CHANGED
@@ -263,6 +263,8 @@ const core = new SpeakCore();
263
263
  core.speak("こんにちは。");
264
264
  ```
265
265
 
266
+ Core の構造サーフェスは wcstack I/O ノード横断の規範です([async-io-node-guidelines §3.9](../../docs/async-io-node-guidelines.md))。要素なしで signals に束縛するには [@wcstack/signals — Core を直接束縛する](../signals/README.ja.md#core-を直接束縛する要素なし) を参照。
267
+
266
268
  ## ライセンス
267
269
 
268
270
  MIT
package/README.md CHANGED
@@ -264,6 +264,8 @@ const core = new SpeakCore();
264
264
  core.speak("Hello, world.");
265
265
  ```
266
266
 
267
+ The structural Core surface is normative across wcstack IO nodes ([async-io-node-guidelines §3.9](../../docs/async-io-node-guidelines.md)); to bind it into signals with no element at all, see [@wcstack/signals — Binding a Core directly](../signals/README.md#binding-a-core-directly-no-element).
268
+
267
269
  ## License
268
270
 
269
271
  MIT
package/dist/index.d.ts CHANGED
@@ -9,10 +9,27 @@ interface WcsIoErrorInfo {
9
9
  readonly message: string;
10
10
  }
11
11
 
12
+ /**
13
+ * Observation semantics of a `properties` entry.
14
+ *
15
+ * "state" — current value. A snapshot may cache it, and equality-based dedupe is safe.
16
+ * "event" — occurrence. Repeated identical payloads are distinct occurrences; never dedupe.
17
+ * "handle" — live / opaque resource with its own lifecycle (e.g. MediaStream). Not
18
+ * snapshot-safe and not necessarily serializable; consumers need an explicit
19
+ * ref / callback surface rather than a value slot.
20
+ */
21
+ type WcBindableSemantics = "state" | "event" | "handle";
12
22
  interface IWcBindableProperty {
13
23
  readonly name: string;
14
24
  readonly event: string;
15
25
  readonly getter?: (event: Event) => any;
26
+ /**
27
+ * Optional, additive, forward-compatible. An absent value means **unspecified**, NOT
28
+ * "state": a reader that finds no `semantics` MUST keep the behavior it had before this
29
+ * field existed (deliver the update as-is; do not start deduping, caching or serializing
30
+ * on assumption). Only an explicit value licenses a reader to change its handling.
31
+ */
32
+ readonly semantics?: WcBindableSemantics;
16
33
  }
17
34
  interface IWcBindableInput {
18
35
  readonly name: string;
package/dist/index.esm.js CHANGED
@@ -238,21 +238,21 @@ class SpeakCore extends EventTarget {
238
238
  protocol: "wc-bindable",
239
239
  version: 1,
240
240
  properties: [
241
- { name: "voices", event: "wcs-speak:voices-changed" },
242
- { name: "speaking", event: "wcs-speak:speaking-changed" },
243
- { name: "paused", event: "wcs-speak:paused-changed" },
244
- { name: "pending", event: "wcs-speak:pending-changed" },
245
- { name: "charIndex", event: "wcs-speak:boundary", getter: (e) => e.detail?.charIndex ?? null },
246
- { name: "spokenWord", event: "wcs-speak:boundary", getter: (e) => e.detail?.word ?? null },
247
- { name: "error", event: "wcs-speak:error" },
241
+ { name: "voices", event: "wcs-speak:voices-changed", semantics: "state" },
242
+ { name: "speaking", event: "wcs-speak:speaking-changed", semantics: "state" },
243
+ { name: "paused", event: "wcs-speak:paused-changed", semantics: "state" },
244
+ { name: "pending", event: "wcs-speak:pending-changed", semantics: "state" },
245
+ { name: "charIndex", event: "wcs-speak:boundary", semantics: "event", getter: (e) => e.detail?.charIndex ?? null },
246
+ { name: "spokenWord", event: "wcs-speak:boundary", semantics: "event", getter: (e) => e.detail?.word ?? null },
247
+ { name: "error", event: "wcs-speak:error", semantics: "state" },
248
248
  // Serializable failure taxonomy (stable code / phase / recoverable), or null.
249
249
  // Additive bindable output derived from `error.error` (the
250
250
  // SpeechSynthesisErrorEvent.error code / "unsupported"); the existing `error`
251
251
  // property/event are unchanged. Fires wcs-speak:error-info-changed. No lane —
252
252
  // speak() is a momentary queue submission with no competing async operation to
253
253
  // serialize.
254
- { name: "errorInfo", event: "wcs-speak:error-info-changed" },
255
- { name: "unsupported", event: "wcs-speak:unsupported-changed" },
254
+ { name: "errorInfo", event: "wcs-speak:error-info-changed", semantics: "state" },
255
+ { name: "unsupported", event: "wcs-speak:unsupported-changed", semantics: "state" },
256
256
  ],
257
257
  commands: [
258
258
  { name: "speak" },
@@ -722,6 +722,48 @@ function registerAutoTrigger() {
722
722
  document.addEventListener("click", handleClick$1);
723
723
  }
724
724
 
725
+ // ===========================================================================
726
+ // AUTO-GENERATED FILE - DO NOT EDIT.
727
+ // Generated from /protocol/upgrade-properties.ts by scripts/sync-protocol-types.mjs.
728
+ // Run `node scripts/sync-protocol-types.mjs` after editing the source.
729
+ // ===========================================================================
730
+ function hasAccessorOnPrototype(target, name) {
731
+ let proto = Object.getPrototypeOf(target);
732
+ while (proto !== null) {
733
+ const descriptor = Object.getOwnPropertyDescriptor(proto, name);
734
+ if (descriptor !== undefined) {
735
+ return typeof descriptor.get === "function" || typeof descriptor.set === "function";
736
+ }
737
+ proto = Object.getPrototypeOf(proto);
738
+ }
739
+ return false;
740
+ }
741
+ /**
742
+ * `connectedCallback` の先頭で呼ぶ。宣言済み input のうち upgrade 前の代入で
743
+ * accessor をシャドウしている own プロパティを、delete → 再代入で setter に通し直す。
744
+ *
745
+ * - 冪等: 再代入は accessor を通るので own プロパティは残らず、2 回目以降は no-op。
746
+ * - 宣言に `inputs` が無い要素、`wcBindable` を持たない要素では何もしない。
747
+ * - 値の意味は変えない。今まで捨てられていた代入が届くようになる一方向の変化。
748
+ */
749
+ function upgradeProperties(element) {
750
+ const declaration = element.constructor?.wcBindable;
751
+ const inputs = declaration?.inputs;
752
+ if (inputs === undefined)
753
+ return;
754
+ for (const input of inputs) {
755
+ const name = input.name;
756
+ if (!Object.prototype.hasOwnProperty.call(element, name))
757
+ continue;
758
+ if (!hasAccessorOnPrototype(element, name))
759
+ continue;
760
+ const record = element;
761
+ const value = record[name];
762
+ delete record[name];
763
+ record[name] = value;
764
+ }
765
+ }
766
+
725
767
  /**
726
768
  * `<wcs-speak>` — declarative text-to-speech. Wraps SpeakCore and exposes:
727
769
  *
@@ -970,6 +1012,8 @@ class WcsSpeak extends HTMLElement {
970
1012
  }
971
1013
  // --- Lifecycle ---
972
1014
  connectedCallback() {
1015
+ // upgrade 前に代入された input を取り込み直す(doc 13 §1.2 / Phase A1)
1016
+ upgradeProperties(this);
973
1017
  this.style.display = "none";
974
1018
  if (config.autoTrigger) {
975
1019
  registerAutoTrigger();
@@ -1016,19 +1060,19 @@ class ListenCore extends EventTarget {
1016
1060
  protocol: "wc-bindable",
1017
1061
  version: 1,
1018
1062
  properties: [
1019
- { name: "interimTranscript", event: "wcs-listen:interim-changed" },
1020
- { name: "finalTranscript", event: "wcs-listen:final-changed" },
1021
- { name: "result", event: "wcs-listen:result" },
1022
- { name: "listening", event: "wcs-listen:listening-changed" },
1023
- { name: "permission", event: "wcs-listen:permission-changed" },
1024
- { name: "error", event: "wcs-listen:error" },
1063
+ { name: "interimTranscript", event: "wcs-listen:interim-changed", semantics: "state" },
1064
+ { name: "finalTranscript", event: "wcs-listen:final-changed", semantics: "state" },
1065
+ { name: "result", event: "wcs-listen:result", semantics: "event" },
1066
+ { name: "listening", event: "wcs-listen:listening-changed", semantics: "state" },
1067
+ { name: "permission", event: "wcs-listen:permission-changed", semantics: "state" },
1068
+ { name: "error", event: "wcs-listen:error", semantics: "state" },
1025
1069
  // Serializable failure taxonomy (stable code / phase / recoverable), or null.
1026
1070
  // Additive bindable output derived from `error.error` (the
1027
1071
  // SpeechRecognitionErrorEvent.error code / "unsupported"); the existing `error`
1028
1072
  // property/event are unchanged. Fires wcs-listen:error-info-changed. No lane —
1029
1073
  // recognition has no competing async operation to serialize.
1030
- { name: "errorInfo", event: "wcs-listen:error-info-changed" },
1031
- { name: "unsupported", event: "wcs-listen:unsupported-changed" },
1074
+ { name: "errorInfo", event: "wcs-listen:error-info-changed", semantics: "state" },
1075
+ { name: "unsupported", event: "wcs-listen:unsupported-changed", semantics: "state" },
1032
1076
  ],
1033
1077
  commands: [
1034
1078
  { name: "start" },
@@ -1466,7 +1510,7 @@ class WcsListen extends HTMLElement {
1466
1510
  ...ListenCore.wcBindable,
1467
1511
  properties: [
1468
1512
  ...ListenCore.wcBindable.properties,
1469
- { name: "trigger", event: "wcs-listen:trigger-changed" },
1513
+ { name: "trigger", event: "wcs-listen:trigger-changed", semantics: "state" },
1470
1514
  ],
1471
1515
  inputs: [
1472
1516
  { name: "lang", attribute: "lang" },
@@ -1673,6 +1717,8 @@ class WcsListen extends HTMLElement {
1673
1717
  }
1674
1718
  // --- Lifecycle ---
1675
1719
  connectedCallback() {
1720
+ // upgrade 前に代入された input を取り込み直す(doc 13 §1.2 / Phase A1)
1721
+ upgradeProperties(this);
1676
1722
  this.style.display = "none";
1677
1723
  if (config.autoTrigger) {
1678
1724
  registerListenAutoTrigger();