@superinterface/react 5.3.0-beta.4 → 5.3.0-beta.6

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/dist/index.js CHANGED
@@ -47287,39 +47287,74 @@ function _toPrimitive47(t, r) {
47287
47287
  }
47288
47288
  return ("string" === r ? String : Number)(t);
47289
47289
  }
47290
- var splitSentencesFast = function(text) {
47291
- var t = text.replace(/\s+/g, " ").trim();
47292
- if (!t) return [];
47293
- var parts = t.split(RegExp("(?<=[.!?])\\s+(?=[^\\s])", "g"));
47294
- return parts;
47290
+ var THROTTLE_MS = 80;
47291
+ var MAX_SEG_CACHE = 256;
47292
+ var KEEP_FINISHED_MESSAGES = 12;
47293
+ var hasLetters = function(s) {
47294
+ for(var i = 0; i < s.length; i++){
47295
+ var ch = s.charAt(i);
47296
+ if (ch.toLowerCase() !== ch.toUpperCase()) return true;
47297
+ }
47298
+ return false;
47295
47299
  };
47296
- var getIncrementalSentences = function(prev, nextInput) {
47297
- if (!prev) {
47298
- return {
47299
- input: nextInput,
47300
- sentences: splitSentencesFast(nextInput)
47301
- };
47300
+ var isSentencePunct = function(ch) {
47301
+ return ch === "." || ch === "!" || ch === "?" || ch === "\u3002" || ch === "\uFF01" || ch === "\uFF1F";
47302
+ };
47303
+ var normalizeBoundaries = function(text) {
47304
+ var out = "";
47305
+ for(var i = 0; i < text.length; i++){
47306
+ var ch = text.charAt(i);
47307
+ out += ch;
47308
+ if (isSentencePunct(ch)) {
47309
+ var next = text.charAt(i + 1);
47310
+ if (next && next !== " " && hasLetters(next)) {
47311
+ out += " ";
47312
+ }
47313
+ }
47302
47314
  }
47303
- if (nextInput === prev.input) {
47304
- return prev;
47315
+ return out;
47316
+ };
47317
+ var splitSentencesFast = function(raw) {
47318
+ var t = normalizeBoundaries(raw.replace(/\s+/g, " ").trim());
47319
+ if (!t) return [];
47320
+ var parts = t.split(RegExp("(?<=[.!?])\\s+(?=[^\\s])", "g"));
47321
+ var filtered = [];
47322
+ for(var i = 0; i < parts.length; i++){
47323
+ var p = parts[i].trim();
47324
+ if (p && hasLetters(p)) filtered.push(p);
47305
47325
  }
47326
+ return filtered;
47327
+ };
47328
+ var getIncrementalSentences = function(prev, nextInput, now) {
47329
+ if (!prev) return {
47330
+ input: nextInput,
47331
+ sentences: splitSentencesFast(nextInput),
47332
+ touched: now
47333
+ };
47334
+ if (nextInput === prev.input) return {
47335
+ input: prev.input,
47336
+ sentences: prev.sentences,
47337
+ touched: now
47338
+ };
47306
47339
  if (nextInput.startsWith(prev.input)) {
47307
- var _prev$sentences;
47308
- var prevLast = (_prev$sentences = prev.sentences[prev.sentences.length - 1]) !== null && _prev$sentences !== void 0 ? _prev$sentences : "";
47340
+ var prevSentences = prev.sentences;
47341
+ var prevLast = prevSentences[prevSentences.length - 1] || "";
47309
47342
  var baseLen = prev.input.length - prevLast.length;
47310
47343
  if (baseLen >= 0 && prev.input.slice(baseLen) === prevLast) {
47311
47344
  var tail = nextInput.slice(baseLen);
47312
47345
  var tailSegments = splitSentencesFast(tail);
47313
- var merged = prev.sentences.length > 0 ? _to_consumable_array(prev.sentences.slice(0, -1)).concat(_to_consumable_array(tailSegments)) : tailSegments;
47346
+ var merged = prevSentences.length > 0 ? prevSentences.slice(0, -1).concat(tailSegments) : tailSegments;
47314
47347
  return {
47315
47348
  input: nextInput,
47316
- sentences: merged
47349
+ sentences: merged,
47350
+ touched: now
47317
47351
  };
47318
47352
  }
47319
47353
  }
47320
47354
  return {
47321
47355
  input: nextInput,
47322
- sentences: splitSentencesFast(nextInput)
47356
+ sentences: splitSentencesFast(nextInput),
47357
+ touched: now
47323
47358
  };
47324
47359
  };
47325
47360
  var useMessageAudio = function(_ref) {
@@ -47340,41 +47375,65 @@ var useMessageAudio = function(_ref) {
47340
47375
  var currentSentenceRef = useRef8(null);
47341
47376
  var messagesProps = useMessages();
47342
47377
  var segCacheRef = useRef8(/* @__PURE__ */ new Map());
47378
+ var mirrorTimerRef = useRef8(null);
47379
+ var pendingMirrorRef = useRef8(false);
47343
47380
  useEffect10(function() {
47344
- var assistantsDesc = messagesProps.messages.filter(function(m) {
47345
- return m.role === "assistant";
47346
- });
47347
- var assistantsAsc = _to_consumable_array(assistantsDesc).reverse();
47348
- setAudioQueue(function(prev) {
47349
- var prevById = new Map(prev.map(function(p) {
47350
- return [
47351
- p.id,
47352
- p
47353
- ];
47354
- }));
47355
- var changed = false;
47356
- var next = [];
47357
- var _iteratorNormalCompletion = true, _didIteratorError = false, _iteratorError = undefined;
47358
- try {
47359
- for(var _iterator = assistantsAsc[Symbol.iterator](), _step; !(_iteratorNormalCompletion = (_step = _iterator.next()).done); _iteratorNormalCompletion = true){
47360
- var m_0 = _step.value;
47381
+ if (mirrorTimerRef.current != null) {
47382
+ pendingMirrorRef.current = true;
47383
+ return;
47384
+ }
47385
+ var run = function() {
47386
+ var assistantsDesc = messagesProps.messages.filter(function(m) {
47387
+ return m.role === "assistant";
47388
+ });
47389
+ var assistantsAsc = assistantsDesc.slice().reverse();
47390
+ var nowTs = typeof performance !== "undefined" && performance.now ? performance.now() : Date.now();
47391
+ var segCache = segCacheRef.current;
47392
+ var touch = function(id, entry) {
47393
+ segCache.set(id, {
47394
+ input: entry.input,
47395
+ sentences: entry.sentences,
47396
+ touched: nowTs
47397
+ });
47398
+ };
47399
+ var evictLRU = function() {
47400
+ if (segCache.size <= MAX_SEG_CACHE) return;
47401
+ var entries = Array.from(segCache.entries());
47402
+ entries.sort(function(a, b) {
47403
+ return a[1].touched - b[1].touched;
47404
+ });
47405
+ var toRemove = segCache.size - MAX_SEG_CACHE;
47406
+ for(var i = 0; i < toRemove; i++)segCache.delete(entries[i][0]);
47407
+ };
47408
+ setAudioQueue(function(prev) {
47409
+ var prevById = new Map(prev.map(function(p) {
47410
+ return [
47411
+ p.id,
47412
+ p
47413
+ ];
47414
+ }));
47415
+ var next = [];
47416
+ var changed = false;
47417
+ for(var i_0 = 0; i_0 < assistantsAsc.length; i_0++){
47361
47418
  var _existing$nextIndex, _existing$stopped;
47419
+ var m_0 = assistantsAsc[i_0];
47362
47420
  var inp = input({
47363
47421
  message: m_0
47364
47422
  });
47365
47423
  if (inp == null) continue;
47366
- var prevSeg = segCacheRef.current.get(m_0.id);
47367
- var nextSeg = getIncrementalSentences(prevSeg, inp);
47368
- if (!prevSeg || nextSeg.input !== prevSeg.input) {
47369
- segCacheRef.current.set(m_0.id, nextSeg);
47424
+ var prevSeg = segCache.get(m_0.id);
47425
+ var nextSeg = getIncrementalSentences(prevSeg, inp, nowTs);
47426
+ if (!prevSeg || nextSeg.input !== prevSeg.input || nextSeg.sentences !== prevSeg.sentences) {
47427
+ touch(m_0.id, nextSeg);
47428
+ } else {
47429
+ touch(m_0.id, prevSeg);
47370
47430
  }
47371
47431
  var existing = prevById.get(m_0.id);
47372
47432
  var sentences = nextSeg.sentences;
47373
47433
  var nextIndex = Math.min((_existing$nextIndex = existing === null || existing === void 0 ? void 0 : existing.nextIndex) !== null && _existing$nextIndex !== void 0 ? _existing$nextIndex : 0, sentences.length);
47374
47434
  var stopped = (_existing$stopped = existing === null || existing === void 0 ? void 0 : existing.stopped) !== null && _existing$stopped !== void 0 ? _existing$stopped : false;
47375
- var reuseExisting = !!existing && existing.status === m_0.status && existing.sentences === sentences && // same array ref -> no change
47376
- existing.nextIndex === nextIndex && existing.stopped === stopped;
47377
- if (reuseExisting) {
47435
+ var reuse = !!existing && existing.status === m_0.status && existing.sentences === sentences && existing.nextIndex === nextIndex && existing.stopped === stopped;
47436
+ if (reuse) {
47378
47437
  next.push(existing);
47379
47438
  } else {
47380
47439
  next.push({
@@ -47387,32 +47446,69 @@ var useMessageAudio = function(_ref) {
47387
47446
  changed = true;
47388
47447
  }
47389
47448
  }
47390
- } catch (err) {
47391
- _didIteratorError = true;
47392
- _iteratorError = err;
47393
- } finally{
47449
+ var unfinished = [];
47450
+ var finished = [];
47451
+ for(var i_1 = 0; i_1 < next.length; i_1++){
47452
+ var m_1 = next[i_1];
47453
+ if (!m_1.stopped && (m_1.status === "in_progress" || m_1.nextIndex < m_1.sentences.length)) {
47454
+ unfinished.push(m_1);
47455
+ } else {
47456
+ finished.push(m_1);
47457
+ }
47458
+ }
47459
+ var prunedFinished = finished.length > KEEP_FINISHED_MESSAGES ? finished.slice(finished.length - KEEP_FINISHED_MESSAGES) : finished;
47460
+ var combined = unfinished.concat(prunedFinished);
47461
+ if (!changed) {
47462
+ if (combined.length !== prev.length) changed = true;
47463
+ else {
47464
+ for(var i_2 = 0; i_2 < combined.length; i_2++){
47465
+ if (combined[i_2] !== prev[i_2]) {
47466
+ changed = true;
47467
+ break;
47468
+ }
47469
+ }
47470
+ }
47471
+ }
47472
+ var idsInQueue = new Set(combined.map(function(m_2) {
47473
+ return m_2.id;
47474
+ }));
47475
+ var _iteratorNormalCompletion = true, _didIteratorError = false, _iteratorError = undefined;
47394
47476
  try {
47395
- if (!_iteratorNormalCompletion && _iterator.return != null) {
47396
- _iterator.return();
47477
+ for(var _iterator = Array.from(segCache.keys())[Symbol.iterator](), _step; !(_iteratorNormalCompletion = (_step = _iterator.next()).done); _iteratorNormalCompletion = true){
47478
+ var id_0 = _step.value;
47479
+ if (!idsInQueue.has(id_0)) segCache.delete(id_0);
47397
47480
  }
47481
+ } catch (err) {
47482
+ _didIteratorError = true;
47483
+ _iteratorError = err;
47398
47484
  } finally{
47399
- if (_didIteratorError) {
47400
- throw _iteratorError;
47485
+ try {
47486
+ if (!_iteratorNormalCompletion && _iterator.return != null) {
47487
+ _iterator.return();
47488
+ }
47489
+ } finally{
47490
+ if (_didIteratorError) {
47491
+ throw _iteratorError;
47492
+ }
47401
47493
  }
47402
47494
  }
47495
+ evictLRU();
47496
+ return changed ? combined : prev;
47497
+ });
47498
+ mirrorTimerRef.current = null;
47499
+ if (pendingMirrorRef.current) {
47500
+ pendingMirrorRef.current = false;
47501
+ mirrorTimerRef.current = window.setTimeout(run, THROTTLE_MS);
47403
47502
  }
47404
- if (next.length !== prev.length) {
47405
- changed = true;
47406
- } else {
47407
- for(var i = 0; i < next.length; i++){
47408
- if (next[i] !== prev[i]) {
47409
- changed = true;
47410
- break;
47411
- }
47412
- }
47503
+ };
47504
+ mirrorTimerRef.current = window.setTimeout(run, THROTTLE_MS);
47505
+ return function() {
47506
+ if (mirrorTimerRef.current != null) {
47507
+ clearTimeout(mirrorTimerRef.current);
47508
+ mirrorTimerRef.current = null;
47413
47509
  }
47414
- return changed ? next : prev;
47415
- });
47510
+ pendingMirrorRef.current = false;
47511
+ };
47416
47512
  }, [
47417
47513
  messagesProps.messages
47418
47514
  ]);
@@ -47424,15 +47520,14 @@ var useMessageAudio = function(_ref) {
47424
47520
  audioPlayer.load("".concat(superinterfaceContext.baseUrl, "/audio-runtimes/tts?").concat(searchParams), {
47425
47521
  format: "mp3",
47426
47522
  autoplay: isAudioPlayed,
47427
- // first call false; then true for snappier chaining
47428
47523
  html5: isHtmlAudioSupported,
47429
47524
  onplay: onPlay,
47430
47525
  onstop: onStop,
47431
47526
  onload: function() {
47432
47527
  var current = currentSentenceRef.current;
47433
47528
  if (!current) return;
47434
- var msg = audioQueueRef.current.find(function(m_1) {
47435
- return m_1.id === current.messageId;
47529
+ var msg = audioQueueRef.current.find(function(m_3) {
47530
+ return m_3.id === current.messageId;
47436
47531
  });
47437
47532
  if (!msg) return;
47438
47533
  var nextSentence = msg.sentences[msg.nextIndex];
@@ -47467,42 +47562,23 @@ var useMessageAudio = function(_ref) {
47467
47562
  if (audioPlayer.playing) return;
47468
47563
  if (pickLockRef.current) return;
47469
47564
  var candidate = null;
47470
- var _iteratorNormalCompletion = true, _didIteratorError = false, _iteratorError = undefined;
47471
- try {
47472
- for(var _iterator = audioQueue[Symbol.iterator](), _step; !(_iteratorNormalCompletion = (_step = _iterator.next()).done); _iteratorNormalCompletion = true){
47473
- var msg_0 = _step.value;
47474
- if (msg_0.stopped) continue;
47475
- var sentence = msg_0.sentences[msg_0.nextIndex];
47476
- while(sentence && !/\S/.test(sentence)){
47477
- msg_0.nextIndex++;
47478
- sentence = msg_0.sentences[msg_0.nextIndex];
47479
- }
47480
- if (!sentence) continue;
47481
- var isFull = isOptimistic({
47482
- id: msg_0.id
47483
- }) || msg_0.status !== "in_progress" || fullSentenceRegex.test(sentence);
47484
- if (isFull) {
47485
- candidate = {
47486
- messageId: msg_0.id,
47487
- sentence: sentence,
47488
- index: msg_0.nextIndex,
47489
- ownerStatus: msg_0.status
47490
- };
47491
- break;
47492
- }
47493
- }
47494
- } catch (err) {
47495
- _didIteratorError = true;
47496
- _iteratorError = err;
47497
- } finally{
47498
- try {
47499
- if (!_iteratorNormalCompletion && _iterator.return != null) {
47500
- _iterator.return();
47501
- }
47502
- } finally{
47503
- if (_didIteratorError) {
47504
- throw _iteratorError;
47505
- }
47565
+ for(var mIdx = 0; mIdx < audioQueue.length; mIdx++){
47566
+ var msg_0 = audioQueue[mIdx];
47567
+ if (msg_0.stopped) continue;
47568
+ var idx = msg_0.nextIndex;
47569
+ var sentence = msg_0.sentences[idx];
47570
+ if (!sentence) continue;
47571
+ var isFull = isOptimistic({
47572
+ id: msg_0.id
47573
+ }) || msg_0.status !== "in_progress" || fullSentenceRegex.test(sentence);
47574
+ if (isFull) {
47575
+ candidate = {
47576
+ messageId: msg_0.id,
47577
+ sentence: sentence,
47578
+ index: idx,
47579
+ ownerStatus: msg_0.status
47580
+ };
47581
+ break;
47506
47582
  }
47507
47583
  }
47508
47584
  if (!candidate) return;
@@ -47513,10 +47589,10 @@ var useMessageAudio = function(_ref) {
47513
47589
  index: candidate.index
47514
47590
  };
47515
47591
  setAudioQueue(function(prev_0) {
47516
- return prev_0.map(function(m_2) {
47517
- return m_2.id === candidate.messageId ? _objectSpread47(_objectSpread47({}, m_2), {}, {
47518
- nextIndex: m_2.nextIndex + 1
47519
- }) : m_2;
47592
+ return prev_0.map(function(m_4) {
47593
+ return m_4.id === candidate.messageId ? _objectSpread47(_objectSpread47({}, m_4), {}, {
47594
+ nextIndex: candidate.index + 1
47595
+ }) : m_4;
47520
47596
  });
47521
47597
  });
47522
47598
  play({
@@ -47526,10 +47602,10 @@ var useMessageAudio = function(_ref) {
47526
47602
  },
47527
47603
  onStop: function() {
47528
47604
  setAudioQueue(function(prev_1) {
47529
- return prev_1.map(function(m_3) {
47530
- return m_3.id === candidate.messageId ? _objectSpread47(_objectSpread47({}, m_3), {}, {
47605
+ return prev_1.map(function(m_5) {
47606
+ return m_5.id === candidate.messageId ? _objectSpread47(_objectSpread47({}, m_5), {}, {
47531
47607
  stopped: true
47532
- }) : m_3;
47608
+ }) : m_5;
47533
47609
  });
47534
47610
  });
47535
47611
  setIsPlaying(false);
@@ -47540,10 +47616,10 @@ var useMessageAudio = function(_ref) {
47540
47616
  setIsPlaying(false);
47541
47617
  currentSentenceRef.current = null;
47542
47618
  pickLockRef.current = false;
47543
- var hasPending = audioQueueRef.current.some(function(m_4) {
47544
- if (m_4.stopped) return false;
47545
- var hasMore = m_4.nextIndex < m_4.sentences.length;
47546
- var streaming = m_4.status === "in_progress";
47619
+ var hasPending = audioQueueRef.current.some(function(m_6) {
47620
+ if (m_6.stopped) return false;
47621
+ var hasMore = m_6.nextIndex < m_6.sentences.length;
47622
+ var streaming = m_6.status === "in_progress";
47547
47623
  return hasMore || streaming;
47548
47624
  });
47549
47625
  if (!hasPending) _onEnd();
@@ -47559,9 +47635,9 @@ var useMessageAudio = function(_ref) {
47559
47635
  ]);
47560
47636
  useEffect10(function() {
47561
47637
  if (isHtmlAudioSupported) {
47562
- var _Howler$_howls$;
47563
- if (!(Howler !== null && Howler !== void 0 && (_Howler$_howls$ = Howler._howls[0]) !== null && _Howler$_howls$ !== void 0 && (_Howler$_howls$ = _Howler$_howls$._sounds[0]) !== null && _Howler$_howls$ !== void 0 && _Howler$_howls$._node)) return;
47564
- Howler._howls[0]._sounds[0]._node.crossOrigin = "anonymous";
47638
+ var _Howler$_howls;
47639
+ var node = Howler === null || Howler === void 0 || (_Howler$_howls = Howler._howls) === null || _Howler$_howls === void 0 || (_Howler$_howls = _Howler$_howls[0]) === null || _Howler$_howls === void 0 || (_Howler$_howls = _Howler$_howls._sounds) === null || _Howler$_howls === void 0 || (_Howler$_howls = _Howler$_howls[0]) === null || _Howler$_howls === void 0 ? void 0 : _Howler$_howls._node;
47640
+ if (node) node.crossOrigin = "anonymous";
47565
47641
  }
47566
47642
  }, [
47567
47643
  audioPlayer
@@ -47573,14 +47649,17 @@ var useMessageAudio = function(_ref) {
47573
47649
  if (isAudioEngineInited.current) return;
47574
47650
  isAudioEngineInited.current = true;
47575
47651
  if (isHtmlAudioSupported) {
47576
- var _Howler$_howls$2;
47577
- var audioContext = new AudioContext();
47578
- setAudioEngine({
47579
- // @ts-ignore-next-line
47580
- source: audioContext.createMediaElementSource(// @ts-ignore-next-line
47581
- (_Howler$_howls$2 = Howler._howls[0]) === null || _Howler$_howls$2 === void 0 || (_Howler$_howls$2 = _Howler$_howls$2._sounds[0]) === null || _Howler$_howls$2 === void 0 ? void 0 : _Howler$_howls$2._node),
47582
- audioContext: audioContext
47583
- });
47652
+ var _Howler$_howls2;
47653
+ var AudioCtx = window.AudioContext || window.webkitAudioContext;
47654
+ var audioContext = new AudioCtx();
47655
+ var node_0 = Howler === null || Howler === void 0 || (_Howler$_howls2 = Howler._howls) === null || _Howler$_howls2 === void 0 || (_Howler$_howls2 = _Howler$_howls2[0]) === null || _Howler$_howls2 === void 0 || (_Howler$_howls2 = _Howler$_howls2._sounds) === null || _Howler$_howls2 === void 0 || (_Howler$_howls2 = _Howler$_howls2[0]) === null || _Howler$_howls2 === void 0 ? void 0 : _Howler$_howls2._node;
47656
+ if (node_0) {
47657
+ setAudioEngine({
47658
+ // @ts-ignore-next-line
47659
+ source: audioContext.createMediaElementSource(node_0),
47660
+ audioContext: audioContext
47661
+ });
47662
+ }
47584
47663
  } else {
47585
47664
  setAudioEngine({
47586
47665
  source: Howler.masterGain,
@@ -47600,8 +47679,8 @@ var useMessageAudio = function(_ref) {
47600
47679
  audioEngine
47601
47680
  ]);
47602
47681
  var isPending = useMemo17(function() {
47603
- return isPlaying || audioQueue.some(function(m_5) {
47604
- return !m_5.stopped && (m_5.nextIndex < m_5.sentences.length || m_5.status === "in_progress");
47682
+ return isPlaying || audioQueue.some(function(m_7) {
47683
+ return !m_7.stopped && (m_7.nextIndex < m_7.sentences.length || m_7.status === "in_progress");
47605
47684
  });
47606
47685
  }, [
47607
47686
  isPlaying,