@pie-players/pie-tool-annotation-toolbar 0.3.19 → 0.3.20

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.
@@ -0,0 +1,33 @@
1
+ function o(e) {
2
+ "@babel/helpers - typeof";
3
+ return o = typeof Symbol == "function" && typeof Symbol.iterator == "symbol" ? function(t) {
4
+ return typeof t;
5
+ } : function(t) {
6
+ return t && typeof Symbol == "function" && t.constructor === Symbol && t !== Symbol.prototype ? "symbol" : typeof t;
7
+ }, o(e);
8
+ }
9
+ function i(e, t) {
10
+ if (o(e) != "object" || !e) return e;
11
+ var r = e[Symbol.toPrimitive];
12
+ if (r !== void 0) {
13
+ var n = r.call(e, t || "default");
14
+ if (o(n) != "object") return n;
15
+ throw new TypeError("@@toPrimitive must return a primitive value.");
16
+ }
17
+ return (t === "string" ? String : Number)(e);
18
+ }
19
+ function u(e) {
20
+ var t = i(e, "string");
21
+ return o(t) == "symbol" ? t : t + "";
22
+ }
23
+ function f(e, t, r) {
24
+ return (t = u(t)) in e ? Object.defineProperty(e, t, {
25
+ value: r,
26
+ enumerable: !0,
27
+ configurable: !0,
28
+ writable: !0
29
+ }) : e[t] = r, e;
30
+ }
31
+ export {
32
+ f as t
33
+ };
@@ -0,0 +1,393 @@
1
+ import { t as h } from "./defineProperty-CyepwRr5.js";
2
+ var b = (t) => {
3
+ const e = (t.providerOptions && typeof t.providerOptions == "object" ? t.providerOptions : {}).__pieTelemetry;
4
+ return typeof e == "function" ? e : void 0;
5
+ }, S = {
6
+ pie: 3e3,
7
+ custom: 3e3
8
+ }, v = (t) => t.replace(/\/+$/, ""), k = (t) => {
9
+ const e = v(t.apiEndpoint), r = (t.provider || "").toLowerCase();
10
+ return r === "polly" || r === "google" ? `${e}/${r}/voices` : `${e}/voices`;
11
+ }, T = (t) => t.transportMode === "custom" ? "custom" : t.transportMode === "pie" ? "pie" : t.provider === "custom" ? "custom" : "pie", w = (t, e) => t.endpointMode ? t.endpointMode : e === "custom" ? "rootPost" : "synthesizePath", A = (t, e) => t.endpointValidationMode ? t.endpointValidationMode : e === "custom" ? "none" : "voices", R = (t) => {
12
+ const e = t.providerOptions || {};
13
+ if (typeof e.speedRate == "string") return e.speedRate;
14
+ const r = Number(t.rate ?? 1);
15
+ return !Number.isFinite(r) || r <= 0.95 ? "slow" : r >= 1.5 ? "fast" : "medium";
16
+ }, I = (t) => {
17
+ const e = [];
18
+ let r = 0;
19
+ const i = t.split(`
20
+ `).map((o) => o.trim()).filter(Boolean);
21
+ for (const o of i) try {
22
+ const s = JSON.parse(o), d = typeof s.type == "string" ? s.type : "word", n = typeof s.time == "number" && Number.isFinite(s.time) ? s.time : 0, a = typeof s.value == "string" ? s.value : "", c = typeof s.start == "number" && Number.isFinite(s.start) ? s.start : null, y = typeof s.end == "number" && Number.isFinite(s.end) ? s.end : null, g = c ?? r, l = y ?? g + Math.max(1, a.length || String(s.value || "").length);
23
+ r = Math.max(l + 1, r), e.push({
24
+ time: n,
25
+ type: d,
26
+ start: g,
27
+ end: l,
28
+ value: a
29
+ });
30
+ } catch {
31
+ }
32
+ return e;
33
+ }, M = {
34
+ pie: {
35
+ id: "pie",
36
+ resolveSynthesisUrl: (t) => {
37
+ const e = w(t, "pie"), r = v(t.apiEndpoint);
38
+ return e === "rootPost" ? r : `${r}/synthesize`;
39
+ },
40
+ buildRequestBody: (t, e) => {
41
+ const r = e.providerOptions || {}, i = typeof e.engine == "string" ? e.engine : typeof r.engine == "string" ? r.engine : void 0, o = typeof r.sampleRate == "number" && Number.isFinite(r.sampleRate) ? r.sampleRate : void 0, s = r.format === "mp3" || r.format === "ogg" || r.format === "pcm" ? r.format : void 0, d = Array.isArray(r.speechMarkTypes) ? r.speechMarkTypes.filter((n) => n === "word" || n === "sentence" || n === "ssml") : void 0;
42
+ return {
43
+ text: t,
44
+ provider: e.provider || "polly",
45
+ voice: e.voice,
46
+ language: e.language,
47
+ rate: e.rate,
48
+ engine: i,
49
+ sampleRate: o,
50
+ format: s,
51
+ speechMarkTypes: d,
52
+ includeSpeechMarks: !0
53
+ };
54
+ },
55
+ parseResponse: async (t) => {
56
+ const e = await t.json();
57
+ return {
58
+ audio: {
59
+ kind: "base64",
60
+ data: e.audio,
61
+ contentType: e.contentType
62
+ },
63
+ speechMarks: Array.isArray(e.speechMarks) ? e.speechMarks : []
64
+ };
65
+ }
66
+ },
67
+ custom: {
68
+ id: "custom",
69
+ resolveSynthesisUrl: (t) => {
70
+ const e = w(t, "custom"), r = v(t.apiEndpoint);
71
+ return e === "synthesizePath" ? `${r}/synthesize` : r;
72
+ },
73
+ buildRequestBody: (t, e) => {
74
+ const r = e.providerOptions || {}, i = typeof r.lang_id == "string" ? r.lang_id : e.language || "en-US", o = typeof r.cache == "boolean" ? r.cache : !0;
75
+ return {
76
+ text: t,
77
+ speedRate: R(e),
78
+ lang_id: i,
79
+ cache: o
80
+ };
81
+ },
82
+ parseResponse: async (t, e, r, i) => {
83
+ const o = await t.json(), s = {};
84
+ if (e.includeAuthOnAssetFetch)
85
+ for (const [n, a] of Object.entries(r)) n.toLowerCase() === "authorization" && (s[n] = a);
86
+ let d = [];
87
+ if (typeof o.word == "string" && o.word.length > 0) {
88
+ const n = await fetch(o.word, {
89
+ headers: s,
90
+ signal: i
91
+ });
92
+ n.ok && (d = I(await n.text()));
93
+ }
94
+ return {
95
+ audio: {
96
+ kind: "url",
97
+ url: o.audioContent
98
+ },
99
+ speechMarks: d
100
+ };
101
+ }
102
+ }
103
+ }, E = class {
104
+ constructor(t, e) {
105
+ h(this, "config", void 0), h(this, "adapter", void 0), h(this, "currentAudio", null), h(this, "pausedState", !1), h(this, "wordTimings", []), h(this, "highlightInterval", null), h(this, "intentionallyStopped", !1), h(this, "activeSynthesisController", null), h(this, "synthesisRunId", 0), h(this, "telemetryReporter", void 0), h(this, "onWordBoundary", void 0), this.config = t, this.adapter = e, this.telemetryReporter = b(t);
106
+ }
107
+ async emitTelemetry(t, e) {
108
+ try {
109
+ await this.telemetryReporter?.(t, e);
110
+ } catch (r) {
111
+ console.warn("[ServerTTSProvider] telemetry callback failed:", r);
112
+ }
113
+ }
114
+ async speak(t) {
115
+ this.stop(), this.intentionallyStopped = !1;
116
+ const e = ++this.synthesisRunId, r = new AbortController();
117
+ this.activeSynthesisController = r;
118
+ const { audioUrl: i, wordTimings: o } = await this.synthesizeSpeech(t, r.signal, e);
119
+ if (e !== this.synthesisRunId) {
120
+ URL.revokeObjectURL(i);
121
+ return;
122
+ }
123
+ const s = this.config.rate || 1;
124
+ return this.wordTimings = o.map((d) => ({
125
+ ...d,
126
+ time: d.time / s
127
+ })), new Promise((d, n) => {
128
+ const a = new Audio(i);
129
+ this.currentAudio = a, this.config.rate && (a.playbackRate = Math.max(0.25, Math.min(4, this.config.rate))), this.config.volume !== void 0 && (a.volume = Math.max(0, Math.min(1, this.config.volume))), a.onplay = () => {
130
+ this.pausedState = !1, this.onWordBoundary && this.wordTimings.length > 0 && this.startWordHighlighting();
131
+ }, a.onended = () => {
132
+ this.stopWordHighlighting(), URL.revokeObjectURL(i), this.currentAudio = null, this.wordTimings = [], d();
133
+ }, a.onerror = (c) => {
134
+ this.stopWordHighlighting(), URL.revokeObjectURL(i), this.currentAudio = null, this.wordTimings = [], this.intentionallyStopped ? d() : n(/* @__PURE__ */ new Error("Failed to play audio from server"));
135
+ }, a.onpause = () => {
136
+ this.stopWordHighlighting(), this.pausedState = !0;
137
+ }, a.play().catch(n);
138
+ });
139
+ }
140
+ async synthesizeSpeech(t, e, r) {
141
+ const i = Date.now();
142
+ await this.emitTelemetry("pie-tool-backend-call-start", {
143
+ toolId: "tts",
144
+ backend: this.config.provider || "server",
145
+ operation: "synthesize-speech"
146
+ });
147
+ const o = {
148
+ "Content-Type": "application/json",
149
+ ...this.config.headers
150
+ };
151
+ this.config.authToken && (o.Authorization = `Bearer ${this.config.authToken}`);
152
+ const s = this.adapter.resolveSynthesisUrl(this.config), d = this.adapter.buildRequestBody(t, this.config), n = await (async () => {
153
+ try {
154
+ return await fetch(s, {
155
+ method: "POST",
156
+ headers: o,
157
+ body: JSON.stringify(d),
158
+ signal: e
159
+ });
160
+ } catch (l) {
161
+ throw await this.emitTelemetry("pie-tool-backend-call-error", {
162
+ toolId: "tts",
163
+ backend: this.config.provider || "server",
164
+ operation: "synthesize-speech",
165
+ duration: Date.now() - i,
166
+ errorType: "TTSBackendNetworkError",
167
+ message: l instanceof Error ? l.message : String(l)
168
+ }), l;
169
+ }
170
+ })();
171
+ if (!n.ok) {
172
+ const l = await n.json().catch(() => ({})), u = l.message || l.error?.message || `Server returned ${n.status}`;
173
+ throw await this.emitTelemetry("pie-tool-backend-call-error", {
174
+ toolId: "tts",
175
+ backend: this.config.provider || "server",
176
+ operation: "synthesize-speech",
177
+ duration: Date.now() - i,
178
+ statusCode: n.status,
179
+ errorType: "TTSBackendRequestError",
180
+ message: u
181
+ }), new Error(u);
182
+ }
183
+ const a = await this.adapter.parseResponse(n, this.config, o, e);
184
+ if (r !== this.synthesisRunId || e.aborted) throw new Error("Synthesis superseded by a newer request");
185
+ let c;
186
+ if (a.audio.kind === "base64") c = this.base64ToBlob(a.audio.data, a.audio.contentType);
187
+ else {
188
+ const l = a.audio.url, u = Date.now();
189
+ await this.emitTelemetry("pie-tool-backend-call-start", {
190
+ toolId: "tts",
191
+ backend: this.config.provider || "server",
192
+ operation: "fetch-synthesized-audio-asset"
193
+ });
194
+ const f = {};
195
+ this.config.includeAuthOnAssetFetch && this.config.authToken && (f.Authorization = `Bearer ${this.config.authToken}`);
196
+ const p = await (async () => {
197
+ try {
198
+ return await fetch(l, {
199
+ headers: f,
200
+ signal: e
201
+ });
202
+ } catch (m) {
203
+ throw await this.emitTelemetry("pie-tool-backend-call-error", {
204
+ toolId: "tts",
205
+ backend: this.config.provider || "server",
206
+ operation: "fetch-synthesized-audio-asset",
207
+ duration: Date.now() - u,
208
+ errorType: "TTSAssetNetworkError",
209
+ message: m instanceof Error ? m.message : String(m)
210
+ }), m;
211
+ }
212
+ })();
213
+ if (!p.ok)
214
+ throw await this.emitTelemetry("pie-tool-backend-call-error", {
215
+ toolId: "tts",
216
+ backend: this.config.provider || "server",
217
+ operation: "fetch-synthesized-audio-asset",
218
+ duration: Date.now() - u,
219
+ statusCode: p.status,
220
+ errorType: "TTSAssetFetchError",
221
+ message: `Failed to download synthesized audio (${p.status})`
222
+ }), new Error(`Failed to download synthesized audio (${p.status})`);
223
+ c = await p.blob(), await this.emitTelemetry("pie-tool-backend-call-success", {
224
+ toolId: "tts",
225
+ backend: this.config.provider || "server",
226
+ operation: "fetch-synthesized-audio-asset",
227
+ duration: Date.now() - u
228
+ });
229
+ }
230
+ const y = URL.createObjectURL(c), g = this.parseSpeechMarks(a.speechMarks);
231
+ return await this.emitTelemetry("pie-tool-backend-call-success", {
232
+ toolId: "tts",
233
+ backend: this.config.provider || "server",
234
+ operation: "synthesize-speech",
235
+ duration: Date.now() - i
236
+ }), {
237
+ audioUrl: y,
238
+ wordTimings: g
239
+ };
240
+ }
241
+ base64ToBlob(t, e) {
242
+ const r = atob(t), i = new Array(r.length);
243
+ for (let o = 0; o < r.length; o++) i[o] = r.charCodeAt(o);
244
+ return new Blob([new Uint8Array(i)], { type: e });
245
+ }
246
+ parseSpeechMarks(t) {
247
+ return t.filter((e) => e.type === "word").map((e, r) => ({
248
+ time: e.time,
249
+ wordIndex: r,
250
+ charIndex: e.start,
251
+ length: e.end - e.start
252
+ }));
253
+ }
254
+ startWordHighlighting() {
255
+ if (this.stopWordHighlighting(), !this.currentAudio || !this.onWordBoundary || this.wordTimings.length === 0) {
256
+ console.log("[ServerTTSProvider] Cannot start highlighting:", {
257
+ hasAudio: !!this.currentAudio,
258
+ hasCallback: !!this.onWordBoundary,
259
+ wordTimingsCount: this.wordTimings.length
260
+ });
261
+ return;
262
+ }
263
+ console.log("[ServerTTSProvider] Starting word highlighting with", this.wordTimings.length, "word timings"), console.log("[ServerTTSProvider] Playback rate:", this.currentAudio.playbackRate), console.log("[ServerTTSProvider] First 3 timings:", this.wordTimings.slice(0, 3));
264
+ let t = -1;
265
+ this.highlightInterval = window.setInterval(() => {
266
+ if (!this.currentAudio) {
267
+ this.stopWordHighlighting();
268
+ return;
269
+ }
270
+ const e = this.currentAudio.currentTime * 1e3;
271
+ for (let r = 0; r < this.wordTimings.length; r++) {
272
+ const i = this.wordTimings[r];
273
+ if (e >= i.time && r > t) {
274
+ this.onWordBoundary && (console.log("[ServerTTSProvider] Highlighting word at charIndex:", i.charIndex, "length:", i.length, "time:", i.time, "currentTime:", e), this.onWordBoundary("", i.charIndex, i.length)), t = r;
275
+ break;
276
+ }
277
+ }
278
+ }, 50);
279
+ }
280
+ stopWordHighlighting() {
281
+ this.highlightInterval !== null && (clearInterval(this.highlightInterval), this.highlightInterval = null);
282
+ }
283
+ pause() {
284
+ this.currentAudio && !this.pausedState && (this.currentAudio.pause(), this.stopWordHighlighting(), this.pausedState = !0);
285
+ }
286
+ resume() {
287
+ this.currentAudio && this.pausedState && (this.currentAudio.play(), this.pausedState = !1, this.onWordBoundary && this.wordTimings.length > 0 && this.startWordHighlighting());
288
+ }
289
+ stop() {
290
+ this.synthesisRunId += 1, this.activeSynthesisController && (this.activeSynthesisController.abort(), this.activeSynthesisController = null), this.stopWordHighlighting(), this.currentAudio && (this.intentionallyStopped = !0, this.currentAudio.pause(), this.currentAudio.src && URL.revokeObjectURL(this.currentAudio.src), this.currentAudio.src = "", this.currentAudio = null), this.pausedState = !1, this.wordTimings = [];
291
+ }
292
+ isPlaying() {
293
+ return this.currentAudio !== null && !this.pausedState;
294
+ }
295
+ isPaused() {
296
+ return this.pausedState;
297
+ }
298
+ updateSettings(t) {
299
+ t.rate !== void 0 && (this.config.rate = t.rate, this.currentAudio && (this.currentAudio.playbackRate = Math.max(0.25, Math.min(4, t.rate)))), t.pitch !== void 0 && (this.config.pitch = t.pitch), t.voice !== void 0 && (this.config.voice = t.voice);
300
+ }
301
+ }, C = class {
302
+ constructor() {
303
+ h(this, "providerId", "server-tts"), h(this, "providerName", "Server TTS"), h(this, "version", "1.0.0"), h(this, "config", null), h(this, "adapter", null), h(this, "telemetryReporter", void 0);
304
+ }
305
+ async emitTelemetry(t, e) {
306
+ try {
307
+ await this.telemetryReporter?.(t, e);
308
+ } catch (r) {
309
+ console.warn("[ServerTTSProvider] telemetry callback failed:", r);
310
+ }
311
+ }
312
+ async initialize(t) {
313
+ const e = t;
314
+ if (!e.apiEndpoint) throw new Error("apiEndpoint is required for ServerTTSProvider");
315
+ if (this.config = e, this.telemetryReporter = b(e), this.adapter = M[T(e)], e.validateEndpoint) {
316
+ const r = Date.now();
317
+ if (await this.emitTelemetry("pie-tool-backend-call-start", {
318
+ toolId: "tts",
319
+ backend: e.provider || "server",
320
+ operation: "validate-endpoint"
321
+ }), !await this.testAPIAvailability())
322
+ throw await this.emitTelemetry("pie-tool-backend-call-error", {
323
+ toolId: "tts",
324
+ backend: e.provider || "server",
325
+ operation: "validate-endpoint",
326
+ duration: Date.now() - r,
327
+ errorType: "TTSEndpointValidationError",
328
+ message: `Server TTS API not available at ${e.apiEndpoint}`
329
+ }), new Error(`Server TTS API not available at ${e.apiEndpoint}`);
330
+ await this.emitTelemetry("pie-tool-backend-call-success", {
331
+ toolId: "tts",
332
+ backend: e.provider || "server",
333
+ operation: "validate-endpoint",
334
+ duration: Date.now() - r
335
+ });
336
+ }
337
+ return new E(e, this.adapter);
338
+ }
339
+ async testAPIAvailability() {
340
+ if (!this.config || !this.adapter) return !1;
341
+ try {
342
+ const t = { ...this.config.headers };
343
+ this.config.authToken && (t.Authorization = `Bearer ${this.config.authToken}`);
344
+ const e = new AbortController(), r = setTimeout(() => e.abort(), 5e3), i = A(this.config, this.adapter.id);
345
+ if (i === "none")
346
+ return clearTimeout(r), !0;
347
+ const o = i === "voices" ? k(this.config) : this.adapter.resolveSynthesisUrl(this.config), s = i === "voices" ? "GET" : "OPTIONS";
348
+ try {
349
+ const d = await fetch(o, {
350
+ method: s,
351
+ headers: t,
352
+ signal: e.signal
353
+ });
354
+ return clearTimeout(r), d.ok || d.status === 405;
355
+ } catch {
356
+ return clearTimeout(r), !1;
357
+ }
358
+ } catch {
359
+ return !1;
360
+ }
361
+ }
362
+ supportsFeature(t) {
363
+ switch (t) {
364
+ case "pause":
365
+ case "resume":
366
+ case "wordBoundary":
367
+ case "voiceSelection":
368
+ case "rateControl":
369
+ return !0;
370
+ case "pitchControl":
371
+ return !1;
372
+ default:
373
+ return !1;
374
+ }
375
+ }
376
+ getCapabilities() {
377
+ return {
378
+ supportsPause: !0,
379
+ supportsResume: !0,
380
+ supportsWordBoundary: !0,
381
+ supportsVoiceSelection: !0,
382
+ supportsRateControl: !0,
383
+ supportsPitchControl: !1,
384
+ maxTextLength: S[this.config ? T(this.config) : "pie"]
385
+ };
386
+ }
387
+ destroy() {
388
+ this.config = null, this.adapter = null, this.telemetryReporter = void 0;
389
+ }
390
+ };
391
+ export {
392
+ C as ServerTTSProvider
393
+ };
@@ -1,21 +1,11 @@
1
- var l = Object.defineProperty;
2
- var n = (s, e, o) => e in s ? l(s, e, { enumerable: !0, configurable: !0, writable: !0, value: o }) : s[e] = o;
3
- var r = (s, e, o) => n(s, typeof e != "symbol" ? e + "" : e, o);
4
- class p {
1
+ import { t as s } from "./defineProperty-CyepwRr5.js";
2
+ var n = class {
5
3
  constructor() {
6
- r(this, "providerId", "desmos");
7
- r(this, "providerName", "Desmos");
8
- r(this, "supportedTypes", [
4
+ s(this, "providerId", "desmos"), s(this, "providerName", "Desmos"), s(this, "supportedTypes", [
9
5
  "basic",
10
6
  "scientific",
11
7
  "graphing"
12
- ]);
13
- r(this, "version", "1.10");
14
- r(this, "initialized", !1);
15
- r(this, "apiKey");
16
- r(this, "proxyEndpoint");
17
- r(this, "isDevelopment", !1);
18
- r(this, "onTelemetry");
8
+ ]), s(this, "version", "1.10"), s(this, "initialized", !1), s(this, "apiKey", void 0), s(this, "proxyEndpoint", void 0), s(this, "isDevelopment", !1), s(this, "onTelemetry", void 0);
19
9
  }
20
10
  async emitTelemetry(e, o) {
21
11
  try {
@@ -24,35 +14,22 @@ class p {
24
14
  console.warn("[DesmosProvider] telemetry callback failed:", t);
25
15
  }
26
16
  }
27
- /**
28
- * Get the configured API key
29
- * @internal Used internally by calculator instances
30
- */
31
17
  getApiKey() {
32
18
  return this.apiKey;
33
19
  }
34
- /**
35
- * Dynamically load the Desmos calculator library
36
- * @private
37
- */
38
20
  async loadDesmosScript() {
39
21
  return new Promise((e, o) => {
40
- const t = document.createElement("script"), i = this.apiKey ? `https://www.desmos.com/api/v1.10/calculator.js?apiKey=${this.apiKey}` : "https://www.desmos.com/api/v1.10/calculator.js";
41
- t.src = i, t.async = !0, t.onload = () => {
42
- window.Desmos ? (console.log("[DesmosProvider] Desmos API loaded successfully"), e()) : o(new Error("Desmos API loaded but window.Desmos is undefined"));
22
+ const t = document.createElement("script");
23
+ t.src = this.apiKey ? `https://www.desmos.com/api/v1.10/calculator.js?apiKey=${this.apiKey}` : "https://www.desmos.com/api/v1.10/calculator.js", t.async = !0, t.onload = () => {
24
+ window.Desmos ? (console.log("[DesmosProvider] Desmos API loaded successfully"), e()) : o(/* @__PURE__ */ new Error("Desmos API loaded but window.Desmos is undefined"));
43
25
  }, t.onerror = () => {
44
- o(new Error("Failed to load Desmos API from CDN"));
26
+ o(/* @__PURE__ */ new Error("Failed to load Desmos API from CDN"));
45
27
  }, document.head.appendChild(t);
46
28
  });
47
29
  }
48
- /**
49
- * Initialize Desmos library
50
- * @param config Configuration with API key (development) or proxy endpoint (production)
51
- */
52
30
  async initialize(e) {
53
31
  if (!this.initialized) {
54
- if (this.onTelemetry = e?.onTelemetry, typeof window > "u")
55
- throw new Error("Desmos calculators can only be initialized in the browser");
32
+ if (this.onTelemetry = e?.onTelemetry, typeof window > "u") throw new Error("Desmos calculators can only be initialized in the browser");
56
33
  if (this.isDevelopment = process.env.NODE_ENV === "development" || typeof process > "u" || !process.env.NODE_ENV, e?.proxyEndpoint) {
57
34
  this.proxyEndpoint = e.proxyEndpoint;
58
35
  const o = Date.now();
@@ -63,10 +40,8 @@ class p {
63
40
  });
64
41
  try {
65
42
  const t = await fetch(e.proxyEndpoint);
66
- if (!t.ok)
67
- throw new Error(`Proxy endpoint returned ${t.status}`);
68
- const i = await t.json();
69
- this.apiKey = i.apiKey, await this.emitTelemetry("pie-tool-backend-call-success", {
43
+ if (!t.ok) throw new Error(`Proxy endpoint returned ${t.status}`);
44
+ this.apiKey = (await t.json()).apiKey, await this.emitTelemetry("pie-tool-backend-call-success", {
70
45
  toolId: "calculator",
71
46
  backend: "desmos",
72
47
  operation: "proxy-auth-fetch",
@@ -116,51 +91,34 @@ Recommended: Use proxyEndpoint for production, apiKey for development only.`);
116
91
  this.initialized = !0;
117
92
  }
118
93
  }
119
- /**
120
- * Create a calculator instance
121
- */
122
94
  async createCalculator(e, o, t) {
123
- if (this.initialized || await this.initialize(), !this.supportsType(e))
124
- throw new Error(`Desmos does not support calculator type: ${e}`);
125
- return new c(this, e, o, t, this.apiKey);
95
+ if (this.initialized || await this.initialize(), !this.supportsType(e)) throw new Error(`Desmos does not support calculator type: ${e}`);
96
+ return new a(this, e, o, t, this.apiKey);
126
97
  }
127
- /**
128
- * Check if type is supported
129
- */
130
98
  supportsType(e) {
131
99
  return this.supportedTypes.includes(e);
132
100
  }
133
- /**
134
- * Cleanup
135
- */
136
101
  destroy() {
137
102
  this.initialized = !1, this.onTelemetry = void 0;
138
103
  }
139
- /**
140
- * Get provider capabilities
141
- */
142
104
  getCapabilities() {
143
105
  return {
144
106
  supportsHistory: !1,
145
- // Desmos doesn't expose history API
146
107
  supportsGraphing: !0,
147
108
  supportsExpressions: !0,
148
109
  canExport: !0,
149
110
  maxPrecision: 15,
150
- inputMethods: ["keyboard", "mouse", "touch"]
111
+ inputMethods: [
112
+ "keyboard",
113
+ "mouse",
114
+ "touch"
115
+ ]
151
116
  };
152
117
  }
153
- }
154
- class c {
155
- constructor(e, o, t, i, a) {
156
- r(this, "provider");
157
- r(this, "type");
158
- r(this, "Desmos");
159
- r(this, "calculator");
160
- r(this, "container");
161
- if (this.provider = e, this.type = o, this.container = t, this.Desmos = window.Desmos, !this.Desmos)
162
- throw new Error("Desmos API not available");
163
- this._initializeCalculator(i, a);
118
+ }, a = class {
119
+ constructor(e, o, t, r, i) {
120
+ if (s(this, "provider", void 0), s(this, "type", void 0), s(this, "Desmos", void 0), s(this, "calculator", void 0), s(this, "container", void 0), this.provider = e, this.type = o, this.container = t, this.Desmos = window.Desmos, !this.Desmos) throw new Error("Desmos API not available");
121
+ this._initializeCalculator(r, i);
164
122
  }
165
123
  _initializeCalculator(e, o) {
166
124
  const t = {
@@ -196,13 +154,12 @@ class c {
196
154
  return "";
197
155
  }
198
156
  setValue(e) {
199
- if (this.type === "graphing" && this.calculator.setState)
200
- try {
201
- const o = JSON.parse(e);
202
- this.calculator.setState(o);
203
- } catch (o) {
204
- console.error("[DesmosCalculator] Failed to set state:", o);
205
- }
157
+ if (this.type === "graphing" && this.calculator.setState) try {
158
+ const o = JSON.parse(e);
159
+ this.calculator.setState(o);
160
+ } catch (o) {
161
+ console.error("[DesmosCalculator] Failed to set state:", o);
162
+ }
206
163
  }
207
164
  clear() {
208
165
  this.calculator.setBlank && this.calculator.setBlank();
@@ -210,11 +167,12 @@ class c {
210
167
  async evaluate(e) {
211
168
  return this.type === "graphing" ? new Promise((o) => {
212
169
  const t = `eval_${Date.now()}`;
213
- this.calculator.setExpression({ id: t, latex: e }), setTimeout(() => {
214
- const a = this.calculator.HelperExpression({
215
- latex: e
216
- }).numericValue || e;
217
- this.calculator.removeExpression({ id: t }), o(String(a));
170
+ this.calculator.setExpression({
171
+ id: t,
172
+ latex: e
173
+ }), setTimeout(() => {
174
+ const r = this.calculator.HelperExpression({ latex: e }).numericValue || e;
175
+ this.calculator.removeExpression({ id: t }), o(String(r));
218
176
  }, 100);
219
177
  }) : e;
220
178
  }
@@ -231,14 +189,13 @@ class c {
231
189
  };
232
190
  }
233
191
  importState(e) {
234
- if (e.provider !== "desmos")
235
- throw new Error(`Cannot import state from provider: ${e.provider}`);
192
+ if (e.provider !== "desmos") throw new Error(`Cannot import state from provider: ${e.provider}`);
236
193
  e.providerState && this.calculator.setState ? this.calculator.setState(e.providerState) : e.value && this.setValue(e.value);
237
194
  }
238
195
  destroy() {
239
196
  this.calculator && this.calculator.destroy && this.calculator.destroy(), this.container.replaceChildren(), console.log("[DesmosCalculator] destroyed");
240
197
  }
241
- }
198
+ };
242
199
  export {
243
- p as DesmosCalculatorProvider
200
+ n as DesmosCalculatorProvider
244
201
  };
@@ -1 +1,2 @@
1
- ::highlight(tts-word){background-color:var(--pie-tts-word-highlight, color-mix(in srgb, var(--pie-missing, #ffeb3b) 68%, transparent));text-decoration:underline 2px solid var(--pie-tts-word-underline, color-mix(in srgb, var(--pie-text, #111827) 70%, transparent));text-underline-offset:2px;text-shadow:0 0 1px var(--pie-tts-word-shadow, color-mix(in srgb, var(--pie-text, #111827) 35%, transparent));color:inherit}::highlight(tts-sentence){background-color:var(--pie-tts-sentence-highlight, color-mix(in srgb, var(--pie-missing, #ffeb3b) 38%, transparent));color:inherit}::highlight(annotation-yellow){background-color:color-mix(in srgb,var(--pie-missing, #fde995) 50%,transparent);color:inherit}::highlight(annotation-pink){background-color:#ff9fae80;color:inherit}::highlight(annotation-blue){background-color:#a7e0f680;color:inherit}::highlight(annotation-green){background-color:#a6e1c580;color:inherit}::highlight(annotation-underline){background-color:transparent;text-decoration:underline 2px solid var(--pie-primary, #0066cc);text-underline-offset:2px;color:inherit}@media(prefers-color-scheme:dark){::highlight(tts-word){background-color:var(--pie-tts-word-highlight, color-mix(in srgb, var(--pie-missing, #ffeb3b) 72%, transparent));text-decoration:underline 2px solid var(--pie-tts-word-underline, color-mix(in srgb, var(--pie-white, #fff) 70%, transparent));text-shadow:0 0 2px var(--pie-tts-word-shadow, color-mix(in srgb, var(--pie-white, #fff) 32%, transparent))}::highlight(tts-sentence){background-color:var(--pie-tts-sentence-highlight, color-mix(in srgb, var(--pie-missing, #ffeb3b) 42%, transparent))}::highlight(annotation-yellow){background-color:#8b750099}::highlight(annotation-pink){background-color:#8b334a99}::highlight(annotation-blue){background-color:#06a9}::highlight(annotation-green){background-color:#2d5c3f99}::highlight(annotation-underline){text-decoration-color:#4da6ff}}@media(prefers-contrast:high){::highlight(tts-word){background-color:var(--pie-tts-word-highlight, color-mix(in srgb, var(--pie-missing, #ffeb3b) 85%, transparent));text-decoration-color:var(--pie-tts-word-underline, color-mix(in srgb, var(--pie-text, #111827) 85%, transparent));text-decoration-thickness:3px;text-shadow:none}::highlight(tts-sentence){background-color:var(--pie-tts-sentence-highlight, color-mix(in srgb, var(--pie-missing, #ffeb3b) 55%, transparent))}::highlight(annotation-yellow){background-color:#ffff00b3}::highlight(annotation-pink){background-color:#ff69b4b3}::highlight(annotation-blue){background-color:#00bfffb3}::highlight(annotation-green){background-color:#00ff7fb3}::highlight(annotation-underline){text-decoration-thickness:3px;text-decoration-color:#000}}@media(prefers-color-scheme:dark)and (prefers-contrast:high){::highlight(tts-word){background-color:var(--pie-tts-word-highlight, color-mix(in srgb, var(--pie-missing, #ffeb3b) 85%, transparent));text-decoration-color:var(--pie-tts-word-underline, color-mix(in srgb, var(--pie-white, #fff) 88%, transparent))}::highlight(annotation-underline){text-decoration-color:#fff}}@media print{::highlight(tts-word),::highlight(tts-sentence){background-color:transparent;text-decoration:none;text-shadow:none}::highlight(annotation-yellow),::highlight(annotation-pink),::highlight(annotation-blue),::highlight(annotation-green){background-color:transparent;border-bottom:2px solid currentColor}::highlight(annotation-yellow){border-bottom-color:#ffeb3b}::highlight(annotation-pink){border-bottom-color:#ff9fae}::highlight(annotation-blue){border-bottom-color:#a7e0f6}::highlight(annotation-green){border-bottom-color:#a6e1c5}::highlight(annotation-underline){text-decoration-color:#000;border-bottom:none}}@media(prefers-reduced-motion:reduce){::highlight(tts-word){text-shadow:none}}.pie-sr-only{position:absolute;width:1px;height:1px;padding:0;margin:-1px;overflow:hidden;clip:rect(0,0,0,0);white-space:nowrap;border-width:0}.pie-tool-annotation-toolbar button:focus-visible{outline:2px solid var(--pie-button-focus-outline, var(--pie-primary, #0066cc));outline-offset:2px}@media(prefers-color-scheme:dark){.pie-tool-annotation-toolbar button:focus-visible{outline-color:#4da6ff}}@media(prefers-contrast:high){.pie-tool-annotation-toolbar button:focus-visible{outline-width:3px}}
1
+ ::highlight(tts-word){background-color:var(--pie-tts-word-highlight,color-mix(in srgb, var(--pie-missing,#ffeb3b) 68%, transparent));-webkit-text-decoration:underline 2px solid var(--pie-tts-word-underline,color-mix(in srgb, var(--pie-text,#111827) 70%, transparent));text-decoration:underline 2px solid var(--pie-tts-word-underline,color-mix(in srgb, var(--pie-text,#111827) 70%, transparent));text-underline-offset:2px;text-shadow:0 0 1px var(--pie-tts-word-shadow,color-mix(in srgb, var(--pie-text,#111827) 35%, transparent));color:inherit}::highlight(tts-sentence){background-color:var(--pie-tts-sentence-highlight,color-mix(in srgb, var(--pie-missing,#ffeb3b) 38%, transparent));color:inherit}::highlight(annotation-yellow){background-color:color-mix(in srgb, var(--pie-missing,#fde995) 50%, transparent);color:inherit}::highlight(annotation-pink){color:inherit;background-color:#ff9fae80}::highlight(annotation-blue){color:inherit;background-color:#a7e0f680}::highlight(annotation-green){color:inherit;background-color:#a6e1c580}::highlight(annotation-underline){-webkit-text-decoration:underline 2px solid var(--pie-primary,#06c);text-decoration:underline 2px solid var(--pie-primary,#06c);text-underline-offset:2px;color:inherit;background-color:#0000}@media (prefers-color-scheme:dark){::highlight(tts-word){background-color:var(--pie-tts-word-highlight,color-mix(in srgb, var(--pie-missing,#ffeb3b) 72%, transparent));-webkit-text-decoration:underline 2px solid var(--pie-tts-word-underline,color-mix(in srgb, var(--pie-white,#fff) 70%, transparent));text-decoration:underline 2px solid var(--pie-tts-word-underline,color-mix(in srgb, var(--pie-white,#fff) 70%, transparent));text-shadow:0 0 2px var(--pie-tts-word-shadow,color-mix(in srgb, var(--pie-white,#fff) 32%, transparent))}::highlight(tts-sentence){background-color:var(--pie-tts-sentence-highlight,color-mix(in srgb, var(--pie-missing,#ffeb3b) 42%, transparent))}::highlight(annotation-yellow){background-color:#8b750099}::highlight(annotation-pink){background-color:#8b334a99}::highlight(annotation-blue){background-color:#06a9}::highlight(annotation-green){background-color:#2d5c3f99}::highlight(annotation-underline){text-decoration-color:#4da6ff}}@media (prefers-contrast:high){::highlight(tts-word){background-color:var(--pie-tts-word-highlight,color-mix(in srgb, var(--pie-missing,#ffeb3b) 85%, transparent));-webkit-text-decoration-color:var(--pie-tts-word-underline,color-mix(in srgb, var(--pie-text,#111827) 85%, transparent));text-decoration-color:var(--pie-tts-word-underline,color-mix(in srgb, var(--pie-text,#111827) 85%, transparent));text-shadow:none;text-decoration-thickness:3px}::highlight(tts-sentence){background-color:var(--pie-tts-sentence-highlight,color-mix(in srgb, var(--pie-missing,#ffeb3b) 55%, transparent))}::highlight(annotation-yellow){background-color:#ffff00b3}::highlight(annotation-pink){background-color:#ff69b4b3}::highlight(annotation-blue){background-color:#00bfffb3}::highlight(annotation-green){background-color:#00ff7fb3}::highlight(annotation-underline){text-decoration-color:#000;text-decoration-thickness:3px}}@media (prefers-color-scheme:dark) and (prefers-contrast:high){::highlight(tts-word){background-color:var(--pie-tts-word-highlight,color-mix(in srgb, var(--pie-missing,#ffeb3b) 85%, transparent));-webkit-text-decoration-color:var(--pie-tts-word-underline,color-mix(in srgb, var(--pie-white,#fff) 88%, transparent));text-decoration-color:var(--pie-tts-word-underline,color-mix(in srgb, var(--pie-white,#fff) 88%, transparent))}::highlight(annotation-underline){text-decoration-color:#fff}}@media print{::highlight(tts-word){text-shadow:none;background-color:#0000;text-decoration:none}::highlight(tts-sentence){text-shadow:none;background-color:#0000;text-decoration:none}::highlight(annotation-yellow){background-color:#0000;border-bottom:2px solid}::highlight(annotation-pink){background-color:#0000;border-bottom:2px solid}::highlight(annotation-blue){background-color:#0000;border-bottom:2px solid}::highlight(annotation-green){background-color:#0000;border-bottom:2px solid}::highlight(annotation-yellow){border-bottom-color:#ffeb3b}::highlight(annotation-pink){border-bottom-color:#ff9fae}::highlight(annotation-blue){border-bottom-color:#a7e0f6}::highlight(annotation-green){border-bottom-color:#a6e1c5}::highlight(annotation-underline){border-bottom:none;text-decoration-color:#000}}@media (prefers-reduced-motion:reduce){::highlight(tts-word){text-shadow:none}}.pie-sr-only{clip:rect(0, 0, 0, 0);white-space:nowrap;border-width:0;width:1px;height:1px;margin:-1px;padding:0;position:absolute;overflow:hidden}.pie-tool-annotation-toolbar button:focus-visible{outline:2px solid var(--pie-button-focus-outline,var(--pie-primary,#06c));outline-offset:2px}@media (prefers-color-scheme:dark){.pie-tool-annotation-toolbar button:focus-visible{outline-color:#4da6ff}}@media (prefers-contrast:high){.pie-tool-annotation-toolbar button:focus-visible{outline-width:3px}}
2
+ /*$vite$:1*/