Spaces:
Running
Running
deploy 2571727
Browse files- assets/index-BhKIy_1y.js +0 -3
- assets/index-CzDNqk0f.css +0 -1
- assets/index-DIGGJAq1.js +3 -0
- assets/index-DTUQ8gca.css +1 -0
- assets/{readall-D11mojeC.js → readall-CNVhfTRg.js} +1 -1
- assets/tts-BfNZpTEA.js +0 -1
- assets/tts-DDfrpA1Y.js +1 -0
- index.html +3 -3
- readall.html +2 -2
assets/index-BhKIy_1y.js
DELETED
|
@@ -1,3 +0,0 @@
|
|
| 1 |
-
import{l as e}from"./loader-D0INP31U.js";import{i as t,r as n,t as r}from"./pins-DVBrHC3g.js";import{a as i,i as a,n as o,r as s,t as c}from"./llm-DH311QE0.js";import{a as l,i as u}from"./tts-BfNZpTEA.js";var d,f,p,m,h,g,_,v,y,b,x,S,C,w,T={},ee=[],E=/acit|ex(?:s|g|n|p|$)|rph|grid|ows|mnc|ntw|ine[ch]|zoo|^ord|itera/i,D=Array.isArray;function O(e,t){for(var n in t)e[n]=t[n];return e}function te(e){e&&e.parentNode&&e.parentNode.removeChild(e)}function k(e,t,n){var r,i,a,o={};for(a in t)a==`key`?r=t[a]:a==`ref`?i=t[a]:o[a]=t[a];if(arguments.length>2&&(o.children=arguments.length>3?d.call(arguments,2):n),typeof e==`function`&&e.defaultProps!=null)for(a in e.defaultProps)o[a]===void 0&&(o[a]=e.defaultProps[a]);return ne(e,o,r,i,null)}function ne(e,t,n,r,i){var a={type:e,props:t,key:n,ref:r,__k:null,__:null,__b:0,__e:null,__c:null,constructor:void 0,__v:i??++p,__i:-1,__u:0};return i==null&&f.vnode!=null&&f.vnode(a),a}function A(e){return e.children}function re(e,t){this.props=e,this.context=t}function j(e,t){if(t==null)return e.__?j(e.__,e.__i+1):null;for(var n;t<e.__k.length;t++)if((n=e.__k[t])!=null&&n.__e!=null)return n.__e;return typeof e.type==`function`?j(e):null}function ie(e){if(e.__P&&e.__d){var t=e.__v,n=t.__e,r=[],i=[],a=O({},t);a.__v=t.__v+1,f.vnode&&f.vnode(a),pe(e.__P,a,t,e.__n,e.__P.namespaceURI,32&t.__u?[n]:null,r,n??j(t),!!(32&t.__u),i),a.__v=t.__v,a.__.__k[a.__i]=a,he(r,a,i),t.__e=t.__=null,a.__e!=n&&ae(a)}}function ae(e){if((e=e.__)!=null&&e.__c!=null)return e.__e=e.__c.base=null,e.__k.some(function(t){if(t!=null&&t.__e!=null)return e.__e=e.__c.base=t.__e}),ae(e)}function oe(e){(!e.__d&&(e.__d=!0)&&m.push(e)&&!M.__r++||h!=f.debounceRendering)&&((h=f.debounceRendering)||g)(M)}function M(){try{for(var e,t=1;m.length;)m.length>t&&m.sort(_),e=m.shift(),t=m.length,ie(e)}finally{m.length=M.__r=0}}function se(e,t,n,r,i,a,o,s,c,l,u){var d,f,p,m,h,g,_=r&&r.__k||ee,v=t.length;for(c=ce(n,t,_,c,v),d=0;d<v;d++)(p=n.__k[d])!=null&&(f=p.__i!=-1&&_[p.__i]||T,p.__i=d,g=pe(e,p,f,i,a,o,s,c,l,u),m=p.__e,p.ref&&f.ref!=p.ref&&(f.ref&&ve(f.ref,null,p),u.push(p.ref,p.__c||m,p)),h==null&&m!=null&&(h=m),4&p.__u?(c=le(p,c,e),f.__e&&(f.__e=null)):typeof p.type==`function`&&g!==void 0?c=g:m&&(c=m.nextSibling),p.__u&=-7);return n.__e=h,c}function ce(e,t,n,r,i){var a,o,s,c,l,u=n.length,d=u,f=0;for(e.__k=Array(i),a=0;a<i;a++)(o=t[a])!=null&&typeof o!=`boolean`&&typeof o!=`function`?(typeof o==`string`||typeof o==`number`||typeof o==`bigint`||o.constructor==String?o=e.__k[a]=ne(null,o,null,null,null):D(o)?o=e.__k[a]=ne(A,{children:o},null,null,null):o.constructor===void 0&&o.__b>0?o=e.__k[a]=ne(o.type,o.props,o.key,o.ref?o.ref:null,o.__v):e.__k[a]=o,c=a+f,o.__=e,o.__b=e.__b+1,s=null,(l=o.__i=ue(o,n,c,d))!=-1&&(d--,(s=n[l])&&(s.__u|=2)),s==null||s.__v==null?(l==-1&&(i>u?f--:i<u&&f++),typeof o.type!=`function`&&(o.__u|=4)):l!=c&&(l==c-1?f--:l==c+1?f++:(l>c?f--:f++,o.__u|=4))):e.__k[a]=null;if(d)for(a=0;a<u;a++)(s=n[a])!=null&&!(2&s.__u)&&(s.__e==r&&(r=j(s)),ye(s,s));return r}function le(e,t,n){var r,i;if(typeof e.type==`function`){for(r=e.__k,i=0;r&&i<r.length;i++)r[i]&&(r[i].__=e,t=le(r[i],t,n));return t}e.__e!=t&&(t&&e.type&&!t.parentNode&&(t=j(e)),t=n.insertBefore(e.__e,t||null));do t&&=t.nextSibling;while(t!=null&&t.nodeType==8);return t}function ue(e,t,n,r){var i,a,o,s=e.key,c=e.type,l=t[n],u=l!=null&&!(2&l.__u);if(l===null&&s==null||u&&s==l.key&&c==l.type)return n;if(r>+!!u){for(i=n-1,a=n+1;i>=0||a<t.length;)if((l=t[o=i>=0?i--:a++])!=null&&!(2&l.__u)&&s==l.key&&c==l.type)return o}return-1}function de(e,t,n){t[0]==`-`?e.setProperty(t,n??``):e[t]=n==null?``:typeof n!=`number`||E.test(t)?n:n+`px`}function N(e,t,n,r,i){var a,o;n:if(t==`style`){if(typeof n==`string`)e.style.cssText=n;else{if(typeof r==`string`&&(e.style.cssText=r=``),r)for(t in r)n&&t in n||de(e.style,t,``);if(n)for(t in n)r&&n[t]==r[t]||de(e.style,t,n[t])}}else if(t[0]==`o`&&t[1]==`n`)a=t!=(t=t.replace(x,`$1`)),o=t.toLowerCase(),t=o in e||t==`onFocusOut`||t==`onFocusIn`?o.slice(2):t.slice(2),e.l||={},e.l[t+a]=n,n?r?n[b]=r[b]:(n[b]=S,e.addEventListener(t,a?w:C,a)):e.removeEventListener(t,a?w:C,a);else{if(i==`http://www.w3.org/2000/svg`)t=t.replace(/xlink(H|:h)/,`h`).replace(/sName$/,`s`);else if(t!=`width`&&t!=`height`&&t!=`href`&&t!=`list`&&t!=`form`&&t!=`tabIndex`&&t!=`download`&&t!=`rowSpan`&&t!=`colSpan`&&t!=`role`&&t!=`popover`&&t in e)try{e[t]=n??``;break n}catch{}typeof n==`function`||(n==null||!1===n&&t[4]!=`-`?e.removeAttribute(t):e.setAttribute(t,t==`popover`&&n==1?``:n))}}function fe(e){return function(t){if(this.l){var n=this.l[t.type+e];if(t[y]==null)t[y]=S++;else if(t[y]<n[b])return;return n(f.event?f.event(t):t)}}}function pe(e,t,n,r,i,a,o,s,c,l){var u,d,p,m,h,g,_,v,y,b,x,S,C,w,T,E,k=t.type;if(t.constructor!==void 0)return null;128&n.__u&&(c=!!(32&n.__u),a=[s=t.__e=n.__e]),(u=f.__b)&&u(t);n:if(typeof k==`function`){d=o.length;try{if(y=t.props,b=k.prototype&&k.prototype.render,x=(u=k.contextType)&&r[u.__c],S=u?x?x.props.value:u.__:r,n.__c?v=(p=t.__c=n.__c).__=p.__E:(b?t.__c=p=new k(y,S):(t.__c=p=new re(y,S),p.constructor=k,p.render=be),x&&x.sub(p),p.state||(p.state={}),p.__n=r,m=p.__d=!0,p.__h=[],p._sb=[]),b&&p.__s==null&&(p.__s=p.state),b&&k.getDerivedStateFromProps!=null&&(p.__s==p.state&&(p.__s=O({},p.__s)),O(p.__s,k.getDerivedStateFromProps(y,p.__s))),h=p.props,g=p.state,p.__v=t,m)b&&k.getDerivedStateFromProps==null&&p.componentWillMount!=null&&p.componentWillMount(),b&&p.componentDidMount!=null&&p.__h.push(p.componentDidMount);else{if(b&&k.getDerivedStateFromProps==null&&y!==h&&p.componentWillReceiveProps!=null&&p.componentWillReceiveProps(y,S),t.__v==n.__v||!p.__e&&p.shouldComponentUpdate!=null&&!1===p.shouldComponentUpdate(y,p.__s,S)){t.__v!=n.__v&&(p.props=y,p.state=p.__s,p.__d=!1),t.__e=n.__e,t.__k=n.__k,t.__k.some(function(e){e&&(e.__=t)}),ee.push.apply(p.__h,p._sb),p._sb=[],p.__h.length&&o.push(p),s=j(n);break n}p.componentWillUpdate!=null&&p.componentWillUpdate(y,p.__s,S),b&&p.componentDidUpdate!=null&&p.__h.push(function(){p.componentDidUpdate(h,g,_)})}if(p.context=S,p.props=y,p.__P=e,p.__e=!1,C=f.__r,w=0,b)p.state=p.__s,p.__d=!1,C&&C(t),u=p.render(p.props,p.state,p.context),ee.push.apply(p.__h,p._sb),p._sb=[];else do p.__d=!1,C&&C(t),u=p.render(p.props,p.state,p.context),p.state=p.__s;while(p.__d&&++w<25);p.state=p.__s,p.getChildContext!=null&&(r=O(O({},r),p.getChildContext())),b&&!m&&p.getSnapshotBeforeUpdate!=null&&(_=p.getSnapshotBeforeUpdate(h,g)),T=u!=null&&u.type===A&&u.key==null?ge(u.props.children):u,s=se(e,D(T)?T:[T],t,n,r,i,a,o,s,c,l),p.base=t.__e,t.__u&=-161,p.__h.length&&o.push(p),v&&(p.__E=p.__=null)}catch(e){if(o.length=d,t.__v=null,c||a!=null){if(e.then){for(t.__u|=c?160:128;s&&s.nodeType==8&&s.nextSibling;)s=s.nextSibling;a!=null&&(a[a.indexOf(s)]=null),t.__e=s}else if(a!=null)for(E=a.length;E--;)te(a[E])}else t.__e=n.__e;t.__k??=n.__k||[],e.then||me(t),f.__e(e,t,n)}}else a==null&&t.__v==n.__v?(t.__k=n.__k,t.__e=n.__e):s=t.__e=_e(n.__e,t,n,r,i,a,o,c,l);return(u=f.diffed)&&u(t),128&t.__u?void 0:s}function me(e){e&&(e.__c&&(e.__c.__e=!0),e.__k&&e.__k.some(me))}function he(e,t,n){for(var r=0;r<n.length;r++)ve(n[r],n[++r],n[++r]);f.__c&&f.__c(t,e),e.some(function(t){try{e=t.__h,t.__h=[],e.some(function(e){e.call(t)})}catch(e){f.__e(e,t.__v)}})}function ge(e){return typeof e!=`object`||!e||e.__b>0?e:D(e)?e.map(ge):e.constructor===void 0?O({},e):null}function _e(e,t,n,r,i,a,o,s,c){var l,u,p,m,h,g,_,v=n.props||T,y=t.props,b=t.type;if(b==`svg`?i=`http://www.w3.org/2000/svg`:b==`math`?i=`http://www.w3.org/1998/Math/MathML`:i||=`http://www.w3.org/1999/xhtml`,a!=null){for(l=0;l<a.length;l++)if((h=a[l])&&`setAttribute`in h==!!b&&(b?h.localName==b:h.nodeType==3)){e=h,a[l]=null;break}}if(e==null){if(b==null)return document.createTextNode(y);e=document.createElementNS(i,b,y.is&&y),s&&=(f.__m&&f.__m(t,a),!1),a=null}if(b==null)v===y||s&&e.data==y||(e.data=y);else{if(a=b==`textarea`&&y.defaultValue!=null?null:a&&d.call(e.childNodes),!s&&a!=null)for(v={},l=0;l<e.attributes.length;l++)v[(h=e.attributes[l]).name]=h.value;for(l in v)h=v[l],l==`dangerouslySetInnerHTML`?p=h:l==`children`||l in y||l==`value`&&`defaultValue`in y||l==`checked`&&`defaultChecked`in y||N(e,l,null,h,i);for(l in y)h=y[l],l==`children`?m=h:l==`dangerouslySetInnerHTML`?u=h:l==`value`?g=h:l==`checked`?_=h:s&&typeof h!=`function`||v[l]===h||N(e,l,h,v[l],i);if(u)s||p&&(u.__html==p.__html||u.__html==e.innerHTML)||(e.innerHTML=u.__html),t.__k=[];else if(p&&(e.innerHTML=``),se(t.type==`template`?e.content:e,D(m)?m:[m],t,n,r,b==`foreignObject`?`http://www.w3.org/1999/xhtml`:i,a,o,a?a[0]:n.__k&&j(n,0),s,c),a!=null)for(l=a.length;l--;)te(a[l]);s&&b!=`textarea`||(l=`value`,b==`progress`&&g==null?e.removeAttribute(`value`):g!=null&&(g!==e[l]||b==`progress`&&!g||b==`option`&&g!=v[l])&&N(e,l,g,v[l],i),l=`checked`,_!=null&&_!=e[l]&&N(e,l,_,v[l],i))}return e}function ve(e,t,n){try{if(typeof e==`function`){var r=typeof e.__u==`function`;r&&e.__u(),r&&t==null||(e.__u=e(t))}else e.current=t}catch(e){f.__e(e,n)}}function ye(e,t,n){var r,i;if(f.unmount&&f.unmount(e),(r=e.ref)&&(r.current&&r.current!=e.__e||ve(r,null,t)),(r=e.__c)!=null){if(r.componentWillUnmount)try{r.componentWillUnmount()}catch(e){f.__e(e,t)}r.base=r.__P=r.__n=null}if(r=e.__k)for(i=0;i<r.length;i++)r[i]&&ye(r[i],t,n||typeof e.type!=`function`);n||te(e.__e),e.__c=e.__=e.__e=void 0}function be(e,t,n){return this.constructor(e,n)}function xe(e,t,n){var r,i,a,o;t==document&&(t=document.documentElement),f.__&&f.__(e,t),i=(r=typeof n==`function`)?null:n&&n.__k||t.__k,a=[],o=[],pe(t,e=(!r&&n||t).__k=k(A,null,[e]),i||T,T,t.namespaceURI,!r&&n?[n]:i?null:t.firstChild?d.call(t.childNodes):null,a,!r&&n?n:i?i.__e:t.firstChild,r,o),he(a,e,o),e.props.children=null}d=ee.slice,f={__e:function(e,t,n,r){for(var i,a,o;t=t.__;)if((i=t.__c)&&!i.__)try{if((a=i.constructor)&&a.getDerivedStateFromError!=null&&(i.setState(a.getDerivedStateFromError(e)),o=i.__d),i.componentDidCatch!=null&&(i.componentDidCatch(e,r||{}),o=i.__d),o)return i.__E=i}catch(t){e=t}throw e}},p=0,re.prototype.setState=function(e,t){var n=this.__s!=null&&this.__s!=this.state?this.__s:this.__s=O({},this.state);typeof e==`function`&&(e=e(O({},n),this.props)),e&&O(n,e),e!=null&&this.__v&&(t&&this._sb.push(t),oe(this))},re.prototype.forceUpdate=function(e){this.__v&&(this.__e=!0,e&&this.__h.push(e),oe(this))},re.prototype.render=A,m=[],g=typeof Promise==`function`?Promise.prototype.then.bind(Promise.resolve()):setTimeout,_=function(e,t){return e.__v.__b-t.__v.__b},M.__r=0,v=Math.random().toString(8),y=`__d`+v,b=`__a`+v,x=/(PointerCapture)$|Capture$/i,S=0,C=fe(!1),w=fe(!0);var P,F,Se,Ce,we=0,Te=[],I=f,Ee=I.__b,De=I.__r,Oe=I.diffed,ke=I.__c,Ae=I.unmount,je=I.__;function Me(e,t){I.__h&&I.__h(F,e,we||t),we=0;var n=F.__H||(F.__H={__:[],__h:[]});return e>=n.__.length&&n.__.push({}),n.__[e]}function L(e){return we=1,Ne(Be,e)}function Ne(e,t,n){var r=Me(P++,2);if(r.t=e,!r.__c&&(r.__=[n?n(t):Be(void 0,t),function(e){var t=r.__N?r.__N[0]:r.__[0],n=r.t(t,e);t!==n&&(r.__N=[n,r.__[1]],r.__c.setState({}))}],r.__c=F,!F.__f)){var i=function(e,t,n){if(!r.__c.__H)return!0;var i=!1,o=r.__c.props!==e;if(r.__c.__H.__.some(function(e){if(e.__N){i=!0;var t=e.__[0];e.__=e.__N,e.__N=void 0,t!==e.__[0]&&(o=!0)}}),a){var s=a.call(this,e,t,n);return i?s||o:s}return!i||o};F.__f=!0;var a=F.shouldComponentUpdate,o=F.componentWillUpdate;F.componentWillUpdate=function(e,t,n){if(this.__e){var r=a;a=void 0,i(e,t,n),a=r}o&&o.call(this,e,t,n)},F.shouldComponentUpdate=i}return r.__N||r.__}function R(e,t){var n=Me(P++,3);!I.__s&&ze(n.__H,t)&&(n.__=e,n.u=t,F.__H.__h.push(n))}function z(e){return we=5,Pe(function(){return{current:e}},[])}function Pe(e,t){var n=Me(P++,7);return ze(n.__H,t)&&(n.__=e(),n.__H=t,n.__h=e),n.__}function Fe(){for(var e;e=Te.shift();){var t=e.__H;if(e.__P&&t)try{t.__h.some(B),t.__h.some(Re),t.__h=[]}catch(n){t.__h=[],I.__e(n,e.__v)}}}I.__b=function(e){F=null,Ee&&Ee(e)},I.__=function(e,t){e&&t.__k&&t.__k.__m&&(e.__m=t.__k.__m),je&&je(e,t)},I.__r=function(e){De&&De(e),P=0;var t=(F=e.__c).__H;t&&(Se===F?(t.__h=[],F.__h=[],t.__.some(function(e){e.__N&&(e.__=e.__N),e.u=e.__N=void 0})):(t.__h.some(B),t.__h.some(Re),t.__h=[],P=0)),Se=F},I.diffed=function(e){Oe&&Oe(e);var t=e.__c;t&&t.__H&&(t.__H.__h.length&&(Te.push(t)!==1&&Ce===I.requestAnimationFrame||((Ce=I.requestAnimationFrame)||Le)(Fe)),t.__H.__.some(function(e){e.u&&=(e.__H=e.u,void 0)})),Se=F=null},I.__c=function(e,t){t.some(function(e){try{e.__h.some(B),e.__h=e.__h.filter(function(e){return!e.__||Re(e)})}catch(n){t.some(function(e){e.__h&&=[]}),t=[],I.__e(n,e.__v)}}),ke&&ke(e,t)},I.unmount=function(e){Ae&&Ae(e);var t,n=e.__c;n&&n.__H&&(n.__H.__.some(function(e){try{B(e)}catch(e){t=e}}),n.__H=void 0,t&&I.__e(t,n.__v))};var Ie=typeof requestAnimationFrame==`function`;function Le(e){var t,n=function(){clearTimeout(r),Ie&&cancelAnimationFrame(t),setTimeout(e)},r=setTimeout(n,35);Ie&&(t=requestAnimationFrame(n))}function B(e){var t=F,n=e.__c;typeof n==`function`&&(e.__c=void 0,n()),F=t}function Re(e){var t=F;e.__c=e.__(),F=t}function ze(e,t){return!e||e.length!==t.length||t.some(function(t,n){return t!==e[n]})}function Be(e,t){return typeof t==`function`?t(e):t}var V=i.default??`short`,Ve=new Set;function He(){return V}function Ue(e){if(e!==V){V=e;for(let e of Ve)e(V)}}function We(e){return Ve.add(e),()=>Ve.delete(e)}var Ge=96,Ke=36,H=8;function qe(){let e=typeof window<`u`?window.getSelection():null;return!e||e.isCollapsed||e.rangeCount===0?``:e.toString().trim()}function Je(){return qe().length>0}function Ye(e){return e.trim().length>=20}function Xe(){let e=typeof window<`u`?window.getSelection():null;if(!e||e.rangeCount===0)return null;let t=e.getRangeAt(0).getBoundingClientRect();return t.width===0&&t.height===0?null:t}function Ze(e,t,n){let r=e.bottom+H;return r+Ke>n&&(r=e.top-Ke-H),r=Math.max(H,Math.min(r,n-Ke-H)),{left:Math.max(H,Math.min(e.left,t-Ge-H)),top:r}}function Qe(e){return e.altKey&&e.code===`KeyR`}function $e(e){let t=e.trim();t&&window.__fruitbat.run(t,He())}var et=0;Array.isArray;function U(e,t,n,r,i,a){t||={};var o,s,c=t;if(`ref`in c)for(s in c={},t)s==`ref`?o=t[s]:c[s]=t[s];var l={type:e,props:c,key:n,ref:o,__k:null,__:null,__b:0,__e:null,__c:null,constructor:void 0,__v:--et,__i:-1,__u:0,__source:i,__self:a};if(typeof e==`function`&&(o=e.defaultProps))for(s in o)c[s]===void 0&&(c[s]=o[s]);return f.vnode&&f.vnode(l),l}function tt(e){let t=e.trim();return t===``?0:t.split(/\s+/).length}function nt(){let[e,t]=L(``),n=tt(e),r=e.trim()===``;function i(){r||$e(e)}return U(`div`,{class:`paste-box`,children:[U(`label`,{class:`paste-label`,for:`paste-input`,children:l(`intake.paste_placeholder`)}),U(`textarea`,{id:`paste-input`,class:`paste-textarea`,placeholder:l(`intake.paste_placeholder`),value:e,onInput:e=>t(e.target.value),onKeyDown:e=>{(e.metaKey||e.ctrlKey)&&e.key===`Enter`&&(e.preventDefault(),i())}}),U(`div`,{class:`paste-row`,children:[U(`p`,{class:`word-count`,"aria-live":`polite`,"data-word-count":n,children:l(`intake.word_count`).replace(`{n}`,String(n))}),U(`button`,{type:`button`,class:`read-button`,onClick:i,disabled:r,children:l(`intake.read_button`)})]})]})}function rt(){let[e,t]=L(null);return R(()=>{function e(){let e=qe();if(!Ye(e)){t(null);return}let n=Xe();if(!n){t(null);return}t({text:e,position:Ze(n,window.innerWidth,window.innerHeight)})}function n(t){t.key!==`Escape`&&e()}function r(e){if(e.key===`Escape`){t(null);return}Qe(e)&&Je()&&(e.preventDefault(),$e(qe()),t(null))}return document.addEventListener(`mouseup`,e),document.addEventListener(`keyup`,n),document.addEventListener(`keydown`,r),window.addEventListener(`scroll`,e,{passive:!0,capture:!0}),window.addEventListener(`resize`,e),()=>{document.removeEventListener(`mouseup`,e),document.removeEventListener(`keyup`,n),document.removeEventListener(`keydown`,r),window.removeEventListener(`scroll`,e,{capture:!0}),window.removeEventListener(`resize`,e)}},[]),e?U(`button`,{type:`button`,class:`read-chip`,style:{left:`${e.position.left}px`,top:`${e.position.top}px`},"aria-label":l(`panel.read_chip`),onMouseDown:e=>e.preventDefault(),onClick:()=>{$e(e.text),t(null)},children:l(`panel.read_chip`)}):null}var it={idle:{start:`loading`,stop:`idle`},loading:{loaded:`running`,fail:`failed`,stop:`idle`},running:{finish:`done`,fail:`failed`,stop:`idle`},done:{start:`loading`,stop:`idle`},failed:{start:`loading`,stop:`idle`}},at={idle:{audio:`playing`,stop:`stopped`,reset:`idle`},playing:{audio:`playing`,pause:`paused`,stop:`stopped`,drain:`idle`,reset:`idle`},paused:{resume:`playing`,stop:`stopped`,drain:`idle`,reset:`idle`},stopped:{audio:`playing`,stop:`stopped`,reset:`idle`}};function W(e,t){return it[e][t]??e}function G(e,t){return at[e][t]??e}function ot(e,t){return e===`loading`||e===`running`||t===`playing`||t===`paused`}var st=i.levels.map(e=>e.id),ct=i.default??`short`,lt=`fruitbat.speakMessages`,ut=[`notice.dial_shorter`,`notice.dial_longer`,`notice.stopped`,`notice.all_cut`,`notice.oneline_failed`,`notice.input_limit`,`notice.done`];function dt(e){try{return localStorage.getItem(e)}catch{return null}}function ft(e,t){try{localStorage.setItem(e,t)}catch{}}var pt=class{voice;llm;gen=`idle`;play=`idle`;level=ct;speakMessages;bullets=[];allCut=[];notices=[];lastNotice=null;current=null;error=null;progress=null;voiceProgress=null;runId=0;text=``;chunks=null;voiceReady=!1;listeners=new Set;runs=0;last=null;ttfa=null;runT0=0;stopMs=null;noticeLatency=null;spoken=[];genStats=null;voiceRun=null;constructor(e=u(),t=new c(s())){this.voice=e,this.llm=t,this.speakMessages=dt(lt)!==`off`,t.onNotice=e=>this.onLlmNotice(e);let n=new Map,r=new Map,i=e=>{let t=0,n=0;for(let r of e.values())t+=r.loaded,n+=r.total;return{loaded:t,total:n}};t.onProgress=e=>{e.file&&n.set(e.file,{loaded:e.loaded??0,total:e.total??0}),this.progress={file:e.file,...i(n)},this.emit()},e.onProgress((e,t,n)=>{r.set(e,{loaded:t,total:n}),this.voiceProgress={file:e,...i(r)},this.emit()}),typeof Worker<`u`&&!a()&&!o()&&this.warmVoice()}markVoiceReady(){if(!this.voiceReady){this.voiceReady=!0,this.emit();for(let e of this.pendingNotices.splice(0))this.notice(e)}}finishPrewarm(){this.voiceReady&&!this.voice.prewarmed&&this.voice.prewarm(ut).catch(()=>void 0)}async warmVoice(){try{await this.voice.load(),this.markVoiceReady(),await this.voice.prewarm(ut)}catch(e){this.error=e instanceof Error?`${e.name}: ${e.message}`:String(e),this.notice(`error.voice`)}this.emit()}subscribe(e){return this.listeners.add(e),e(this.snapshot()),()=>this.listeners.delete(e)}snapshot(){let e=this.voice.state();return{gen:this.gen,play:this.play,level:this.level,runId:this.runId,settledRunId:this.settledRunId,bullets:[...this.bullets],current:this.current,allCut:[...this.allCut],notices:[...this.notices],lastNotice:this.lastNotice,chunks:this.chunks?.length??0,voiceReady:this.voiceReady,prewarmed:this.voice.prewarmed,speakMessages:this.speakMessages,progress:this.progress,voiceProgress:this.voiceProgress,error:this.error,voice:{aheadSeconds:e.aheadSeconds,enqueued:e.enqueued,inFlight:e.inFlight,ended:e.ended,pending:e.pending,phase:e.phase}}}emit(){let e=this.snapshot();for(let t of this.listeners)t(e)}stats(){return{runs:this.runs,last:this.last,ttfa_ms:this.ttfa===null?null:Math.round(this.ttfa),stop_ms:this.stopMs===null?null:Math.round(this.stopMs*100)/100,notice_latency_ms:this.noticeLatency,notices_spoken:[...this.spoken],gen:this.genStats??((this.last?.level??this.level)===`readall`?null:this.llm.stats()),voice:this.voice.stats(),voice_run:this.voiceRun}}setSpeakMessages(e){this.speakMessages=e,ft(lt,e?`on`:`off`),this.emit()}onLlmNotice(e){e.key!==`notice.stopped`&&(e.key===`notice.all_cut`&&e.chunkIndex!==void 0&&!this.allCut.includes(e.chunkIndex)&&this.allCut.push(e.chunkIndex),this.notice(e.key))}pendingNotices=[];notice(e,t){if(this.notices.push(e),this.lastNotice=e,this.emit(),this.speakMessages){if(!this.voiceReady){this.pendingNotices.push(e);return}this.spoken.push(e),this.voice.speak(e,t).then(()=>{t!==void 0&&(this.noticeLatency=this.voice.lastNoticeLatencyMs,this.emit())}).catch(()=>{})}}runAbort=null;newRun(){let e=++this.runId;return this.pendingNotices=[],this.runAbort?.abort(),this.runAbort=new AbortController,this.llm.abort(),this.stopMs=this.voice.stop(),this.gen=W(this.gen,`stop`),this.play=G(this.play,`stop`),e}run(e,t){this.voice.ensureContext(),this.runs++,this.last={level:t,chars:e.length},this.text=e,this.level=t,this.chunks=null,this.notices=[],this.lastNotice=null,this.regenFrom=null;let n=this.newRun();return this.begin(n,t,{fromChunk:0,base:0,end:e.length})}speakMessage(e){this.speakMessages&&this.voiceReady&&!this.busy()&&(this.spoken.push(e),this.voice.speak(e).catch(()=>void 0))}silenceVoice(){this.voice.stop()}stop(e={}){let t=ot(this.gen,this.play)&&!e.quiet;return this.newRun(),this.current=null,this.progress=null,this.emit(),t&&this.notice(`notice.stopped`),this.stopMs??0}pause(){this.play===`playing`&&(this.voice.pause(),this.play=G(this.play,`pause`),this.emit())}resume(){this.play===`paused`&&(this.voice.resume(),this.play=G(this.play,`resume`),this.emit())}skip(){return this.voice.skip()}async setLevel(e){let t=performance.now(),n=this.level;if(e===n)return;if(this.level=e,!this.busy()||!this.text){this.emit();return}let r=st.indexOf(e)>st.indexOf(n),i=this.newRun();this.notice(r?`notice.dial_shorter`:`notice.dial_longer`,t),this.regenPending=i;let a=await this.currentChunkIndex();if(this.regenPending===i&&(this.regenPending=null),i!==this.runId)return;this.regenFrom=a;let o=this.chunks?.[a];await this.begin(i,e,{fromChunk:a,base:o?.start??0,end:this.text.length})}regenPending=null;busy(){if(this.regenPending===this.runId||ot(this.gen,this.play))return!0;if(this.play===`stopped`)return!1;let e=this.voice.state();return e.pending>0||e.inFlight>0||e.enqueued>e.ended}async readThisPart(e){let t=this.newRun(),n=await this.ensureChunks();if(t!==this.runId)return;let r=n?.[e];r&&await this.begin(t,`readall`,{fromChunk:e,base:r.start,end:r.end,keep:!0})}async ensureChunks(){if(this.chunks)return this.chunks;if(!this.text)return null;let e=this.text,t=null;try{t=await this.llm.chunk(e)}catch{t=null}return e===this.text?(this.chunks=t,this.chunks):null}async currentChunkIndex(){let e=this.current;if(e?.kind===`bullet`)return e.chunkIndex;let t=await this.ensureChunks();if(!t)return 0;if(e?.kind===`sentence`){let n=t.findIndex(t=>e.start>=t.start&&e.start<t.end);return n>=0?n:0}return this.heardChunk===null?this.regenFrom??0:this.heardChunk}heardChunk=null;regenFrom=null;async begin(e,t,n){this.last={level:t,chars:n.end-n.base},typeof window<`u`&&window.dispatchEvent(new CustomEvent(`fruitbat:live`)),this.play=G(this.play,`reset`),n.keep||(this.bullets=[],this.allCut=[],this.heardChunk=null),this.current=null,this.error=null,this.ttfa=null,this.runT0=performance.now(),this.voiceRun=null,this.genStats=null,this.gen=W(this.gen,`start`),this.emit();try{t===`readall`?await this.readAloud(e,n.base,n.end):await this.summarize(e,t,n.fromChunk)}catch(t){if(e!==this.runId)return;this.gen=W(this.gen,`fail`),this.error=t instanceof Error?`${t.name}: ${t.message}`:String(t),this.notice(`error.generation`)}e===this.runId&&(this.settledRunId=e),this.emit()}settledRunId=0;markAudio(){this.ttfa===null&&(this.ttfa=performance.now()-this.runT0),this.play=G(this.play,`audio`)}async readAloud(e,t,n){let r=this.text.slice(t,n),i=[];if(await this.voice.load(),e!==this.runId)return;this.markVoiceReady(),this.gen=W(this.gen,`loaded`),this.emit();let a=await this.voice.readAll(r,{onPlanned:e=>{i=e},onStart:n=>{e===this.runId&&(this.markAudio(),this.current={kind:`sentence`,start:t+n.start,end:t+n.end,text:r.slice(n.start,n.end),next:i[n.seq+1]?.text??null},this.emit())}});if(e===this.runId){if(this.voice.phase===`failed`){this.gen=W(this.gen,`fail`),this.error=this.voice.error,this.play=G(this.play,`stop`),this.current=null,this.notice(`error.voice`);return}this.gen=W(this.gen,`finish`),this.voiceRun=this.voice.metrics(a.seconds),a.finished&&(this.play=G(this.play,`drain`),this.current=null,this.notice(`notice.done`),this.finishPrewarm())}}async summarize(e,t,n){this.voice.load().then(()=>{this.markVoiceReady(),this.voice.prewarm(ut).catch(()=>void 0)},()=>void 0);let r=this.voice.beginStream({onStart:t=>{if(e!==this.runId)return;this.markAudio();let n=t.tag===void 0?void 0:this.bullets[t.tag];n&&(this.current={kind:`bullet`,chunkIndex:n.chunkIndex,index:t.tag},this.heardChunk=n.chunkIndex),this.emit()}}),i=this.runAbort?.signal,a=await this.llm.ensureLoaded({signal:i});if(!a&&e===this.runId&&this.llm.error===`aborted`&&(a=await this.llm.ensureLoaded({signal:i})),e!==this.runId)return;if(!a){this.gen=W(this.gen,`fail`),this.error=this.llm.error,this.llm.gpu?.ok===!1&&!this.notices.includes(`notice.no_webgpu`)&&this.notice(`notice.no_webgpu`),this.voice.endStream(r),this.play=G(this.play,`reset`);return}if(this.gen=W(this.gen,`loaded`),this.emit(),await this.ensureChunks(),e!==this.runId)return;let o=await this.llm.summarize(this.text,t,{signal:this.runAbort?.signal,fromChunk:n,onBullet:t=>{if(e!==this.runId)return;let n=this.bullets.push(t)-1;this.emit(),this.voice.pushText(r,t.text,t.start,t.end,n)}});if(e!==this.runId)return;this.genStats=o,this.llm.state===`failed`?(this.gen=W(this.gen,`fail`),this.error=this.llm.error):this.gen=W(this.gen,`finish`),this.emit();let{finished:s,metrics:c}=await this.voice.endStream(r);e===this.runId&&(this.voiceRun=c,s||(this.play=G(this.play,`stop`),this.current=null),!s&&this.gen===`done`&&(this.error=this.error??`voice_failed`,this.notice(`error.voice`)),s&&(this.play=G(this.play,`drain`),this.current=null,this.gen===`done`&&this.bullets.length>0&&this.notice(`notice.done`),this.finishPrewarm()))}},mt=null;function K(){return mt||=new pt,mt}function ht(e,t){for(let n=0;n<e.length;n++){let r=e[n],i=t>=r.audioStart,a=t<r.audioEnd;if(i&&a)return n}let n=e[e.length-1];return n&&t>=n.audioEnd?e.length-1:-1}function gt(){let[t,n]=L(He),[r,i]=L({});return R(()=>We(n),[]),R(()=>{if(r[t])return;let n=!1;return e(`/demo/${t}.json`).then(e=>e.json()).then(e=>{n||i(n=>({...n,[t]:e}))}).catch(()=>{}),()=>{n=!0}},[t,r]),{track:r[t]??null,level:t}}function _t(){let{track:e,level:t}=gt(),[n,r]=L(!1),[i,a]=L(-1),o=z(null);return R(()=>{let t=o.current;if(!t||!e)return;let i=n;t.load(),a(-1),i&&t.play().catch(()=>r(!1))},[e?.level]),R(()=>{let e=()=>{let e=o.current;e&&!e.paused&&e.pause(),r(!1)},t=t=>{t.key===`Escape`&&e()};return window.addEventListener(`fruitbat:stop`,e),window.addEventListener(`fruitbat:run`,e),window.addEventListener(`fruitbat:live`,e),document.addEventListener(`keydown`,t),()=>{window.removeEventListener(`fruitbat:stop`,e),window.removeEventListener(`fruitbat:run`,e),window.removeEventListener(`fruitbat:live`,e),document.removeEventListener(`keydown`,t)}},[]),U(`section`,{class:`demo`,"data-testid":`demo`,"data-level":t,children:[U(`p`,{class:`demo-recording-label`,children:l(`demo.recording_label`)}),U(`p`,{class:`demo-excerpt-note`,children:l(`demo.excerpt_note`)}),U(`button`,{type:`button`,class:`demo-try-it-now`,"data-testid":`demo-try`,onClick:()=>{let e=o.current;e&&(window.dispatchEvent(new CustomEvent(`fruitbat:demo`)),e.play().catch(()=>r(!1)))},disabled:!e,children:l(`demo.try_it_now`)}),U(`p`,{class:`demo-switch-level`,children:l(`demo.switch_level`)}),e&&U(`audio`,{ref:o,"data-testid":`demo-audio`,preload:`auto`,src:`/demo/${e.level}.wav`,onPlay:()=>r(!0),onPause:()=>r(!1),onEnded:()=>r(!1),onTimeUpdate:()=>{let t=o.current;t&&e&&a(ht(e.items,t.currentTime))}}),e&&U(`ul`,{class:`demo-items`,"data-testid":`demo-bullets`,"aria-label":l(`a11y.bullet_list`),children:e.items.map((e,t)=>U(`li`,{"aria-current":t===i?`true`:void 0,children:e.text},t))})]})}async function vt(e){if(typeof caches>`u`)return!1;try{return!!await caches.match(e)}catch{return!1}}function yt(e){let t=[...e.files].sort((e,t)=>t.bytes-e.bytes)[0];return t?vt(r(e,t.path)):Promise.resolve(!1)}function q(e){return Math.round((e??0)/1e6)}function bt(e,t){return Object.entries(t).reduce((e,[t,n])=>e.replaceAll(`{${t}}`,String(n)),e)}function xt({testId:e,loaded:t,total:n}){let r=n>0?Math.min(100,Math.round(t/n*100)):void 0;return r===void 0?U(`progress`,{"data-testid":e,class:`loading-bar`}):U(`progress`,{"data-testid":e,class:`loading-bar`,max:100,value:r,"aria-valuenow":r,"aria-valuemin":0,"aria-valuemax":100})}function St(e){let[t,n]=L(`unknown`);return R(()=>{if(!e)return;let t=!1;return yt(e).then(e=>{t||n(e?`cached`:`first_time`)}),()=>{t=!0}},[e?.id,e?.revision]),t}function Ct({state:e}){return e===`unknown`?null:U(`p`,{class:`loading-cache`,children:l(e===`cached`?`loading.cached`:`loading.first_time`)})}function wt(){let[e,t]=L(()=>K().snapshot());return R(()=>K().subscribe(t),[]),e}function Tt({s:e}){let t=K().llm,[n,r]=L(`idle`),i=St(t.tier()),a=t.isLoaded(),o=!a&&(n===`failed`||t.state===`failed`||t.state===`stopped`),s=a||!o&&(n!==`idle`||e.progress!==null||t.state===`loading`),c=a||n===`ready`,u=q(e.progress?.loaded),d=Math.max(q(e.progress?.total),s?t.sizeMb():0);return U(`div`,{class:`loading-summarizer`,"data-started":s,children:[U(`p`,{class:`loading-line`,children:l(`loading.summarizer_size`).replace(`{mb}`,String(t.sizeMb()))}),!s&&U(`button`,{type:`button`,class:`loading-summarizer-button`,"data-testid":`summarizer-load`,onClick:()=>{s||(r(`loading`),t.ensureLoaded().then(e=>r(e?`ready`:`failed`)))},children:l(`loading.summarizer_button`).replace(`{mb}`,String(t.sizeMb()))}),s&&U(A,{children:[U(xt,{testId:`summarizer-progress`,loaded:c?1:u,total:c?1:d}),U(`p`,{class:`loading-line`,children:bt(l(`loading.progress`),{mb:u})}),U(Ct,{state:i})]}),e.notices.filter((t,n)=>(t===`notice.no_webgpu`||t===`notice.probe_failed`||t===`notice.low_end_tier`)&&e.notices.indexOf(t)===n).map(e=>U(`p`,{class:`loading-notice`,role:`status`,"data-notice":e,children:l(e)},e))]})}function Et({s:e}){let t=n().web.voice,r=St(t);if(a())return U(`p`,{class:`loading-line`,"data-phase":`save_data`,children:l(`loading.save_data`)});if(o())return U(`p`,{class:`loading-line`,"data-phase":`mobile`,children:l(`loading.mobile`)});if(e.voiceReady)return U(`p`,{class:`loading-line`,"data-phase":`ready`,children:l(`loading.ready`)});if(e.voiceProgress){let n=q(e.voiceProgress.loaded),i=Math.max(q(e.voiceProgress.total),Math.round(t.files.reduce((e,t)=>e+t.bytes,0)/1e6));return U(`div`,{class:`loading-voice`,"data-phase":`voice`,children:[U(`p`,{class:`loading-line`,children:l(`loading.voice`)}),U(xt,{testId:`voice-progress`,loaded:n,total:i}),U(`p`,{class:`loading-line`,children:bt(l(`loading.progress`),{mb:n})}),U(Ct,{state:r})]})}return U(`p`,{class:`loading-line`,"data-phase":`probing`,children:l(`loading.probing`)})}function Dt(){let e=wt();return U(`section`,{class:`loading`,"data-testid":`loading`,children:[U(Et,{s:e}),U(Tt,{s:e})]})}var Ot=Object.freeze([`level`,`from_level`,`to_level`,`device`,`model_id`,`model_role`,`reason`,`probe_result`,`resource`,`store`,`chunk_count`,`chunk_index`,`bullets_total`,`word_count`,`phoneme_count`,`bytes`,`bytes_attempted`,`duration_ms`,`latency_ms`,`at_ms`]),kt=200,J=[],At=typeof performance<`u`?performance.now():0;function jt(){return typeof performance<`u`?performance.now():0}function Y(e,t={}){try{for(J.push({event:e,t_ms:Math.round(jt()-At),fields:t});J.length>kt;)J.shift()}catch{}}function Mt(){return[...J]}var Nt={web:`0.0.0`,mac:`0.0.0`},X={$schema:`https://json-schema.org/draft/2020-12/schema`,$id:`run-stats.schema.json`,title:`RunStats`,$comment:"One bench measurement (docs/PLAN.md rule 3, C11, S0-05). Numbers, enums, and validated metadata only — no free-text field. Metrics are nullable when a dial level doesn't produce them (readall has no LLM metrics; only readall has `coverage`). Bench identity = target, model_id, model_rev, dtype, device, browser(+major), os(+major), machine_id, cache_state, doc_id, level (bench/identity.md). Field order here is the fixed column order of bench/results.csv.",type:`object`,additionalProperties:!1,$defs:{level:{type:`string`,enum:[`readall`,`short`,`caveman`,`oneline`]},device:{type:`string`,enum:[`webgpu`,`wasm`,`mlx`]},model_id:{type:`string`,$comment:`Closed set sourced from spec/models.json. Add a value here (small PR) whenever a new model_id is pinned there.`,enum:[`onnx-community/Qwen3.5-0.8B-Text-ONNX`,`onnx-community/Qwen2.5-0.5B-Instruct`,`onnx-community/Qwen3-0.6B-ONNX`,`HuggingFaceTB/SmolLM2-360M-Instruct`,`onnx-community/Kokoro-82M-v1.0-ONNX`,`mlx-community/Qwen3.5-2B-4bit`,`mlx-community/Qwen3-1.7B-4bit`,`mlx-community/Kokoro-82M-bf16`]}},required:`schema_version.target.device.level.browser.browser_major.os.os_major.cache_state.model_id.model_rev.dtype.doc_id.commit.date.machine_id.ttfa_ms.gen_ms.tok_s.rtf.gap_ms.stop_ms.coverage.bullets_total.bullets_cut.cut_rate.facts_token_hit.halluc_flags.forbidden_hits.oneline_keyword_hit.tts_overlimit.peak_mb.heap_mb`.split(`.`),properties:{schema_version:{type:`integer`,enum:[1]},target:{type:`string`,enum:[`web`,`mac`]},device:{$ref:`#/$defs/device`},level:{$ref:`#/$defs/level`},browser:{type:`string`,enum:[`chrome`,`safari`,`firefox`,`none`]},browser_major:{type:[`integer`,`null`],minimum:0},os:{type:`string`,enum:[`macos`,`windows`,`linux`,`ios`,`android`]},os_major:{type:`integer`,minimum:0},cache_state:{type:`string`,enum:[`cold`,`warm`]},model_id:{$ref:`#/$defs/model_id`},model_rev:{type:`string`,pattern:`^[0-9a-f]{40}$`},dtype:{type:`string`,enum:[`q4f16`,`q8`,`q8f16`,`q4`,`fp32`,`bf16`,`fp16`,`4bit`,`8bit`],$comment:`q8f16: the WebGPU voice variant (?tts=webgpu, spec/models.json).`},doc_id:{type:`string`,pattern:`^([0-9]{3}|paste)$`,$comment:`S1-10: bench rows use the 3-digit eval corpus id; every other row (real usage, not the corpus) is 'paste' unless window.__fruitbat.setDocId(id) overrides it.`},commit:{type:`string`,pattern:`^[0-9a-f]{7,40}$`},date:{type:`string`,pattern:`^\\d{4}-\\d{2}-\\d{2}(T\\d{2}:\\d{2}:\\d{2}(\\.\\d+)?(Z|[+-]\\d{2}:\\d{2})?)?$`},machine_id:{type:`string`,pattern:`^(web|[0-9a-f]{12})$`},ttfa_ms:{type:[`number`,`null`],minimum:0},gen_ms:{type:[`number`,`null`],minimum:0},tok_s:{type:[`number`,`null`],minimum:0},rtf:{type:[`number`,`null`],minimum:0},gap_ms:{type:[`number`,`null`],minimum:0},stop_ms:{type:[`number`,`null`],minimum:0},coverage:{type:[`number`,`null`],minimum:0,maximum:1},bullets_total:{type:[`integer`,`null`],minimum:0},bullets_cut:{type:[`integer`,`null`],minimum:0},cut_rate:{type:[`number`,`null`],minimum:0,maximum:1},facts_token_hit:{type:[`number`,`null`],minimum:0,maximum:1},halluc_flags:{type:[`integer`,`null`],minimum:0},forbidden_hits:{type:[`integer`,`null`],minimum:0},oneline_keyword_hit:{type:[`number`,`null`],minimum:0,maximum:1},tts_overlimit:{type:[`integer`,`null`],minimum:0},peak_mb:{type:[`number`,`null`],minimum:0},heap_mb:{type:[`number`,`null`],minimum:0}}},Pt=Object.freeze([...X.required??[]]);function Ft(e){let t=/^#\/\$defs\/(.+)$/.exec(e);if(!t)throw Error(`stats/schema: unsupported $ref "${e}"`);let n=X.$defs?.[t[1]];if(!n)throw Error(`stats/schema: unknown $defs entry "${t[1]}"`);return n}function It(e){return e===null?`null`:Array.isArray(e)?`array`:typeof e==`number`?Number.isInteger(e)?`integer`:`number`:typeof e==`string`?`string`:typeof e==`boolean`?`boolean`:`object`}function Lt(e,t){let n=It(e);return t===`number`?n===`number`||n===`integer`:n===t}function Rt(e,t,n,r){let i=n.$ref?Ft(n.$ref):n;if(i.type!==void 0&&!(Array.isArray(i.type)?i.type:[i.type]).some(e=>Lt(t,e))){r.push(`${e}: expected type ${JSON.stringify(i.type)}, got ${It(t)} (${JSON.stringify(t)})`);return}t!==null&&(i.enum!==void 0&&!i.enum.includes(t)&&r.push(`${e}: ${JSON.stringify(t)} is not one of ${JSON.stringify(i.enum)}`),i.pattern!==void 0&&typeof t==`string`&&!new RegExp(i.pattern).test(t)&&r.push(`${e}: ${JSON.stringify(t)} does not match pattern ${i.pattern}`),i.minimum!==void 0&&typeof t==`number`&&t<i.minimum&&r.push(`${e}: ${t} is below minimum ${i.minimum}`),i.maximum!==void 0&&typeof t==`number`&&t>i.maximum&&r.push(`${e}: ${t} is above maximum ${i.maximum}`))}function zt(e){let t=[];if(typeof e!=`object`||!e||Array.isArray(e))return{ok:!1,errors:[`row is not a plain object`]};let n=e,r=X.properties??{};for(let e of X.required??[])e in n||t.push(`missing required field: ${e}`);if(X.additionalProperties===!1)for(let e of Object.keys(n))e in r||t.push(`unknown field: ${e}`);for(let[e,i]of Object.entries(r))e in n&&Rt(e,n[e],i,t);return{ok:t.length===0,errors:t}}var Bt=2e3,Vt=8e3,Ht=`https://github.com/aj-prabhu/fruitbat`,Ut={ua:300,gpu:200,os:100,chip:50};function Z(e,t){return e.length>t?e.slice(0,t):e}async function Wt(){try{let e=navigator.gpu;if(!e)return`unknown`;let t=await e.requestAdapter();if(!t)return`unknown`;let n=t.info,r=[n.vendor,n.architecture,n.description].filter(e=>!!e);return r.length?r.join(` `):`unknown`}catch{return`unknown`}}function Gt(){let e=navigator.deviceMemory;return typeof e!=`number`||!Number.isFinite(e)?`unknown`:e<8?`under_8gb`:`8gb`}function Kt(e=typeof navigator<`u`&&navigator.userAgent||``){return/iPhone|iPad/.test(e)?`ios ${/OS (\d+)_/.exec(e)?.[1]??``}`.trim():/Mac OS X/.test(e)?`macos ${/Mac OS X (\d+)/.exec(e)?.[1]??``}`.trim():/Windows NT/.test(e)?`windows ${/Windows NT (\d+)/.exec(e)?.[1]??``}`.trim():/Android/.test(e)?`android ${/Android (\d+)/.exec(e)?.[1]??``}`.trim():/Linux/.test(e)?`linux`:`unknown`}function qt(){return navigator.platform||`unknown`}async function Jt(){return{ua:Z(typeof navigator<`u`&&navigator.userAgent||``,Ut.ua),gpu:Z(await Wt(),Ut.gpu),os:Z(Kt(),Ut.os),chip:Z(qt(),Ut.chip),ram_bucket:Gt()}}function Yt(e){let{voice:r}=n().web,i=[{id:r.id,rev:r.revision}],a=e.last?.level;if(a&&a!==`readall`){let n=t(),r=n.find(t=>t.id===e.gen?.model_id)??n[0];i.push({id:r.id,rev:r.revision})}return i}function Xt(e){let t={},n=e;for(let e of Pt)t[e]=n[e];return t}function Zt(e){let t={},n=e.fields;for(let e of Ot)e in n&&(t[e]=n[e]);return{event:e.event,t_ms:e.t_ms,fields:t}}async function Qt({orchestratorStats:e,rows:t,events:n,description:r}){return{app:`web`,version:Nt.web,env:await Jt(),models:Yt(e),run_stats:t.slice(-5).map(Xt),events:n.slice(-50).map(Zt),user_description:Z(r,Bt)}}function $t(e){let t=e.events[e.events.length-1];return t?(t.fields.reason?`${t.event} ${t.fields.reason}`:t.event).replace(/_/g,` `):`no events`}function en(e){return e.run_stats[e.run_stats.length-1]?.level??`unknown`}function tn(e){return`bug: ${en(e)} ${e.app} ${$t(e)}`}function nn(e){let t=tn(e),n=[...e.events],r=[...e.run_stats],i=e.user_description,a=()=>{let a=new URLSearchParams;return a.set(`template`,`bug.yml`),a.set(`title`,t),a.set(`what_happened`,i),a.set(`env`,JSON.stringify(e.env,null,2)),a.set(`models`,JSON.stringify(e.models,null,2)),a.set(`run_stats`,JSON.stringify(r,null,2)),a.set(`events`,JSON.stringify(n,null,2)),a.set(`app_version`,`${e.app} ${e.version}`),`${Ht}/issues/new?${a.toString()}`},o=a();for(;o.length>Vt&&n.length>0;)n.shift(),o=a();for(;o.length>Vt&&r.length>0;)r.shift(),o=a();for(;o.length>Vt&&i.length>0;)i=i.slice(0,Math.max(0,i.length-200)),o=a();return o}function rn(e){return JSON.stringify(e,null,2)}var an=`fruitbat.stats`,on=`fruitbat.stats.errors`,sn=`paste`;function cn(e){sn=e}function ln(){return sn}function Q(e,t){let n=e.exec(t);return n?Number(n[1]):null}function un(e=typeof navigator<`u`?navigator.userAgent:``){let t=`none`,n=null;/Firefox\//.test(e)?(t=`firefox`,n=Q(/Firefox\/(\d+)/,e)):/Chrome\//.test(e)&&!/Edg\//.test(e)?(t=`chrome`,n=Q(/Chrome\/(\d+)/,e)):/Safari\//.test(e)&&/Version\//.test(e)&&(t=`safari`,n=Q(/Version\/(\d+)/,e));let r=`linux`,i=0;return/iPhone|iPad/.test(e)?(r=`ios`,i=Q(/OS (\d+)_/,e)??0):/Android/.test(e)?(r=`android`,i=Q(/Android (\d+)/,e)??0):/Mac OS X/.test(e)?(r=`macos`,i=Q(/Mac OS X (\d+)/,e)??0):/Windows NT/.test(e)&&(r=`windows`,i=Q(/Windows NT (\d+)/,e)??0),{browser:t,browser_major:n,os:r,os_major:i}}function dn(){return`b5e7143`}function fn(){let e=un(),t=typeof performance<`u`?performance.memory:void 0,n=t?Math.round(t.usedJSHeapSize/1e6*10)/10:null;return{...e,machine_id:`web`,commit:dn(),date:new Date().toISOString(),doc_id:ln(),heap_mb:n}}function pn(e,r){let i=e.last?.level??`short`,a=i===`readall`?e.voice:null,o=e.gen,s=e.voice_run,c,l,u,d;if(i===`readall`){let e=n().web.voice;c=e.id,l=e.revision,u=s?s.dtype:a?.dtype??e.dtype,d=s?s.device:a?.device??e.device}else{let e=t(),n=e.find(e=>e.id===o?.model_id)??e[0];c=n.id,l=n.revision,u=n.dtype,d=n.device}let f=(s?s.cache_state:a?.cache_state)===`cold`,p=i!==`readall`&&o?.cache_cold===!0,m=f||p?`cold`:`warm`,h=o?.bullets_total??null,g=o?.bullets_cut??null,_=h===null?null:h>0?(g??0)/h:0;return{schema_version:1,target:`web`,device:d,level:i,browser:r.browser,browser_major:r.browser_major,os:r.os,os_major:r.os_major,cache_state:m,model_id:c,model_rev:l,dtype:u,doc_id:r.doc_id,commit:r.commit,date:r.date,machine_id:r.machine_id,ttfa_ms:e.ttfa_ms,gen_ms:o?.gen_ms??null,tok_s:o?.tok_s??null,rtf:s?s.rtf:a?.rtf??null,gap_ms:s?s.gap_ms:a?.gap_ms??null,stop_ms:null,coverage:i===`readall`?a?.coverage??null:null,bullets_total:h,bullets_cut:g,cut_rate:_,facts_token_hit:null,halluc_flags:null,forbidden_hits:null,oneline_keyword_hit:null,tts_overlimit:s?s.tts_overlimit:a?.tts_overlimit??0,peak_mb:null,heap_mb:r.heap_mb??null}}function mn(){try{let e=localStorage.getItem(an);if(!e)return[];let t=JSON.parse(e);return Array.isArray(t)?t:[]}catch{return[]}}function hn(){try{let e=Number(localStorage.getItem(`fruitbat.stats.errors`))||0;localStorage.setItem(on,String(e+1))}catch{}}function gn(){return mn()}function _n(){try{localStorage.removeItem(an),localStorage.removeItem(on)}catch{}}function vn(e){try{let t=mn();for(t.push(e);t.length>200;)t.shift();localStorage.setItem(an,JSON.stringify(t))}catch{hn()}}function yn(e,t=fn()){let n=pn(e,t),{ok:r,errors:i}=zt(n);return r&&vn(n),{ok:r,errors:i,row:n}}function bn(e){if(e==null)return``;let t=String(e);return/[",\n]/.test(t)?`"${t.replace(/"/g,`""`)}"`:t}function xn(){let e=[Pt.join(`,`)];for(let t of mn()){let n=t;e.push(Pt.map(e=>bn(n[e])).join(`,`))}return e.join(`
|
| 2 |
-
`)+`
|
| 3 |
-
`}function Sn({onClose:e}){let[t,n]=L(null),[r,i]=L(``),[a,o]=L(!1),[s,c]=L(!1),u=z(null);R(()=>{let e=!1;return Qt({orchestratorStats:K().stats(),rows:gn(),events:Mt(),description:``}).then(t=>{e||n(t)}),()=>{e=!0}},[]);let d=t?{...t,user_description:r.slice(0,2e3)}:null,f=z(null);return R(()=>{f.current?.scrollIntoView({block:`start`}),f.current?.focus()},[]),U(`div`,{class:`report-view`,role:`dialog`,"aria-label":l(`report.title`),ref:f,tabIndex:-1,children:[U(`div`,{class:`report-view-header`,children:[U(`h2`,{children:l(`report.title`)}),U(`button`,{type:`button`,class:`report-close`,onClick:e,children:l(`panel.close`)})]}),U(`p`,{class:`report-privacy-note`,children:l(`report.privacy_note`)}),U(`label`,{class:`report-describe-label`,for:`report-describe`,children:l(`report.describe`)}),U(`textarea`,{id:`report-describe`,class:`report-describe`,maxLength:Bt,value:r,onInput:e=>i(e.target.value)}),U(`p`,{class:`report-preview-intro`,children:l(`report.preview_intro`)}),U(`pre`,{class:`report-preview`,"data-testid":`report-preview`,ref:u,children:d?JSON.stringify(d,null,2):``}),U(`div`,{class:`report-actions`,children:[U(`button`,{type:`button`,class:`report-open-github`,disabled:!d,onClick:()=>{d&&window.open(nn(d),`_blank`,`noopener`)},children:l(`report.open_github`)}),U(`button`,{type:`button`,class:`report-copy`,disabled:!d,onClick:()=>{if(!d)return;let e=typeof navigator<`u`?navigator.clipboard:void 0;(e?e.writeText(rn(d)):Promise.reject(Error(`no clipboard`))).then(()=>{c(!1),o(!0),K().speakMessage(`report.copied`)},()=>{o(!1),c(!0),K().speakMessage(`report.copy_failed`);let e=u.current,t=typeof window<`u`?window.getSelection():null;if(e&&t){let n=document.createRange();n.selectNodeContents(e),t.removeAllRanges(),t.addRange(n)}})},children:U(`span`,{"aria-live":`polite`,children:l(s?`report.copy_failed`:a?`report.copied`:`report.copy`)})})]})]})}var Cn=[`date`,`level`,`device`,`dtype`,`cache_state`,`doc_id`,`ttfa_ms`,`tok_s`,`rtf`,`bullets_total`,`bullets_cut`],wn={date:`stats.col.date`,level:`stats.col.level`,device:`stats.col.device`,dtype:`stats.col.dtype`,cache_state:`stats.col.cache_state`,doc_id:`stats.col.doc_id`,ttfa_ms:`stats.col.ttfa_ms`,tok_s:`stats.col.tok_s`,rtf:`stats.col.rtf`,bullets_total:`stats.col.bullets_total`,bullets_cut:`stats.col.bullets_cut`};function Tn(e){let t=new Blob([e],{type:`text/csv`}),n=URL.createObjectURL(t),r=document.createElement(`a`);r.href=n,r.download=`fruitbat-stats.csv`,r.click(),URL.revokeObjectURL(n)}function En({onClose:e}){let[t,n]=L(()=>gn()),r=z(null);return R(()=>{r.current?.scrollIntoView({block:`start`}),r.current?.focus()},[]),U(`div`,{class:`stats-view`,role:`dialog`,"aria-label":l(`stats.title`),ref:r,tabIndex:-1,children:[U(`div`,{class:`stats-view-header`,children:[U(`h2`,{children:l(`stats.title`)}),U(`button`,{type:`button`,class:`stats-close`,onClick:e,children:l(`panel.close`)})]}),t.length===0?U(`p`,{class:`stats-empty`,children:l(`stats.empty`)}):U(`table`,{class:`stats-table`,children:[U(`thead`,{children:U(`tr`,{children:Cn.map(e=>U(`th`,{children:l(wn[e])},e))})}),U(`tbody`,{children:t.map((e,t)=>U(`tr`,{children:Cn.map(t=>U(`td`,{children:e[t]===null?``:String(e[t])},t))},t))})]}),U(`div`,{class:`stats-actions`,children:[U(`button`,{type:`button`,onClick:()=>Tn(xn()),children:l(`stats.export`)}),U(`button`,{type:`button`,onClick:()=>{_n(),n(gn())},children:l(`stats.clear`)})]})]})}var Dn=i.levels,On=i.default??`short`;function kn({level:e,onChange:t}){return U(`fieldset`,{class:`dial`,children:[U(`legend`,{class:`visually-hidden`,children:l(`a11y.dial`)}),Dn.map(n=>U(`label`,{class:`dial-option`,children:[U(`input`,{type:`radio`,name:`level`,value:n.id,checked:e===n.id,onChange:()=>t(n.id)}),U(`span`,{children:l(n.label_key)})]},n.id))]})}function An(){if(typeof document<`u`){let e=document.documentElement.getAttribute(`data-theme`);if(e===`dark`||e===`light`)return e}return typeof matchMedia<`u`&&matchMedia(`(prefers-color-scheme: dark)`).matches?`dark`:`light`}function jn(){let[e,t]=L(An);return U(`button`,{type:`button`,class:`theme-toggle`,onClick:()=>{let n=e===`dark`?`light`:`dark`;t(n),document.documentElement.setAttribute(`data-theme`,n);try{localStorage.setItem(`fruitbat-theme`,n)}catch{}},"aria-pressed":e===`dark`,children:l(`theme.toggle`)})}function Mn({paragraphs:e}){return U(`article`,{class:`article`,"aria-label":l(`intake.sample_label`),children:e.map((e,t)=>U(`p`,{children:e},t))})}function Nn(){let[t,n]=L([]);return R(()=>{let t=!1;return e(`/sample.txt`).then(e=>e.text()).then(e=>{t||n(e.split(/\n{2,}/).map(e=>e.trim()).filter(Boolean))}).catch(()=>{t||n([])}),()=>{t=!0}},[]),t}function Pn(){let[e,t]=L(()=>K().snapshot());return R(()=>K().subscribe(t),[]),e}function Fn(){let e=Pn(),t=e.current,n=e.bullets.length===0&&!t&&e.allCut.length===0&&!e.lastNotice;return U(`aside`,{id:`panel`,class:`panel`,"aria-label":l(`a11y.panel_region`),"data-gen":e.gen,"data-play":e.play,children:[n&&U(`p`,{class:`panel-empty`,children:l(`panel.empty`)}),t?.kind===`sentence`&&U(`div`,{class:`now-reading`,children:[U(`p`,{class:`now-label`,children:l(`panel.now_reading`)}),U(`p`,{class:`now-text`,"data-testid":`now-text`,children:t.text}),t.next&&U(`p`,{class:`next-text`,children:[U(`span`,{class:`next-label`,children:l(`panel.next_up`)}),` `,t.next]})]}),e.bullets.length>0&&U(`ul`,{class:`bullets`,"aria-label":l(`a11y.bullet_list`),children:e.bullets.map((e,n)=>U(`li`,{"data-chunk":e.chunkIndex,"aria-current":t?.kind===`bullet`&&t.index===n?`true`:void 0,children:e.text},n))}),e.allCut.map(e=>U(`p`,{class:`read-part-row`,children:U(`button`,{type:`button`,class:`read-part`,"data-chunk":e,onClick:()=>void K().readThisPart(e),children:l(`panel.read_this_part`)})},e)),e.lastNotice&&U(`p`,{class:`panel-notice`,role:`status`,"aria-live":`polite`,"data-notice":e.lastNotice,children:l(e.lastNotice)})]})}function In(){let[e,t]=L(On),[n,r]=L(!1),[i,a]=L(!1),o=Nn();return R(()=>{document.title=l(`app.title`)},[]),R(()=>{Ue(e)},[e]),U(`div`,{class:`app-shell`,children:[U(`header`,{class:`app-header`,children:[U(`h1`,{class:`app-title`,children:l(`app.title`)}),U(kn,{level:e,onChange:e=>{Ue(e),t(e)}}),U(`button`,{type:`button`,class:`stats-toggle`,onClick:()=>r(!0),children:l(`panel.stats`)}),U(`button`,{type:`button`,class:`report-toggle`,onClick:()=>a(!0),children:l(`panel.bug_report`)}),U(jn,{})]}),U(Dt,{}),U(`main`,{class:`app-main`,children:[U(_t,{}),U(Mn,{paragraphs:o}),U(nt,{})]}),U(Fn,{}),U(rt,{}),n&&U(En,{onClose:()=>r(!1)}),i&&U(Sn,{onClose:()=>a(!1)})]})}function Ln(){try{let e=localStorage.getItem(`fruitbat-theme`);(e===`dark`||e===`light`)&&document.documentElement.setAttribute(`data-theme`,e)}catch{}}var $=K();window.__fruitbat={run(e,t){window.dispatchEvent(new CustomEvent(`fruitbat:run`,{detail:{text:e,level:t}}))},stop(){window.dispatchEvent(new CustomEvent(`fruitbat:stop`))},stats(){return $.stats()},state:()=>$.snapshot(),setLevel:e=>$.setLevel(e),readThisPart:e=>$.readThisPart(e),pause:()=>$.pause(),resume:()=>$.resume(),skip:()=>$.skip(),setSpeakMessages:e=>$.setSpeakMessages(e),rows:()=>gn(),setDocId:e=>cn(e)},window.addEventListener(`fruitbat:run`,e=>void $.run(e.detail.text,e.detail.level)),window.addEventListener(`fruitbat:stop`,()=>$.stop()),window.addEventListener(`fruitbat:demo`,()=>{let e=$.snapshot(),t=e.voice.pending>0||e.voice.inFlight>0||e.voice.enqueued>e.voice.ended;ot(e.gen,e.play)||t?$.stop({quiet:!0}):$.silenceVoice()});var Rn=0;$.subscribe(e=>{(e.gen===`done`||e.gen===`failed`)&&e.settledRunId===e.runId&&e.runId!==Rn&&(Rn=e.runId,yn($.stats()))});var zn=null;$.subscribe(e=>{let t=zn;zn=e,t&&(e.level!==t.level&&Y(`dial_change`,{from_level:t.level,to_level:e.level}),t.gen!==`loading`&&e.gen===`loading`&&Y(`run_start`,{level:e.level}),t.gen!==`done`&&e.gen===`done`&&Y(`run_done`,{level:e.level}),t.gen!==`failed`&&e.gen===`failed`&&Y(`run_failed`,{level:e.level,reason:`unknown`}),e.allCut.length>t.allCut.length&&Y(`all_cut`,{chunk_index:e.allCut[e.allCut.length-1]}),e.lastNotice!==t.lastNotice&&e.lastNotice&&(e.lastNotice===`notice.stopped`?Y(`run_stopped`,{level:e.level}):e.lastNotice===`notice.input_limit`?Y(`input_limit`,{}):e.lastNotice===`error.storage_full`?Y(`quota_error`,{store:`stats`}):(e.lastNotice===`notice.no_webgpu`||e.lastNotice===`notice.probe_failed`)&&Y(`probe_result`,{probe_result:`fail`})))}),We(e=>void $.setLevel(e)),document.addEventListener(`keydown`,e=>{e.key===`Escape`&&$.stop()}),Ln();var Bn=document.getElementById(`app`);Bn&&xe(U(In,{}),Bn);
|
|
|
|
|
|
|
|
|
|
|
|
assets/index-CzDNqk0f.css
DELETED
|
@@ -1 +0,0 @@
|
|
| 1 |
-
@font-face{font-family:Atkinson Hyperlegible;src:url(/fonts/AtkinsonHyperlegible-Regular.woff2)format("woff2");font-weight:400;font-style:normal;font-display:swap}@font-face{font-family:Atkinson Hyperlegible;src:url(/fonts/AtkinsonHyperlegible-Bold.woff2)format("woff2");font-weight:700;font-style:normal;font-display:swap}@font-face{font-family:Atkinson Hyperlegible;src:url(/fonts/AtkinsonHyperlegible-Italic.woff2)format("woff2");font-weight:400;font-style:italic;font-display:swap}@font-face{font-family:Atkinson Hyperlegible;src:url(/fonts/AtkinsonHyperlegible-BoldItalic.woff2)format("woff2");font-weight:700;font-style:italic;font-display:swap}:root{--gutter:16px;--measure:65ch;--border-radius:8px;--color-bg:#faf9f6;--color-fg:#1a1a1a;--color-muted:#5b5b5b;--color-border:#d8d5cd;--color-accent:#7a3b2e;--color-accent-fg:#fff;--color-panel-bg:#fff;--color-input-bg:#fff;--color-focus-ring:#7a3b2e}@media (prefers-color-scheme:dark){:root:not([data-theme=light]){--color-bg:#17171a;--color-fg:#eceae6;--color-muted:#a8a49c;--color-border:#3a3a3f;--color-accent:#e0a893;--color-accent-fg:#17171a;--color-panel-bg:#201f23;--color-input-bg:#201f23;--color-focus-ring:#e0a893}}:root[data-theme=dark]{--color-bg:#17171a;--color-fg:#eceae6;--color-muted:#a8a49c;--color-border:#3a3a3f;--color-accent:#e0a893;--color-accent-fg:#17171a;--color-panel-bg:#201f23;--color-input-bg:#201f23;--color-focus-ring:#e0a893}*{box-sizing:border-box}html,body{max-width:100%;margin:0;padding:0;overflow-x:hidden}body{background:var(--color-bg);color:var(--color-fg);font-family:Atkinson Hyperlegible,system-ui,sans-serif;line-height:1.5}.visually-hidden{clip:rect(0, 0, 0, 0);white-space:nowrap;border:0;width:1px;height:1px;margin:-1px;padding:0;position:absolute;overflow:hidden}.app-shell{min-height:100vh;padding:var(--gutter);padding-bottom:calc(var(--gutter) * 6);flex-direction:column;display:flex}.app-header{justify-content:space-between;align-items:center;gap:var(--gutter);padding-bottom:var(--gutter);border-bottom:1px solid var(--color-border);margin-bottom:var(--gutter);flex-wrap:wrap;display:flex}.app-title{flex:auto;min-width:0;margin:0;font-size:1.25rem}.dial{border:1px solid var(--color-border);border-radius:var(--border-radius);flex-wrap:wrap;gap:4px;margin:0;padding:4px;display:flex}.dial-option{border-radius:calc(var(--border-radius) - 2px);cursor:pointer;align-items:center;gap:6px;padding:6px 10px;font-size:.9rem;display:inline-flex}.dial-option:has(input:checked){background:var(--color-accent);color:var(--color-accent-fg)}.dial-option input{accent-color:var(--color-accent)}.dial-option input:focus-visible{outline:2px solid var(--color-focus-ring);outline-offset:2px}.theme-toggle{border:1px solid var(--color-border);background:var(--color-panel-bg);color:var(--color-fg);border-radius:var(--border-radius);cursor:pointer;font:inherit;padding:6px 12px}.theme-toggle:focus-visible{outline:2px solid var(--color-focus-ring);outline-offset:2px}.app-main{gap:calc(var(--gutter) * 1.5);max-width:var(--measure);flex-direction:column;flex:auto;width:100%;margin:0 auto;display:flex}.article p{margin:0 0 1em}.paste-box{flex-direction:column;gap:6px;display:flex}.paste-label{font-weight:700}.paste-textarea{border:1px solid var(--color-border);border-radius:var(--border-radius);background:var(--color-input-bg);width:100%;max-width:100%;min-height:8em;color:var(--color-fg);font:inherit;resize:vertical;padding:10px}.paste-textarea:focus-visible{outline:2px solid var(--color-focus-ring);outline-offset:2px}.paste-row{justify-content:space-between;align-items:center;gap:var(--gutter);flex-wrap:wrap;display:flex}.word-count{color:var(--color-muted);margin:0;font-size:.85rem}.read-button{border:1px solid var(--color-accent);background:var(--color-accent);color:var(--color-accent-fg);border-radius:var(--border-radius);cursor:pointer;font:inherit;white-space:nowrap;padding:6px 14px}.read-button:disabled{opacity:.5;cursor:not-allowed}.read-button:focus-visible{outline:2px solid var(--color-focus-ring);outline-offset:2px}.read-chip{z-index:10;border:1px solid var(--color-accent);background:var(--color-accent);color:var(--color-accent-fg);font:inherit;cursor:pointer;border-radius:999px;padding:6px 14px;font-size:.85rem;position:fixed;box-shadow:0 2px 8px #0003}.read-chip:focus-visible{outline:2px solid var(--color-focus-ring);outline-offset:2px}.panel{right:var(--gutter);bottom:var(--gutter);width:min(320px, calc(100% - var(--gutter) * 2));background:var(--color-panel-bg);border:1px solid var(--color-border);border-radius:var(--border-radius);padding:var(--gutter);position:fixed}.panel-empty{color:var(--color-muted);margin:0}@media (width<=640px){.panel{left:var(--gutter);right:var(--gutter);width:auto}}.bullets{margin:0;padding-left:1.2em}.bullets li{margin:.35em 0}.bullets li[aria-current=true]{background:var(--color-accent-soft,#785ac826);border-radius:4px}.now-label,.next-label{opacity:.7;font-size:.8em}.now-text{margin:.2em 0 .6em;font-size:1.35em;line-height:1.4}.next-text{opacity:.6}.read-part{font:inherit;padding:.4em .8em}.panel-notice{opacity:.85;font-size:.95em}.report-preview{white-space:pre-wrap;overflow-wrap:anywhere;max-width:100%}.loading{margin-bottom:var(--gutter);max-width:var(--measure);flex-direction:column;gap:6px;width:100%;margin-left:auto;margin-right:auto;display:flex}.loading-line{color:var(--color-muted);margin:0;font-size:.9rem}.loading-bar{width:100%;height:6px;accent-color:var(--color-accent)}.loading-cache{opacity:.7;margin:0;font-size:.8rem}.loading-notice{opacity:.85;margin:0;font-size:.9rem}.loading-summarizer{flex-direction:column;gap:4px;display:flex}.loading-summarizer-button{border:1px solid var(--color-accent);background:var(--color-panel-bg);color:var(--color-fg);border-radius:var(--border-radius);cursor:pointer;font:inherit;align-self:flex-start;padding:6px 12px}.loading-summarizer-button:focus-visible{outline:2px solid var(--color-focus-ring);outline-offset:2px}.demo{border:1px solid var(--color-border);border-radius:var(--border-radius);padding:var(--gutter);flex-direction:column;gap:6px;display:flex}.demo-recording-label,.demo-excerpt-note,.demo-switch-level{color:var(--color-muted);margin:0;font-size:.85rem}.demo-try-it-now{border:1px solid var(--color-accent);background:var(--color-accent);color:var(--color-accent-fg);border-radius:var(--border-radius);cursor:pointer;font:inherit;align-self:flex-start;padding:6px 14px}.demo-try-it-now:disabled{opacity:.5;cursor:not-allowed}.demo-try-it-now:focus-visible{outline:2px solid var(--color-focus-ring);outline-offset:2px}.demo-items{margin:0;padding-left:1.2em}.demo-items li{margin:.35em 0}.demo-items li[aria-current=true]{background:var(--color-accent-soft,#785ac826);border-radius:4px}
|
|
|
|
|
|
assets/index-DIGGJAq1.js
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
import{l as e}from"./loader-D0INP31U.js";import{i as t,r as n,t as r}from"./pins-DVBrHC3g.js";import{a as i,i as a,n as o,r as s,t as c}from"./llm-DH311QE0.js";import{a as l,i as u,n as d,r as f,t as p}from"./tts-DDfrpA1Y.js";var m,h,g,_,v,y,b,x,S,C,w,T,E,D,ee={},te=[],ne=/acit|ex(?:s|g|n|p|$)|rph|grid|ows|mnc|ntw|ine[ch]|zoo|^ord|itera/i,O=Array.isArray;function k(e,t){for(var n in t)e[n]=t[n];return e}function re(e){e&&e.parentNode&&e.parentNode.removeChild(e)}function ie(e,t,n){var r,i,a,o={};for(a in t)a==`key`?r=t[a]:a==`ref`?i=t[a]:o[a]=t[a];if(arguments.length>2&&(o.children=arguments.length>3?m.call(arguments,2):n),typeof e==`function`&&e.defaultProps!=null)for(a in e.defaultProps)o[a]===void 0&&(o[a]=e.defaultProps[a]);return A(e,o,r,i,null)}function A(e,t,n,r,i){var a={type:e,props:t,key:n,ref:r,__k:null,__:null,__b:0,__e:null,__c:null,constructor:void 0,__v:i??++g,__i:-1,__u:0};return i==null&&h.vnode!=null&&h.vnode(a),a}function j(e){return e.children}function ae(e,t){this.props=e,this.context=t}function M(e,t){if(t==null)return e.__?M(e.__,e.__i+1):null;for(var n;t<e.__k.length;t++)if((n=e.__k[t])!=null&&n.__e!=null)return n.__e;return typeof e.type==`function`?M(e):null}function oe(e){if(e.__P&&e.__d){var t=e.__v,n=t.__e,r=[],i=[],a=k({},t);a.__v=t.__v+1,h.vnode&&h.vnode(a),_e(e.__P,a,t,e.__n,e.__P.namespaceURI,32&t.__u?[n]:null,r,n??M(t),!!(32&t.__u),i),a.__v=t.__v,a.__.__k[a.__i]=a,ye(r,a,i),t.__e=t.__=null,a.__e!=n&&se(a)}}function se(e){if((e=e.__)!=null&&e.__c!=null)return e.__e=e.__c.base=null,e.__k.some(function(t){if(t!=null&&t.__e!=null)return e.__e=e.__c.base=t.__e}),se(e)}function ce(e){(!e.__d&&(e.__d=!0)&&_.push(e)&&!le.__r++||v!=h.debounceRendering)&&((v=h.debounceRendering)||y)(le)}function le(){try{for(var e,t=1;_.length;)_.length>t&&_.sort(b),e=_.shift(),t=_.length,oe(e)}finally{_.length=le.__r=0}}function ue(e,t,n,r,i,a,o,s,c,l,u){var d,f,p,m,h,g,_=r&&r.__k||te,v=t.length;for(c=de(n,t,_,c,v),d=0;d<v;d++)(p=n.__k[d])!=null&&(f=p.__i!=-1&&_[p.__i]||ee,p.__i=d,g=_e(e,p,f,i,a,o,s,c,l,u),m=p.__e,p.ref&&f.ref!=p.ref&&(f.ref&&Se(f.ref,null,p),u.push(p.ref,p.__c||m,p)),h==null&&m!=null&&(h=m),4&p.__u?(c=fe(p,c,e),f.__e&&(f.__e=null)):typeof p.type==`function`&&g!==void 0?c=g:m&&(c=m.nextSibling),p.__u&=-7);return n.__e=h,c}function de(e,t,n,r,i){var a,o,s,c,l,u=n.length,d=u,f=0;for(e.__k=Array(i),a=0;a<i;a++)(o=t[a])!=null&&typeof o!=`boolean`&&typeof o!=`function`?(typeof o==`string`||typeof o==`number`||typeof o==`bigint`||o.constructor==String?o=e.__k[a]=A(null,o,null,null,null):O(o)?o=e.__k[a]=A(j,{children:o},null,null,null):o.constructor===void 0&&o.__b>0?o=e.__k[a]=A(o.type,o.props,o.key,o.ref?o.ref:null,o.__v):e.__k[a]=o,c=a+f,o.__=e,o.__b=e.__b+1,s=null,(l=o.__i=pe(o,n,c,d))!=-1&&(d--,(s=n[l])&&(s.__u|=2)),s==null||s.__v==null?(l==-1&&(i>u?f--:i<u&&f++),typeof o.type!=`function`&&(o.__u|=4)):l!=c&&(l==c-1?f--:l==c+1?f++:(l>c?f--:f++,o.__u|=4))):e.__k[a]=null;if(d)for(a=0;a<u;a++)(s=n[a])!=null&&!(2&s.__u)&&(s.__e==r&&(r=M(s)),Ce(s,s));return r}function fe(e,t,n){var r,i;if(typeof e.type==`function`){for(r=e.__k,i=0;r&&i<r.length;i++)r[i]&&(r[i].__=e,t=fe(r[i],t,n));return t}e.__e!=t&&(t&&e.type&&!t.parentNode&&(t=M(e)),t=n.insertBefore(e.__e,t||null));do t&&=t.nextSibling;while(t!=null&&t.nodeType==8);return t}function pe(e,t,n,r){var i,a,o,s=e.key,c=e.type,l=t[n],u=l!=null&&!(2&l.__u);if(l===null&&s==null||u&&s==l.key&&c==l.type)return n;if(r>+!!u){for(i=n-1,a=n+1;i>=0||a<t.length;)if((l=t[o=i>=0?i--:a++])!=null&&!(2&l.__u)&&s==l.key&&c==l.type)return o}return-1}function me(e,t,n){t[0]==`-`?e.setProperty(t,n??``):e[t]=n==null?``:typeof n!=`number`||ne.test(t)?n:n+`px`}function he(e,t,n,r,i){var a,o;n:if(t==`style`){if(typeof n==`string`)e.style.cssText=n;else{if(typeof r==`string`&&(e.style.cssText=r=``),r)for(t in r)n&&t in n||me(e.style,t,``);if(n)for(t in n)r&&n[t]==r[t]||me(e.style,t,n[t])}}else if(t[0]==`o`&&t[1]==`n`)a=t!=(t=t.replace(w,`$1`)),o=t.toLowerCase(),t=o in e||t==`onFocusOut`||t==`onFocusIn`?o.slice(2):t.slice(2),e.l||={},e.l[t+a]=n,n?r?n[C]=r[C]:(n[C]=T,e.addEventListener(t,a?D:E,a)):e.removeEventListener(t,a?D:E,a);else{if(i==`http://www.w3.org/2000/svg`)t=t.replace(/xlink(H|:h)/,`h`).replace(/sName$/,`s`);else if(t!=`width`&&t!=`height`&&t!=`href`&&t!=`list`&&t!=`form`&&t!=`tabIndex`&&t!=`download`&&t!=`rowSpan`&&t!=`colSpan`&&t!=`role`&&t!=`popover`&&t in e)try{e[t]=n??``;break n}catch{}typeof n==`function`||(n==null||!1===n&&t[4]!=`-`?e.removeAttribute(t):e.setAttribute(t,t==`popover`&&n==1?``:n))}}function ge(e){return function(t){if(this.l){var n=this.l[t.type+e];if(t[S]==null)t[S]=T++;else if(t[S]<n[C])return;return n(h.event?h.event(t):t)}}}function _e(e,t,n,r,i,a,o,s,c,l){var u,d,f,p,m,g,_,v,y,b,x,S,C,w,T,E,D=t.type;if(t.constructor!==void 0)return null;128&n.__u&&(c=!!(32&n.__u),a=[s=t.__e=n.__e]),(u=h.__b)&&u(t);n:if(typeof D==`function`){d=o.length;try{if(y=t.props,b=D.prototype&&D.prototype.render,x=(u=D.contextType)&&r[u.__c],S=u?x?x.props.value:u.__:r,n.__c?v=(f=t.__c=n.__c).__=f.__E:(b?t.__c=f=new D(y,S):(t.__c=f=new ae(y,S),f.constructor=D,f.render=we),x&&x.sub(f),f.state||(f.state={}),f.__n=r,p=f.__d=!0,f.__h=[],f._sb=[]),b&&f.__s==null&&(f.__s=f.state),b&&D.getDerivedStateFromProps!=null&&(f.__s==f.state&&(f.__s=k({},f.__s)),k(f.__s,D.getDerivedStateFromProps(y,f.__s))),m=f.props,g=f.state,f.__v=t,p)b&&D.getDerivedStateFromProps==null&&f.componentWillMount!=null&&f.componentWillMount(),b&&f.componentDidMount!=null&&f.__h.push(f.componentDidMount);else{if(b&&D.getDerivedStateFromProps==null&&y!==m&&f.componentWillReceiveProps!=null&&f.componentWillReceiveProps(y,S),t.__v==n.__v||!f.__e&&f.shouldComponentUpdate!=null&&!1===f.shouldComponentUpdate(y,f.__s,S)){t.__v!=n.__v&&(f.props=y,f.state=f.__s,f.__d=!1),t.__e=n.__e,t.__k=n.__k,t.__k.some(function(e){e&&(e.__=t)}),te.push.apply(f.__h,f._sb),f._sb=[],f.__h.length&&o.push(f),s=M(n);break n}f.componentWillUpdate!=null&&f.componentWillUpdate(y,f.__s,S),b&&f.componentDidUpdate!=null&&f.__h.push(function(){f.componentDidUpdate(m,g,_)})}if(f.context=S,f.props=y,f.__P=e,f.__e=!1,C=h.__r,w=0,b)f.state=f.__s,f.__d=!1,C&&C(t),u=f.render(f.props,f.state,f.context),te.push.apply(f.__h,f._sb),f._sb=[];else do f.__d=!1,C&&C(t),u=f.render(f.props,f.state,f.context),f.state=f.__s;while(f.__d&&++w<25);f.state=f.__s,f.getChildContext!=null&&(r=k(k({},r),f.getChildContext())),b&&!p&&f.getSnapshotBeforeUpdate!=null&&(_=f.getSnapshotBeforeUpdate(m,g)),T=u!=null&&u.type===j&&u.key==null?be(u.props.children):u,s=ue(e,O(T)?T:[T],t,n,r,i,a,o,s,c,l),f.base=t.__e,t.__u&=-161,f.__h.length&&o.push(f),v&&(f.__E=f.__=null)}catch(e){if(o.length=d,t.__v=null,c||a!=null){if(e.then){for(t.__u|=c?160:128;s&&s.nodeType==8&&s.nextSibling;)s=s.nextSibling;a!=null&&(a[a.indexOf(s)]=null),t.__e=s}else if(a!=null)for(E=a.length;E--;)re(a[E])}else t.__e=n.__e;t.__k??=n.__k||[],e.then||ve(t),h.__e(e,t,n)}}else a==null&&t.__v==n.__v?(t.__k=n.__k,t.__e=n.__e):s=t.__e=xe(n.__e,t,n,r,i,a,o,c,l);return(u=h.diffed)&&u(t),128&t.__u?void 0:s}function ve(e){e&&(e.__c&&(e.__c.__e=!0),e.__k&&e.__k.some(ve))}function ye(e,t,n){for(var r=0;r<n.length;r++)Se(n[r],n[++r],n[++r]);h.__c&&h.__c(t,e),e.some(function(t){try{e=t.__h,t.__h=[],e.some(function(e){e.call(t)})}catch(e){h.__e(e,t.__v)}})}function be(e){return typeof e!=`object`||!e||e.__b>0?e:O(e)?e.map(be):e.constructor===void 0?k({},e):null}function xe(e,t,n,r,i,a,o,s,c){var l,u,d,f,p,g,_,v=n.props||ee,y=t.props,b=t.type;if(b==`svg`?i=`http://www.w3.org/2000/svg`:b==`math`?i=`http://www.w3.org/1998/Math/MathML`:i||=`http://www.w3.org/1999/xhtml`,a!=null){for(l=0;l<a.length;l++)if((p=a[l])&&`setAttribute`in p==!!b&&(b?p.localName==b:p.nodeType==3)){e=p,a[l]=null;break}}if(e==null){if(b==null)return document.createTextNode(y);e=document.createElementNS(i,b,y.is&&y),s&&=(h.__m&&h.__m(t,a),!1),a=null}if(b==null)v===y||s&&e.data==y||(e.data=y);else{if(a=b==`textarea`&&y.defaultValue!=null?null:a&&m.call(e.childNodes),!s&&a!=null)for(v={},l=0;l<e.attributes.length;l++)v[(p=e.attributes[l]).name]=p.value;for(l in v)p=v[l],l==`dangerouslySetInnerHTML`?d=p:l==`children`||l in y||l==`value`&&`defaultValue`in y||l==`checked`&&`defaultChecked`in y||he(e,l,null,p,i);for(l in y)p=y[l],l==`children`?f=p:l==`dangerouslySetInnerHTML`?u=p:l==`value`?g=p:l==`checked`?_=p:s&&typeof p!=`function`||v[l]===p||he(e,l,p,v[l],i);if(u)s||d&&(u.__html==d.__html||u.__html==e.innerHTML)||(e.innerHTML=u.__html),t.__k=[];else if(d&&(e.innerHTML=``),ue(t.type==`template`?e.content:e,O(f)?f:[f],t,n,r,b==`foreignObject`?`http://www.w3.org/1999/xhtml`:i,a,o,a?a[0]:n.__k&&M(n,0),s,c),a!=null)for(l=a.length;l--;)re(a[l]);s&&b!=`textarea`||(l=`value`,b==`progress`&&g==null?e.removeAttribute(`value`):g!=null&&(g!==e[l]||b==`progress`&&!g||b==`option`&&g!=v[l])&&he(e,l,g,v[l],i),l=`checked`,_!=null&&_!=e[l]&&he(e,l,_,v[l],i))}return e}function Se(e,t,n){try{if(typeof e==`function`){var r=typeof e.__u==`function`;r&&e.__u(),r&&t==null||(e.__u=e(t))}else e.current=t}catch(e){h.__e(e,n)}}function Ce(e,t,n){var r,i;if(h.unmount&&h.unmount(e),(r=e.ref)&&(r.current&&r.current!=e.__e||Se(r,null,t)),(r=e.__c)!=null){if(r.componentWillUnmount)try{r.componentWillUnmount()}catch(e){h.__e(e,t)}r.base=r.__P=r.__n=null}if(r=e.__k)for(i=0;i<r.length;i++)r[i]&&Ce(r[i],t,n||typeof e.type!=`function`);n||re(e.__e),e.__c=e.__=e.__e=void 0}function we(e,t,n){return this.constructor(e,n)}function Te(e,t,n){var r,i,a,o;t==document&&(t=document.documentElement),h.__&&h.__(e,t),i=(r=typeof n==`function`)?null:n&&n.__k||t.__k,a=[],o=[],_e(t,e=(!r&&n||t).__k=ie(j,null,[e]),i||ee,ee,t.namespaceURI,!r&&n?[n]:i?null:t.firstChild?m.call(t.childNodes):null,a,!r&&n?n:i?i.__e:t.firstChild,r,o),ye(a,e,o),e.props.children=null}m=te.slice,h={__e:function(e,t,n,r){for(var i,a,o;t=t.__;)if((i=t.__c)&&!i.__)try{if((a=i.constructor)&&a.getDerivedStateFromError!=null&&(i.setState(a.getDerivedStateFromError(e)),o=i.__d),i.componentDidCatch!=null&&(i.componentDidCatch(e,r||{}),o=i.__d),o)return i.__E=i}catch(t){e=t}throw e}},g=0,ae.prototype.setState=function(e,t){var n=this.__s!=null&&this.__s!=this.state?this.__s:this.__s=k({},this.state);typeof e==`function`&&(e=e(k({},n),this.props)),e&&k(n,e),e!=null&&this.__v&&(t&&this._sb.push(t),ce(this))},ae.prototype.forceUpdate=function(e){this.__v&&(this.__e=!0,e&&this.__h.push(e),ce(this))},ae.prototype.render=j,_=[],y=typeof Promise==`function`?Promise.prototype.then.bind(Promise.resolve()):setTimeout,b=function(e,t){return e.__v.__b-t.__v.__b},le.__r=0,x=Math.random().toString(8),S=`__d`+x,C=`__a`+x,w=/(PointerCapture)$|Capture$/i,T=0,E=ge(!1),D=ge(!0);var N,P,Ee,De,F=0,Oe=[],I=h,ke=I.__b,Ae=I.__r,je=I.diffed,Me=I.__c,Ne=I.unmount,Pe=I.__;function Fe(e,t){I.__h&&I.__h(P,e,F||t),F=0;var n=P.__H||(P.__H={__:[],__h:[]});return e>=n.__.length&&n.__.push({}),n.__[e]}function L(e){return F=1,Ie(Ue,e)}function Ie(e,t,n){var r=Fe(N++,2);if(r.t=e,!r.__c&&(r.__=[n?n(t):Ue(void 0,t),function(e){var t=r.__N?r.__N[0]:r.__[0],n=r.t(t,e);t!==n&&(r.__N=[n,r.__[1]],r.__c.setState({}))}],r.__c=P,!P.__f)){var i=function(e,t,n){if(!r.__c.__H)return!0;var i=!1,o=r.__c.props!==e;if(r.__c.__H.__.some(function(e){if(e.__N){i=!0;var t=e.__[0];e.__=e.__N,e.__N=void 0,t!==e.__[0]&&(o=!0)}}),a){var s=a.call(this,e,t,n);return i?s||o:s}return!i||o};P.__f=!0;var a=P.shouldComponentUpdate,o=P.componentWillUpdate;P.componentWillUpdate=function(e,t,n){if(this.__e){var r=a;a=void 0,i(e,t,n),a=r}o&&o.call(this,e,t,n)},P.shouldComponentUpdate=i}return r.__N||r.__}function R(e,t){var n=Fe(N++,3);!I.__s&&He(n.__H,t)&&(n.__=e,n.u=t,P.__H.__h.push(n))}function z(e){return F=5,Le(function(){return{current:e}},[])}function Le(e,t){var n=Fe(N++,7);return He(n.__H,t)&&(n.__=e(),n.__H=t,n.__h=e),n.__}function Re(){for(var e;e=Oe.shift();){var t=e.__H;if(e.__P&&t)try{t.__h.some(B),t.__h.some(Ve),t.__h=[]}catch(n){t.__h=[],I.__e(n,e.__v)}}}I.__b=function(e){P=null,ke&&ke(e)},I.__=function(e,t){e&&t.__k&&t.__k.__m&&(e.__m=t.__k.__m),Pe&&Pe(e,t)},I.__r=function(e){Ae&&Ae(e),N=0;var t=(P=e.__c).__H;t&&(Ee===P?(t.__h=[],P.__h=[],t.__.some(function(e){e.__N&&(e.__=e.__N),e.u=e.__N=void 0})):(t.__h.some(B),t.__h.some(Ve),t.__h=[],N=0)),Ee=P},I.diffed=function(e){je&&je(e);var t=e.__c;t&&t.__H&&(t.__H.__h.length&&(Oe.push(t)!==1&&De===I.requestAnimationFrame||((De=I.requestAnimationFrame)||Be)(Re)),t.__H.__.some(function(e){e.u&&=(e.__H=e.u,void 0)})),Ee=P=null},I.__c=function(e,t){t.some(function(e){try{e.__h.some(B),e.__h=e.__h.filter(function(e){return!e.__||Ve(e)})}catch(n){t.some(function(e){e.__h&&=[]}),t=[],I.__e(n,e.__v)}}),Me&&Me(e,t)},I.unmount=function(e){Ne&&Ne(e);var t,n=e.__c;n&&n.__H&&(n.__H.__.some(function(e){try{B(e)}catch(e){t=e}}),n.__H=void 0,t&&I.__e(t,n.__v))};var ze=typeof requestAnimationFrame==`function`;function Be(e){var t,n=function(){clearTimeout(r),ze&&cancelAnimationFrame(t),setTimeout(e)},r=setTimeout(n,35);ze&&(t=requestAnimationFrame(n))}function B(e){var t=P,n=e.__c;typeof n==`function`&&(e.__c=void 0,n()),P=t}function Ve(e){var t=P;e.__c=e.__(),P=t}function He(e,t){return!e||e.length!==t.length||t.some(function(t,n){return t!==e[n]})}function Ue(e,t){return typeof t==`function`?t(e):t}var V=i.default??`short`,We=new Set;function Ge(){return V}function Ke(e){if(e!==V){V=e;for(let e of We)e(V)}}function qe(e){return We.add(e),()=>We.delete(e)}var Je=96,Ye=36,H=8;function Xe(){let e=typeof window<`u`?window.getSelection():null;return!e||e.isCollapsed||e.rangeCount===0?``:e.toString().trim()}function Ze(){return Xe().length>0}function Qe(e){return e.trim().length>=20}function $e(){let e=typeof window<`u`?window.getSelection():null;if(!e||e.rangeCount===0)return null;let t=e.getRangeAt(0).getBoundingClientRect();return t.width===0&&t.height===0?null:t}function et(e,t,n){let r=e.bottom+H;return r+Ye>n&&(r=e.top-Ye-H),r=Math.max(H,Math.min(r,n-Ye-H)),{left:Math.max(H,Math.min(e.left,t-Je-H)),top:r}}function tt(e){return e.altKey&&e.code===`KeyR`}function nt(e){let t=e.trim();t&&window.__fruitbat.run(t,Ge())}var rt=0;Array.isArray;function U(e,t,n,r,i,a){t||={};var o,s,c=t;if(`ref`in c)for(s in c={},t)s==`ref`?o=t[s]:c[s]=t[s];var l={type:e,props:c,key:n,ref:o,__k:null,__:null,__b:0,__e:null,__c:null,constructor:void 0,__v:--rt,__i:-1,__u:0,__source:i,__self:a};if(typeof e==`function`&&(o=e.defaultProps))for(s in o)c[s]===void 0&&(c[s]=o[s]);return h.vnode&&h.vnode(l),l}function it(e){let t=e.trim();return t===``?0:t.split(/\s+/).length}function at(){let[e,t]=L(``),n=it(e),r=e.trim()===``;function i(){r||nt(e)}return U(`div`,{class:`paste-box`,children:[U(`label`,{class:`paste-label`,for:`paste-input`,children:l(`intake.paste_placeholder`)}),U(`textarea`,{id:`paste-input`,class:`paste-textarea`,placeholder:l(`intake.paste_placeholder`),value:e,onInput:e=>t(e.target.value),onKeyDown:e=>{(e.metaKey||e.ctrlKey)&&e.key===`Enter`&&(e.preventDefault(),i())}}),U(`div`,{class:`paste-row`,children:[U(`p`,{class:`word-count`,"aria-live":`polite`,"data-word-count":n,children:l(`intake.word_count`).replace(`{n}`,String(n))}),U(`button`,{type:`button`,class:`read-button`,onClick:i,disabled:r,children:l(`intake.read_button`)})]})]})}function ot(){let[e,t]=L(null);return R(()=>{function e(){let e=Xe();if(!Qe(e)){t(null);return}let n=$e();if(!n){t(null);return}t({text:e,position:et(n,window.innerWidth,window.innerHeight)})}function n(t){t.key!==`Escape`&&e()}function r(e){if(e.key===`Escape`){t(null);return}tt(e)&&Ze()&&(e.preventDefault(),nt(Xe()),t(null))}return document.addEventListener(`mouseup`,e),document.addEventListener(`keyup`,n),document.addEventListener(`keydown`,r),window.addEventListener(`scroll`,e,{passive:!0,capture:!0}),window.addEventListener(`resize`,e),()=>{document.removeEventListener(`mouseup`,e),document.removeEventListener(`keyup`,n),document.removeEventListener(`keydown`,r),window.removeEventListener(`scroll`,e,{capture:!0}),window.removeEventListener(`resize`,e)}},[]),e?U(`button`,{type:`button`,class:`read-chip`,style:{left:`${e.position.left}px`,top:`${e.position.top}px`},"aria-label":l(`panel.read_chip`),onMouseDown:e=>e.preventDefault(),onClick:()=>{nt(e.text),t(null)},children:l(`panel.read_chip`)}):null}function st(e,t){for(let n=0;n<e.length;n++){let r=e[n],i=t>=r.audioStart,a=t<r.audioEnd;if(i&&a)return n}let n=e[e.length-1];return n&&t>=n.audioEnd?e.length-1:-1}function ct(){let[t,n]=L(Ge),[r,i]=L({});return R(()=>qe(n),[]),R(()=>{if(r[t])return;let n=!1;return e(`/demo/${t}.json`).then(e=>e.json()).then(e=>{n||i(n=>({...n,[t]:e}))}).catch(()=>{}),()=>{n=!0}},[t,r]),{track:r[t]??null,level:t}}function lt(){let{track:e,level:t}=ct(),[n,r]=L(!1),[i,a]=L(-1),o=z(null);return R(()=>{let t=o.current;if(!t||!e)return;let i=n;t.load(),a(-1),i&&t.play().catch(()=>r(!1))},[e?.level]),R(()=>{let e=()=>{let e=o.current;e&&!e.paused&&e.pause(),r(!1)},t=t=>{t.key===`Escape`&&e()};return window.addEventListener(`fruitbat:stop`,e),window.addEventListener(`fruitbat:run`,e),window.addEventListener(`fruitbat:live`,e),document.addEventListener(`keydown`,t),()=>{window.removeEventListener(`fruitbat:stop`,e),window.removeEventListener(`fruitbat:run`,e),window.removeEventListener(`fruitbat:live`,e),document.removeEventListener(`keydown`,t)}},[]),U(`section`,{class:`demo`,"data-testid":`demo`,"data-level":t,children:[U(`p`,{class:`demo-recording-label`,children:l(`demo.recording_label`)}),U(`p`,{class:`demo-excerpt-note`,children:l(`demo.excerpt_note`)}),U(`button`,{type:`button`,class:`demo-try-it-now`,"data-testid":`demo-try`,onClick:()=>{let e=o.current;e&&(window.dispatchEvent(new CustomEvent(`fruitbat:demo`)),e.play().catch(()=>r(!1)))},disabled:!e,children:l(`demo.try_it_now`)}),U(`p`,{class:`demo-switch-level`,children:l(`demo.switch_level`)}),e&&U(`audio`,{ref:o,"data-testid":`demo-audio`,preload:`auto`,src:`/demo/${e.level}.wav`,onPlay:()=>{r(!0),window.dispatchEvent(new CustomEvent(`fruitbat:demo-playing`,{detail:!0}))},onPause:()=>{r(!1),window.dispatchEvent(new CustomEvent(`fruitbat:demo-playing`,{detail:!1}))},onEnded:()=>{r(!1),window.dispatchEvent(new CustomEvent(`fruitbat:demo-playing`,{detail:!1}))},onTimeUpdate:()=>{let t=o.current;t&&e&&a(st(e.items,t.currentTime))}}),e&&U(`ul`,{class:`demo-items`,"data-testid":`demo-bullets`,"aria-label":l(`a11y.bullet_list`),children:e.items.map((e,t)=>U(`li`,{"aria-current":t===i?`true`:void 0,children:e.text},t))})]})}async function ut(e){if(typeof caches>`u`)return!1;try{return!!await caches.match(e)}catch{return!1}}function dt(e){let t=[...e.files].sort((e,t)=>t.bytes-e.bytes)[0];return t?ut(r(e,t.path)):Promise.resolve(!1)}var ft={idle:{start:`loading`,stop:`idle`},loading:{loaded:`running`,fail:`failed`,stop:`idle`},running:{finish:`done`,fail:`failed`,stop:`idle`},done:{start:`loading`,stop:`idle`},failed:{start:`loading`,stop:`idle`}},pt={idle:{audio:`playing`,stop:`stopped`,reset:`idle`},playing:{audio:`playing`,pause:`paused`,stop:`stopped`,drain:`idle`,reset:`idle`},paused:{resume:`playing`,stop:`stopped`,drain:`idle`,reset:`idle`},stopped:{audio:`playing`,stop:`stopped`,reset:`idle`}};function W(e,t){return ft[e][t]??e}function G(e,t){return pt[e][t]??e}function mt(e,t){return e===`loading`||e===`running`||t===`playing`||t===`paused`}var ht=i.levels.map(e=>e.id),gt=i.default??`short`,_t=`fruitbat.speakMessages`,vt=[`notice.dial_shorter`,`notice.dial_longer`,`notice.stopped`,`notice.all_cut`,`notice.oneline_failed`,`notice.input_limit`,`notice.done`];function yt(e){try{return localStorage.getItem(e)}catch{return null}}function bt(e,t){try{localStorage.setItem(e,t)}catch{}}var xt=class{voice;llm;gen=`idle`;play=`idle`;level=gt;speakMessages;bullets=[];allCut=[];notices=[];lastNotice=null;current=null;error=null;progress=null;voiceProgress=null;runId=0;text=``;chunks=null;voiceReady=!1;listeners=new Set;runs=0;last=null;ttfa=null;runT0=0;stopMs=null;noticeLatency=null;spoken=[];genStats=null;voiceRun=null;constructor(e=u(),t=new c(s())){this.voice=e,this.llm=t,this.speakMessages=yt(_t)!==`off`,t.onNotice=e=>this.onLlmNotice(e);let n=new Map,r=new Map,i=e=>{let t=0,n=0;for(let r of e.values())t+=r.loaded,n+=r.total;return{loaded:t,total:n}};t.onProgress=e=>{e.file&&n.set(e.file,{loaded:e.loaded??0,total:e.total??0}),this.progress={file:e.file,...i(n)},this.emit()},e.onProgress((e,t,n)=>{r.set(e,{loaded:t,total:n}),this.voiceProgress={file:e,...i(r)},this.emit()}),typeof Worker<`u`&&!a()&&!o()&&this.warmVoice()}markVoiceReady(){if(!this.voiceReady){this.voiceReady=!0,this.emit();for(let e of this.pendingNotices.splice(0))this.notice(e)}}finishPrewarm(){this.voiceReady&&!this.voice.prewarmed&&this.voice.prewarm(vt).catch(()=>void 0)}async warmVoice(){try{await this.voice.load(),this.markVoiceReady(),await this.voice.prewarm(vt)}catch(e){this.error=e instanceof Error?`${e.name}: ${e.message}`:String(e),this.notice(`error.voice`)}this.emit()}subscribe(e){return this.listeners.add(e),e(this.snapshot()),()=>this.listeners.delete(e)}snapshot(){let e=this.voice.state();return{gen:this.gen,play:this.play,level:this.level,runId:this.runId,settledRunId:this.settledRunId,bullets:[...this.bullets],current:this.current,allCut:[...this.allCut],notices:[...this.notices],lastNotice:this.lastNotice,chunks:this.chunks?.length??0,voiceReady:this.voiceReady,prewarmed:this.voice.prewarmed,speakMessages:this.speakMessages,progress:this.progress,voiceProgress:this.voiceProgress,error:this.error,voice:{aheadSeconds:e.aheadSeconds,enqueued:e.enqueued,inFlight:e.inFlight,ended:e.ended,pending:e.pending,phase:e.phase}}}emit(){let e=this.snapshot();for(let t of this.listeners)t(e)}stats(){return{runs:this.runs,last:this.last,ttfa_ms:this.ttfa===null?null:Math.round(this.ttfa),stop_ms:this.stopMs===null?null:Math.round(this.stopMs*100)/100,notice_latency_ms:this.noticeLatency,notices_spoken:[...this.spoken],gen:this.genStats??((this.last?.level??this.level)===`readall`?null:this.llm.stats()),voice:this.voice.stats(),voice_run:this.voiceRun}}setSpeakMessages(e){this.speakMessages=e,bt(_t,e?`on`:`off`),this.emit()}onLlmNotice(e){e.key!==`notice.stopped`&&(e.key===`notice.all_cut`&&e.chunkIndex!==void 0&&!this.allCut.includes(e.chunkIndex)&&this.allCut.push(e.chunkIndex),this.notice(e.key))}pendingNotices=[];notice(e,t){if(this.notices.push(e),this.lastNotice=e,this.emit(),this.speakMessages){if(!this.voiceReady){this.pendingNotices.push(e);return}this.spoken.push(e),this.voice.speak(e,t).then(()=>{t!==void 0&&(this.noticeLatency=this.voice.lastNoticeLatencyMs,this.emit())}).catch(()=>{})}}runAbort=null;newRun(){let e=++this.runId;return this.pendingNotices=[],this.runAbort?.abort(),this.runAbort=new AbortController,this.llm.abort(),this.stopMs=this.voice.stop(),this.gen=W(this.gen,`stop`),this.play=G(this.play,`stop`),e}run(e,t){this.voice.ensureContext(),this.runs++,this.last={level:t,chars:e.length},this.text=e,this.level=t,this.chunks=null,this.notices=[],this.lastNotice=null,this.regenFrom=null;let n=this.newRun();return this.begin(n,t,{fromChunk:0,base:0,end:e.length})}speakMessage(e){this.speakMessages&&this.voiceReady&&!this.busy()&&(this.spoken.push(e),this.voice.speak(e).catch(()=>void 0))}silenceVoice(){this.voice.stop()}stop(e={}){let t=mt(this.gen,this.play)&&!e.quiet;return this.newRun(),this.current=null,this.progress=null,this.emit(),t&&this.notice(`notice.stopped`),this.stopMs??0}pause(){this.play===`playing`&&(this.voice.pause(),this.play=G(this.play,`pause`),this.emit())}resume(){this.play===`paused`&&(this.voice.resume(),this.play=G(this.play,`resume`),this.emit())}skip(){return this.voice.skip()}async setLevel(e){let t=performance.now(),n=this.level;if(e===n)return;if(this.level=e,!this.busy()||!this.text){this.emit();return}let r=ht.indexOf(e)>ht.indexOf(n),i=this.newRun();this.notice(r?`notice.dial_shorter`:`notice.dial_longer`,t),this.regenPending=i;let a=await this.currentChunkIndex();if(this.regenPending===i&&(this.regenPending=null),i!==this.runId)return;this.regenFrom=a;let o=this.chunks?.[a];await this.begin(i,e,{fromChunk:a,base:o?.start??0,end:this.text.length})}regenPending=null;busy(){if(this.regenPending===this.runId||mt(this.gen,this.play))return!0;if(this.play===`stopped`)return!1;let e=this.voice.state();return e.pending>0||e.inFlight>0||e.enqueued>e.ended}async readThisPart(e){let t=this.newRun(),n=await this.ensureChunks();if(t!==this.runId)return;let r=n?.[e];r&&await this.begin(t,`readall`,{fromChunk:e,base:r.start,end:r.end,keep:!0})}async ensureChunks(){if(this.chunks)return this.chunks;if(!this.text)return null;let e=this.text,t=null;try{t=await this.llm.chunk(e)}catch{t=null}return e===this.text?(this.chunks=t,this.chunks):null}async currentChunkIndex(){let e=this.current;if(e?.kind===`bullet`)return e.chunkIndex;let t=await this.ensureChunks();if(!t)return 0;if(e?.kind===`sentence`){let n=t.findIndex(t=>e.start>=t.start&&e.start<t.end);return n>=0?n:0}return this.heardChunk===null?this.regenFrom??0:this.heardChunk}heardChunk=null;regenFrom=null;async begin(e,t,n){this.last={level:t,chars:n.end-n.base},typeof window<`u`&&window.dispatchEvent(new CustomEvent(`fruitbat:live`)),this.play=G(this.play,`reset`),n.keep||(this.bullets=[],this.allCut=[],this.heardChunk=null),this.current=null,this.error=null,this.ttfa=null,this.runT0=performance.now(),this.voiceRun=null,this.genStats=null,this.gen=W(this.gen,`start`),this.emit();try{t===`readall`?await this.readAloud(e,n.base,n.end):await this.summarize(e,t,n.fromChunk)}catch(t){if(e!==this.runId)return;this.gen=W(this.gen,`fail`),this.error=t instanceof Error?`${t.name}: ${t.message}`:String(t),this.notice(`error.generation`)}e===this.runId&&(this.settledRunId=e),this.emit()}settledRunId=0;markAudio(){this.ttfa===null&&(this.ttfa=performance.now()-this.runT0),this.play=G(this.play,`audio`)}async readAloud(e,t,n){let r=this.text.slice(t,n),i=[];if(await this.voice.load(),e!==this.runId)return;this.markVoiceReady(),this.gen=W(this.gen,`loaded`),this.emit();let a=await this.voice.readAll(r,{onPlanned:e=>{i=e},onStart:n=>{e===this.runId&&(this.markAudio(),this.current={kind:`sentence`,start:t+n.start,end:t+n.end,text:r.slice(n.start,n.end),next:i[n.seq+1]?.text??null},this.emit())}});if(e===this.runId){if(this.voice.phase===`failed`){this.gen=W(this.gen,`fail`),this.error=this.voice.error,this.play=G(this.play,`stop`),this.current=null,this.notice(`error.voice`);return}this.gen=W(this.gen,`finish`),this.voiceRun=this.voice.metrics(a.seconds),a.finished&&(this.play=G(this.play,`drain`),this.current=null,this.notice(`notice.done`),this.finishPrewarm())}}async summarize(e,t,n){this.voice.load().then(()=>{this.markVoiceReady(),this.voice.prewarm(vt).catch(()=>void 0)},()=>void 0);let r=this.voice.beginStream({onStart:t=>{if(e!==this.runId)return;this.markAudio();let n=t.tag===void 0?void 0:this.bullets[t.tag];n&&(this.current={kind:`bullet`,chunkIndex:n.chunkIndex,index:t.tag},this.heardChunk=n.chunkIndex),this.emit()}}),i=this.runAbort?.signal,a=await this.llm.ensureLoaded({signal:i});if(!a&&e===this.runId&&this.llm.error===`aborted`&&(a=await this.llm.ensureLoaded({signal:i})),e!==this.runId)return;if(!a){this.gen=W(this.gen,`fail`),this.error=this.llm.error,this.llm.gpu?.ok===!1&&!this.notices.includes(`notice.no_webgpu`)&&this.notice(`notice.no_webgpu`),this.voice.endStream(r),this.play=G(this.play,`reset`);return}if(this.gen=W(this.gen,`loaded`),this.emit(),await this.ensureChunks(),e!==this.runId)return;let o=await this.llm.summarize(this.text,t,{signal:this.runAbort?.signal,fromChunk:n,onBullet:t=>{if(e!==this.runId)return;let n=this.bullets.push(t)-1;this.emit(),this.voice.pushText(r,t.text,t.start,t.end,n)}});if(e!==this.runId)return;this.genStats=o,this.llm.state===`failed`?(this.gen=W(this.gen,`fail`),this.error=this.llm.error):this.gen=W(this.gen,`finish`),this.emit();let{finished:s,metrics:c}=await this.voice.endStream(r);e===this.runId&&(this.voiceRun=c,s||(this.play=G(this.play,`stop`),this.current=null),!s&&this.gen===`done`&&(this.error=this.error??`voice_failed`,this.notice(`error.voice`)),s&&(this.play=G(this.play,`drain`),this.current=null,this.gen===`done`&&this.bullets.length>0&&this.notice(`notice.done`),this.finishPrewarm()))}},St=null;function K(){return St||=new xt,St}function q(e){return Math.round((e??0)/1e6)}function Ct(e,t){return Object.entries(t).reduce((e,[t,n])=>e.replaceAll(`{${t}}`,String(n)),e)}function wt({testId:e,loaded:t,total:n}){let r=n>0?Math.min(100,Math.round(t/n*100)):void 0;return r===void 0?U(`progress`,{"data-testid":e,class:`loading-bar`}):U(`progress`,{"data-testid":e,class:`loading-bar`,max:100,value:r,"aria-valuenow":r,"aria-valuemin":0,"aria-valuemax":100})}function Tt(e){let[t,n]=L(`unknown`);return R(()=>{if(!e)return;let t=!1;return dt(e).then(e=>{t||n(e?`cached`:`first_time`)}),()=>{t=!0}},[e?.id,e?.revision]),t}function Et({state:e}){return e===`unknown`?null:U(`p`,{class:`loading-cache`,children:l(e===`cached`?`loading.cached`:`loading.first_time`)})}function Dt(){let[e,t]=L(()=>K().snapshot());return R(()=>K().subscribe(t),[]),e}function Ot({s:e}){let t=K().llm,[n,r]=L(`idle`),i=Tt(t.tier()),a=t.isLoaded(),o=!a&&(n===`failed`||t.state===`failed`||t.state===`stopped`),s=a||!o&&(n!==`idle`||e.progress!==null||t.state===`loading`),c=a||n===`ready`,u=q(e.progress?.loaded),d=Math.max(q(e.progress?.total),s?t.sizeMb():0);return U(`div`,{class:`loading-summarizer`,"data-started":s,children:[U(`p`,{class:`loading-line`,children:l(`loading.summarizer_size`).replace(`{mb}`,String(t.sizeMb()))}),!s&&U(`button`,{type:`button`,class:`loading-summarizer-button`,"data-testid":`summarizer-load`,onClick:()=>{s||(r(`loading`),t.ensureLoaded().then(e=>r(e?`ready`:`failed`)))},children:l(`loading.summarizer_button`).replace(`{mb}`,String(t.sizeMb()))}),s&&U(j,{children:[U(wt,{testId:`summarizer-progress`,loaded:c?1:u,total:c?1:d}),U(`p`,{class:`loading-line`,children:Ct(l(`loading.progress`),{mb:u})}),U(Et,{state:i})]}),e.notices.filter((t,n)=>(t===`notice.no_webgpu`||t===`notice.probe_failed`||t===`notice.low_end_tier`)&&e.notices.indexOf(t)===n).map(e=>U(`p`,{class:`loading-notice`,role:`status`,"data-notice":e,children:l(e)},e))]})}function kt({s:e}){let t=n().web.voice,r=Tt(t);if(a())return U(`p`,{class:`loading-line`,"data-phase":`save_data`,children:l(`loading.save_data`)});if(o())return U(`p`,{class:`loading-line`,"data-phase":`mobile`,children:l(`loading.mobile`)});if(e.voiceReady)return U(`p`,{class:`loading-line`,"data-phase":`ready`,children:l(`loading.ready`)});if(e.voiceProgress){let n=q(e.voiceProgress.loaded),i=Math.max(q(e.voiceProgress.total),Math.round(t.files.reduce((e,t)=>e+t.bytes,0)/1e6));return U(`div`,{class:`loading-voice`,"data-phase":`voice`,children:[U(`p`,{class:`loading-line`,children:l(`loading.voice`)}),U(wt,{testId:`voice-progress`,loaded:n,total:i}),U(`p`,{class:`loading-line`,children:Ct(l(`loading.progress`),{mb:n})}),U(Et,{state:r})]})}return U(`p`,{class:`loading-line`,"data-phase":`probing`,children:l(`loading.probing`)})}function At(){let e=Dt();return U(`section`,{class:`loading`,"data-testid":`loading`,children:[U(kt,{s:e}),U(Ot,{s:e})]})}var jt=[`sm`,`md`,`lg`],Mt=[`compact`,`cozy`,`roomy`],Nt=`fruitbat.panelFontSize`,Pt=`fruitbat.panelSpacing`;function Ft(e){try{return localStorage.getItem(e)}catch{return null}}function It(e,t){try{localStorage.setItem(e,t)}catch{}}function Lt(){let[e,t]=L(()=>K().snapshot());return R(()=>K().subscribe(t),[]),e}function Rt(){return U(`svg`,{viewBox:`0 0 16 16`,width:`16`,height:`16`,"aria-hidden":`true`,class:`panel-transport-icon`,children:U(`rect`,{x:`3`,y:`3`,width:`10`,height:`10`,rx:`1.5`,fill:`currentColor`})})}function zt(){return U(`svg`,{viewBox:`0 0 16 16`,width:`16`,height:`16`,"aria-hidden":`true`,class:`panel-transport-icon`,children:[U(`rect`,{x:`3`,y:`2`,width:`3.5`,height:`12`,rx:`1`,fill:`currentColor`}),U(`rect`,{x:`9.5`,y:`2`,width:`3.5`,height:`12`,rx:`1`,fill:`currentColor`})]})}function Bt(){return U(`svg`,{viewBox:`0 0 16 16`,width:`16`,height:`16`,"aria-hidden":`true`,class:`panel-transport-icon`,children:U(`path`,{d:`M4 2.5 13 8 4 13.5Z`,fill:`currentColor`})})}function Vt(){return U(`svg`,{viewBox:`0 0 16 16`,width:`16`,height:`16`,"aria-hidden":`true`,class:`panel-transport-icon`,children:[U(`path`,{d:`M3 2.5 9 8 3 13.5Z`,fill:`currentColor`}),U(`rect`,{x:`11`,y:`2.5`,width:`2`,height:`11`,rx:`1`,fill:`currentColor`})]})}function Ht(){return U(`div`,{class:`panel-pip`,children:U(`svg`,{viewBox:`0 0 48 24`,width:`30`,height:`15`,role:`img`,"aria-label":l(`a11y.pip`),class:`panel-pip-svg`,children:[U(`path`,{d:`M26 11 34 4 30 10 44 6 34 13 40 18 28 15 26 17Z`,fill:`currentColor`,"aria-hidden":`true`}),U(`path`,{d:`M22 11 14 4 18 10 4 6 14 13 8 18 20 15 22 17Z`,fill:`currentColor`,"aria-hidden":`true`}),U(`ellipse`,{cx:`24`,cy:`13`,rx:`3`,ry:`4.5`,fill:`currentColor`,"aria-hidden":`true`}),U(`path`,{d:`M21 9 22.5 4 24 9Z`,fill:`currentColor`,"aria-hidden":`true`}),U(`path`,{d:`M27 9 25.5 4 24 9Z`,fill:`currentColor`,"aria-hidden":`true`})]})})}function Ut({step:e}){return U(`svg`,{viewBox:`0 0 20 14`,width:`18`,height:`13`,"aria-hidden":`true`,class:`panel-step-glyph`,children:[U(`rect`,{x:`1`,y:`9`,width:`4`,height:`5`,rx:`1`,fill:`currentColor`,opacity:e>=0?1:.35}),U(`rect`,{x:`8`,y:`6`,width:`4`,height:`8`,rx:`1`,fill:`currentColor`,opacity:e>=1?1:.35}),U(`rect`,{x:`15`,y:`3`,width:`4`,height:`11`,rx:`1`,fill:`currentColor`,opacity:e>=2?1:.35})]})}function Wt({step:e}){let t=[[2,7,12],[2,9,16],[2,11,20]][e];return U(`svg`,{viewBox:`0 0 20 24`,width:`16`,height:`19`,"aria-hidden":`true`,class:`panel-step-glyph`,children:t.map((e,t)=>U(`rect`,{x:`2`,y:e,width:`16`,height:`2.5`,rx:`1`,fill:`currentColor`},t))})}function Gt({s:e}){let t=e.current?.kind===`bullet`?e.current.index:-1;return R(()=>{t<0||document.querySelector(`.panel-bullets li[data-index="${t}"]`)?.scrollIntoView({block:`nearest`})},[t]),U(`ol`,{class:`panel-bullets`,"aria-live":`polite`,"aria-label":l(`a11y.bullet_list`),children:e.bullets.map((e,n)=>U(`li`,{"data-index":n,"data-chunk":e.chunkIndex,"aria-current":t===n?`true`:void 0,children:e.text},n))})}function Kt({cur:e}){let t=z(null);return R(()=>{t.current?.scrollIntoView({block:`nearest`})},[e.start]),U(`div`,{class:`now-reading`,ref:t,children:[U(`p`,{class:`now-label`,children:l(`panel.now_reading`)}),U(`p`,{class:`now-text`,"data-testid":`now-text`,children:e.text}),e.next&&U(`div`,{children:[U(`p`,{class:`next-label`,children:l(`panel.next_up`)}),U(`p`,{class:`next-text`,children:e.next})]})]})}function qt({allCut:e}){return U(j,{children:e.map(e=>U(`p`,{class:`read-part-row`,children:U(`button`,{type:`button`,class:`read-part`,"data-chunk":e,onClick:()=>void K().readThisPart(e),children:[U(Bt,{}),l(`panel.read_this_part`)]})},e))})}function Jt({s:e}){let[t,n]=L(!1);R(()=>{let e=e=>n(e.detail);return window.addEventListener(`fruitbat:demo-playing`,e),()=>window.removeEventListener(`fruitbat:demo-playing`,e)},[]);let r=t||e.gen!==`idle`||e.play===`playing`||e.play===`paused`,i=e.play===`playing`,a=e.play===`paused`,o=e.play===`playing`||e.play===`paused`;return U(`div`,{class:`panel-controls-row`,children:[U(`button`,{type:`button`,class:`panel-transport`,disabled:!r,onClick:()=>window.dispatchEvent(new CustomEvent(`fruitbat:stop`)),children:[U(Rt,{}),l(`panel.stop`)]}),a?U(`button`,{type:`button`,class:`panel-transport panel-transport--primary`,onClick:()=>K().resume(),children:[U(Bt,{}),l(`panel.resume`)]}):U(`button`,{type:`button`,class:`panel-transport`,disabled:!i,onClick:()=>K().pause(),children:[U(zt,{}),l(`panel.pause`)]}),U(`button`,{type:`button`,class:`panel-transport`,disabled:!o,onClick:()=>K().skip(),children:[U(Vt,{}),l(`panel.skip`)]})]})}function Yt({rate:e,onChange:t}){return U(`div`,{class:`panel-field`,children:[U(`span`,{class:`panel-field-label`,id:`panel-rate-label`,children:l(`panel.rate`)}),U(`div`,{class:`panel-rate-row`,children:[U(`span`,{class:`panel-rate-end`,children:l(`panel.rate_slower`)}),U(`input`,{type:`range`,class:`panel-rate-slider`,"data-testid":`rate-slider`,min:d,max:p,step:.05,value:e,"aria-labelledby":`panel-rate-label`,onInput:e=>t(Number(e.target.value))}),U(`span`,{class:`panel-rate-end`,children:l(`panel.rate_faster`)}),U(`span`,{class:`panel-rate-value`,"data-testid":`rate-value`,children:`${e.toFixed(2)}×`})]})]})}var Xt={af_heart:`panel.voice.af_heart`,af_bella:`panel.voice.af_bella`};function Zt({voice:e,onChange:t}){return U(`div`,{class:`panel-field`,children:[U(`label`,{class:`panel-field-label`,for:`panel-voice-select`,children:l(`panel.voice`)}),U(`select`,{id:`panel-voice-select`,class:`panel-select`,"data-testid":`voice-select`,value:e,onChange:e=>t(e.target.value),children:f.map(e=>U(`option`,{value:e,children:l(Xt[e])},e))})]})}function Qt({checked:e,onChange:t}){return U(`div`,{class:`panel-toggle-row`,children:[U(`input`,{type:`checkbox`,id:`panel-speak-toggle`,checked:e,onChange:e=>t(e.target.checked)}),U(`label`,{for:`panel-speak-toggle`,children:l(`panel.speak_messages`)})]})}function $t({value:e,onChange:t}){return U(`div`,{class:`panel-field`,children:[U(`span`,{class:`panel-field-label`,id:`panel-fontsize-label`,children:l(`panel.font_size`)}),U(`div`,{class:`panel-steps`,role:`group`,"aria-labelledby":`panel-fontsize-label`,children:[{id:`sm`,key:`panel.font_size_small`},{id:`md`,key:`panel.font_size_medium`},{id:`lg`,key:`panel.font_size_large`}].map((n,r)=>U(`button`,{type:`button`,class:`panel-step-btn`,"data-testid":`font-size-${n.id}`,"aria-pressed":e===n.id,"aria-label":l(n.key),onClick:()=>t(n.id),children:U(Ut,{step:r})},n.id))})]})}function en({value:e,onChange:t}){return U(`div`,{class:`panel-field`,children:[U(`span`,{class:`panel-field-label`,id:`panel-spacing-label`,children:l(`panel.spacing`)}),U(`div`,{class:`panel-steps`,role:`group`,"aria-labelledby":`panel-spacing-label`,children:[{id:`compact`,key:`panel.spacing_compact`},{id:`cozy`,key:`panel.spacing_cozy`},{id:`roomy`,key:`panel.spacing_roomy`}].map((n,r)=>U(`button`,{type:`button`,class:`panel-step-btn`,"data-testid":`spacing-${n.id}`,"aria-pressed":e===n.id,"aria-label":l(n.key),onClick:()=>t(n.id),children:U(Wt,{step:r})},n.id))})]})}function tn(){let e=Lt(),[t,n]=L(()=>K().voice.getRate()),[r,i]=L(()=>K().voice.getVoice()),[a,o]=L(()=>{let e=Ft(Nt);return jt.includes(e??``)?e:`md`}),[s,c]=L(()=>{let e=Ft(Pt);return Mt.includes(e??``)?e:`cozy`}),u=e=>n(K().voice.setRate(e)),d=e=>i(K().voice.setVoice(e)),f=e=>{o(e),It(Nt,e)},p=e=>{c(e),It(Pt,e)},m=e.current,h=e.bullets.length===0&&!m&&e.allCut.length===0&&!e.lastNotice;return U(`aside`,{id:`panel`,class:`panel`,role:`complementary`,"aria-label":l(`a11y.panel_region`),"data-gen":e.gen,"data-play":e.play,"data-font-size":a,"data-spacing":s,children:[U(Ht,{}),U(`div`,{class:`panel-scroll`,children:[U(`div`,{class:`panel-head`,children:U(`h2`,{class:`panel-title`,children:l(`panel.title`)})}),U(`div`,{class:`panel-body`,tabIndex:0,children:[h&&U(`p`,{class:`panel-empty`,children:l(`panel.empty`)}),m?.kind===`sentence`&&U(Kt,{cur:m}),e.bullets.length>0&&U(Gt,{s:e}),U(qt,{allCut:e.allCut}),e.lastNotice&&U(`p`,{class:`panel-notice`,role:`status`,"aria-live":`polite`,"data-notice":e.lastNotice,children:l(e.lastNotice)})]}),U(`div`,{class:`panel-controls`,children:[U(Jt,{s:e}),U(Yt,{rate:t,onChange:u}),U(Zt,{voice:r,onChange:d}),U(Qt,{checked:e.speakMessages,onChange:e=>K().setSpeakMessages(e)}),U(`div`,{class:`panel-controls-row`,children:[U($t,{value:a,onChange:f}),U(en,{value:s,onChange:p})]})]})]})]})}var nn=Object.freeze([`level`,`from_level`,`to_level`,`device`,`model_id`,`model_role`,`reason`,`probe_result`,`resource`,`store`,`chunk_count`,`chunk_index`,`bullets_total`,`word_count`,`phoneme_count`,`bytes`,`bytes_attempted`,`duration_ms`,`latency_ms`,`at_ms`]),rn=200,an=[],on=typeof performance<`u`?performance.now():0;function sn(){return typeof performance<`u`?performance.now():0}function J(e,t={}){try{for(an.push({event:e,t_ms:Math.round(sn()-on),fields:t});an.length>rn;)an.shift()}catch{}}function cn(){return[...an]}var ln={web:`0.0.0`,mac:`0.0.0`},Y={$schema:`https://json-schema.org/draft/2020-12/schema`,$id:`run-stats.schema.json`,title:`RunStats`,$comment:"One bench measurement (docs/PLAN.md rule 3, C11, S0-05). Numbers, enums, and validated metadata only — no free-text field. Metrics are nullable when a dial level doesn't produce them (readall has no LLM metrics; only readall has `coverage`). Bench identity = target, model_id, model_rev, dtype, device, browser(+major), os(+major), machine_id, cache_state, doc_id, level (bench/identity.md). Field order here is the fixed column order of bench/results.csv.",type:`object`,additionalProperties:!1,$defs:{level:{type:`string`,enum:[`readall`,`short`,`caveman`,`oneline`]},device:{type:`string`,enum:[`webgpu`,`wasm`,`mlx`]},model_id:{type:`string`,$comment:`Closed set sourced from spec/models.json. Add a value here (small PR) whenever a new model_id is pinned there.`,enum:[`onnx-community/Qwen3.5-0.8B-Text-ONNX`,`onnx-community/Qwen2.5-0.5B-Instruct`,`onnx-community/Qwen3-0.6B-ONNX`,`HuggingFaceTB/SmolLM2-360M-Instruct`,`onnx-community/Kokoro-82M-v1.0-ONNX`,`mlx-community/Qwen3.5-2B-4bit`,`mlx-community/Qwen3-1.7B-4bit`,`mlx-community/Kokoro-82M-bf16`]}},required:`schema_version.target.device.level.browser.browser_major.os.os_major.cache_state.model_id.model_rev.dtype.doc_id.commit.date.machine_id.ttfa_ms.gen_ms.tok_s.rtf.gap_ms.stop_ms.coverage.bullets_total.bullets_cut.cut_rate.facts_token_hit.halluc_flags.forbidden_hits.oneline_keyword_hit.tts_overlimit.peak_mb.heap_mb`.split(`.`),properties:{schema_version:{type:`integer`,enum:[1]},target:{type:`string`,enum:[`web`,`mac`]},device:{$ref:`#/$defs/device`},level:{$ref:`#/$defs/level`},browser:{type:`string`,enum:[`chrome`,`safari`,`firefox`,`none`]},browser_major:{type:[`integer`,`null`],minimum:0},os:{type:`string`,enum:[`macos`,`windows`,`linux`,`ios`,`android`]},os_major:{type:`integer`,minimum:0},cache_state:{type:`string`,enum:[`cold`,`warm`]},model_id:{$ref:`#/$defs/model_id`},model_rev:{type:`string`,pattern:`^[0-9a-f]{40}$`},dtype:{type:`string`,enum:[`q4f16`,`q8`,`q8f16`,`q4`,`fp32`,`bf16`,`fp16`,`4bit`,`8bit`],$comment:`q8f16: the WebGPU voice variant (?tts=webgpu, spec/models.json).`},doc_id:{type:`string`,pattern:`^([0-9]{3}|paste)$`,$comment:`S1-10: bench rows use the 3-digit eval corpus id; every other row (real usage, not the corpus) is 'paste' unless window.__fruitbat.setDocId(id) overrides it.`},commit:{type:`string`,pattern:`^[0-9a-f]{7,40}$`},date:{type:`string`,pattern:`^\\d{4}-\\d{2}-\\d{2}(T\\d{2}:\\d{2}:\\d{2}(\\.\\d+)?(Z|[+-]\\d{2}:\\d{2})?)?$`},machine_id:{type:`string`,pattern:`^(web|[0-9a-f]{12})$`},ttfa_ms:{type:[`number`,`null`],minimum:0},gen_ms:{type:[`number`,`null`],minimum:0},tok_s:{type:[`number`,`null`],minimum:0},rtf:{type:[`number`,`null`],minimum:0},gap_ms:{type:[`number`,`null`],minimum:0},stop_ms:{type:[`number`,`null`],minimum:0},coverage:{type:[`number`,`null`],minimum:0,maximum:1},bullets_total:{type:[`integer`,`null`],minimum:0},bullets_cut:{type:[`integer`,`null`],minimum:0},cut_rate:{type:[`number`,`null`],minimum:0,maximum:1},facts_token_hit:{type:[`number`,`null`],minimum:0,maximum:1},halluc_flags:{type:[`integer`,`null`],minimum:0},forbidden_hits:{type:[`integer`,`null`],minimum:0},oneline_keyword_hit:{type:[`number`,`null`],minimum:0,maximum:1},tts_overlimit:{type:[`integer`,`null`],minimum:0},peak_mb:{type:[`number`,`null`],minimum:0},heap_mb:{type:[`number`,`null`],minimum:0}}},un=Object.freeze([...Y.required??[]]);function dn(e){let t=/^#\/\$defs\/(.+)$/.exec(e);if(!t)throw Error(`stats/schema: unsupported $ref "${e}"`);let n=Y.$defs?.[t[1]];if(!n)throw Error(`stats/schema: unknown $defs entry "${t[1]}"`);return n}function fn(e){return e===null?`null`:Array.isArray(e)?`array`:typeof e==`number`?Number.isInteger(e)?`integer`:`number`:typeof e==`string`?`string`:typeof e==`boolean`?`boolean`:`object`}function pn(e,t){let n=fn(e);return t===`number`?n===`number`||n===`integer`:n===t}function mn(e,t,n,r){let i=n.$ref?dn(n.$ref):n;if(i.type!==void 0&&!(Array.isArray(i.type)?i.type:[i.type]).some(e=>pn(t,e))){r.push(`${e}: expected type ${JSON.stringify(i.type)}, got ${fn(t)} (${JSON.stringify(t)})`);return}t!==null&&(i.enum!==void 0&&!i.enum.includes(t)&&r.push(`${e}: ${JSON.stringify(t)} is not one of ${JSON.stringify(i.enum)}`),i.pattern!==void 0&&typeof t==`string`&&!new RegExp(i.pattern).test(t)&&r.push(`${e}: ${JSON.stringify(t)} does not match pattern ${i.pattern}`),i.minimum!==void 0&&typeof t==`number`&&t<i.minimum&&r.push(`${e}: ${t} is below minimum ${i.minimum}`),i.maximum!==void 0&&typeof t==`number`&&t>i.maximum&&r.push(`${e}: ${t} is above maximum ${i.maximum}`))}function hn(e){let t=[];if(typeof e!=`object`||!e||Array.isArray(e))return{ok:!1,errors:[`row is not a plain object`]};let n=e,r=Y.properties??{};for(let e of Y.required??[])e in n||t.push(`missing required field: ${e}`);if(Y.additionalProperties===!1)for(let e of Object.keys(n))e in r||t.push(`unknown field: ${e}`);for(let[e,i]of Object.entries(r))e in n&&mn(e,n[e],i,t);return{ok:t.length===0,errors:t}}var gn=2e3,_n=8e3,vn=`https://github.com/aj-prabhu/fruitbat`,yn={ua:300,gpu:200,os:100,chip:50};function X(e,t){return e.length>t?e.slice(0,t):e}async function bn(){try{let e=navigator.gpu;if(!e)return`unknown`;let t=await e.requestAdapter();if(!t)return`unknown`;let n=t.info,r=[n.vendor,n.architecture,n.description].filter(e=>!!e);return r.length?r.join(` `):`unknown`}catch{return`unknown`}}function xn(){let e=navigator.deviceMemory;return typeof e!=`number`||!Number.isFinite(e)?`unknown`:e<8?`under_8gb`:`8gb`}function Sn(e=typeof navigator<`u`&&navigator.userAgent||``){return/iPhone|iPad/.test(e)?`ios ${/OS (\d+)_/.exec(e)?.[1]??``}`.trim():/Mac OS X/.test(e)?`macos ${/Mac OS X (\d+)/.exec(e)?.[1]??``}`.trim():/Windows NT/.test(e)?`windows ${/Windows NT (\d+)/.exec(e)?.[1]??``}`.trim():/Android/.test(e)?`android ${/Android (\d+)/.exec(e)?.[1]??``}`.trim():/Linux/.test(e)?`linux`:`unknown`}function Cn(){return navigator.platform||`unknown`}async function wn(){return{ua:X(typeof navigator<`u`&&navigator.userAgent||``,yn.ua),gpu:X(await bn(),yn.gpu),os:X(Sn(),yn.os),chip:X(Cn(),yn.chip),ram_bucket:xn()}}function Tn(e){let{voice:r}=n().web,i=[{id:r.id,rev:r.revision}],a=e.last?.level;if(a&&a!==`readall`){let n=t(),r=n.find(t=>t.id===e.gen?.model_id)??n[0];i.push({id:r.id,rev:r.revision})}return i}function En(e){let t={},n=e;for(let e of un)t[e]=n[e];return t}function Dn(e){let t={},n=e.fields;for(let e of nn)e in n&&(t[e]=n[e]);return{event:e.event,t_ms:e.t_ms,fields:t}}async function On({orchestratorStats:e,rows:t,events:n,description:r}){return{app:`web`,version:ln.web,env:await wn(),models:Tn(e),run_stats:t.slice(-5).map(En),events:n.slice(-50).map(Dn),user_description:X(r,gn)}}function kn(e){let t=e.events[e.events.length-1];return t?(t.fields.reason?`${t.event} ${t.fields.reason}`:t.event).replace(/_/g,` `):`no events`}function An(e){return e.run_stats[e.run_stats.length-1]?.level??`unknown`}function jn(e){return`bug: ${An(e)} ${e.app} ${kn(e)}`}function Mn(e){let t=jn(e),n=[...e.events],r=[...e.run_stats],i=e.user_description,a=()=>{let a=new URLSearchParams;return a.set(`template`,`bug.yml`),a.set(`title`,t),a.set(`what_happened`,i),a.set(`env`,JSON.stringify(e.env,null,2)),a.set(`models`,JSON.stringify(e.models,null,2)),a.set(`run_stats`,JSON.stringify(r,null,2)),a.set(`events`,JSON.stringify(n,null,2)),a.set(`app_version`,`${e.app} ${e.version}`),`${vn}/issues/new?${a.toString()}`},o=a();for(;o.length>_n&&n.length>0;)n.shift(),o=a();for(;o.length>_n&&r.length>0;)r.shift(),o=a();for(;o.length>_n&&i.length>0;)i=i.slice(0,Math.max(0,i.length-200)),o=a();return o}function Nn(e){return JSON.stringify(e,null,2)}var Pn=`fruitbat.stats`,Fn=`fruitbat.stats.errors`,In=`paste`;function Ln(e){In=e}function Rn(){return In}function Z(e,t){let n=e.exec(t);return n?Number(n[1]):null}function zn(e=typeof navigator<`u`?navigator.userAgent:``){let t=`none`,n=null;/Firefox\//.test(e)?(t=`firefox`,n=Z(/Firefox\/(\d+)/,e)):/Chrome\//.test(e)&&!/Edg\//.test(e)?(t=`chrome`,n=Z(/Chrome\/(\d+)/,e)):/Safari\//.test(e)&&/Version\//.test(e)&&(t=`safari`,n=Z(/Version\/(\d+)/,e));let r=`linux`,i=0;return/iPhone|iPad/.test(e)?(r=`ios`,i=Z(/OS (\d+)_/,e)??0):/Android/.test(e)?(r=`android`,i=Z(/Android (\d+)/,e)??0):/Mac OS X/.test(e)?(r=`macos`,i=Z(/Mac OS X (\d+)/,e)??0):/Windows NT/.test(e)&&(r=`windows`,i=Z(/Windows NT (\d+)/,e)??0),{browser:t,browser_major:n,os:r,os_major:i}}function Bn(){return`2571727`}function Vn(){let e=zn(),t=typeof performance<`u`?performance.memory:void 0,n=t?Math.round(t.usedJSHeapSize/1e6*10)/10:null;return{...e,machine_id:`web`,commit:Bn(),date:new Date().toISOString(),doc_id:Rn(),heap_mb:n}}function Hn(e,r){let i=e.last?.level??`short`,a=i===`readall`?e.voice:null,o=e.gen,s=e.voice_run,c,l,u,d;if(i===`readall`){let e=n().web.voice;c=e.id,l=e.revision,u=s?s.dtype:a?.dtype??e.dtype,d=s?s.device:a?.device??e.device}else{let e=t(),n=e.find(e=>e.id===o?.model_id)??e[0];c=n.id,l=n.revision,u=n.dtype,d=n.device}let f=(s?s.cache_state:a?.cache_state)===`cold`,p=i!==`readall`&&o?.cache_cold===!0,m=f||p?`cold`:`warm`,h=o?.bullets_total??null,g=o?.bullets_cut??null,_=h===null?null:h>0?(g??0)/h:0;return{schema_version:1,target:`web`,device:d,level:i,browser:r.browser,browser_major:r.browser_major,os:r.os,os_major:r.os_major,cache_state:m,model_id:c,model_rev:l,dtype:u,doc_id:r.doc_id,commit:r.commit,date:r.date,machine_id:r.machine_id,ttfa_ms:e.ttfa_ms,gen_ms:o?.gen_ms??null,tok_s:o?.tok_s??null,rtf:s?s.rtf:a?.rtf??null,gap_ms:s?s.gap_ms:a?.gap_ms??null,stop_ms:null,coverage:i===`readall`?a?.coverage??null:null,bullets_total:h,bullets_cut:g,cut_rate:_,facts_token_hit:null,halluc_flags:null,forbidden_hits:null,oneline_keyword_hit:null,tts_overlimit:s?s.tts_overlimit:a?.tts_overlimit??0,peak_mb:null,heap_mb:r.heap_mb??null}}function Un(){try{let e=localStorage.getItem(Pn);if(!e)return[];let t=JSON.parse(e);return Array.isArray(t)?t:[]}catch{return[]}}function Wn(){try{let e=Number(localStorage.getItem(`fruitbat.stats.errors`))||0;localStorage.setItem(Fn,String(e+1))}catch{}}function Q(){return Un()}function Gn(){try{localStorage.removeItem(Pn),localStorage.removeItem(Fn)}catch{}}function Kn(e){try{let t=Un();for(t.push(e);t.length>200;)t.shift();localStorage.setItem(Pn,JSON.stringify(t))}catch{Wn()}}function qn(e,t=Vn()){let n=Hn(e,t),{ok:r,errors:i}=hn(n);return r&&Kn(n),{ok:r,errors:i,row:n}}function Jn(e){if(e==null)return``;let t=String(e);return/[",\n]/.test(t)?`"${t.replace(/"/g,`""`)}"`:t}function Yn(){let e=[un.join(`,`)];for(let t of Un()){let n=t;e.push(un.map(e=>Jn(n[e])).join(`,`))}return e.join(`
|
| 2 |
+
`)+`
|
| 3 |
+
`}function Xn({onClose:e}){let[t,n]=L(null),[r,i]=L(``),[a,o]=L(!1),[s,c]=L(!1),u=z(null);R(()=>{let e=!1;return On({orchestratorStats:K().stats(),rows:Q(),events:cn(),description:``}).then(t=>{e||n(t)}),()=>{e=!0}},[]);let d=t?{...t,user_description:r.slice(0,2e3)}:null,f=z(null);return R(()=>{f.current?.scrollIntoView({block:`start`}),f.current?.focus()},[]),U(`div`,{class:`report-view`,role:`dialog`,"aria-label":l(`report.title`),ref:f,tabIndex:-1,children:[U(`div`,{class:`report-view-header`,children:[U(`h2`,{children:l(`report.title`)}),U(`button`,{type:`button`,class:`report-close`,onClick:e,children:l(`panel.close`)})]}),U(`p`,{class:`report-privacy-note`,children:l(`report.privacy_note`)}),U(`label`,{class:`report-describe-label`,for:`report-describe`,children:l(`report.describe`)}),U(`textarea`,{id:`report-describe`,class:`report-describe`,maxLength:gn,value:r,onInput:e=>i(e.target.value)}),U(`p`,{class:`report-preview-intro`,children:l(`report.preview_intro`)}),U(`pre`,{class:`report-preview`,"data-testid":`report-preview`,ref:u,children:d?JSON.stringify(d,null,2):``}),U(`div`,{class:`report-actions`,children:[U(`button`,{type:`button`,class:`report-open-github`,disabled:!d,onClick:()=>{d&&window.open(Mn(d),`_blank`,`noopener`)},children:l(`report.open_github`)}),U(`button`,{type:`button`,class:`report-copy`,disabled:!d,onClick:()=>{if(!d)return;let e=typeof navigator<`u`?navigator.clipboard:void 0;(e?e.writeText(Nn(d)):Promise.reject(Error(`no clipboard`))).then(()=>{c(!1),o(!0),K().speakMessage(`report.copied`)},()=>{o(!1),c(!0),K().speakMessage(`report.copy_failed`);let e=u.current,t=typeof window<`u`?window.getSelection():null;if(e&&t){let n=document.createRange();n.selectNodeContents(e),t.removeAllRanges(),t.addRange(n)}})},children:U(`span`,{"aria-live":`polite`,children:l(s?`report.copy_failed`:a?`report.copied`:`report.copy`)})})]})]})}var Zn=[`date`,`level`,`device`,`dtype`,`cache_state`,`doc_id`,`ttfa_ms`,`tok_s`,`rtf`,`bullets_total`,`bullets_cut`],Qn={date:`stats.col.date`,level:`stats.col.level`,device:`stats.col.device`,dtype:`stats.col.dtype`,cache_state:`stats.col.cache_state`,doc_id:`stats.col.doc_id`,ttfa_ms:`stats.col.ttfa_ms`,tok_s:`stats.col.tok_s`,rtf:`stats.col.rtf`,bullets_total:`stats.col.bullets_total`,bullets_cut:`stats.col.bullets_cut`};function $n(e){let t=new Blob([e],{type:`text/csv`}),n=URL.createObjectURL(t),r=document.createElement(`a`);r.href=n,r.download=`fruitbat-stats.csv`,r.click(),URL.revokeObjectURL(n)}function er({onClose:e}){let[t,n]=L(()=>Q()),r=z(null);return R(()=>{r.current?.scrollIntoView({block:`start`}),r.current?.focus()},[]),U(`div`,{class:`stats-view`,role:`dialog`,"aria-label":l(`stats.title`),ref:r,tabIndex:-1,children:[U(`div`,{class:`stats-view-header`,children:[U(`h2`,{children:l(`stats.title`)}),U(`button`,{type:`button`,class:`stats-close`,onClick:e,children:l(`panel.close`)})]}),t.length===0?U(`p`,{class:`stats-empty`,children:l(`stats.empty`)}):U(`table`,{class:`stats-table`,children:[U(`thead`,{children:U(`tr`,{children:Zn.map(e=>U(`th`,{children:l(Qn[e])},e))})}),U(`tbody`,{children:t.map((e,t)=>U(`tr`,{children:Zn.map(t=>U(`td`,{children:e[t]===null?``:String(e[t])},t))},t))})]}),U(`div`,{class:`stats-actions`,children:[U(`button`,{type:`button`,onClick:()=>$n(Yn()),children:l(`stats.export`)}),U(`button`,{type:`button`,onClick:()=>{Gn(),n(Q())},children:l(`stats.clear`)})]})]})}var tr=i.levels,nr=i.default??`short`;function rr({level:e,onChange:t}){return U(`fieldset`,{class:`dial`,children:[U(`legend`,{class:`visually-hidden`,children:l(`a11y.dial`)}),tr.map(n=>U(`label`,{class:`dial-option`,children:[U(`input`,{type:`radio`,name:`level`,value:n.id,checked:e===n.id,onChange:()=>t(n.id)}),U(`span`,{children:l(n.label_key)})]},n.id))]})}function ir(){if(typeof document<`u`){let e=document.documentElement.getAttribute(`data-theme`);if(e===`dark`||e===`light`)return e}return typeof matchMedia<`u`&&matchMedia(`(prefers-color-scheme: dark)`).matches?`dark`:`light`}function ar(){let[e,t]=L(ir);return U(`button`,{type:`button`,class:`theme-toggle`,onClick:()=>{let n=e===`dark`?`light`:`dark`;t(n),document.documentElement.setAttribute(`data-theme`,n);try{localStorage.setItem(`fruitbat-theme`,n)}catch{}},"aria-pressed":e===`dark`,children:l(`theme.toggle`)})}function or({paragraphs:e}){return U(`article`,{class:`article`,"aria-label":l(`intake.sample_label`),children:e.map((e,t)=>U(`p`,{children:e},t))})}function sr(){let[t,n]=L([]);return R(()=>{let t=!1;return e(`/sample.txt`).then(e=>e.text()).then(e=>{t||n(e.split(/\n{2,}/).map(e=>e.trim()).filter(Boolean))}).catch(()=>{t||n([])}),()=>{t=!0}},[]),t}function cr(){let[e,t]=L(nr),[n,r]=L(!1),[i,a]=L(!1),o=sr();return R(()=>{document.title=l(`app.title`)},[]),R(()=>{Ke(e)},[e]),U(`div`,{class:`app-shell`,children:[U(`header`,{class:`app-header`,children:[U(`h1`,{class:`app-title`,children:l(`app.title`)}),U(rr,{level:e,onChange:e=>{Ke(e),t(e)}}),U(`button`,{type:`button`,class:`stats-toggle`,onClick:()=>r(!0),children:l(`panel.stats`)}),U(`button`,{type:`button`,class:`report-toggle`,onClick:()=>a(!0),children:l(`panel.bug_report`)}),U(ar,{})]}),U(At,{}),U(`main`,{class:`app-main`,children:[U(lt,{}),U(or,{paragraphs:o}),U(at,{})]}),U(tn,{}),U(ot,{}),n&&U(er,{onClose:()=>r(!1)}),i&&U(Xn,{onClose:()=>a(!1)})]})}function lr(){try{let e=localStorage.getItem(`fruitbat-theme`);(e===`dark`||e===`light`)&&document.documentElement.setAttribute(`data-theme`,e)}catch{}}var $=K();window.__fruitbat={run(e,t){window.dispatchEvent(new CustomEvent(`fruitbat:run`,{detail:{text:e,level:t}}))},stop(){window.dispatchEvent(new CustomEvent(`fruitbat:stop`))},stats(){return $.stats()},state:()=>$.snapshot(),setLevel:e=>$.setLevel(e),readThisPart:e=>$.readThisPart(e),pause:()=>$.pause(),resume:()=>$.resume(),skip:()=>$.skip(),setSpeakMessages:e=>$.setSpeakMessages(e),rows:()=>Q(),setDocId:e=>Ln(e)},window.addEventListener(`fruitbat:run`,e=>void $.run(e.detail.text,e.detail.level)),window.addEventListener(`fruitbat:stop`,()=>$.stop()),window.addEventListener(`fruitbat:demo`,()=>{let e=$.snapshot(),t=e.voice.pending>0||e.voice.inFlight>0||e.voice.enqueued>e.voice.ended;mt(e.gen,e.play)||t?$.stop({quiet:!0}):$.silenceVoice()});var ur=0;$.subscribe(e=>{(e.gen===`done`||e.gen===`failed`)&&e.settledRunId===e.runId&&e.runId!==ur&&(ur=e.runId,qn($.stats()))});var dr=null;$.subscribe(e=>{let t=dr;dr=e,t&&(e.level!==t.level&&J(`dial_change`,{from_level:t.level,to_level:e.level}),t.gen!==`loading`&&e.gen===`loading`&&J(`run_start`,{level:e.level}),t.gen!==`done`&&e.gen===`done`&&J(`run_done`,{level:e.level}),t.gen!==`failed`&&e.gen===`failed`&&J(`run_failed`,{level:e.level,reason:`unknown`}),e.allCut.length>t.allCut.length&&J(`all_cut`,{chunk_index:e.allCut[e.allCut.length-1]}),e.lastNotice!==t.lastNotice&&e.lastNotice&&(e.lastNotice===`notice.stopped`?J(`run_stopped`,{level:e.level}):e.lastNotice===`notice.input_limit`?J(`input_limit`,{}):e.lastNotice===`error.storage_full`?J(`quota_error`,{store:`stats`}):(e.lastNotice===`notice.no_webgpu`||e.lastNotice===`notice.probe_failed`)&&J(`probe_result`,{probe_result:`fail`})))}),qe(e=>void $.setLevel(e)),document.addEventListener(`keydown`,e=>{e.key===`Escape`&&$.stop()}),lr();var fr=document.getElementById(`app`);fr&&Te(U(cr,{}),fr);
|
assets/index-DTUQ8gca.css
ADDED
|
@@ -0,0 +1 @@
|
|
|
|
|
|
|
| 1 |
+
.panel{right:var(--gutter);bottom:var(--gutter);width:min(360px, calc(100% - var(--gutter) * 2));max-height:calc(100vh - var(--gutter) * 2);background:var(--color-panel-bg);border:1px solid var(--color-border);border-radius:var(--border-radius);--panel-pad:var(--space-lg);--panel-gap:var(--space-sm);flex-direction:column;display:flex;position:fixed;overflow:visible;box-shadow:0 8px 24px -12px #00000040}.panel[data-spacing=compact]{--panel-pad:var(--space-md);--panel-gap:var(--space-xs)}.panel[data-spacing=roomy]{--panel-pad:var(--space-xl);--panel-gap:var(--space-md)}.panel[data-font-size=sm]{font-size:.9375rem}.panel[data-font-size=lg]{font-size:1.125rem}@media (width<=640px){.panel{left:var(--gutter);right:var(--gutter);width:auto;max-height:70vh}}@media (width>=641px){body .app-shell{padding-right:calc(min(360px, 100% - var(--gutter) * 2) + var(--gutter))}}@media (width<=640px){body .app-shell{padding-bottom:70vh}}.panel-scroll{border-radius:inherit;flex-direction:column;flex:auto;min-height:0;display:flex;overflow-y:auto}.panel-pip{top:0;left:var(--space-lg);background:var(--color-panel-bg);border:1px solid var(--color-border);width:48px;height:48px;color:var(--color-accent);border-radius:50%;justify-content:center;align-items:center;display:flex;position:absolute;transform:translateY(-62%)}.panel-pip-svg{display:block}.panel-head{padding:var(--panel-pad) var(--panel-pad) var(--space-sm);border-bottom:1px solid var(--color-border)}.panel-title{padding-left:calc(48px - var(--space-lg) + var(--space-sm));margin:0;font-size:1.05em;font-weight:700}.panel-body{padding:var(--panel-pad);gap:var(--panel-gap);flex-direction:column;flex-shrink:0;min-height:min(8em,30vh);max-height:40vh;display:flex;overflow-y:auto}.panel-body:focus-visible{outline:2px solid var(--color-focus-ring);outline-offset:-2px}.panel-empty{color:var(--color-muted);margin:0}.panel-controls{padding:var(--space-sm) var(--panel-pad) var(--panel-pad);border-top:1px solid var(--color-border);gap:var(--panel-gap);flex-direction:column;display:flex}.panel-controls-row{align-items:center;gap:var(--space-xs);flex-wrap:wrap;display:flex}.panel-bullets{gap:var(--space-2xs);flex-direction:column;margin:0;padding-left:1.3em;display:flex}.panel-bullets li{padding:var(--space-3xs) var(--space-2xs);border-radius:4px;transition:background-color .15s ease-out}.panel-bullets li[aria-current=true]{background:var(--color-accent-soft);margin-inline-start:calc(-1 * var(--space-2xs));font-weight:700}.now-reading{gap:var(--space-3xs);flex-direction:column;display:flex}.now-label,.next-label{color:var(--color-muted);text-transform:none;margin:0;font-size:.8em;font-weight:700}.now-text{margin:0;font-size:1.5em;font-weight:700;line-height:1.35}.next-text{color:var(--color-muted);margin:0}.read-part-row{margin:0}.read-part{align-items:center;gap:var(--space-2xs);font:inherit;min-height:44px;padding:var(--space-xs) var(--space-sm);border:1px solid var(--color-accent);border-radius:var(--border-radius);background:var(--color-panel-bg);color:var(--color-fg);cursor:pointer;display:inline-flex}.read-part:focus-visible{outline:2px solid var(--color-focus-ring);outline-offset:2px}.panel-notice{color:var(--color-muted);margin:0;font-size:.95em}@media (prefers-reduced-motion:reduce){.panel-bullets li{transition:none}}.panel-transport{align-items:center;gap:var(--space-2xs);min-height:44px;padding:var(--space-xs) var(--space-sm);border:1px solid var(--color-border);border-radius:var(--border-radius);background:var(--color-panel-bg);color:var(--color-fg);font:inherit;cursor:pointer;display:inline-flex}.panel-transport:hover:not(:disabled){border-color:var(--color-accent)}.panel-transport:focus-visible{outline:2px solid var(--color-focus-ring);outline-offset:2px}.panel-transport:disabled{opacity:.5;cursor:not-allowed}.panel-transport-icon{flex:none}.panel-transport--primary{border-color:var(--color-accent);background:var(--color-accent);color:var(--color-accent-fg)}.panel-transport--primary:hover:not(:disabled){border-color:var(--color-accent)}.panel-field{gap:var(--space-2xs);flex-direction:column;display:flex}.panel-field-label{color:var(--color-muted);font-size:.85em;font-weight:700}.panel-rate-row{align-items:center;gap:var(--space-xs);display:flex}.panel-rate-end{color:var(--color-muted);white-space:nowrap;font-size:.8em}.panel-rate-value{font-variant-numeric:tabular-nums;color:var(--color-muted);text-align:right;min-width:3ch;font-size:.85em}.panel-rate-slider{min-width:0;height:44px;accent-color:var(--color-accent);cursor:pointer;flex:auto}.panel-rate-slider:focus-visible{outline:2px solid var(--color-focus-ring);outline-offset:2px}.panel-select{min-height:44px;padding:var(--space-2xs) var(--space-xs);border:1px solid var(--color-border);border-radius:var(--border-radius);background:var(--color-input-bg);color:var(--color-fg);font:inherit}.panel-select:focus-visible{outline:2px solid var(--color-focus-ring);outline-offset:2px}.panel-toggle-row{align-items:center;gap:var(--space-xs);min-height:44px;display:flex}.panel-toggle-row input{accent-color:var(--color-accent);width:18px;height:18px}.panel-toggle-row label{cursor:pointer}.panel-steps{gap:var(--space-3xs);border:1px solid var(--color-border);border-radius:var(--border-radius);padding:var(--space-3xs);display:inline-flex}.panel-step-btn{border-radius:calc(var(--border-radius) - 3px);width:36px;height:36px;color:var(--color-fg);cursor:pointer;background:0 0;border:none;justify-content:center;align-items:center;display:flex;position:relative}.panel-step-btn:before{content:"";position:absolute;inset:-4px}.panel-step-btn:hover{background:var(--color-accent-soft)}.panel-step-btn:focus-visible{outline:2px solid var(--color-focus-ring);outline-offset:2px}.panel-step-btn[aria-pressed=true]{background:var(--color-accent);color:var(--color-accent-fg)}.panel-step-glyph{display:block}@font-face{font-family:Atkinson Hyperlegible;src:url(/fonts/AtkinsonHyperlegible-Regular.woff2)format("woff2");font-weight:400;font-style:normal;font-display:swap}@font-face{font-family:Atkinson Hyperlegible;src:url(/fonts/AtkinsonHyperlegible-Bold.woff2)format("woff2");font-weight:700;font-style:normal;font-display:swap}@font-face{font-family:Atkinson Hyperlegible;src:url(/fonts/AtkinsonHyperlegible-Italic.woff2)format("woff2");font-weight:400;font-style:italic;font-display:swap}@font-face{font-family:Atkinson Hyperlegible;src:url(/fonts/AtkinsonHyperlegible-BoldItalic.woff2)format("woff2");font-weight:700;font-style:italic;font-display:swap}:root{--gutter:16px;--measure:65ch;--border-radius:8px;--space-3xs:2px;--space-2xs:4px;--space-xs:8px;--space-sm:12px;--space-md:16px;--space-lg:24px;--space-xl:32px;--space-2xl:48px;--color-bg:#faf9f6;--color-fg:#1a1a1a;--color-muted:#5b5b5b;--color-border:#d8d5cd;--color-accent:#7a3b2e;--color-accent-fg:#fff;--color-panel-bg:#fff;--color-input-bg:#fff;--color-focus-ring:#7a3b2e;--color-accent-soft:color-mix(in oklch, var(--color-accent) 16%, var(--color-panel-bg))}@media (prefers-color-scheme:dark){:root:not([data-theme=light]){--color-bg:#17171a;--color-fg:#eceae6;--color-muted:#a8a49c;--color-border:#3a3a3f;--color-accent:#e0a893;--color-accent-fg:#17171a;--color-panel-bg:#201f23;--color-input-bg:#201f23;--color-focus-ring:#e0a893;--color-accent-soft:color-mix(in oklch, var(--color-accent) 22%, var(--color-panel-bg))}}:root[data-theme=dark]{--color-bg:#17171a;--color-fg:#eceae6;--color-muted:#a8a49c;--color-border:#3a3a3f;--color-accent:#e0a893;--color-accent-fg:#17171a;--color-panel-bg:#201f23;--color-input-bg:#201f23;--color-focus-ring:#e0a893;--color-accent-soft:color-mix(in oklch, var(--color-accent) 22%, var(--color-panel-bg))}*{box-sizing:border-box}html,body{max-width:100%;margin:0;padding:0;overflow-x:hidden}body{background:var(--color-bg);color:var(--color-fg);font-family:Atkinson Hyperlegible,system-ui,sans-serif;line-height:1.5}.visually-hidden{clip:rect(0, 0, 0, 0);white-space:nowrap;border:0;width:1px;height:1px;margin:-1px;padding:0;position:absolute;overflow:hidden}.app-shell{min-height:100vh;padding:var(--gutter);padding-bottom:calc(var(--gutter) * 6);flex-direction:column;display:flex}.app-header{justify-content:space-between;align-items:center;gap:var(--gutter);padding-bottom:var(--gutter);border-bottom:1px solid var(--color-border);margin-bottom:var(--gutter);flex-wrap:wrap;display:flex}.app-title{flex:auto;min-width:0;margin:0;font-size:1.25rem}.dial{border:1px solid var(--color-border);border-radius:var(--border-radius);flex-wrap:wrap;gap:4px;margin:0;padding:4px;display:flex}.dial-option{border-radius:calc(var(--border-radius) - 2px);cursor:pointer;align-items:center;gap:6px;padding:6px 10px;font-size:.9rem;display:inline-flex}.dial-option:has(input:checked){background:var(--color-accent);color:var(--color-accent-fg)}.dial-option input{accent-color:var(--color-accent)}.dial-option input:focus-visible{outline:2px solid var(--color-focus-ring);outline-offset:2px}.theme-toggle{border:1px solid var(--color-border);background:var(--color-panel-bg);color:var(--color-fg);border-radius:var(--border-radius);cursor:pointer;font:inherit;padding:6px 12px}.theme-toggle:focus-visible{outline:2px solid var(--color-focus-ring);outline-offset:2px}.app-main{gap:calc(var(--gutter) * 1.5);max-width:var(--measure);flex-direction:column;flex:auto;width:100%;margin:0 auto;display:flex}.article p{margin:0 0 1em}.paste-box{flex-direction:column;gap:6px;display:flex}.paste-label{font-weight:700}.paste-textarea{border:1px solid var(--color-border);border-radius:var(--border-radius);background:var(--color-input-bg);width:100%;max-width:100%;min-height:8em;color:var(--color-fg);font:inherit;resize:vertical;padding:10px}.paste-textarea:focus-visible{outline:2px solid var(--color-focus-ring);outline-offset:2px}.paste-row{justify-content:space-between;align-items:center;gap:var(--gutter);flex-wrap:wrap;display:flex}.word-count{color:var(--color-muted);margin:0;font-size:.85rem}.read-button{border:1px solid var(--color-accent);background:var(--color-accent);color:var(--color-accent-fg);border-radius:var(--border-radius);cursor:pointer;font:inherit;white-space:nowrap;padding:6px 14px}.read-button:disabled{opacity:.5;cursor:not-allowed}.read-button:focus-visible{outline:2px solid var(--color-focus-ring);outline-offset:2px}.read-chip{z-index:10;border:1px solid var(--color-accent);background:var(--color-accent);color:var(--color-accent-fg);font:inherit;cursor:pointer;border-radius:999px;padding:6px 14px;font-size:.85rem;position:fixed;box-shadow:0 2px 8px #0003}.read-chip:focus-visible{outline:2px solid var(--color-focus-ring);outline-offset:2px}.report-preview{white-space:pre-wrap;overflow-wrap:anywhere;max-width:100%}.loading{margin-bottom:var(--gutter);max-width:var(--measure);flex-direction:column;gap:6px;width:100%;margin-left:auto;margin-right:auto;display:flex}.loading-line{color:var(--color-muted);margin:0;font-size:.9rem}.loading-bar{width:100%;height:6px;accent-color:var(--color-accent)}.loading-cache{opacity:.7;margin:0;font-size:.8rem}.loading-notice{opacity:.85;margin:0;font-size:.9rem}.loading-summarizer{flex-direction:column;gap:4px;display:flex}.loading-summarizer-button{border:1px solid var(--color-accent);background:var(--color-panel-bg);color:var(--color-fg);border-radius:var(--border-radius);cursor:pointer;font:inherit;align-self:flex-start;padding:6px 12px}.loading-summarizer-button:focus-visible{outline:2px solid var(--color-focus-ring);outline-offset:2px}.demo{border:1px solid var(--color-border);border-radius:var(--border-radius);padding:var(--gutter);flex-direction:column;gap:6px;display:flex}.demo-recording-label,.demo-excerpt-note,.demo-switch-level{color:var(--color-muted);margin:0;font-size:.85rem}.demo-try-it-now{border:1px solid var(--color-accent);background:var(--color-accent);color:var(--color-accent-fg);border-radius:var(--border-radius);cursor:pointer;font:inherit;align-self:flex-start;padding:6px 14px}.demo-try-it-now:disabled{opacity:.5;cursor:not-allowed}.demo-try-it-now:focus-visible{outline:2px solid var(--color-focus-ring);outline-offset:2px}.demo-items{margin:0;padding-left:1.2em}.demo-items li{margin:.35em 0}.demo-items li[aria-current=true]{background:var(--color-accent-soft,#785ac826);border-radius:4px}
|
assets/{readall-D11mojeC.js → readall-CNVhfTRg.js}
RENAMED
|
@@ -1 +1 @@
|
|
| 1 |
-
import"./pins-DVBrHC3g.js";import{a as e,i as t,n,r,t as i}from"./tts-
|
|
|
|
| 1 |
+
import"./pins-DVBrHC3g.js";import{a as e,i as t,n,r,t as i}from"./tts-DDfrpA1Y.js";var a=t(),o=e=>document.getElementById(e),s=o(`text`),c=o(`status`),l=o(`now`),u=o(`rate`),d=o(`voice`);o(`readall`).textContent=e(`dial.readall`),o(`stop`).textContent=e(`panel.stop`),o(`pause`).textContent=e(`panel.pause`),o(`resume`).textContent=e(`panel.resume`),o(`skip`).textContent=e(`panel.skip`),o(`rate-label`).textContent=e(`panel.rate`),o(`voice-label`).textContent=e(`panel.voice`),u.min=String(n),u.max=String(i),u.step=`0.1`,u.value=String(a.getRate());for(let e of r){let t=document.createElement(`option`);t.value=e,t.textContent=e,d.appendChild(t)}d.value=a.getVoice();function f(e){c.textContent=e}a.onProgress((t,n,r)=>f(`${e(`loading.voice`)} ${Math.round(n/1e6)} / ${Math.round(r/1e6)} MB ${t}`));async function p(t,n={}){f(e(`notice.reading_all`));let r=await a.readAll(t,{...n,onStart:e=>{l.textContent=t.slice(e.start,e.end),l.dataset.seq=String(e.seq)},onEnd:e=>{l.dataset.seq===String(e.seq)&&(l.textContent=``)}});return f(r.finished?e(`notice.done`):e(`notice.stopped`)),r}o(`readall`).addEventListener(`click`,()=>void p(s.value)),o(`stop`).addEventListener(`click`,()=>{a.stop(),f(e(`notice.stopped`))}),o(`pause`).addEventListener(`click`,()=>a.pause()),o(`resume`).addEventListener(`click`,()=>a.resume()),o(`skip`).addEventListener(`click`,()=>a.skip()),u.addEventListener(`input`,()=>u.value=String(a.setRate(Number(u.value)))),d.addEventListener(`change`,()=>a.setVoice(d.value)),document.addEventListener(`keydown`,t=>{t.key===`Escape`&&(a.stop(),f(e(`notice.stopped`)))}),window.__tts={load:()=>a.load(),plan:e=>a.plan(e),measure:(e,t,n)=>a.measure(e,t,n),readAll:p,speak:e=>a.speak(e),stop:()=>a.stop(),pause:()=>a.pause(),resume:()=>a.resume(),skip:()=>a.skip(),setRate:e=>a.setRate(e),getRate:()=>a.getRate(),setVoice:e=>a.setVoice(e),state:()=>a.state(),stats:()=>a.stats()},f(e(`loading.ready`));
|
assets/tts-BfNZpTEA.js
DELETED
|
@@ -1 +0,0 @@
|
|
| 1 |
-
import{r as e}from"./pins-DVBrHC3g.js";var t={$comment:`Every user-facing string, both targets (docs/PLAN.md rule 8). S0-03 owns the KEYS; Values written in S1-L0 (Claude, Voice Bank protocol, 2026-09-24). Every message is spoken, so key names are spelled out (Control Option V, Command C), never symbols. Web and Mac load this file; no string literal lives in UI code (scripts/strings-check.mjs). Every notice/error is also spoken (rule 8, 'Speak messages' default on). Placeholders {n} {mb} {words} {level} are filled at runtime.`,version:1,locale:`en`,$plan_wording:{"notice.dial_shorter":`Making it shorter.`,"notice.dial_longer":`Adding detail.`,"notice.all_cut":`Couldn't make a summary I trust for this part.`,"notice.oneline_failed":`Couldn't boil this down to one line I trust. Here's the short version.`,"notice.input_limit":`This is over 120,000 words. Select a part of it.`,"mac.intake.press_cmd_c":`Press ⌘C to read it (spoken form: Press Command C to read it.)`,"mac.intake.no_copy_seen":`Didn't see a copy.`,"loading.summarizer_button":`Load summarizer ({mb} MB)`,"dial.readall":`Read all`,"dial.short":`Short`,"dial.caveman":`Caveman`,"dial.oneline":`One line`,$comment:`Wording the plan fixes (rules 2, 11, C3, C9, Architecture). S1-L0 keeps the meaning; it may tune words after the Voice Bank pass.`},strings:{"app.title":`Fruitbat`,"theme.toggle":`Dark mode`,"dial.readall":`Read all`,"dial.short":`Short`,"dial.caveman":`Caveman`,"dial.oneline":`One line`,"panel.title":`The short version`,"panel.empty":`Highlight some text or paste it below. Then pick how short you want it.`,"panel.read_chip":`Read`,"panel.summarize":`Read it`,"panel.stop":`Stop`,"panel.pause":`Pause`,"panel.resume":`Resume`,"panel.skip":`Skip`,"panel.read_this_part":`Read this part`,"panel.rate":`Speed`,"panel.rate_slower":`Slower`,"panel.rate_faster":`Faster`,"panel.voice":`Voice`,"panel.speak_messages":`Speak messages`,"panel.hide_pip":`Hide Pip`,"panel.show_pip":`Show Pip`,"panel.font_size":`Text size`,"panel.spacing":`Spacing`,"panel.dark_mode":`Dark mode`,"panel.position":`Panel position`,"panel.bug_report":`Report a problem`,"panel.stats":`Stats`,"panel.close":`Close`,"panel.now_reading":`Now reading`,"panel.next_up":`Next`,"intake.paste_placeholder":`Paste text here`,"intake.word_count":`{n} words`,"intake.drop_here":`Drop a text or PDF file here`,"intake.empty":`Nothing to read yet. Highlight some text or paste it here.`,"intake.sample_label":`Sample article`,"demo.try_it_now":`Try it now`,"demo.recording_label":`This one is a recording. Your own text runs on your machine.`,"demo.switch_level":`Turn the dial to hear the same article shorter or longer.`,"demo.excerpt_note":`This is the first part of the article, not the whole thing.`,"loading.probing":`Checking what this browser can do.`,"loading.voice":`Getting the voice ready.`,"loading.summarizer_button":`Load summarizer ({mb} MB)`,"loading.summarizer_size":`The summarizer is a {mb} MB download. It happens once and stays on this device.`,"loading.progress":`{mb} MB so far.`,"loading.cached":`Already on this device. No download needed.`,"loading.first_time":`First time here. The models download once and stay on this device.`,"loading.save_data":`Your browser is set to save data, so nothing big downloads until you ask.`,"loading.mobile":`On a phone the voice works and the sample is a recording. Open this on a laptop for the full thing.`,"loading.almost":`Almost there.`,"loading.ready":`Ready.`,"notice.dial_shorter":`Making it shorter.`,"notice.dial_longer":`Adding detail.`,"notice.all_cut":`Couldn't make a summary I trust for this part.`,"notice.oneline_failed":`Couldn't boil this down to one line I trust. Here's the short version.`,"notice.input_limit":`This is over 120,000 words. Select a part of it.`,"notice.no_webgpu":`This browser can't run the summarizer. Read all still works, and the sample is a recording.`,"notice.probe_failed":`The summarizer didn't start on this machine. Read all still works.`,"notice.low_end_tier":`Using a smaller summarizer so it fits this machine.`,"notice.stopped":`Stopped.`,"notice.done":`That's the end.`,"notice.paused":`Paused.`,"notice.making_summary":`Making the short version.`,"notice.reading_all":`Reading all of it.`,"error.model_download":`The download didn't finish. Check your connection and try again.`,"error.voice":`The voice didn't load. Try again in a moment.`,"error.generation":`Something went wrong making the summary. Read all still works.`,"error.storage_full":`This browser is out of storage, so stats won't be saved.`,"error.empty_input":`There's no text to read yet.`,"error.offline":`You're offline. Anything already downloaded still works.`,"error.unknown":`Something went wrong. Try again.`,"report.title":`Report a problem`,"report.preview_intro":`Here is everything the report contains. Nothing you were reading is in it.`,"report.describe":`What happened?`,"report.open_github":`Open on GitHub`,"report.copy":`Copy report`,"report.copied":`Copied.`,"report.copy_failed":`Couldn't copy it. The report above is selected so you can copy it by hand.`,"report.privacy_note":`The report has numbers and settings only. Never your text, your audio or your file names.`,"stats.title":`Stats`,"stats.empty":`No runs yet.`,"stats.export":`Export CSV`,"stats.clear":`Clear stats`,"stats.col.date":`When`,"stats.col.level":`Level`,"stats.col.device":`Device`,"stats.col.dtype":`Precision`,"stats.col.cache_state":`Cache`,"stats.col.doc_id":`Text`,"stats.col.ttfa_ms":`First audio (ms)`,"stats.col.tok_s":`Tokens per second`,"stats.col.rtf":`Voice speed (x real time)`,"stats.col.bullets_total":`Bullets`,"stats.col.bullets_cut":`Bullets cut`,"a11y.panel_region":`Fruitbat panel`,"a11y.bullet_list":`Summary`,"a11y.dial":`How short`,"a11y.pip":`Pip the fruit bat`,"mac.menu.summarize_selection":`Read the selection`,"mac.menu.summarize_clipboard":`Read the clipboard`,"mac.menu.summarize_region":`Read part of the screen`,"mac.menu.settings":`Settings`,"mac.menu.stats":`Stats`,"mac.menu.check_updates":`Check for updates`,"mac.menu.quit":`Quit Fruitbat`,"mac.onboarding.try_it":`Copy any text, then press Control Option V.`,"mac.onboarding.first_success":`Worked. Now try it on anything you highlight.`,"mac.onboarding.offer_accessibility":`Want to skip the copy step? Give Fruitbat the Accessibility permission and it reads what you highlight.`,"mac.onboarding.updates_disclosure":`Fruitbat checks for updates once a day. You can turn that off in Settings.`,"mac.onboarding.done":`You're set. Fruitbat lives in the menu bar.`,"mac.permission.accessibility":`Fruitbat needs the Accessibility permission to read what you highlight. Without it, copy the text first and press Control Option V.`,"mac.permission.accessibility_denied":`No Accessibility permission. Copy the text and press Control Option V instead.`,"mac.permission.screen_recording":`Fruitbat needs Screen Recording to read part of the screen. Without it, the other two ways still work.`,"mac.permission.screen_recording_denied":`No Screen Recording permission. Highlight text or copy it instead.`,"mac.permission.open_settings":`Open System Settings`,"mac.intake.press_cmd_c":`Press Command C to read it.`,"mac.intake.no_copy_seen":`Didn't see a copy.`,"mac.intake.clipboard_empty":`The clipboard is empty.`,"mac.intake.clipboard_not_text":`The clipboard doesn't have text in it.`,"mac.ocr.first_run_warning":`Anything on screen becomes text on this Mac, passwords included. It stays here.`,"mac.ocr.nothing_found":`Couldn't find any text there.`,"mac.ocr.pick_region":`Drag over the part you want read.`,"mac.update.toggle":`Check for updates`,"mac.update.available":`A new version is ready.`,"mac.update.up_to_date":`You're up to date.`,"mac.license.trial_days_left":`{n} days left in the trial.`,"mac.license.enter_key":`Enter your license key`,"mac.license.licensed":`Licensed. Thank you.`,"mac.license.nag":`Couldn't check the license in a while. Fruitbat keeps working.`,"mac.license.sign_out":`Sign out of this Mac`,"mac.license.invalid":`That key didn't work. Check it and try again.`,"intake.read_button":`Read this`}}.strings;function n(e){return t[e]??e}var r=25,i=.005,a=class{maxAheadSeconds;maxInFlight;ctx;opts;runId=0;nextStart=0;scheduled=[];inFlight=0;analyser=null;maxGapMs=0;totalSeconds=0;enqueued=0;ended=0;closed=!1;ticker=null;constructor(e,t={}){this.ctx=e,this.opts=t,this.maxAheadSeconds=t.maxAheadSeconds??30,this.maxInFlight=t.maxInFlight??3}get currentRunId(){return this.runId}beginRun(e){this.stop(),this.runId=e,this.nextStart=this.ctx.currentTime,this.maxGapMs=0,this.totalSeconds=0,this.enqueued=0,this.ended=0,this.closed=!1}close(){this.closed=!0,this.maybeDrain()}requestSent(e=0){return this.inFlight++,this.reserved+=e,{run:this.runId,seconds:e}}requestSettled(e={run:this.runId,seconds:0}){e.run===this.runId&&(this.inFlight=Math.max(0,this.inFlight-1),this.reserved=Math.max(0,this.reserved-e.seconds))}reserved=0;get requestsInFlight(){return this.inFlight}aheadSeconds(){return Math.max(0,this.nextStart-this.ctx.currentTime)}canAccept(e=0){if(this.inFlight>=this.maxInFlight)return!1;let t=this.aheadSeconds()+this.reserved;return t+e<=this.maxAheadSeconds&&t<this.maxAheadSeconds||this.inFlight===0&&t<=Math.min(5,this.maxAheadSeconds/2)}getAnalyser(){return!this.analyser&&this.ctx.createAnalyser&&(this.analyser=this.ctx.createAnalyser(),this.analyser.fftSize=2048,this.analyser.connect(this.ctx.destination)),this.analyser}enqueue(e){if(e.runId!==this.runId||this.closed)return!1;let t=this.ctx.createBuffer(1,e.pcm.length,e.sampleRate);t.copyToChannel(e.pcm,0);let n=this.ctx.currentTime,r=Math.max(n,this.nextStart);if(this.enqueued>0){let e=(r-this.nextStart)*1e3;e>this.maxGapMs&&(this.maxGapMs=e)}let i=this.schedule(e,t,r);return this.nextStart=r+i.seconds,this.totalSeconds+=i.seconds,this.enqueued++,!0}schedule(e,t,n){let r=this.ctx.createBufferSource();r.buffer=t,r.connect(this.getAnalyser()??this.ctx.destination);let i={item:e,buffer:t,source:r,startAt:n,seconds:t.duration,started:!1,ended:!1};return r.onended=()=>{if(i.ended)return;i.ended=!0;let t=this.scheduled.indexOf(i);t>=0&&this.scheduled.splice(t,1),e.runId===this.runId&&(this.ended++,this.opts.onEnd?.({runId:e.runId,seq:e.seq,start:e.start,end:e.end,tag:e.tag,at:this.ctx.currentTime,seconds:i.seconds}),this.maybeDrain())},r.start(n),this.scheduled.push(i),this.ensureTicker(),this.tick(),i}ensureTicker(){this.ticker===null&&(this.ticker=setInterval(()=>this.tick(),r))}tick(){if(this.ctx.state===`suspended`)return;let e=this.ctx.currentTime;for(let t of this.scheduled)t.started||t.ended||t.item.runId!==this.runId||e+i>=t.startAt&&(t.started=!0,this.opts.onStart?.({runId:t.item.runId,seq:t.item.seq,start:t.item.start,end:t.item.end,tag:t.item.tag,at:t.startAt,seconds:t.seconds}));this.scheduled.length===0&&this.ticker!==null&&(clearInterval(this.ticker),this.ticker=null)}maybeDrain(){if(this.closed&&this.scheduled.length===0&&this.enqueued>0&&this.ended>=this.enqueued){let e=this.runId;this.closed=!1,this.opts.onDrain?.(e)}}playing(){let e=this.ctx.currentTime;for(let t of this.scheduled)if(!t.ended&&e+i>=t.startAt&&e<t.startAt+t.seconds)return t.item;return null}stop(){let e=typeof performance<`u`?performance.now():Date.now();for(let e of this.scheduled){e.ended=!0;try{e.source.stop()}catch{}}return this.scheduled=[],this.ticker!==null&&(clearInterval(this.ticker),this.ticker=null),this.nextStart=this.ctx.currentTime,this.runId++,this.closed=!1,this.inFlight=0,this.reserved=0,(typeof performance<`u`?performance.now():Date.now())-e}pause(){return this.ctx.suspend()}resume(){return this.ctx.resume()}skip(){let e=this.ctx.currentTime,t=this.scheduled.findIndex(t=>!t.ended&&e+i>=t.startAt&&e<t.startAt+t.seconds);if(t<0)return!1;let n=this.scheduled.slice(t+1),r=this.scheduled[t];for(let e of[r,...n]){e.ended=!0;try{e.source.stop()}catch{}}this.scheduled=this.scheduled.slice(0,t),this.ended++,this.opts.onEnd?.({runId:r.item.runId,seq:r.item.seq,start:r.item.start,end:r.item.end,tag:r.item.tag,at:e,seconds:r.seconds});let a=e;for(let e of n){let t=this.schedule(e.item,e.buffer,a);a+=t.seconds}return this.nextStart=a,this.maybeDrain(),!0}},o=.7,s=1.5,c=[`af_heart`,`af_bella`],l=`fruitbat.rate`,u=14,d=`fruitbat.voice`,f={target:e().web.voice.tts_phoneme_target,limit:e().web.voice.tts_phoneme_limit};function p(){let e=typeof navigator<`u`?navigator.userAgent:``,t=t=>{let n=t.exec(e);return n?Number(n[1]):null},n=`other`,r=null;/Edg\//.test(e)?(n=`edge`,r=t(/Edg\/(\d+)/)):/Firefox\//.test(e)?(n=`firefox`,r=t(/Firefox\/(\d+)/)):/Chrome\//.test(e)?(n=`chrome`,r=t(/Chrome\/(\d+)/)):/Safari\//.test(e)&&/Version\//.test(e)&&(n=`safari`,r=t(/Version\/(\d+)/));let i=`other`,a=null;return/iPhone|iPad/.test(e)?(i=`ios`,a=t(/OS (\d+)_/)):/Android/.test(e)?(i=`android`,a=t(/Android (\d+)/)):/Mac OS X/.test(e)?(i=`macos`,a=t(/Mac OS X (\d+)/)):/Windows NT/.test(e)?(i=`windows`,a=t(/Windows NT (\d+)/)):/Linux/.test(e)&&(i=`linux`,a=null),{browser:n,browser_major:r,os:i,os_major:a}}function m(e){try{return localStorage.getItem(e)}catch{return null}}function h(e,t){try{localStorage.setItem(e,t)}catch{}}var g=class{worker=null;ctx=null;noticeNextStart=0;queue=null;runId=0;messageSeq=0;waiters=new Map;loaded=null;messageSources=[];lastStats=null;progressListeners=new Set;phase=`idle`;error=null;current=null;next=null;rate;voice;downloadedBytes=0;coldPending=!1;runCold=!1;takeCold(){this.coldPending&&=(this.runCold=!0,!1)}cacheState(){return this.loaded?this.runCold?`cold`:`warm`:`unknown`}device;loadedInfo=null;loadedDevice=`wasm`;loadedDtype=`q8`;noticeCache=new Map;prewarmed=!1;lastNoticeLatencyMs=null;constructor(){let e=Number(m(l));this.rate=Number.isFinite(e)&&e>=.7&&e<=1.5?e:1;let t=m(d);this.voice=c.includes(t??``)?t:`af_heart`;let n=typeof location<`u`?new URLSearchParams(location.search).get(`tts`):null;this.device=n===`webgpu`?`webgpu`:`wasm`}get isLoaded(){return this.loadedInfo!==null}getRate(){return this.rate}setRate(e){let t=Math.min(s,Math.max(o,Number(e)||1));return this.rate=Math.round(t*100)/100,h(l,String(this.rate)),this.rate}getVoice(){return this.voice}setVoice(e){return c.includes(e)&&(this.voice=e,h(d,e)),this.voice}onProgress(e){return this.progressListeners.add(e),()=>this.progressListeners.delete(e)}ensureContext(){return this.ctx||(this.ctx=new AudioContext({sampleRate:24e3}),this.queue=new a(this.ctx,{maxAheadSeconds:30,maxInFlight:3,onStart:e=>this.handleStart(e),onEnd:e=>this.handleEnd(e),onDrain:e=>this.handleDrain(e)})),this.paused||this.ctx.resume(),this.ctx}get context(){return this.ctx}getAnalyser(){return this.queue?.getAnalyser()??null}getWorker(){return this.worker||(this.worker=new Worker(new URL(`/assets/tts.worker-Bmv1fL59.js`,``+import.meta.url),{type:`module`}),this.worker.onmessage=e=>this.handleMessage(e.data),this.worker.onerror=e=>{this.error=`worker: ${e.message}`;for(let e of this.waiters.values())e.reject(Error(this.error));this.waiters.clear()}),this.worker}send(e){this.getWorker().postMessage(e)}wait(e){return new Promise((t,n)=>this.waiters.set(e,{resolve:t,reject:n}))}handleMessage(e){if(e.type===`progress`){for(let t of this.progressListeners)t(e.file,e.loaded,e.total);return}if(e.type===`loaded`){this.downloadedBytes=e.downloadedBytes,this.coldPending=e.downloadedBytes>1e6,this.loadedDevice=e.device,this.loadedDtype=e.dtype,this.loadedInfo=e,this.waiters.get(`loaded`)?.resolve(e),this.waiters.delete(`loaded`);return}if(e.type===`planned`){let t=`planned:${e.runId}`;this.waiters.get(t)?.resolve(e),this.waiters.delete(t);return}if((e.type===`error`||e.type===`overlimit`)&&e.seq===-1){let t=e.type===`error`?Error(`${e.name}: ${e.message}`):Error(`tts_overlimit: ${e.phonemes} > ${e.limit}`),n=e.runId===-1&&this.waiters.has(`loaded`)?`loaded`:`planned:${e.runId}`,r=this.waiters.get(n);if(!r)return;this.waiters.delete(n),r.reject(t);return}let t=`${e.runId}:${e.seq}`,n=this.waiters.get(t);n&&(this.waiters.delete(t),n.resolve(e))}settleWaiters(e,t){let n=Error(t);n.name=`AbortError`;for(let[t,r]of this.waiters)(t===`planned:${e}`||t.startsWith(`${e}:`))&&(this.waiters.delete(t),r.reject(n))}load(){if(!this.loaded){this.phase=`loading`;let e=this.wait(`loaded`).then(e=>(this.phase===`loading`&&(this.phase=`idle`),e));this.send({type:`load`,device:this.device}),this.loaded=e,e.catch(()=>{this.loaded=null,this.phase=`failed`})}return this.loaded}async plan(e){let t=-++this.messageSeq,n=this.wait(`planned:${t}`);this.send({type:`plan`,runId:t,text:e,limits:f});let r=await n;return{segments:r.segments,maxPhonemes:r.maxPhonemes,splitMs:r.splitMs}}pendingDone=null;readSeq=0;lastStop=null;runTtfa=null;runT0=0;runSynthMs=0;runOverlimit=0;secPerChar=1/u;estimateSeconds(e,t){return Math.max(0,e.end-e.start)*this.secPerChar/Math.max(t,.1)}async readAll(e,t={}){this.releasePause(),this.ensureContext();let n=this.runId,r=++this.readSeq;try{await this.load()}catch(e){return this.phase=`failed`,this.error=e instanceof Error?`${e.name}: ${e.message}`:String(e),this.result(n,0,0,!1)}if(this.runId!==n||r!==this.readSeq)return this.result(n,0,0,!1);let i=++this.runId;this.runCold=!1,this.takeCold();let a=this.pendingDone;this.pendingDone=null,a&&(this.replacedMetrics=this.metricsNow(n)),a?.resolve(!1),this.send({type:`cancel`,runId:n}),this.settleWaiters(n,`stopped`);let o=this.queue;o.beginRun(i),this.phase=`planning`,this.error=null,this.current=null,this.next=null,this.runTtfa=null,this.runSynthMs=0,this.runOverlimit=0,this.runT0=performance.now();let s=t.voice??this.voice,c=t.onStart,l=t.onEnd;this.userOnStart=c??null,this.userOnEnd=l??null;let u=this.wait(`planned:${i}`);this.send({type:`plan`,runId:i,text:e,limits:f});let d;try{d=await u}catch(e){return i===this.runId&&(this.phase=`failed`,this.error=e instanceof Error?`${e.name}: ${e.message}`:String(e)),this.result(i,0,0,!1)}if(i!==this.runId)return this.result(i,d.segments.length,0,!1);let p=d.segments;t.onPlanned?.(p);let m=_(e,p);this.phase=`reading`,this.runSegments=p,this.next=p[0]??null;let h,g=new Promise(e=>h=e);this.pendingDone={resolve:h},p.length===0&&(o.close(),this.phase=`done`,h(!0));let v=0,y=null,b=new Map;(async()=>{for(;v<p.length&&i===this.runId&&y===null;){let e=p[v],n=t.rate??this.rate,r=this.estimateSeconds(e,n);if(!o.canAccept(r)){await new Promise(e=>setTimeout(e,50));continue}v++;let a=o.requestSent(r),c=this.synthOne(i,e,s,n,o).catch(e=>{y===null&&(y=e)}).finally(()=>{o.requestSettled(a),b.delete(e.seq)});b.set(e.seq,c)}if(await Promise.all([...b.values()]),y!==null)throw y;i===this.runId&&o.close()})().catch(e=>{i===this.runId&&(this.error=e instanceof Error?`${e.name}: ${e.message}`:String(e),this.phase=`failed`,o.stop(),this.send({type:`cancel`,runId:i}),this.settleWaiters(i,`failed`),this.current=null,this.next=null,this.pendingDone?.resolve(!1),this.pendingDone=null)});let x=await g;return this.result(i,p.length,m,x,o.totalSeconds)}userOnStart=null;userOnEnd=null;async synthOne(e,t,n,r,i,a){let o=`${e}:${t.seq}`,s=this.wait(o);this.send({type:`synth`,runId:e,seq:t.seq,phonemes:t.phonemes,start:t.start,end:t.end,voice:n,speed:r,limit:f.limit,tag:a});let c;try{c=await s}catch(t){if(e!==this.runId)return;throw t}if(e===this.runId){if(c.type===`pcm`){this.runSynthMs+=c.synthMs;let t=c.end-c.start;t>0&&(this.secPerChar=Math.max(this.secPerChar,c.pcm.length/c.sampleRate*r/t)),i.enqueue({runId:e,seq:c.seq,pcm:c.pcm,sampleRate:c.sampleRate,start:c.start,end:c.end,tag:c.tag});return}if(c.type===`overlimit`)throw this.runOverlimit++,Error(`tts_overlimit: ${c.phonemes} > ${c.limit}`);if(c.type===`error`)throw Error(`${c.name}: ${c.message}`)}}runSegments=[];handleStart(e){e.runId===this.runId&&(e.seq<0||(this.runTtfa===null&&(this.runTtfa=performance.now()-this.runT0),this.current={seq:e.seq,start:e.start,end:e.end,at:e.at,seconds:e.seconds,tag:e.tag},this.next=this.runSegments[e.seq+1]??null,this.userOnStart?.(this.current)))}handleEnd(e){e.runId===this.runId&&(e.seq<0||(this.userOnEnd?.({seq:e.seq,start:e.start,end:e.end,at:e.at,seconds:e.seconds,tag:e.tag}),this.current?.seq===e.seq&&(this.current=null)))}handleDrain(e){e===this.runId&&(this.phase=`done`,this.next=null,this.pendingDone?.resolve(!0),this.pendingDone=null)}metrics(e){let t=this.runSynthMs/1e3;return{cache_state:this.cacheState(),ttfa_ms:this.runTtfa===null?null:Math.round(this.runTtfa),rtf:t>0?Math.round(e/t*100)/100:null,gap_ms:Math.round(this.queue?.maxGapMs??0),seconds:Math.round(e*100)/100,synth_ms:Math.round(this.runSynthMs),tts_overlimit:this.runOverlimit,device:this.loadedDevice,dtype:this.loadedDtype}}metricsNow(e){return{runId:e,ttfa:this.runTtfa,synthMs:this.runSynthMs,overlimit:this.runOverlimit,gapMs:this.queue?.maxGapMs??0,seconds:this.queue?.totalSeconds??0}}replacedMetrics=null;result(e,t,n,r,i=0){let a=this.replacedMetrics?.runId===e?this.replacedMetrics:null,o=a??this.metricsNow(e),s=a?a.seconds:i,c=o.synthMs/1e3,l=this.buildRow({ttfa_ms:o.ttfa===null?null:Math.round(o.ttfa),rtf:c>0?Math.round(s/c*100)/100:null,gap_ms:Math.round(o.gapMs),stop_ms:this.lastStop?.runId===e?this.lastStop.ms:null,coverage:n,tts_overlimit:o.overlimit});return this.lastStats=l,{runId:e,segments:t,coverage:n,ttsOverlimit:o.overlimit,seconds:s,finished:r}}buildRow(t){let n=e().web.voice,r=p(),i=performance.memory;return{schema_version:1,target:`web`,device:this.loadedDevice,level:`readall`,browser:r.browser,browser_major:r.browser_major,os:r.os,os_major:r.os_major,cache_state:this.cacheState(),model_id:n.id,model_rev:n.revision,dtype:this.loadedDtype,doc_id:null,commit:null,date:new Date().toISOString(),machine_id:`web`,ttfa_ms:null,gen_ms:null,tok_s:null,rtf:null,gap_ms:null,stop_ms:null,coverage:null,bullets_total:null,bullets_cut:null,cut_rate:null,facts_token_hit:null,halluc_flags:null,forbidden_hits:null,oneline_keyword_hit:null,tts_overlimit:0,peak_mb:null,heap_mb:i?Math.round(i.usedJSHeapSize/1e6):null,...t}}streamChain=Promise.resolve();streamSeq=0;streaming=!1;beginStream(e={}){this.ensureContext();let t=++this.runId;return this.queue.beginRun(t),this.phase=`reading`,this.error=null,this.current=null,this.next=null,this.runTtfa=null,this.runSynthMs=0,this.runOverlimit=0,this.runT0=performance.now(),this.userOnStart=e.onStart??null,this.userOnEnd=e.onEnd??null,this.streamSeq=0,this.streamChain=Promise.resolve(),this.streaming=!0,this.runCold=!1,this.takeCold(),this.pendingDone=null,t}streamPending=0;pushText(e,t,n,r,i){this.streamPending++;let a=this.streamChain.then(async()=>{if(e!==this.runId||this.phase===`failed`||(await this.load(),e!==this.runId))return;this.takeCold();let a=-++this.messageSeq,o=this.wait(`planned:${a}`);this.send({type:`plan`,runId:a,text:t,limits:f,firstPieceTarget:0});let s;try{s=await o}catch(t){if(e!==this.runId)return;throw t}let c=this.queue;for(let t of s.segments){let a=this.rate,o=t.text.length*this.secPerChar/Math.max(a,.1);for(;e===this.runId&&!c.canAccept(o);)await new Promise(e=>setTimeout(e,50));if(e!==this.runId)return;let s=this.streamSeq++,l=c.requestSent(o);try{await this.synthOne(e,{seq:s,text:t.text,start:n,end:r,phonemes:t.phonemes},this.voice,a,c,i)}finally{c.requestSettled(l)}}});return a.then(()=>this.streamPending--,()=>this.streamPending--),this.streamChain=a.catch(t=>{e===this.runId&&(this.phase=`failed`,this.error=t instanceof Error?`${t.name}: ${t.message}`:String(t),this.queue?.stop(),this.send({type:`cancel`,runId:e}),this.settleWaiters(e,`failed`),this.current=null,this.next=null,this.pendingDone?.resolve(!1),this.pendingDone=null)}),a}async endStream(e){let t;do t=this.streamChain,await t;while(t!==this.streamChain);e===this.runId&&(this.streaming=!1);let n=this.queue;if(e!==this.runId||this.phase===`failed`)return{finished:!1,metrics:this.metrics(n.totalSeconds)};if(n.enqueued===0)return this.phase=`done`,{finished:!0,metrics:this.metrics(0)};let r=new Promise(e=>this.pendingDone={resolve:e});return n.close(),{finished:await r,metrics:this.metrics(n.totalSeconds)}}noticeKey(e){return`${e}|${this.voice}|${this.rate}`}async prewarm(e){await this.load();for(let t of e){let e=this.noticeKey(t);if(!this.noticeCache.has(e))try{await this.synthMessage(t,e)}catch{}}this.prewarmed=e.every(e=>this.noticeCache.has(this.noticeKey(e)))}async synthMessage(e,t){let r=n(e),i=++this.messageSeq,a=-i,o=this.messageEpoch,s=this.wait(`${a}:${i}`);this.pendingMessages.add(i),this.send({type:`speak`,runId:a,seq:i,text:r,voice:this.voice,speed:this.rate,limits:f});let c;try{c=await s}catch(e){if(o!==this.messageEpoch)return null;throw e}finally{this.pendingMessages.delete(i)}if(o!==this.messageEpoch)return null;if(c.type!==`pcm`)throw Error(c.type===`error`?`${c.name}: ${c.message}`:`tts_overlimit`);let l={pcm:c.pcm,sampleRate:c.sampleRate};return this.noticeCache.set(t,l),l}pendingMessages=new Set;messageEpoch=0;stop(){this.releasePause(),this.noticeNextStart=0,this.streaming=!1;let e=performance.now(),t=this.runId;this.runId++,this.send({type:`cancel`,runId:t}),this.queue?.stop(),this.settleWaiters(t,`stopped`),this.messageEpoch++;for(let e of this.pendingMessages)this.send({type:`cancel`,runId:-e}),this.settleWaiters(-e,`stopped`);this.pendingMessages.clear();for(let e of this.messageSources.splice(0))try{e.stop()}catch{}this.phase=`stopped`,this.current=null,this.next=null;let n=performance.now()-e;return this.lastStop={runId:t,ms:Math.round(n*100)/100},this.lastStats&&={...this.lastStats,stop_ms:Math.round(n*100)/100},this.pendingDone?.resolve(!1),this.pendingDone=null,n}paused=!1;resumeWaiters=[];releasePause(){this.paused=!1;for(let e of this.resumeWaiters.splice(0))e()}pause(){this.paused=!0,this.queue?.pause()}resume(){this.releasePause(),this.queue?.resume()}skip(){return this.queue?.skip()??!1}async speak(e,t){let n=t??performance.now(),r=this.ensureContext(),i=this.noticeKey(e),a=this.messageEpoch,o=this.noticeCache.get(i)??null;if(!o&&(await this.load(),a!==this.messageEpoch||(o=await this.synthMessage(e,i),!o))||a!==this.messageEpoch||this.paused&&(await new Promise(e=>this.resumeWaiters.push(e)),a!==this.messageEpoch))return{seconds:0};let s=this.queue;if(this.streaming&&s&&s.currentRunId===this.runId){let e=this.runId,{pcm:t,sampleRate:n}=o,r=!1;if(this.streamChain=this.streamChain.then(()=>{e===this.runId&&this.streaming&&(r=s.enqueue({runId:e,seq:-1,pcm:t,sampleRate:n,start:-1,end:-1}))}),await this.streamChain,r)return{seconds:t.length/n};if(a!==this.messageEpoch)return{seconds:0}}let c=r.createBuffer(1,o.pcm.length,o.sampleRate);c.copyToChannel(o.pcm,0);let l=r.createBufferSource();l.buffer=c,l.connect(this.getAnalyser()??r.destination),this.messageSources.push(l);let u=new Promise(e=>{l.onended=()=>{let t=this.messageSources.indexOf(l);t>=0&&this.messageSources.splice(t,1),e()};let t=r.currentTime;setTimeout(()=>{r.currentTime===t&&e()},Math.ceil(c.duration*1e3)+500)}),d=Math.max(r.currentTime,this.noticeNextStart);return l.start(d),this.noticeNextStart=d+c.duration,this.lastNoticeLatencyMs=Math.round((performance.now()-n)*100)/100,await u,{seconds:c.duration}}async measure(e,t,n){await this.load();let r=-++this.messageSeq,i=this.wait(`planned:${r}`);this.send({type:`plan`,runId:r,text:e,limits:{target:t,limit:f.limit},firstPieceTarget:0});let a=await i,o=0,s=0;for(let e of a.segments){let t=`${r}:${e.seq}`,i=this.wait(t);this.send({type:`synth`,runId:r,seq:e.seq,phonemes:e.phonemes,start:e.start,end:e.end,voice:this.voice,speed:n??this.rate,limit:f.limit});let a=await i;if(a.type!==`pcm`)throw Error(a.type===`error`?`${a.name}: ${a.message}`:`tts_overlimit`);o+=a.pcm.length/a.sampleRate,s+=a.synthMs}return{seconds:o,pieces:a.segments.length,synthMs:s,maxPhonemes:a.maxPhonemes}}state(){return{phase:this.phase,error:this.error,current:this.current,next:this.next,rate:this.rate,voice:this.voice,ctxState:this.ctx?.state??`none`,aheadSeconds:this.queue?.aheadSeconds()??0,inFlight:this.queue?.requestsInFlight??0,pending:this.streamPending,playing:this.queue?.playing()??null,enqueued:this.queue?.enqueued??0,ended:this.queue?.ended??0}}stats(){return this.lastStats}};function _(e,t){if(t.length===0)return+(e.trim().length===0);let n=0,r=!0;for(let i of t)i.start<n&&(r=!1),e.slice(n,i.start).trim().length>0&&(r=!1),n=i.end;if(e.slice(n).trim().length>0&&(r=!1),r)return 1;let i=new Uint8Array(e.length);for(let n of t)i.fill(1,Math.max(0,n.start),Math.min(e.length,n.end));let a=0,o=0;for(let t=0;t<e.length;t++)/\s/.test(e[t])||(a++,i[t]&&o++);return Math.min(a===0?1:o/a,.999)}var v=null;function y(){return v||=new g,v}export{n as a,y as i,o as n,c as r,s as t};
|
|
|
|
|
|
assets/tts-DDfrpA1Y.js
ADDED
|
@@ -0,0 +1 @@
|
|
|
|
|
|
|
| 1 |
+
import{r as e}from"./pins-DVBrHC3g.js";var t={$comment:`Every user-facing string, both targets (docs/PLAN.md rule 8). S0-03 owns the KEYS; Values written in S1-L0 (Claude, Voice Bank protocol, 2026-09-24). Every message is spoken, so key names are spelled out (Control Option V, Command C), never symbols. Web and Mac load this file; no string literal lives in UI code (scripts/strings-check.mjs). Every notice/error is also spoken (rule 8, 'Speak messages' default on). Placeholders {n} {mb} {words} {level} are filled at runtime.`,version:1,locale:`en`,$plan_wording:{"notice.dial_shorter":`Making it shorter.`,"notice.dial_longer":`Adding detail.`,"notice.all_cut":`Couldn't make a summary I trust for this part.`,"notice.oneline_failed":`Couldn't boil this down to one line I trust. Here's the short version.`,"notice.input_limit":`This is over 120,000 words. Select a part of it.`,"mac.intake.press_cmd_c":`Press ⌘C to read it (spoken form: Press Command C to read it.)`,"mac.intake.no_copy_seen":`Didn't see a copy.`,"loading.summarizer_button":`Load summarizer ({mb} MB)`,"dial.readall":`Read all`,"dial.short":`Short`,"dial.caveman":`Caveman`,"dial.oneline":`One line`,$comment:`Wording the plan fixes (rules 2, 11, C3, C9, Architecture). S1-L0 keeps the meaning; it may tune words after the Voice Bank pass.`},strings:{"app.title":`Fruitbat`,"theme.toggle":`Dark mode`,"dial.readall":`Read all`,"dial.short":`Short`,"dial.caveman":`Caveman`,"dial.oneline":`One line`,"panel.title":`The short version`,"panel.empty":`Highlight some text or paste it below. Then pick how short you want it.`,"panel.read_chip":`Read`,"panel.summarize":`Read it`,"panel.stop":`Stop`,"panel.pause":`Pause`,"panel.resume":`Resume`,"panel.skip":`Skip`,"panel.read_this_part":`Read this part`,"panel.rate":`Speed`,"panel.rate_slower":`Slower`,"panel.rate_faster":`Faster`,"panel.voice":`Voice`,"panel.speak_messages":`Speak messages`,"panel.hide_pip":`Hide Pip`,"panel.show_pip":`Show Pip`,"panel.font_size":`Text size`,"panel.font_size_small":`Small`,"panel.font_size_medium":`Medium`,"panel.font_size_large":`Large`,"panel.spacing":`Spacing`,"panel.spacing_compact":`Compact`,"panel.spacing_cozy":`Normal`,"panel.spacing_roomy":`Roomy`,"panel.dark_mode":`Dark mode`,"panel.position":`Panel position`,"panel.bug_report":`Report a problem`,"panel.stats":`Stats`,"panel.close":`Close`,"panel.now_reading":`Now reading`,"panel.next_up":`Next`,"intake.paste_placeholder":`Paste text here`,"intake.word_count":`{n} words`,"intake.drop_here":`Drop a text or PDF file here`,"intake.empty":`Nothing to read yet. Highlight some text or paste it here.`,"intake.sample_label":`Sample article`,"demo.try_it_now":`Try it now`,"demo.recording_label":`This one is a recording. Your own text runs on your machine.`,"demo.switch_level":`Turn the dial to hear the same article shorter or longer.`,"demo.excerpt_note":`This is the first part of the article, not the whole thing.`,"loading.probing":`Checking what this browser can do.`,"loading.voice":`Getting the voice ready.`,"loading.summarizer_button":`Load summarizer ({mb} MB)`,"loading.summarizer_size":`The summarizer is a {mb} MB download. It happens once and stays on this device.`,"loading.progress":`{mb} MB so far.`,"loading.cached":`Already on this device. No download needed.`,"loading.first_time":`First time here. The models download once and stay on this device.`,"loading.save_data":`Your browser is set to save data, so nothing big downloads until you ask.`,"loading.mobile":`On a phone the voice works and the sample is a recording. Open this on a laptop for the full thing.`,"loading.almost":`Almost there.`,"loading.ready":`Ready.`,"notice.dial_shorter":`Making it shorter.`,"notice.dial_longer":`Adding detail.`,"notice.all_cut":`Couldn't make a summary I trust for this part.`,"notice.oneline_failed":`Couldn't boil this down to one line I trust. Here's the short version.`,"notice.input_limit":`This is over 120,000 words. Select a part of it.`,"notice.no_webgpu":`This browser can't run the summarizer. Read all still works, and the sample is a recording.`,"notice.probe_failed":`The summarizer didn't start on this machine. Read all still works.`,"notice.low_end_tier":`Using a smaller summarizer so it fits this machine.`,"notice.stopped":`Stopped.`,"notice.done":`That's the end.`,"notice.paused":`Paused.`,"notice.making_summary":`Making the short version.`,"notice.reading_all":`Reading all of it.`,"error.model_download":`The download didn't finish. Check your connection and try again.`,"error.voice":`The voice didn't load. Try again in a moment.`,"error.generation":`Something went wrong making the summary. Read all still works.`,"error.storage_full":`This browser is out of storage, so stats won't be saved.`,"error.empty_input":`There's no text to read yet.`,"error.offline":`You're offline. Anything already downloaded still works.`,"error.unknown":`Something went wrong. Try again.`,"report.title":`Report a problem`,"report.preview_intro":`Here is everything the report contains. Nothing you were reading is in it.`,"report.describe":`What happened?`,"report.open_github":`Open on GitHub`,"report.copy":`Copy report`,"report.copied":`Copied.`,"report.copy_failed":`Couldn't copy it. The report above is selected so you can copy it by hand.`,"report.privacy_note":`The report has numbers and settings only. Never your text, your audio or your file names.`,"panel.voice.af_heart":`Heart`,"panel.voice.af_bella":`Bella`,"stats.title":`Stats`,"stats.empty":`No runs yet.`,"stats.export":`Export CSV`,"stats.clear":`Clear stats`,"stats.col.date":`When`,"stats.col.level":`Level`,"stats.col.device":`Device`,"stats.col.dtype":`Precision`,"stats.col.cache_state":`Cache`,"stats.col.doc_id":`Text`,"stats.col.ttfa_ms":`First audio (ms)`,"stats.col.tok_s":`Tokens per second`,"stats.col.rtf":`Voice speed (x real time)`,"stats.col.bullets_total":`Bullets`,"stats.col.bullets_cut":`Bullets cut`,"a11y.panel_region":`Fruitbat panel`,"a11y.bullet_list":`Summary`,"a11y.dial":`How short`,"a11y.pip":`Pip the fruit bat`,"mac.menu.summarize_selection":`Read the selection`,"mac.menu.summarize_clipboard":`Read the clipboard`,"mac.menu.summarize_region":`Read part of the screen`,"mac.menu.settings":`Settings`,"mac.menu.stats":`Stats`,"mac.menu.check_updates":`Check for updates`,"mac.menu.quit":`Quit Fruitbat`,"mac.onboarding.try_it":`Copy any text, then press Control Option V.`,"mac.onboarding.first_success":`Worked. Now try it on anything you highlight.`,"mac.onboarding.offer_accessibility":`Want to skip the copy step? Give Fruitbat the Accessibility permission and it reads what you highlight.`,"mac.onboarding.updates_disclosure":`Fruitbat checks for updates once a day. You can turn that off in Settings.`,"mac.onboarding.done":`You're set. Fruitbat lives in the menu bar.`,"mac.permission.accessibility":`Fruitbat needs the Accessibility permission to read what you highlight. Without it, copy the text first and press Control Option V.`,"mac.permission.accessibility_denied":`No Accessibility permission. Copy the text and press Control Option V instead.`,"mac.permission.screen_recording":`Fruitbat needs Screen Recording to read part of the screen. Without it, the other two ways still work.`,"mac.permission.screen_recording_denied":`No Screen Recording permission. Highlight text or copy it instead.`,"mac.permission.open_settings":`Open System Settings`,"mac.intake.press_cmd_c":`Press Command C to read it.`,"mac.intake.no_copy_seen":`Didn't see a copy.`,"mac.intake.clipboard_empty":`The clipboard is empty.`,"mac.intake.clipboard_not_text":`The clipboard doesn't have text in it.`,"mac.ocr.first_run_warning":`Anything on screen becomes text on this Mac, passwords included. It stays here.`,"mac.ocr.nothing_found":`Couldn't find any text there.`,"mac.ocr.pick_region":`Drag over the part you want read.`,"mac.update.toggle":`Check for updates`,"mac.update.available":`A new version is ready.`,"mac.update.up_to_date":`You're up to date.`,"mac.license.trial_days_left":`{n} days left in the trial.`,"mac.license.enter_key":`Enter your license key`,"mac.license.licensed":`Licensed. Thank you.`,"mac.license.nag":`Couldn't check the license in a while. Fruitbat keeps working.`,"mac.license.sign_out":`Sign out of this Mac`,"mac.license.invalid":`That key didn't work. Check it and try again.`,"intake.read_button":`Read this`}}.strings;function n(e){return t[e]??e}var r=25,i=.005,a=class{maxAheadSeconds;maxInFlight;ctx;opts;runId=0;nextStart=0;scheduled=[];inFlight=0;analyser=null;maxGapMs=0;totalSeconds=0;enqueued=0;ended=0;closed=!1;ticker=null;constructor(e,t={}){this.ctx=e,this.opts=t,this.maxAheadSeconds=t.maxAheadSeconds??30,this.maxInFlight=t.maxInFlight??3}get currentRunId(){return this.runId}beginRun(e){this.stop(),this.runId=e,this.nextStart=this.ctx.currentTime,this.maxGapMs=0,this.totalSeconds=0,this.enqueued=0,this.ended=0,this.closed=!1}close(){this.closed=!0,this.maybeDrain()}requestSent(e=0){return this.inFlight++,this.reserved+=e,{run:this.runId,seconds:e}}requestSettled(e={run:this.runId,seconds:0}){e.run===this.runId&&(this.inFlight=Math.max(0,this.inFlight-1),this.reserved=Math.max(0,this.reserved-e.seconds))}reserved=0;get requestsInFlight(){return this.inFlight}aheadSeconds(){return Math.max(0,this.nextStart-this.ctx.currentTime)}canAccept(e=0){if(this.inFlight>=this.maxInFlight)return!1;let t=this.aheadSeconds()+this.reserved;return t+e<=this.maxAheadSeconds&&t<this.maxAheadSeconds||this.inFlight===0&&t<=Math.min(5,this.maxAheadSeconds/2)}getAnalyser(){return!this.analyser&&this.ctx.createAnalyser&&(this.analyser=this.ctx.createAnalyser(),this.analyser.fftSize=2048,this.analyser.connect(this.ctx.destination)),this.analyser}enqueue(e){if(e.runId!==this.runId||this.closed)return!1;let t=this.ctx.createBuffer(1,e.pcm.length,e.sampleRate);t.copyToChannel(e.pcm,0);let n=this.ctx.currentTime,r=Math.max(n,this.nextStart);if(this.enqueued>0){let e=(r-this.nextStart)*1e3;e>this.maxGapMs&&(this.maxGapMs=e)}let i=this.schedule(e,t,r);return this.nextStart=r+i.seconds,this.totalSeconds+=i.seconds,this.enqueued++,!0}schedule(e,t,n){let r=this.ctx.createBufferSource();r.buffer=t,r.connect(this.getAnalyser()??this.ctx.destination);let i={item:e,buffer:t,source:r,startAt:n,seconds:t.duration,started:!1,ended:!1};return r.onended=()=>{if(i.ended)return;i.ended=!0;let t=this.scheduled.indexOf(i);t>=0&&this.scheduled.splice(t,1),e.runId===this.runId&&(this.ended++,this.opts.onEnd?.({runId:e.runId,seq:e.seq,start:e.start,end:e.end,tag:e.tag,at:this.ctx.currentTime,seconds:i.seconds}),this.maybeDrain())},r.start(n),this.scheduled.push(i),this.ensureTicker(),this.tick(),i}ensureTicker(){this.ticker===null&&(this.ticker=setInterval(()=>this.tick(),r))}tick(){if(this.ctx.state===`suspended`)return;let e=this.ctx.currentTime;for(let t of this.scheduled)t.started||t.ended||t.item.runId!==this.runId||e+i>=t.startAt&&(t.started=!0,this.opts.onStart?.({runId:t.item.runId,seq:t.item.seq,start:t.item.start,end:t.item.end,tag:t.item.tag,at:t.startAt,seconds:t.seconds}));this.scheduled.length===0&&this.ticker!==null&&(clearInterval(this.ticker),this.ticker=null)}maybeDrain(){if(this.closed&&this.scheduled.length===0&&this.enqueued>0&&this.ended>=this.enqueued){let e=this.runId;this.closed=!1,this.opts.onDrain?.(e)}}playing(){let e=this.ctx.currentTime;for(let t of this.scheduled)if(!t.ended&&e+i>=t.startAt&&e<t.startAt+t.seconds)return t.item;return null}stop(){let e=typeof performance<`u`?performance.now():Date.now();for(let e of this.scheduled){e.ended=!0;try{e.source.stop()}catch{}}return this.scheduled=[],this.ticker!==null&&(clearInterval(this.ticker),this.ticker=null),this.nextStart=this.ctx.currentTime,this.runId++,this.closed=!1,this.inFlight=0,this.reserved=0,(typeof performance<`u`?performance.now():Date.now())-e}pause(){return this.ctx.suspend()}resume(){return this.ctx.resume()}skip(){let e=this.ctx.currentTime,t=this.scheduled.findIndex(t=>!t.ended&&e+i>=t.startAt&&e<t.startAt+t.seconds);if(t<0)return!1;let n=this.scheduled.slice(t+1),r=this.scheduled[t];for(let e of[r,...n]){e.ended=!0;try{e.source.stop()}catch{}}this.scheduled=this.scheduled.slice(0,t),this.ended++,this.opts.onEnd?.({runId:r.item.runId,seq:r.item.seq,start:r.item.start,end:r.item.end,tag:r.item.tag,at:e,seconds:r.seconds});let a=e;for(let e of n){let t=this.schedule(e.item,e.buffer,a);a+=t.seconds}return this.nextStart=a,this.maybeDrain(),!0}},o=.7,s=1.5,c=[`af_heart`,`af_bella`],l=`fruitbat.rate`,u=14,d=`fruitbat.voice`,f={target:e().web.voice.tts_phoneme_target,limit:e().web.voice.tts_phoneme_limit};function p(){let e=typeof navigator<`u`?navigator.userAgent:``,t=t=>{let n=t.exec(e);return n?Number(n[1]):null},n=`other`,r=null;/Edg\//.test(e)?(n=`edge`,r=t(/Edg\/(\d+)/)):/Firefox\//.test(e)?(n=`firefox`,r=t(/Firefox\/(\d+)/)):/Chrome\//.test(e)?(n=`chrome`,r=t(/Chrome\/(\d+)/)):/Safari\//.test(e)&&/Version\//.test(e)&&(n=`safari`,r=t(/Version\/(\d+)/));let i=`other`,a=null;return/iPhone|iPad/.test(e)?(i=`ios`,a=t(/OS (\d+)_/)):/Android/.test(e)?(i=`android`,a=t(/Android (\d+)/)):/Mac OS X/.test(e)?(i=`macos`,a=t(/Mac OS X (\d+)/)):/Windows NT/.test(e)?(i=`windows`,a=t(/Windows NT (\d+)/)):/Linux/.test(e)&&(i=`linux`,a=null),{browser:n,browser_major:r,os:i,os_major:a}}function m(e){try{return localStorage.getItem(e)}catch{return null}}function h(e,t){try{localStorage.setItem(e,t)}catch{}}var g=class{worker=null;ctx=null;noticeNextStart=0;queue=null;runId=0;messageSeq=0;waiters=new Map;loaded=null;messageSources=[];lastStats=null;progressListeners=new Set;phase=`idle`;error=null;current=null;next=null;rate;voice;downloadedBytes=0;coldPending=!1;runCold=!1;takeCold(){this.coldPending&&=(this.runCold=!0,!1)}cacheState(){return this.loaded?this.runCold?`cold`:`warm`:`unknown`}device;loadedInfo=null;loadedDevice=`wasm`;loadedDtype=`q8`;noticeCache=new Map;prewarmed=!1;lastNoticeLatencyMs=null;constructor(){let e=Number(m(l));this.rate=Number.isFinite(e)&&e>=.7&&e<=1.5?e:1;let t=m(d);this.voice=c.includes(t??``)?t:`af_heart`;let n=typeof location<`u`?new URLSearchParams(location.search).get(`tts`):null;this.device=n===`webgpu`?`webgpu`:`wasm`}get isLoaded(){return this.loadedInfo!==null}getRate(){return this.rate}setRate(e){let t=Math.min(s,Math.max(o,Number(e)||1));return this.rate=Math.round(t*100)/100,h(l,String(this.rate)),this.rate}getVoice(){return this.voice}setVoice(e){return c.includes(e)&&(this.voice=e,h(d,e)),this.voice}onProgress(e){return this.progressListeners.add(e),()=>this.progressListeners.delete(e)}ensureContext(){return this.ctx||(this.ctx=new AudioContext({sampleRate:24e3}),this.queue=new a(this.ctx,{maxAheadSeconds:30,maxInFlight:3,onStart:e=>this.handleStart(e),onEnd:e=>this.handleEnd(e),onDrain:e=>this.handleDrain(e)})),this.paused||this.ctx.resume(),this.ctx}get context(){return this.ctx}getAnalyser(){return this.queue?.getAnalyser()??null}getWorker(){return this.worker||(this.worker=new Worker(new URL(`/assets/tts.worker-Bmv1fL59.js`,``+import.meta.url),{type:`module`}),this.worker.onmessage=e=>this.handleMessage(e.data),this.worker.onerror=e=>{this.error=`worker: ${e.message}`;for(let e of this.waiters.values())e.reject(Error(this.error));this.waiters.clear()}),this.worker}send(e){this.getWorker().postMessage(e)}wait(e){return new Promise((t,n)=>this.waiters.set(e,{resolve:t,reject:n}))}handleMessage(e){if(e.type===`progress`){for(let t of this.progressListeners)t(e.file,e.loaded,e.total);return}if(e.type===`loaded`){this.downloadedBytes=e.downloadedBytes,this.coldPending=e.downloadedBytes>1e6,this.loadedDevice=e.device,this.loadedDtype=e.dtype,this.loadedInfo=e,this.waiters.get(`loaded`)?.resolve(e),this.waiters.delete(`loaded`);return}if(e.type===`planned`){let t=`planned:${e.runId}`;this.waiters.get(t)?.resolve(e),this.waiters.delete(t);return}if((e.type===`error`||e.type===`overlimit`)&&e.seq===-1){let t=e.type===`error`?Error(`${e.name}: ${e.message}`):Error(`tts_overlimit: ${e.phonemes} > ${e.limit}`),n=e.runId===-1&&this.waiters.has(`loaded`)?`loaded`:`planned:${e.runId}`,r=this.waiters.get(n);if(!r)return;this.waiters.delete(n),r.reject(t);return}let t=`${e.runId}:${e.seq}`,n=this.waiters.get(t);n&&(this.waiters.delete(t),n.resolve(e))}settleWaiters(e,t){let n=Error(t);n.name=`AbortError`;for(let[t,r]of this.waiters)(t===`planned:${e}`||t.startsWith(`${e}:`))&&(this.waiters.delete(t),r.reject(n))}load(){if(!this.loaded){this.phase=`loading`;let e=this.wait(`loaded`).then(e=>(this.phase===`loading`&&(this.phase=`idle`),e));this.send({type:`load`,device:this.device}),this.loaded=e,e.catch(()=>{this.loaded=null,this.phase=`failed`})}return this.loaded}async plan(e){let t=-++this.messageSeq,n=this.wait(`planned:${t}`);this.send({type:`plan`,runId:t,text:e,limits:f});let r=await n;return{segments:r.segments,maxPhonemes:r.maxPhonemes,splitMs:r.splitMs}}pendingDone=null;readSeq=0;lastStop=null;runTtfa=null;runT0=0;runSynthMs=0;runOverlimit=0;secPerChar=1/u;estimateSeconds(e,t){return Math.max(0,e.end-e.start)*this.secPerChar/Math.max(t,.1)}async readAll(e,t={}){this.releasePause(),this.ensureContext();let n=this.runId,r=++this.readSeq;try{await this.load()}catch(e){return this.phase=`failed`,this.error=e instanceof Error?`${e.name}: ${e.message}`:String(e),this.result(n,0,0,!1)}if(this.runId!==n||r!==this.readSeq)return this.result(n,0,0,!1);let i=++this.runId;this.runCold=!1,this.takeCold();let a=this.pendingDone;this.pendingDone=null,a&&(this.replacedMetrics=this.metricsNow(n)),a?.resolve(!1),this.send({type:`cancel`,runId:n}),this.settleWaiters(n,`stopped`);let o=this.queue;o.beginRun(i),this.phase=`planning`,this.error=null,this.current=null,this.next=null,this.runTtfa=null,this.runSynthMs=0,this.runOverlimit=0,this.runT0=performance.now();let s=t.voice??this.voice,c=t.onStart,l=t.onEnd;this.userOnStart=c??null,this.userOnEnd=l??null;let u=this.wait(`planned:${i}`);this.send({type:`plan`,runId:i,text:e,limits:f});let d;try{d=await u}catch(e){return i===this.runId&&(this.phase=`failed`,this.error=e instanceof Error?`${e.name}: ${e.message}`:String(e)),this.result(i,0,0,!1)}if(i!==this.runId)return this.result(i,d.segments.length,0,!1);let p=d.segments;t.onPlanned?.(p);let m=_(e,p);this.phase=`reading`,this.runSegments=p,this.next=p[0]??null;let h,g=new Promise(e=>h=e);this.pendingDone={resolve:h},p.length===0&&(o.close(),this.phase=`done`,h(!0));let v=0,y=null,b=new Map;(async()=>{for(;v<p.length&&i===this.runId&&y===null;){let e=p[v],n=t.rate??this.rate,r=this.estimateSeconds(e,n);if(!o.canAccept(r)){await new Promise(e=>setTimeout(e,50));continue}v++;let a=o.requestSent(r),c=this.synthOne(i,e,s,n,o).catch(e=>{y===null&&(y=e)}).finally(()=>{o.requestSettled(a),b.delete(e.seq)});b.set(e.seq,c)}if(await Promise.all([...b.values()]),y!==null)throw y;i===this.runId&&o.close()})().catch(e=>{i===this.runId&&(this.error=e instanceof Error?`${e.name}: ${e.message}`:String(e),this.phase=`failed`,o.stop(),this.send({type:`cancel`,runId:i}),this.settleWaiters(i,`failed`),this.current=null,this.next=null,this.pendingDone?.resolve(!1),this.pendingDone=null)});let x=await g;return this.result(i,p.length,m,x,o.totalSeconds)}userOnStart=null;userOnEnd=null;async synthOne(e,t,n,r,i,a){let o=`${e}:${t.seq}`,s=this.wait(o);this.send({type:`synth`,runId:e,seq:t.seq,phonemes:t.phonemes,start:t.start,end:t.end,voice:n,speed:r,limit:f.limit,tag:a});let c;try{c=await s}catch(t){if(e!==this.runId)return;throw t}if(e===this.runId){if(c.type===`pcm`){this.runSynthMs+=c.synthMs;let t=c.end-c.start;t>0&&(this.secPerChar=Math.max(this.secPerChar,c.pcm.length/c.sampleRate*r/t)),i.enqueue({runId:e,seq:c.seq,pcm:c.pcm,sampleRate:c.sampleRate,start:c.start,end:c.end,tag:c.tag});return}if(c.type===`overlimit`)throw this.runOverlimit++,Error(`tts_overlimit: ${c.phonemes} > ${c.limit}`);if(c.type===`error`)throw Error(`${c.name}: ${c.message}`)}}runSegments=[];handleStart(e){e.runId===this.runId&&(e.seq<0||(this.runTtfa===null&&(this.runTtfa=performance.now()-this.runT0),this.current={seq:e.seq,start:e.start,end:e.end,at:e.at,seconds:e.seconds,tag:e.tag},this.next=this.runSegments[e.seq+1]??null,this.userOnStart?.(this.current)))}handleEnd(e){e.runId===this.runId&&(e.seq<0||(this.userOnEnd?.({seq:e.seq,start:e.start,end:e.end,at:e.at,seconds:e.seconds,tag:e.tag}),this.current?.seq===e.seq&&(this.current=null)))}handleDrain(e){e===this.runId&&(this.phase=`done`,this.next=null,this.pendingDone?.resolve(!0),this.pendingDone=null)}metrics(e){let t=this.runSynthMs/1e3;return{cache_state:this.cacheState(),ttfa_ms:this.runTtfa===null?null:Math.round(this.runTtfa),rtf:t>0?Math.round(e/t*100)/100:null,gap_ms:Math.round(this.queue?.maxGapMs??0),seconds:Math.round(e*100)/100,synth_ms:Math.round(this.runSynthMs),tts_overlimit:this.runOverlimit,device:this.loadedDevice,dtype:this.loadedDtype}}metricsNow(e){return{runId:e,ttfa:this.runTtfa,synthMs:this.runSynthMs,overlimit:this.runOverlimit,gapMs:this.queue?.maxGapMs??0,seconds:this.queue?.totalSeconds??0}}replacedMetrics=null;result(e,t,n,r,i=0){let a=this.replacedMetrics?.runId===e?this.replacedMetrics:null,o=a??this.metricsNow(e),s=a?a.seconds:i,c=o.synthMs/1e3,l=this.buildRow({ttfa_ms:o.ttfa===null?null:Math.round(o.ttfa),rtf:c>0?Math.round(s/c*100)/100:null,gap_ms:Math.round(o.gapMs),stop_ms:this.lastStop?.runId===e?this.lastStop.ms:null,coverage:n,tts_overlimit:o.overlimit});return this.lastStats=l,{runId:e,segments:t,coverage:n,ttsOverlimit:o.overlimit,seconds:s,finished:r}}buildRow(t){let n=e().web.voice,r=p(),i=performance.memory;return{schema_version:1,target:`web`,device:this.loadedDevice,level:`readall`,browser:r.browser,browser_major:r.browser_major,os:r.os,os_major:r.os_major,cache_state:this.cacheState(),model_id:n.id,model_rev:n.revision,dtype:this.loadedDtype,doc_id:null,commit:null,date:new Date().toISOString(),machine_id:`web`,ttfa_ms:null,gen_ms:null,tok_s:null,rtf:null,gap_ms:null,stop_ms:null,coverage:null,bullets_total:null,bullets_cut:null,cut_rate:null,facts_token_hit:null,halluc_flags:null,forbidden_hits:null,oneline_keyword_hit:null,tts_overlimit:0,peak_mb:null,heap_mb:i?Math.round(i.usedJSHeapSize/1e6):null,...t}}streamChain=Promise.resolve();streamSeq=0;streaming=!1;beginStream(e={}){this.ensureContext();let t=++this.runId;return this.queue.beginRun(t),this.phase=`reading`,this.error=null,this.current=null,this.next=null,this.runTtfa=null,this.runSynthMs=0,this.runOverlimit=0,this.runT0=performance.now(),this.userOnStart=e.onStart??null,this.userOnEnd=e.onEnd??null,this.streamSeq=0,this.streamChain=Promise.resolve(),this.streaming=!0,this.runCold=!1,this.takeCold(),this.pendingDone=null,t}streamPending=0;pushText(e,t,n,r,i){this.streamPending++;let a=this.streamChain.then(async()=>{if(e!==this.runId||this.phase===`failed`||(await this.load(),e!==this.runId))return;this.takeCold();let a=-++this.messageSeq,o=this.wait(`planned:${a}`);this.send({type:`plan`,runId:a,text:t,limits:f,firstPieceTarget:0});let s;try{s=await o}catch(t){if(e!==this.runId)return;throw t}let c=this.queue;for(let t of s.segments){let a=this.rate,o=t.text.length*this.secPerChar/Math.max(a,.1);for(;e===this.runId&&!c.canAccept(o);)await new Promise(e=>setTimeout(e,50));if(e!==this.runId)return;let s=this.streamSeq++,l=c.requestSent(o);try{await this.synthOne(e,{seq:s,text:t.text,start:n,end:r,phonemes:t.phonemes},this.voice,a,c,i)}finally{c.requestSettled(l)}}});return a.then(()=>this.streamPending--,()=>this.streamPending--),this.streamChain=a.catch(t=>{e===this.runId&&(this.phase=`failed`,this.error=t instanceof Error?`${t.name}: ${t.message}`:String(t),this.queue?.stop(),this.send({type:`cancel`,runId:e}),this.settleWaiters(e,`failed`),this.current=null,this.next=null,this.pendingDone?.resolve(!1),this.pendingDone=null)}),a}async endStream(e){let t;do t=this.streamChain,await t;while(t!==this.streamChain);e===this.runId&&(this.streaming=!1);let n=this.queue;if(e!==this.runId||this.phase===`failed`)return{finished:!1,metrics:this.metrics(n.totalSeconds)};if(n.enqueued===0)return this.phase=`done`,{finished:!0,metrics:this.metrics(0)};let r=new Promise(e=>this.pendingDone={resolve:e});return n.close(),{finished:await r,metrics:this.metrics(n.totalSeconds)}}noticeKey(e){return`${e}|${this.voice}|${this.rate}`}async prewarm(e){await this.load();for(let t of e){let e=this.noticeKey(t);if(!this.noticeCache.has(e))try{await this.synthMessage(t,e)}catch{}}this.prewarmed=e.every(e=>this.noticeCache.has(this.noticeKey(e)))}async synthMessage(e,t){let r=n(e),i=++this.messageSeq,a=-i,o=this.messageEpoch,s=this.wait(`${a}:${i}`);this.pendingMessages.add(i),this.send({type:`speak`,runId:a,seq:i,text:r,voice:this.voice,speed:this.rate,limits:f});let c;try{c=await s}catch(e){if(o!==this.messageEpoch)return null;throw e}finally{this.pendingMessages.delete(i)}if(o!==this.messageEpoch)return null;if(c.type!==`pcm`)throw Error(c.type===`error`?`${c.name}: ${c.message}`:`tts_overlimit`);let l={pcm:c.pcm,sampleRate:c.sampleRate};return this.noticeCache.set(t,l),l}pendingMessages=new Set;messageEpoch=0;stop(){this.releasePause(),this.noticeNextStart=0,this.streaming=!1;let e=performance.now(),t=this.runId;this.runId++,this.send({type:`cancel`,runId:t}),this.queue?.stop(),this.settleWaiters(t,`stopped`),this.messageEpoch++;for(let e of this.pendingMessages)this.send({type:`cancel`,runId:-e}),this.settleWaiters(-e,`stopped`);this.pendingMessages.clear();for(let e of this.messageSources.splice(0))try{e.stop()}catch{}this.phase=`stopped`,this.current=null,this.next=null;let n=performance.now()-e;return this.lastStop={runId:t,ms:Math.round(n*100)/100},this.lastStats&&={...this.lastStats,stop_ms:Math.round(n*100)/100},this.pendingDone?.resolve(!1),this.pendingDone=null,n}paused=!1;resumeWaiters=[];releasePause(){this.paused=!1;for(let e of this.resumeWaiters.splice(0))e()}pause(){this.paused=!0,this.queue?.pause()}resume(){this.releasePause(),this.queue?.resume()}skip(){return this.queue?.skip()??!1}async speak(e,t){let n=t??performance.now(),r=this.ensureContext(),i=this.noticeKey(e),a=this.messageEpoch,o=this.noticeCache.get(i)??null;if(!o&&(await this.load(),a!==this.messageEpoch||(o=await this.synthMessage(e,i),!o))||a!==this.messageEpoch||this.paused&&(await new Promise(e=>this.resumeWaiters.push(e)),a!==this.messageEpoch))return{seconds:0};let s=this.queue;if(this.streaming&&s&&s.currentRunId===this.runId){let e=this.runId,{pcm:t,sampleRate:n}=o,r=!1;if(this.streamChain=this.streamChain.then(()=>{e===this.runId&&this.streaming&&(r=s.enqueue({runId:e,seq:-1,pcm:t,sampleRate:n,start:-1,end:-1}))}),await this.streamChain,r)return{seconds:t.length/n};if(a!==this.messageEpoch)return{seconds:0}}let c=r.createBuffer(1,o.pcm.length,o.sampleRate);c.copyToChannel(o.pcm,0);let l=r.createBufferSource();l.buffer=c,l.connect(this.getAnalyser()??r.destination),this.messageSources.push(l);let u=new Promise(e=>{l.onended=()=>{let t=this.messageSources.indexOf(l);t>=0&&this.messageSources.splice(t,1),e()};let t=r.currentTime;setTimeout(()=>{r.currentTime===t&&e()},Math.ceil(c.duration*1e3)+500)}),d=Math.max(r.currentTime,this.noticeNextStart);return l.start(d),this.noticeNextStart=d+c.duration,this.lastNoticeLatencyMs=Math.round((performance.now()-n)*100)/100,await u,{seconds:c.duration}}async measure(e,t,n){await this.load();let r=-++this.messageSeq,i=this.wait(`planned:${r}`);this.send({type:`plan`,runId:r,text:e,limits:{target:t,limit:f.limit},firstPieceTarget:0});let a=await i,o=0,s=0;for(let e of a.segments){let t=`${r}:${e.seq}`,i=this.wait(t);this.send({type:`synth`,runId:r,seq:e.seq,phonemes:e.phonemes,start:e.start,end:e.end,voice:this.voice,speed:n??this.rate,limit:f.limit});let a=await i;if(a.type!==`pcm`)throw Error(a.type===`error`?`${a.name}: ${a.message}`:`tts_overlimit`);o+=a.pcm.length/a.sampleRate,s+=a.synthMs}return{seconds:o,pieces:a.segments.length,synthMs:s,maxPhonemes:a.maxPhonemes}}state(){return{phase:this.phase,error:this.error,current:this.current,next:this.next,rate:this.rate,voice:this.voice,ctxState:this.ctx?.state??`none`,aheadSeconds:this.queue?.aheadSeconds()??0,inFlight:this.queue?.requestsInFlight??0,pending:this.streamPending,playing:this.queue?.playing()??null,enqueued:this.queue?.enqueued??0,ended:this.queue?.ended??0}}stats(){return this.lastStats}};function _(e,t){if(t.length===0)return+(e.trim().length===0);let n=0,r=!0;for(let i of t)i.start<n&&(r=!1),e.slice(n,i.start).trim().length>0&&(r=!1),n=i.end;if(e.slice(n).trim().length>0&&(r=!1),r)return 1;let i=new Uint8Array(e.length);for(let n of t)i.fill(1,Math.max(0,n.start),Math.min(e.length,n.end));let a=0,o=0;for(let t=0;t<e.length;t++)/\s/.test(e[t])||(a++,i[t]&&o++);return Math.min(a===0?1:o/a,.999)}var v=null;function y(){return v||=new g,v}export{n as a,y as i,o as n,c as r,s as t};
|
index.html
CHANGED
|
@@ -9,12 +9,12 @@
|
|
| 9 |
<!-- csp:end -->
|
| 10 |
<!-- Cross-origin isolation on a static host: the service worker adds COOP/COEP (S1-00a). -->
|
| 11 |
<script src="/coi-serviceworker.js"></script>
|
| 12 |
-
<script type="module" crossorigin src="/assets/index-
|
| 13 |
<link rel="modulepreload" crossorigin href="/assets/pins-DVBrHC3g.js">
|
| 14 |
<link rel="modulepreload" crossorigin href="/assets/loader-D0INP31U.js">
|
| 15 |
<link rel="modulepreload" crossorigin href="/assets/llm-DH311QE0.js">
|
| 16 |
-
<link rel="modulepreload" crossorigin href="/assets/tts-
|
| 17 |
-
<link rel="stylesheet" crossorigin href="/assets/index-
|
| 18 |
</head>
|
| 19 |
<body>
|
| 20 |
<div id="app"></div>
|
|
|
|
| 9 |
<!-- csp:end -->
|
| 10 |
<!-- Cross-origin isolation on a static host: the service worker adds COOP/COEP (S1-00a). -->
|
| 11 |
<script src="/coi-serviceworker.js"></script>
|
| 12 |
+
<script type="module" crossorigin src="/assets/index-DIGGJAq1.js"></script>
|
| 13 |
<link rel="modulepreload" crossorigin href="/assets/pins-DVBrHC3g.js">
|
| 14 |
<link rel="modulepreload" crossorigin href="/assets/loader-D0INP31U.js">
|
| 15 |
<link rel="modulepreload" crossorigin href="/assets/llm-DH311QE0.js">
|
| 16 |
+
<link rel="modulepreload" crossorigin href="/assets/tts-DDfrpA1Y.js">
|
| 17 |
+
<link rel="stylesheet" crossorigin href="/assets/index-DTUQ8gca.css">
|
| 18 |
</head>
|
| 19 |
<body>
|
| 20 |
<div id="app"></div>
|
readall.html
CHANGED
|
@@ -8,9 +8,9 @@
|
|
| 8 |
<meta http-equiv="Content-Security-Policy" content="default-src 'self'; script-src 'self' 'wasm-unsafe-eval'; worker-src 'self' blob:; connect-src 'self' https://huggingface.co https://us.aws.cdn.hf.co https://*.cdn.hf.co; img-src 'self' data:; style-src 'self' 'unsafe-inline'; font-src 'self'; media-src 'self' blob:; object-src 'none'; base-uri 'self'; form-action 'none'">
|
| 9 |
<!-- csp:end -->
|
| 10 |
<script src="/coi-serviceworker.js"></script>
|
| 11 |
-
<script type="module" crossorigin src="/assets/readall-
|
| 12 |
<link rel="modulepreload" crossorigin href="/assets/pins-DVBrHC3g.js">
|
| 13 |
-
<link rel="modulepreload" crossorigin href="/assets/tts-
|
| 14 |
</head>
|
| 15 |
<body>
|
| 16 |
<h1>Read all (S1-04 harness)</h1>
|
|
|
|
| 8 |
<meta http-equiv="Content-Security-Policy" content="default-src 'self'; script-src 'self' 'wasm-unsafe-eval'; worker-src 'self' blob:; connect-src 'self' https://huggingface.co https://us.aws.cdn.hf.co https://*.cdn.hf.co; img-src 'self' data:; style-src 'self' 'unsafe-inline'; font-src 'self'; media-src 'self' blob:; object-src 'none'; base-uri 'self'; form-action 'none'">
|
| 9 |
<!-- csp:end -->
|
| 10 |
<script src="/coi-serviceworker.js"></script>
|
| 11 |
+
<script type="module" crossorigin src="/assets/readall-CNVhfTRg.js"></script>
|
| 12 |
<link rel="modulepreload" crossorigin href="/assets/pins-DVBrHC3g.js">
|
| 13 |
+
<link rel="modulepreload" crossorigin href="/assets/tts-DDfrpA1Y.js">
|
| 14 |
</head>
|
| 15 |
<body>
|
| 16 |
<h1>Read all (S1-04 harness)</h1>
|