@xincmm/foliate-js
Version:
Render e-books in the browser
1 lines • 526 kB
JavaScript
const t=(t,e)=>[-1,...e,t.length].reduce(({xs:e,a:i},s)=>({xs:e?.concat([t.slice(i+1,s)])??[],a:s}),{}).xs,e=/\d/,i=/^epubcfi\((.*)\)$/,s=t=>t.replace(/[\^[\](),;=]/g,"^$&"),n=t=>i.test(t)?t:`epubcfi(${t})`,r=(t=>(...e)=>`epubcfi(${t(...e.map(t=>t.match(i)?.[1]??t))})`)((...t)=>t.join("!")),a=(t,e)=>((t,e)=>t.map((t,i,s)=>e(t,i,s)?i:null).filter(t=>null!=t))(t,([t])=>t===e),o=t=>{const e=[];let i;for(const[s,n]of t){if("/"===s)e.push({index:n});else{const t=e[e.length-1];if(":"===s)t.offset=n;else if("~"===s)t.temporal=n;else if("@"===s)t.spatial=(t.spatial??[]).concat(n);else if(";s"===s)t.side=n;else if("["===s){if("/"!==i||!n){t.text=(t.text??[]).concat(n);continue}t.id=n}}i=s}return e},l=e=>t(e,a(e,"!")).map(o),h=s=>{const n=(t=>{const i=[];let s,n,r="";const a=t=>(i.push(t),s=null,r=""),o=t=>(r+=t,n=!1);for(const i of Array.from(t.trim()).concat(""))if("^"!==i||n){if("!"===s)a(["!"]);else if(","===s)a([","]);else if("/"===s||":"===s){if(e.test(i)){o(i);continue}a([s,parseInt(r)])}else if("~"===s){if(e.test(i)||"."===i){o(i);continue}a(["~",parseFloat(r)])}else if("@"===s){if(":"===i){a(["@",parseFloat(r)]),s="@";continue}if(e.test(i)||"."===i){o(i);continue}a(["@",parseFloat(r)])}else{if("["===s){";"!==i||n?","!==i||n?"]"!==i||n?o(i):a(["[",r]):(a(["[",r]),s="["):(a(["[",r]),s=";");continue}if(s?.startsWith(";")){"="!==i||n?";"!==i||n?"]"!==i||n?o(i):a([s,r]):(a([s,r]),s=";"):(s=`;${r}`,r="");continue}}"/"!==i&&":"!==i&&"~"!==i&&"@"!==i&&"["!==i&&"!"!==i&&","!==i||(s=i)}else n=!0;return i})((t=>t.match(i)?.[1]??t)(s)),r=a(n,",");if(!r.length)return l(n);const[o,h,c]=t(n,r).map(l);return{parent:o,start:h,end:c}},c=({index:t,id:e,offset:i,temporal:n,spatial:r,text:a,side:o})=>{const l=o?`;s=${o}`:"";return`/${t}`+(e?`[${s(e)}${l}]`:"")+(null!=i&&t%2?`:${i}`:"")+(n?`~${n}`:"")+(r?`@${r.join(":")}`:"")+(a||!e&&o?"["+(a?.map(s)?.join(",")??"")+l+"]":"")},d=t=>t.parent?[t.parent,t.start,t.end].map(d).join(","):t.map(t=>t.map(c).join("")).join("!"),u=t=>n(d(t)),p=(t,e)=>"string"==typeof t?u(p(h(t),e)):t.parent?((t,e)=>t.slice(0,-1).concat([t[t.length-1].concat(e[0])]).concat(e.slice(1)))(t.parent,t[e?"end":"start"]):t,g=(t,e)=>{"string"==typeof t&&(t=h(t)),"string"==typeof e&&(e=h(e)),t=p(t),e=p(e,!0);const i=t[t.length-1],s=e[e.length-1],n=[],r=[],a=[];let o=!0;const l=Math.max(i.length,s.length);for(let t=0;t<l;t++){const e=i[t],l=s[t];o&&=e?.index===l?.index&&!e?.offset&&!l?.offset,o?n.push(e):(e&&r.push(e),l&&a.push(l))}const c=t.slice(0,-1).concat([n]);return u({parent:c,start:[r],end:[a]})},f=(t,e)=>{if("string"==typeof t&&(t=h(t)),"string"==typeof e&&(e=h(e)),t.start||e.start)return f(p(t),p(e))||f(p(t,!0),p(e,!0));for(let i=0;i<Math.max(t.length,e.length);i++){const s=t[i]??[],n=e[i]??[],r=Math.max(s.length,n.length)-1;for(let t=0;t<=r;t++){const e=s[t],i=n[t];if(!e)return-1;if(!i)return 1;if(e.index>i.index)return 1;if(e.index<i.index)return-1;if(t===r){if(e.offset>i.offset)return 1;if(e.offset<i.offset)return-1}}}return 0},m=({nodeType:t})=>3===t||4===t,b=({nodeType:t})=>1===t,w=(t,e)=>{const i=Array.from(t.childNodes).filter(t=>m(t)||b(t));return e?i.map(t=>{const i=e(t);return i===NodeFilter.FILTER_REJECT?null:i===NodeFilter.FILTER_SKIP?w(t,e):t}).flat().filter(t=>t):i},y=(t,e)=>{const i=w(t,e).reduce((t,e)=>{let i=t[t.length-1];return i?m(e)?Array.isArray(i)?i.push(e):m(i)?t[t.length-1]=[i,e]:t.push(e):b(i)?t.push(null,e):t.push(e):t.push(e),t},[]);return b(i[0])&&i.unshift("first"),b(i[i.length-1])&&i.push("last"),i.unshift("before"),i.push("after"),i},v=(t,e,i)=>{const{id:s}=e[e.length-1];if(s){const e=t.ownerDocument.getElementById(s);if(e)return{node:e,offset:0}}for(const{index:s}of e){const e=t?y(t,i)[s]:null;if("first"===e)return{node:t.firstChild??t};if("last"===e)return{node:t.lastChild??t};if("before"===e)return{node:t,before:!0};if("after"===e)return{node:t,after:!0};t=e}const{offset:n}=e[e.length-1];if(!Array.isArray(t))return{node:t,offset:n};let r=0;for(const e of t){const{length:t}=e.nodeValue;if(r+t>=n)return{node:e,offset:n-r};r+=t}},x=(t,e,i)=>{const{parentNode:s,id:n}=t,r=y(s,i),a=r.findIndex(e=>Array.isArray(e)?e.some(e=>e===t):e===t),o=r[a];if(Array.isArray(o)){let i=0;for(const s of o){if(s===t){i+=e;break}i+=s.nodeValue.length}e=i}const l={id:n,index:a,offset:e};return(s!==t.ownerDocument.documentElement?x(s,null,i).concat(l):[l]).filter(t=>-1!==t.index)},A=(t,e)=>{const{startContainer:i,startOffset:s,endContainer:n,endOffset:r}=t,a=x(i,s,e);if(t.collapsed)return u([a]);const o=x(n,r,e);return g([a],[o])},_=(t,e,i)=>{const s=p(e),n=p(e,!0),r=t.documentElement,a=v(r,s[0],i),o=v(r,n[0],i),l=t.createRange();return a.before?l.setStartBefore(a.node):a.after?l.setStartAfter(a.node):l.setStart(a.node,a.offset),o.before?l.setEndBefore(o.node):o.after?l.setEndAfter(o.node):l.setEnd(o.node,o.offset),l},S=t=>{const e=[],{parentNode:i}=t[0],s=x(i);for(const[n,r]of y(i).entries()){const i=t[e.length];r===i&&e.push(u([s.concat({id:i.id,index:n})]))}return e},E=(t,e)=>v(t.documentElement,p(e)).node,C={fromIndex:t=>n("/6/"+2*(t+1)),toIndex:t=>t?.at(-1).index/2-1};var T=Object.freeze({__proto__:null,collapse:p,compare:f,fake:C,fromCalibreHighlight:({spine_index:t,start_cfi:e,end_cfi:i})=>{const s=C.fromIndex(t)+"!";return g(s+e.slice(2),s+i.slice(2))},fromCalibrePos:t=>{const[e]=h(t),i=e.shift();return e.shift(),u([[{index:6},i],e])},fromElements:S,fromRange:A,isCFI:i,joinIndir:r,parse:h,toElement:E,toRange:_});const k=t=>t.map(t=>t.subitems?.length?[t,k(t.subitems)].flat():t).flat();class M{async init({toc:t,ids:e,splitHref:i,getFragment:s}){(t=>{let e=0;const i=t=>{if(t.id=e++,t.subitems)for(const e of t.subitems)i(e)};for(const e of t)i(e)})(t);const n=k(t),r=new Map;for(const[t,e]of n.entries()){const[s,a]=await i(e?.href)??[],o={fragment:a,item:e};r.has(s)?r.get(s).items.push(o):r.set(s,{prev:n[t-1],items:[o]})}const a=new Map;for(const[t,i]of e.entries())r.has(i)?a.set(i,r.get(i)):a.set(i,a.get(e[t-1]));this.ids=e,this.map=a,this.getFragment=s}getProgress(t,e){if(!this.ids)return;const i=this.ids[t],s=this.map.get(i);if(!s)return null;const{prev:n,items:r}=s;if(!r)return n;if(!e||1===r.length&&!r[0].fragment)return r[0].item;const a=e.startContainer.getRootNode();for(const[t,{fragment:i}]of r.entries()){const s=this.getFragment(a,i);if(s&&e.comparePoint(s,0)>0)return r[t-1]?.item??n}return r[r.length-1].item}}class I{constructor(t,e,i){this.sizes=t.map(t=>"no"!=t.linear&&t.size>0?t.size:0),this.sizePerLoc=e,this.sizePerTimeUnit=i,this.sizeTotal=this.sizes.reduce((t,e)=>t+e,0),this.sectionFractions=this.#t()}#t(){const{sizeTotal:t}=this,e=[0];let i=0;for(const s of this.sizes)e.push((i+=s)/t);return e}getProgress(t,e,i=0){const{sizes:s,sizePerLoc:n,sizePerTimeUnit:r,sizeTotal:a}=this,o=s[t]??0,l=s.slice(0,t).reduce((t,e)=>t+e,0),h=l+e*o,c=h+i*o,d=a-h,u=(1-e)*o;return{fraction:c/a,section:{current:t,total:s.length},location:{current:Math.floor(h/n),next:Math.floor(c/n),total:Math.ceil(a/n)},time:{section:u/r,total:d/r}}}getSection(t){if(t<=0)return[0,0];if(t>=1)return[this.sizes.length-1,1];t+=Number.EPSILON;const{sizeTotal:e}=this;let i=this.sectionFractions.findIndex(e=>e>t)-1;if(i<0)return[0,0];for(;!this.sizes[i];)i++;return[i,(t-this.sectionFractions[i])/(this.sizes[i]/e)]}}const P=t=>document.createElementNS("http://www.w3.org/2000/svg",t);class R{#e=P("svg");#i=new Map;constructor(){Object.assign(this.#e.style,{position:"absolute",top:"0",left:"0",width:"100%",height:"100%",pointerEvents:"none"})}get element(){return this.#e}add(t,e,i,s){this.#i.has(t)&&this.remove(t),"function"==typeof e&&(e=e(this.#e.getRootNode()));const n=e.getClientRects(),r=i(n,s);this.#e.append(r),this.#i.set(t,{range:e,draw:i,options:s,element:r,rects:n})}remove(t){this.#i.has(t)&&(this.#e.removeChild(this.#i.get(t).element),this.#i.delete(t))}redraw(){for(const t of this.#i.values()){const{range:e,draw:i,options:s,element:n}=t;this.#e.removeChild(n);const r=e.getClientRects(),a=i(r,s);this.#e.append(a),t.element=a,t.rects=r}}hitTest({x:t,y:e}){const i=Array.from(this.#i.entries());for(let s=i.length-1;s>=0;s--){const[n,r]=i[s];for(const{left:i,top:s,right:a,bottom:o}of r.rects)if(s<=e&&i<=t&&o>e&&a>t)return[n,r.range]}return[]}static underline(t,e={}){const{color:i="red",width:s=2,writingMode:n}=e,r=P("g");if(r.setAttribute("fill",i),"vertical-rl"===n||"vertical-lr"===n)for(const{right:e,top:i,height:n}of t){const t=P("rect");t.setAttribute("x",e-s),t.setAttribute("y",i),t.setAttribute("height",n),t.setAttribute("width",s),r.append(t)}else for(const{left:e,bottom:i,width:n}of t){const t=P("rect");t.setAttribute("x",e),t.setAttribute("y",i-s),t.setAttribute("height",s),t.setAttribute("width",n),r.append(t)}return r}static strikethrough(t,e={}){const{color:i="red",width:s=2,writingMode:n}=e,r=P("g");if(r.setAttribute("fill",i),"vertical-rl"===n||"vertical-lr"===n)for(const{right:e,left:i,top:n,height:a}of t){const t=P("rect");t.setAttribute("x",(e+i)/2),t.setAttribute("y",n),t.setAttribute("height",a),t.setAttribute("width",s),r.append(t)}else for(const{left:e,top:i,bottom:n,width:a}of t){const t=P("rect");t.setAttribute("x",e),t.setAttribute("y",(i+n)/2),t.setAttribute("height",s),t.setAttribute("width",a),r.append(t)}return r}static squiggly(t,e={}){const{color:i="red",width:s=2,writingMode:n}=e,r=P("g");r.setAttribute("fill","none"),r.setAttribute("stroke",i),r.setAttribute("stroke-width",s);const a=1.5*s;if("vertical-rl"===n||"vertical-lr"===n)for(const{right:e,top:i,height:s}of t){const t=P("path"),n=Math.round(s/a/1.5),o=s/n,l=Array.from({length:n},(t,e)=>`l${e%2?-a:a} ${o}`).join("");t.setAttribute("d",`M${e} ${i}${l}`),r.append(t)}else for(const{left:e,bottom:i,width:s}of t){const t=P("path"),n=Math.round(s/a/1.5),o=s/n,l=Array.from({length:n},(t,e)=>`l${o} ${e%2?a:-a}`).join("");t.setAttribute("d",`M${e} ${i}${l}`),r.append(t)}return r}static highlight(t,e={}){const{color:i="red"}=e,s=P("g");s.setAttribute("fill",i),s.style.opacity="var(--overlayer-highlight-opacity, .3)",s.style.mixBlendMode="var(--overlayer-highlight-blend-mode, normal)";for(const{left:e,top:i,height:n,width:r}of t){const t=P("rect");t.setAttribute("x",e),t.setAttribute("y",i),t.setAttribute("height",n),t.setAttribute("width",r),s.append(t)}return s}static outline(t,e={}){const{color:i="red",width:s=3,radius:n=3}=e,r=P("g");r.setAttribute("fill","none"),r.setAttribute("stroke",i),r.setAttribute("stroke-width",s);for(const{left:e,top:i,height:s,width:a}of t){const t=P("rect");t.setAttribute("x",e),t.setAttribute("y",i),t.setAttribute("height",s),t.setAttribute("width",a),t.setAttribute("rx",n),r.append(t)}return r}static copyImage([t],e={}){const{src:i}=e,s=P("image"),{left:n,top:r,height:a,width:o}=t;return s.setAttribute("href",i),s.setAttribute("x",n),s.setAttribute("y",r),s.setAttribute("height",a),s.setAttribute("width",o),s}}const L=(t,e)=>{const i=[];for(let s=e.currentNode;s;s=e.nextNode()){const e=t.comparePoint(s,0);if(0===e)i.push(s);else if(e>0)break}return i},D=(t,e)=>{const i=[];for(let t=e.nextNode();t;t=e.nextNode())i.push(t);return i},F=NodeFilter.SHOW_ELEMENT|NodeFilter.SHOW_TEXT|NodeFilter.SHOW_CDATA_SECTION,O=t=>{if(1===t.nodeType){const e=t.tagName.toLowerCase();return"script"===e||"style"===e?NodeFilter.FILTER_REJECT:NodeFilter.FILTER_SKIP}return NodeFilter.FILTER_ACCEPT},N=function*(t,e,i){const s=t.commonAncestorContainer??t.body??t,n=document.createTreeWalker(s,F,{acceptNode:i||O}),r=(t.commonAncestorContainer?L:D)(t,n),a=r.map(t=>t.nodeValue),o=(t,e,i,s)=>{const n=document.createRange();return n.setStart(r[t],e),n.setEnd(r[i],s),n};for(const t of e(a,o))yield t},z="foliate-search:",B=async t=>t.isFile?t:(await Promise.all(Array.from(await new Promise((e,i)=>t.createReader().readEntries(t=>e(t),t=>i(t))),B))).flat(),U=async t=>{const e=await B(t),i=await Promise.all(e.map(t=>new Promise((e,i)=>t.file(i=>e([i,t.fullPath]),t=>i(t))))),s=new Map(i.map(([e,i])=>[i.replace(t.fullPath+"/",""),e])),n=new TextDecoder;return{loadText:async t=>(t=>t?n.decode(t):null)(await(t=>s.get(t)?.arrayBuffer()??null)(t)),loadBlob:t=>s.get(t),getSize:t=>s.get(t)?.size??0}};class H extends Error{}class j extends Error{}class $ extends Error{}const W=async t=>{let e;if("string"==typeof t&&(t=await(async t=>{const e=await fetch(t);if(!e.ok)throw new H(`${e.status} ${e.statusText}`,{cause:e});return new File([await e.blob()],new URL(e.url).pathname)})(t)),t.isDirectory){const i=await U(t),{EPUB:s}=await Promise.resolve().then(function(){return Rt});e=await new s(i).init()}else{if(!t.size)throw new j("File not found");if(await(async t=>{const e=new Uint8Array(await t.slice(0,4).arrayBuffer());return 80===e[0]&&75===e[1]&&3===e[2]&&4===e[3]})(t)){const i=await(async t=>{const{configure:e,ZipReader:i,BlobReader:s,TextWriter:n,BlobWriter:r}=await Promise.resolve().then(function(){return Pd});e({useWebWorkers:!1});const a=new i(new s(t)),o=await a.getEntries(),l=new Map(o.map(t=>[t.filename,t])),h=t=>(e,...i)=>l.has(e)?t(l.get(e),...i):null;return{entries:o,loadText:h(t=>t.getData(new n)),loadBlob:h((t,e)=>t.getData(new r(e))),getSize:t=>l.get(t)?.uncompressedSize??0}})(t);if((({name:t,type:e})=>"application/vnd.comicbook+zip"===e||t.endsWith(".cbz"))(t)){const{makeComicBook:s}=await Promise.resolve().then(function(){return to});e=s(i,t)}else if((({name:t,type:e})=>"application/x-zip-compressed-fb2"===e||t.endsWith(".fb2.zip")||t.endsWith(".fbz"))(t)){const{makeFB2:t}=await Promise.resolve().then(function(){return Ja}),{entries:s}=i,n=s.find(t=>t.filename.endsWith(".fb2")),r=await i.loadBlob((n??s[0]).filename);e=await t(r)}else{const{EPUB:t}=await Promise.resolve().then(function(){return Rt});e=await new t(i).init()}}else if(await(async t=>{const e=new Uint8Array(await t.slice(0,5).arrayBuffer());return 37===e[0]&&80===e[1]&&68===e[2]&&70===e[3]&&45===e[4]})(t)){const{makePDF:i}=await Promise.resolve().then(function(){return za});e=await i(t)}else{const{isMOBI:i,MOBI:s}=await Promise.resolve().then(function(){return Ae});if(await i(t)){const i=await Promise.resolve().then(function(){return au});e=await new s({unzlib:i.unzlibSync}).open(t)}else if((({name:t,type:e})=>"application/x-fictionbook+xml"===e||t.endsWith(".fb2"))(t)){const{makeFB2:i}=await Promise.resolve().then(function(){return Ja});e=await i(t)}}}if(!e)throw new $("File type not supported");return e};class V{#s;#n;#r;#a;constructor(t,e,i={}){this.#n=t,this.#r=e,this.#a=i,this.#a.hidden&&this.hide(),this.#n.addEventListener("mousemove",({screenX:t,screenY:i})=>{t===this.#a.x&&i===this.#a.y||(this.#a.x=t,this.#a.y=i,this.show(),this.#s&&clearTimeout(this.#s),e()&&(this.#s=setTimeout(this.hide.bind(this),1e3)))},!1)}cloneFor(t){return new V(t,this.#r,this.#a)}hide(){this.#n.style.cursor="none",this.#a.hidden=!0}show(){this.#n.style.removeProperty("cursor"),this.#a.hidden=!1}}class G extends EventTarget{#o=[];#l=-1;pushState(t){const e=this.#o[this.#l];e===t||e?.fraction&&e.fraction===t.fraction||(this.#o[++this.#l]=t,this.#o.length=this.#l+1,this.dispatchEvent(new Event("index-change")))}replaceState(t){const e=this.#l;this.#o[e]=t}back(){const t=this.#l;if(t<=0)return;const e={state:this.#o[t-1]};this.#l=t-1,this.dispatchEvent(new CustomEvent("popstate",{detail:e})),this.dispatchEvent(new Event("index-change"))}forward(){const t=this.#l;if(t>=this.#o.length-1)return;const e={state:this.#o[t+1]};this.#l=t+1,this.dispatchEvent(new CustomEvent("popstate",{detail:e})),this.dispatchEvent(new Event("index-change"))}get canGoBack(){return this.#l>0}get canGoForward(){return this.#l<this.#o.length-1}clear(){this.#o=[],this.#l=-1}}let q=class extends HTMLElement{#h=this.attachShadow({mode:"closed"});#c;#d;#u;#p=new Map;#g=new V(this,()=>this.hasAttribute("autohide-cursor"));isFixedLayout=!1;lastLocation;history=new G;constructor(){super(),this.history.addEventListener("popstate",({detail:t})=>{const e=this.resolveNavigation(t.state);this.renderer.goTo(e)})}async open(t){if(("string"==typeof t||"function"==typeof t.arrayBuffer||t.isDirectory)&&(t=await W(t)),this.book=t,this.language=(t=>{if(!t)return{};try{const e=Intl.getCanonicalLocales(t)[0],i=new Intl.Locale(e),s=["zh","ja","kr"].includes(i.language),n=(i.getTextInfo?.()??i.textInfo)?.direction;return{canonical:e,locale:i,isCJK:s,direction:n}}catch(t){return console.warn(t),{}}})(t.metadata?.language),t.splitTOCHref&&t.getTOCFragment){const e=t.sections.map(t=>t.id);this.#c=new I(t.sections,1500,1600);const i=t.splitTOCHref.bind(t),s=t.getTOCFragment.bind(t);this.#d=new M,await this.#d.init({toc:t.toc??[],ids:e,splitHref:i,getFragment:s}),this.#u=new M,await this.#u.init({toc:t.pageList??[],ids:e,splitHref:i,getFragment:s})}if(this.isFixedLayout="pre-paginated"===this.book.rendition?.layout,this.isFixedLayout?(await Promise.resolve().then(function(){return Eo}),this.renderer=document.createElement("foliate-fxl")):(await Promise.resolve().then(function(){return Ao}),this.renderer=document.createElement("foliate-paginator")),this.renderer.setAttribute("exportparts","head,foot,filter"),this.renderer.addEventListener("load",t=>this.#f(t.detail)),this.renderer.addEventListener("relocate",t=>this.#m(t.detail)),this.renderer.addEventListener("create-overlayer",t=>t.detail.attach(this.#b(t.detail))),this.renderer.open(t),this.#h.append(this.renderer),t.sections.some(t=>t.mediaOverlay)){const e=t.media.activeClass,i=t.media.playbackActiveClass;let s;this.mediaOverlay=t.getMediaOverlay(),this.mediaOverlay.addEventListener("highlight",t=>{const n=this.resolveNavigation(t.detail.text);this.renderer.goTo(n).then(()=>{const{doc:t}=this.renderer.getContents().find(t=>t.index=n.index),r=n.anchor(t);r.classList.add(e),i&&r.ownerDocument.documentElement.classList.add(i),s=new WeakRef(r)})}),this.mediaOverlay.addEventListener("unhighlight",()=>{const t=s?.deref();t&&(t.classList.remove(e),i&&t.ownerDocument.documentElement.classList.remove(i))})}}close(){this.renderer?.destroy(),this.renderer?.remove(),this.#c=null,this.#d=null,this.#u=null,this.#p=new Map,this.lastLocation=null,this.history.clear(),this.tts=null,this.mediaOverlay=null}goToTextStart(){return this.goTo(this.book.landmarks?.find(t=>t.type.includes("bodymatter")||t.type.includes("text"))?.href??this.book.sections.findIndex(t=>"no"!==t.linear))}async init({lastLocation:t,showTextStart:e}){const i=t?this.resolveNavigation(t):null;i?(await this.renderer.goTo(i),this.history.pushState(t)):e?await this.goToTextStart():(this.history.pushState(0),await this.next())}#w(t,e,i){return this.dispatchEvent(new CustomEvent(t,{detail:e,cancelable:i}))}#m({reason:t,range:e,index:i,fraction:s,size:n}){const r=this.#c?.getProgress(i,s,n)??{},a=this.#d?.getProgress(i,e),o=this.#u?.getProgress(i,e),l=this.getCFI(i,e);this.lastLocation={...r,tocItem:a,pageItem:o,cfi:l,range:e},"snap"!==t&&"page"!==t&&"scroll"!==t||this.history.replaceState(l),this.#w("relocate",this.lastLocation)}#f({doc:t,index:e}){t.documentElement.lang||=this.language.canonical??"",this.language.isCJK||(t.documentElement.dir||=this.language.direction??""),this.#y(t,e),this.#g.cloneFor(t.documentElement),this.#w("load",{doc:t,index:e})}#y(t,e){const{book:i}=this,s=i.sections[e];t.addEventListener("click",t=>{const e=t.target.closest("a[href]");if(!e)return;t.preventDefault();const n=e.getAttribute("href"),r=s?.resolveHref?.(n)??n;i?.isExternal?.(r)?Promise.resolve(this.#w("external-link",{a:e,href:r},!0)).then(t=>t?globalThis.open(r,"_blank"):null).catch(t=>console.error(t)):Promise.resolve(this.#w("link",{a:e,href:r},!0)).then(t=>t?this.goTo(r):null).catch(t=>console.error(t))})}async addAnnotation(t,e){const{value:i}=t;if(i.startsWith(z)){const t=i.replace(z,""),{index:s,anchor:n}=await this.resolveNavigation(t),r=this.#v(s);if(r){const{overlayer:t,doc:s}=r;if(e)return void t.remove(i);const a=s?n(s):n;t.add(i,a,R.outline)}return}const{index:s,anchor:n}=await this.resolveNavigation(i),r=this.#v(s);if(r){const{overlayer:s,doc:a}=r;if(s.remove(i),!e){const e=a?n(a):n,r=(t,n)=>s.add(i,e,t,n);this.#w("draw-annotation",{draw:r,annotation:t,doc:a,range:e})}}return{index:s,label:this.#d.getProgress(s)?.label??""}}deleteAnnotation(t){return this.addAnnotation(t,!0)}#v(t){return this.renderer.getContents().find(e=>e.index===t&&e.overlayer)}#b({doc:t,index:e}){const i=new R;t.addEventListener("click",t=>{const[s,n]=i.hitTest(t);s&&!s.startsWith(z)&&this.#w("show-annotation",{value:s,index:e,range:n})},!1);const s=this.#p.get(e);if(s)for(const t of s)this.addAnnotation(t);return this.#w("create-overlay",{index:e}),i}async showAnnotation(t){const{value:e}=t,i=await this.goTo(e);if(i){const{index:t,anchor:s}=i,{doc:n}=this.#v(t),r=s(n);this.#w("show-annotation",{value:e,index:t,range:r})}}getCFI(t,e){const i=this.book.sections[t].cfi??C.fromIndex(t);return e?r(i,A(e)):i}resolveCFI(t){if(this.book.resolveCFI)return this.book.resolveCFI(t);{const e=h(t);return{index:C.toIndex((e.parent??e).shift()),anchor:t=>_(t,e)}}}resolveNavigation(t){try{if("number"==typeof t)return{index:t};if("number"==typeof t.fraction){const[e,i]=this.#c.getSection(t.fraction);return{index:e,anchor:i}}return i.test(t)?this.resolveCFI(t):this.book.resolveHref(t)}catch(e){console.error(e),console.error(`Could not resolve target ${t}`)}}async goTo(t){const e=this.resolveNavigation(t);try{return await this.renderer.goTo(e),this.history.pushState(t),e}catch(e){console.error(e),console.error(`Could not go to ${t}`)}}async goToFraction(t){const[e,i]=this.#c.getSection(t);await this.renderer.goTo({index:e,anchor:i}),this.history.pushState({fraction:t})}async select(t){try{const e=await this.resolveNavigation(t);await this.renderer.goTo({...e,select:!0}),this.history.pushState(t)}catch(e){console.error(e),console.error(`Could not go to ${t}`)}}deselect(){for(const{doc:t}of this.renderer.getContents())t.defaultView.getSelection().removeAllRanges()}getSectionFractions(){return(this.#c?.sectionFractions??[]).map(t=>t+Number.EPSILON)}getProgressOf(t,e){const i=this.#d?.getProgress(t,e),s=this.#u?.getProgress(t,e);return{tocItem:i,pageItem:s}}async getTOCItemOf(t){try{const{index:e,anchor:i}=await this.resolveNavigation(t),s=await this.book.sections[e].createDocument(),n=i(s),r=n instanceof Range,a=r?n:s.createRange();return r||a.selectNodeContents(n),this.#d.getProgress(e,a)}catch(e){console.error(e),console.error(`Could not get ${t}`)}}async prev(t){await this.renderer.prev(t)}async next(t){await this.renderer.next(t)}goLeft(){return"rtl"===this.book.dir?this.next():this.prev()}goRight(){return"rtl"===this.book.dir?this.prev():this.next()}async*#x(t,e,i){const s=await this.book.sections[i].createDocument();for(const{range:n,excerpt:r}of t(s,e))yield{cfi:this.getCFI(i,n),excerpt:r}}async*#A(t,e){const{sections:i}=this.book;for(const[s,{createDocument:n}]of i.entries()){if(!n)continue;const r=await n(),a=Array.from(t(r,e),({range:t,excerpt:e})=>({cfi:this.getCFI(s,t),excerpt:e})),o=(s+1)/i.length;yield{progress:o},a.length&&(yield{index:s,subitems:a})}}async*search(t){this.clearSearch();const{searchMatcher:e}=await Promise.resolve().then(function(){return qo}),{query:i,index:s}=t,n=e(N,{defaultLocale:this.language,...t}),r=null!=s?this.#x(n,i,s):this.#A(n,i),a=[];this.#p.set(s,a);for await(const t of r)if(t.subitems){const e=t.subitems.map(({cfi:t})=>({value:z+t}));this.#p.set(t.index,e);for(const t of e)this.addAnnotation(t);yield{label:this.#d.getProgress(t.index)?.label??"",subitems:t.subitems}}else{if(t.cfi){const e={value:z+t.cfi};a.push(e),this.addAnnotation(e)}yield t}yield"done"}clearSearch(){for(const t of this.#p.values())for(const e of t)this.deleteAnnotation(e);this.#p.clear()}async initTTS(t="word",e){const i=this.renderer.getContents()[0].doc;if(this.tts&&this.tts.doc===i)return;const{TTS:s}=await Promise.resolve().then(function(){return jo});this.tts=new s(i,N,e||(t=>this.renderer.scrollToAnchor(t,!0)),t)}startMediaOverlay(){const{index:t}=this.renderer.getContents()[0];return this.mediaOverlay.start(t)}};customElements.define("foliate-view",q);const X="urn:oasis:names:tc:opendocument:xmlns:container",K="http://www.w3.org/1999/xhtml",Y="http://www.idpf.org/2007/opf",Q="http://www.idpf.org/2007/ops",J="http://purl.org/dc/elements/1.1/",Z="http://www.w3.org/2001/04/xmlenc#",tt="http://www.daisy.org/z3986/2005/ncx/",et="http://www.w3.org/1999/xlink",it="http://www.w3.org/ns/SMIL",st={XML:"application/xml",NCX:"application/x-dtbncx+xml",XHTML:"application/xhtml+xml",HTML:"text/html",CSS:"text/css",SVG:"image/svg+xml",JS:/\/(x-)?(javascript|ecmascript)/},nt={a11y:"http://www.idpf.org/epub/vocab/package/a11y/#",dcterms:"http://purl.org/dc/terms/",marc:"http://id.loc.gov/vocabulary/",media:"http://www.idpf.org/epub/vocab/overlays/#",onix:"http://www.editeur.org/ONIX/book/codelists/current.html#",rendition:"http://www.idpf.org/vocab/rendition/#",schema:"http://schema.org/",xsd:"http://www.w3.org/2001/XMLSchema#",msv:"http://www.idpf.org/epub/vocab/structure/magazine/#",prism:"http://www.prismstandard.org/specifications/3.0/PRISM_CV_Spec_3.0.htm#"},rt={art:"artist",aut:"author",clr:"colorist",edt:"editor",ill:"illustrator",nrt:"narrator",trl:"translator",pbl:"publisher"},at={"02":"isbn","06":"doi",15:"isbn",26:"doi",34:"issn"},ot=t=>t.toLowerCase().replace(/[-:](.)/g,(t,e)=>e.toUpperCase()),lt=(...t)=>e=>e?Object.fromEntries(t.map(t=>[ot(t),e.getAttribute(t)])):null,ht=t=>{return e=t?.textContent,e?e.replace(/[\t\n\f\r ]+/g," ").replace(/^[\t\n\f\r ]+/,"").replace(/[\t\n\f\r ]+$/,""):"";var e},ct=(t,e)=>{const i=t.lookupNamespaceURI(null)===e||t.lookupPrefix(e),s=i?(t,i)=>t=>t.namespaceURI===e&&t.localName===i:(t,e)=>t=>t.localName===e;return{$:(t,e)=>[...t.children].find(s(t,e)),$$:(t,e)=>[...t.children].filter(s(t,e)),$$$:i?(t,i)=>[...t.getElementsByTagNameNS(e,i)]:(t,e)=>[...t.getElementsByTagName(e)]}},dt=(t,e)=>{try{if(e.includes(":"))return new URL(t,e);const i="https://invalid.invalid/",s=new URL(t,i+e);return s.search="",decodeURI(s.href.replace(i,""))}catch(e){return console.warn(e),t}},ut=t=>/^(?!blob)\w+:/i.test(t),pt=async(t,e,i)=>{const s=[];t.replace(e,(...t)=>(s.push(t),null));const n=[];for(const t of s)n.push(await i(...t));return t.replace(e,()=>n.shift())},gt=t=>t.replace(/[-/\\^$*+?.()|[\]{}]/g,"\\$&"),ft=t=>{for(const[e,i]of Object.entries(t))null==i?delete t[e]:Array.isArray(i)?(t[e]=i.filter(t=>t).map(t=>"object"!=typeof t||Array.isArray(t)?t:ft(t)),t[e].length?1===t[e].length&&(t[e]=t[e][0]):delete t[e]):"object"==typeof i&&(t[e]=ft(i),Object.keys(i).length||delete t[e]);const e=Object.keys(t);return 1===e.length&&"name"===e[0]?t[e[0]]:t},mt=(t,e)=>{if(!t)return null;const[i,s]=t.split(":"),n=s?i:null,r=s||i,a=e.get(n);return a?a+r:null},bt=t=>{const{$:e}=ct(t,Y),i=e(t.documentElement,"metadata"),s=Object.groupBy(i.children,t=>t.namespaceURI===J?"dc":t.namespaceURI===Y&&"meta"===t.localName?t.hasAttribute("name")?"legacyMeta":"meta":""),n=i.getAttribute("xml:lang")??t.documentElement.getAttribute("xml:lang")??"und",r=(t=>{const e=new Map(Object.entries(nt)),i=t.documentElement.getAttributeNS(Q,"prefix")||t.documentElement.getAttribute("prefix");if(i)for(const[,t,s]of i.matchAll(/(.+): +(.+)[ \t\r\n]*/g))e.set(t,s);return e})(t),a=t=>{const e=t.getAttribute("property"),i=t.getAttribute("scheme");return{property:mt(e,r)??e,scheme:mt(i,r)??i,lang:t.getAttribute("xml:lang"),value:ht(t),props:l(t),attrs:Object.fromEntries(Array.from(t.attributes).filter(t=>t.namespaceURI===Y).map(t=>[t.localName,t.value]))}},o=Map.groupBy(s.meta??[],t=>t.getAttribute("refines")),l=t=>{const e=o.get(t?"#"+t.getAttribute("id"):null);return e?Object.groupBy(e.map(a),t=>t.property):null},h=Object.fromEntries(Object.entries(Object.groupBy(s.dc,t=>t.localName)).map(([t,e])=>[t,e.map(a)])),c=l()??{},d=Object.fromEntries(s.legacyMeta?.map(t=>[t.getAttribute("name"),t.getAttribute("content")])??[]),u=t=>t?.[0]?.value,p=(t,e)=>u(t?.props?.[e]),g=t=>{if(!t)return null;const e=t.props?.["alternate-script"]??[],i=t.attrs["alt-rep"];if(!(e.length||t.lang&&t.lang!==n||i))return t.value;const s={[t.lang??n]:t.value};i&&(s[t.attrs["alt-rep-lang"]]=i);for(const t of e)s[t.lang]??=t.value;return s},f=t=>t?{name:g(t),sortAs:g(t.props?.["file-as"]?.[0])??t.attrs["file-as"],role:t.props?.role?.filter(t=>t.scheme===nt.marc+"relators")?.map(t=>t.value)??[t.attrs.role],code:p(t,"term")??t.attrs.term,scheme:p(t,"authority")??t.attrs.authority}:null,m=t=>({name:g(t),position:u(t.props?.["group-position"])}),b=t=>{const{value:e}=t;if(/^urn:/i.test(e))return e;if(/^doi:/i.test(e))return`urn:${e}`;const i=t.props?.["identifier-type"];if(!i){const i=t.attrs.scheme;return i?/^(doi|isbn|uuid)$/i.test(i)?`urn:${i}:${e}`:{scheme:i,value:e}:e}if(i.scheme===nt.onix+"codelist5"){const t=at[i.value];if(t)return`urn:${t}:${e}`}return e},w=Object.groupBy(c["belongs-to-collection"]??[],t=>"series"===p(t,"collection-type")?"series":"collection"),y=h.title?.find(t=>"main"===p(t,"title-type"))??h.title?.[0],v={identifier:_t(t),title:g(y),sortAs:g(y?.props?.["file-as"]?.[0])??y?.attrs?.["file-as"]??d?.["calibre:title_sort"],subtitle:h.title?.find(t=>"subtitle"===p(t,"title-type"))?.value,language:h.language?.map(t=>t.value),description:u(h.description),publisher:f(h.publisher?.[0]),published:h.date?.find(t=>"publication"===t.attrs.event)?.value??u(h.date),modified:u(c[nt.dcterms+"modified"])??h.date?.find(t=>"modification"===t.attrs.event)?.value,subject:h.subject?.map(f),belongsTo:{collection:w.collection?.map(m),series:w.series?.map(m)??d?.["calibre:series"]?{name:d?.["calibre:series"],position:parseFloat(d?.["calibre:series_index"])}:null},altIdentifier:h.identifier?.map(b),source:h.source?.map(b),rights:u(h.rights)},x=t=>e=>{const i=new Set(e.role?.map(e=>rt[e]??t));return[i.size?i:[t],e]};for(const[t,e]of[].concat(h.creator?.map(f)?.map(x("author"))??[],h.contributor?.map(f)?.map(x("contributor"))??[]))for(const i of t)v[i]?v[i].push(e):v[i]=[e];ft(v),v.altIdentifier===v.identifier&&delete v.altIdentifier;const A={},_={};for(const[t,e]of Object.entries(c))t.startsWith(nt.rendition)?A[ot(t.replace(nt.rendition,""))]=u(e):t.startsWith(nt.media)&&(_[ot(t.replace(nt.media,""))]=u(e));return _.duration&&(_.duration=vt(_.duration)),{metadata:v,rendition:A,media:_}},wt=(t,e=t=>t)=>{const{$:i,$$:s,$$$:n}=ct(t,K),r=t=>s=>{const n=i(s,"a")??i(s,"span"),r=i(s,"ol"),o=(t=>t?decodeURI(e(t)):null)(n?.getAttribute("href")),l={label:ht(n)||n?.getAttribute("title"),href:o,subitems:a(r)};return t&&(l.type=n?.getAttributeNS(Q,"type")?.split(/\s/)),l},a=(t,e)=>t?s(t,"li").map(r(e)):null,o=(t,e)=>a(i(t,"ol"),e),l=n(t,"nav");let h=null,c=null,d=null,u=[];for(const t of l){const e=t.getAttributeNS(Q,"type")?.split(/\s/)??[];e.includes("toc")?h??=o(t):e.includes("page-list")?c??=o(t):e.includes("landmarks")?d??=o(t,!0):u.push({label:ht(t.firstElementChild),type:e,list:o(t)})}return{toc:h,pageList:c,landmarks:d,others:u}},yt=(t,e=t=>t)=>{const{$:i,$$:s}=ct(t,tt),n=t=>{const r=i(t,"navLabel"),a=i(t,"content"),o=ht(r),l=(t=>t?decodeURI(e(t)):null)(a.getAttribute("src"));if("navPoint"===t.localName){const e=s(t,"navPoint");return{label:o,href:l,subitems:e.length?e.map(n):null}}return{label:o,href:l}},r=(t,e)=>s(t,e).map(n),a=(e,s)=>{const n=i(t.documentElement,e);return n?r(n,s):null};return{toc:a("navMap","navPoint"),pageList:a("pageList","pageTarget"),others:s(t.documentElement,"navList").map(t=>({label:ht(i(t,"navLabel")),list:r(t,"navTarget")}))}},vt=t=>{if(!t)return;const e=t.split(":").map(t=>parseFloat(t));if(3===e.length){const[t,i,s]=e;return 60*t*60+60*i+s}if(2===e.length){const[t,i]=e;return 60*t+i}const[i,s]=t.split(/(?=[^\d.])/);return parseFloat(i)*("h"===s?3600:"min"===s?60:"ms"===s?.001:1)};class xt extends EventTarget{#_;#S;#E;#C;#T;#k;#M=1;#I=1;#a;constructor(t,e){super(),this.book=t,this.loadXML=e}async#P(t){if(this.#S===t)return;const e=await this.loadXML(t.href),i=e=>e?dt(e,t.href):null,{$:s,$$$:n}=ct(e,it);this.#C=-1,this.#T=-1,this.#_=n(e,"par").reduce((t,e)=>{const n=i(s(e,"text")?.getAttribute("src")),r=s(e,"audio");if(!n||!r)return t;const a=i(r.getAttribute("src")),o=vt(r.getAttribute("clipBegin")),l=vt(r.getAttribute("clipEnd")),h=t.at(-1);return h?.src===a?h.items.push({text:n,begin:o,end:l}):t.push({src:a,items:[{text:n,begin:o,end:l}]}),t},[]),this.#S=t}get#R(){return this.#_[this.#C]}get#L(){return this.#R?.items?.[this.#T]}#D(t){console.error(t),this.dispatchEvent(new CustomEvent("error",{detail:t}))}#F(){this.dispatchEvent(new CustomEvent("highlight",{detail:this.#L}))}#O(){this.dispatchEvent(new CustomEvent("unhighlight",{detail:this.#L}))}async#N(t,e){this.#z(),this.#C=t,this.#T=e;const i=this.#R?.src;if(!i||!this.#L)return this.start(this.#E+1);const s=URL.createObjectURL(await this.book.loadBlob(i)),n=new Audio(s);this.#k=n,n.volume=this.#M,n.playbackRate=this.#I,n.addEventListener("timeupdate",()=>{if(n.paused)return;const t=n.currentTime,{items:e}=this.#R;if(t>this.#L?.end&&(this.#O(),this.#T===e.length-1))return void this.#N(this.#C+1,0).catch(t=>this.#D(t));const i=this.#T;for(;e[this.#T+1]?.begin<=t;)this.#T++;this.#T!==i&&this.#F()}),n.addEventListener("error",()=>this.#D(new Error(`Failed to load ${i}`))),n.addEventListener("playing",()=>this.#F()),n.addEventListener("ended",()=>{this.#O(),URL.revokeObjectURL(s),this.#k=null,this.#N(t+1,0).catch(t=>this.#D(t))}),"paused"===this.#a?(this.#F(),n.currentTime=this.#L.begin??0):n.addEventListener("canplaythrough",()=>{n.currentTime=this.#L.begin??0,this.#a="playing",n.play().catch(t=>this.#D(t))},{once:!0})}async start(t,e=()=>!0){this.#k?.pause();const i=this.book.sections[t],s=i?.id;if(!s)return;const{mediaOverlay:n}=i;if(!n)return this.start(t+1);this.#E=t,await this.#P(n);for(let t=0;t<this.#_.length;t++){const{items:i}=this.#_[t];for(let n=0;n<i.length;n++)if(i[n].text.split("#")[0]===s&&e(i[n],n,i))return this.#N(t,n).catch(t=>this.#D(t))}}pause(){this.#a="paused",this.#k?.pause()}resume(){this.#a="playing",this.#k?.play().catch(t=>this.#D(t))}#z(){this.#k&&(this.#k.pause(),URL.revokeObjectURL(this.#k.src),this.#k=null,this.#O())}stop(){this.#a="stopped",this.#z()}prev(){this.#T>0?this.#N(this.#C,this.#T-1):this.#C>0?this.#N(this.#C-1,this.#_[this.#C-1].items.length-1):this.#E>0&&this.start(this.#E-1,(t,e,i)=>e===i.length-1)}next(){this.#N(this.#C,this.#T+1)}setVolume(t){this.#M=t,this.#k&&(this.#k.volume=t)}setRate(t){this.#I=t,this.#k&&(this.#k.playbackRate=t)}}const At=/([0-9a-f]{8})-([0-9a-f]{4})-([0-9a-f]{4})-([0-9a-f]{4})-([0-9a-f]{12})/,_t=t=>ht(t.getElementById(t.documentElement.getAttribute("unique-identifier"))??t.getElementsByTagNameNS(J,"identifier")[0]),St=async(t,e,i)=>{const s=new Uint8Array(await i.slice(0,e).arrayBuffer());e=Math.min(e,s.length);for(var n=0;n<e;n++)s[n]=s[n]^t[n%t.length];return new Blob([s,i.slice(e)],{type:i.type})},Et=async t=>{const e=(new TextEncoder).encode(t),i=await globalThis.crypto.subtle.digest("SHA-1",e);return new Uint8Array(i)},Ct=(t=Et)=>({"http://www.idpf.org/2008/embedding":{key:e=>t(_t(e).replaceAll(/[\u0020\u0009\u000d\u000a]/g,"")),decode:(t,e)=>St(t,1040,e)},"http://ns.adobe.com/pdf/enc#RC":{key:t=>{const e=(t=>{for(const e of t.getElementsByTagNameNS(J,"identifier")){const[t]=ht(e).split(":").slice(-1);if(At.test(t))return t}return""})(t).replaceAll("-","");return Uint8Array.from({length:16},(t,i)=>parseInt(e.slice(2*i,2*i+2),16))},decode:(t,e)=>St(t,1024,e)}});class Tt{#B=new Map;#U=new Map;#H;constructor(t){this.#H=t}async init(t,e){if(!t)return;const i=Array.from(t.getElementsByTagNameNS(Z,"EncryptedData"),t=>({algorithm:t.getElementsByTagNameNS(Z,"EncryptionMethod")[0]?.getAttribute("Algorithm"),uri:t.getElementsByTagNameNS(Z,"CipherReference")[0]?.getAttribute("URI")}));for(const{algorithm:t,uri:s}of i){if(!this.#U.has(t)){const i=this.#H[t];if(!i){console.warn("Unknown encryption algorithm");continue}const s=await i.key(e);this.#U.set(t,t=>i.decode(s,t))}this.#B.set(s,t)}}getDecoder(t){return this.#U.get(this.#B.get(t))??(t=>t)}}class kt{constructor({opf:t,resolveHref:e}){this.opf=t;const{$:i,$$:s,$$$:n}=ct(t,Y),r=i(t.documentElement,"manifest"),a=i(t.documentElement,"spine"),o=s(a,"itemref");this.manifest=s(r,"item").map(lt("href","id","media-type","properties","media-overlay")).map(t=>(t.href=e(t.href),t.properties=t.properties?.split(/\s/),t)),this.manifestById=new Map(this.manifest.map(t=>[t.id,t])),this.spine=o.map(lt("idref","id","linear","properties")).map(t=>(t.properties=t.properties?.split(/\s/),t)),this.pageProgressionDirection=a.getAttribute("page-progression-direction"),this.navPath=this.getItemByProperty("nav")?.href,this.ncxPath=(this.getItemByID(a.getAttribute("toc"))??this.manifest.find(t=>t.mediaType===st.NCX))?.href;const l=i(t.documentElement,"guide");var h,c,d;l&&(this.guide=s(l,"reference").map(lt("type","title","href")).map(({type:t,title:i,href:s})=>({label:i,type:t.split(/\s/),href:e(s)}))),this.cover=this.getItemByProperty("cover-image")??this.getItemByID(n(t,"meta").find((h="name",c="cover",d?t=>t.getAttribute(h)?.split(/\s/)?.includes(c):"function"==typeof c?t=>c(t.getAttribute(h)):t=>t.getAttribute(h)===c))?.getAttribute("content"))??this.getItemByHref(this.guide?.find(t=>t.type.includes("cover"))?.href),this.cfis=S(o)}getItemByID(t){return this.manifestById.get(t)}getItemByHref(t){return this.manifest.find(e=>e.href===t)}getItemByProperty(t){return this.manifest.find(e=>e.properties?.includes(t))}resolveCFI(t){const e=h(t),i=(e.parent??e).shift();let s=E(this.opf,i);s&&"idref"!==s.nodeName&&(i.at(-1).id=null,s=E(this.opf,i));const n=s?.getAttribute("idref");return{index:this.spine.findIndex(t=>t.idref===n),anchor:t=>_(t,e)}}}class Mt{#j=new Map;#$=new Map;#W=new Map;allowScript=!1;eventTarget=new EventTarget;constructor({loadText:t,loadBlob:e,resources:i}){this.loadText=t,this.loadBlob=e,this.manifest=i.manifest,this.assets=i.manifest}async createURL(t,e,i,s){if(!e)return"";const n={data:e,type:i};Object.defineProperty(n,"name",{value:t});const r=new CustomEvent("data",{detail:n});this.eventTarget.dispatchEvent(r);const a=await r.detail.data,o=await r.detail.type,l=URL.createObjectURL(new Blob([a],{type:o}));if(this.#j.set(t,l),this.#W.set(t,1),s){const e=this.#$.get(s);e?e.push(t):this.#$.set(s,[t])}return l}ref(t,e){const i=this.#$.get(e);return i?.includes(t)||(this.#W.set(t,this.#W.get(t)+1),i?i.push(t):this.#$.set(e,[t])),this.#j.get(t)}unref(t){if(!this.#W.has(t))return;const e=this.#W.get(t)-1;if(e<1){URL.revokeObjectURL(this.#j.get(t)),this.#j.delete(t),this.#W.delete(t);const e=this.#$.get(t);if(e)for(;e.length;)this.unref(e.pop());this.#$.delete(t)}else this.#W.set(t,e)}async loadItem(t,e=[]){if(!t)return null;const{href:i,mediaType:s}=t,n=st.JS.test(t.mediaType);if(n&&!this.allowScript)return null;const r=e.at(-1);if(this.#j.has(i))return this.ref(i,r);const a=(n||[st.XHTML,st.HTML,st.CSS,st.SVG].includes(s))&&e.every(t=>t!==i);if(a)return this.loadReplaced(t,e);const o=Promise.resolve().then(()=>this.loadBlob(i));return this.createURL(i,o,s,r)}async loadHref(t,e,i=[]){if(ut(t))return t;const s=dt(t,e),n=this.manifest.find(t=>t.href===s);return n?this.loadItem(n,i.concat(e)):t}async loadReplaced(t,e=[]){const{href:i,mediaType:s}=t,n=e.at(-1);let r="";try{r=await this.loadText(i)}catch(t){return this.createURL(i,Promise.reject(t),s,n)}if(!r)return null;if([st.XHTML,st.HTML,st.SVG].includes(s)){let a=(new DOMParser).parseFromString(r,s);if(s!==st.XHTML||!a.querySelector("parsererror")&&a.documentElement?.namespaceURI||(console.warn(a.querySelector("parsererror")?.innerText??"Invalid XHTML"),t.mediaType=st.HTML,a=(new DOMParser).parseFromString(r,t.mediaType)),[st.XHTML,st.SVG].includes(t.mediaType)){let t=a.firstChild;for(;t instanceof ProcessingInstruction;){if(t.data){const s=await pt(t.data,/(?:^|\s*)(href\s*=\s*['"])([^'"]*)(['"])/i,(t,s,n,r)=>this.loadHref(n,i,e).then(t=>`${s}${t}${r}`));t.replaceWith(a.createProcessingInstruction(t.target,s))}t=t.nextSibling}}const o=async(t,s)=>t.setAttribute(s,await this.loadHref(t.getAttribute(s),i,e));for(const t of a.querySelectorAll("link[href]"))await o(t,"href");for(const t of a.querySelectorAll("[src]"))await o(t,"src");for(const t of a.querySelectorAll("[poster]"))await o(t,"poster");for(const t of a.querySelectorAll("object[data]"))await o(t,"data");for(const t of a.querySelectorAll("[*|href]:not([href])"))t.setAttributeNS(et,"href",await this.loadHref(t.getAttributeNS(et,"href"),i,e));for(const t of a.querySelectorAll("style"))t.textContent&&(t.textContent=await this.replaceCSS(t.textContent,i,e));for(const t of a.querySelectorAll("[style]"))t.setAttribute("style",await this.replaceCSS(t.getAttribute("style"),i,e));const l=(new XMLSerializer).serializeToString(a);return this.createURL(i,l,t.mediaType,n)}const a=s===st.CSS?await this.replaceCSS(r,i,e):await this.replaceString(r,i,e);return this.createURL(i,a,s,n)}async replaceCSS(t,e,i=[]){const s=await pt(t,/url\(\s*["']?([^'"\n]*?)\s*["']?\s*\)/gi,(t,s)=>this.loadHref(s,e,i).then(t=>`url("${t}")`));return pt(s,/@import\s*["']([^"'\n]*?)["']/gi,(t,s)=>this.loadHref(s,e,i).then(t=>`@import "${t}"`))}replaceString(t,e,i=[]){const s=new Map,n=this.assets.map(t=>{if(t.href===e)return;const i=((t,e)=>{if(!t)return e;const i=t.replace(/\/$/,"").split("/"),s=e.replace(/\/$/,"").split("/"),n=(i.length>s.length?i:s).findIndex((t,e)=>i[e]!==s[e]);return n<0?"":Array(i.length-n).fill("..").concat(s.slice(n)).join("/")})((t=>t.slice(0,t.lastIndexOf("/")+1))(e),t.href),n=encodeURI(i),r="/"+t.href,a=encodeURI(r),o=new Set([i,n,r,a]);for(const e of o)s.set(e,t);return Array.from(o)}).flat().filter(t=>t);if(!n.length)return t;const r=new RegExp(n.map(gt).join("|"),"g");return pt(t,r,async t=>this.loadItem(s.get(t.replace(/^\//,"")),i.concat(e)))}unloadItem(t){this.unref(t?.href)}destroy(){for(const t of this.#j.values())URL.revokeObjectURL(t)}}const It=t=>{for(const e of t){if("page-spread-left"===e||"rendition:page-spread-left"===e)return"left";if("page-spread-right"===e||"rendition:page-spread-right"===e)return"right";if("rendition:page-spread-center"===e)return"center"}};class Pt{parser=new DOMParser;#V;#G;constructor({loadText:t,loadBlob:e,getSize:i,sha1:s}){this.loadText=t,this.loadBlob=e,this.getSize=i,this.#G=new Tt(Ct(s))}async#q(t){const e=await this.loadText(t);if(!e)return null;const i=this.parser.parseFromString(e,st.XML);if(i.querySelector("parsererror"))throw new Error(`XML parsing error: ${t}\n${i.querySelector("parsererror").innerText}`);return i}async init(){const t=await this.#q("META-INF/container.xml");if(!t)throw new Error("Failed to load container file");const e=Array.from(t.getElementsByTagNameNS(X,"rootfile"),lt("full-path","media-type")).filter(t=>"application/oebps-package+xml"===t.mediaType);if(!e.length)throw new Error("No package document defined in container");const i=e[0].fullPath,s=await this.#q(i);if(!s)throw new Error("Failed to load package document");const n=await this.#q("META-INF/encryption.xml");await this.#G.init(n,s),this.resources=new kt({opf:s,resolveHref:t=>dt(t,i)}),this.#V=new Mt({loadText:this.loadText,loadBlob:t=>Promise.resolve(this.loadBlob(t)).then(this.#G.getDecoder(t)),resources:this.resources}),this.transformTarget=this.#V.eventTarget,this.sections=this.resources.spine.map((t,e)=>{const{idref:i,linear:s,properties:n=[]}=t,r=this.resources.getItemByID(i);return r?{id:r.href,load:()=>this.#V.loadItem(r),unload:()=>this.#V.unloadItem(r),createDocument:()=>this.loadDocument(r),size:this.getSize(r.href),cfi:this.resources.cfis[e],linear:s,pageSpread:It(n),resolveHref:t=>dt(t,r.href),mediaOverlay:r.mediaOverlay?this.resources.getItemByID(r.mediaOverlay):null}:(console.warn(`Could not find item with ID "${i}" in manifest`),null)}).filter(t=>t);const{navPath:r,ncxPath:a}=this.resources;if(r)try{const t=t=>dt(t,r),e=wt(await this.#q(r),t);this.toc=e.toc,this.pageList=e.pageList,this.landmarks=e.landmarks}catch(t){console.warn(t)}if(!this.toc&&a)try{const t=t=>dt(t,a),e=yt(await this.#q(a),t);this.toc=e.toc,this.pageList=e.pageList}catch(t){console.warn(t)}this.landmarks??=this.resources.guide;const{metadata:o,rendition:l,media:h}=bt(s);this.metadata=o,this.rendition=l,this.media=h,this.dir=this.resources.pageProgressionDirection;const c=(d=await this.#q("META-INF/com.apple.ibooks.display-options.xml")??await this.#q("META-INF/com.kobobooks.display-options.xml"))?{fixedLayout:ht(d.querySelector('option[name="fixed-layout"]')),openToSpread:ht(d.querySelector('option[name="open-to-spread"]'))}:null;var d;return c&&("true"===c.fixedLayout&&(this.rendition.layout??="pre-paginated"),"false"===c.openToSpread&&(this.sections.find(t=>"no"!==t.linear).pageSpread??="rtl"===this.dir?"left":"right")),this}async loadDocument(t){const e=await this.loadText(t.href);return this.parser.parseFromString(e,t.mediaType)}getMediaOverlay(){return new xt(this,this.#q.bind(this))}resolveCFI(t){return this.resources.resolveCFI(t)}resolveHref(t){const[e,i]=t.split("#"),s=this.resources.getItemByHref(decodeURI(e));if(!s)return null;return{index:this.resources.spine.findIndex(({idref:t})=>t===s.id),anchor:i?t=>((t,e)=>t.getElementById(e)??t.querySelector(`[name="${CSS.escape(e)}"]`))(t,i):()=>0}}splitTOCHref(t){return t?.split("#")??[]}getTOCFragment(t,e){return t.getElementById(e)??t.querySelector(`[name="${CSS.escape(e)}"]`)}isExternal(t){return ut(t)}async getCover(){const t=this.resources?.cover;return t?.href?new Blob([await this.loadBlob(t.href)],{type:t.mediaType}):null}async getCalibreBookmarks(){const t=await this.loadText("META-INF/calibre_bookmarks.txt"),e="encoding=json+base64:";if(t?.startsWith(e)){const e=atob(t.slice(21));return JSON.parse(e)}}destroy(){this.#V?.destroy()}}var Rt=Object.freeze({__proto__:null,EPUB:Pt});const Lt=t=>{if(!t)return"";const e=document.createElement("textarea");return e.innerHTML=t,e.value},Dt={XML:"application/xml",XHTML:"application/xhtml+xml",HTML:"text/html",CSS:"text/css",SVG:"image/svg+xml"},Ft={name:[0,32,"string"],type:[60,4,"string"],creator:[64,4,"string"],numRecords:[76,2,"uint"]},Ot={compression:[0,2,"uint"],numTextRecords:[8,2,"uint"],recordSize:[10,2,"uint"],encryption:[12,2,"uint"]},Nt={magic:[16,4,"string"],length:[20,4,"uint"],type:[24,4,"uint"],encoding:[28,4,"uint"],uid:[32,4,"uint"],version:[36,4,"uint"],titleOffset:[84,4,"uint"],titleLength:[88,4,"uint"],localeRegion:[94,1,"uint"],localeLanguage:[95,1,"uint"],resourceStart:[108,4,"uint"],huffcdic:[112,4,"uint"],numHuffcdic:[116,4,"uint"],exthFlag:[128,4,"uint"],trailingFlags:[240,4,"uint"],indx:[244,4,"uint"]},zt={resourceStart:[108,4,"uint"],fdst:[192,4,"uint"],numFdst:[196,4,"uint"],frag:[248,4,"uint"],skel:[252,4,"uint"],guide:[260,4,"uint"]},Bt={magic:[0,4,"string"],length:[4,4,"uint"],count:[8,4,"uint"]},Ut={magic:[0,4,"string"],length:[4,4,"uint"],type:[8,4,"uint"],idxt:[20,4,"uint"],numRecords:[24,4,"uint"],encoding:[28,4,"uint"],language:[32,4,"uint"],total:[36,4,"uint"],ordt:[40,4,"uint"],ligt:[44,4,"uint"],numLigt:[48,4,"uint"],numCncx:[52,4,"uint"]},Ht={magic:[0,4,"string"],length:[4,4,"uint"],numControlBytes:[8,4,"uint"]},jt={magic:[0,4,"string"],offset1:[8,4,"uint"],offset2:[12,4,"uint"]},$t={magic:[0,4,"string"],length:[4,4,"uint"],numEntries:[8,4,"uint"],codeLength:[12,4,"uint"]},Wt={magic:[0,4,"string"],numEntries:[8,4,"uint"]},Vt={flags:[8,4,"uint"],dataStart:[12,4,"uint"],keyLength:[16,4,"uint"],keyStart:[20,4,"uint"]},Gt={1252:"windows-1252",65001:"utf-8"},qt={100:["creator","string",!0],101:["publisher"],103:["description"],104:["isbn"],105:["subject","string",!0],106:["date"],108:["contributor","string",!0],109:["rights"],110:["subjectCode","string",!0],112:["source","string",!0],113:["asin"],121:["boundary","uint"],122:["fixedLayout"],125:["numResources","uint"],126:["originalResolution"],127:["zeroGutter"],128:["zeroMargin"],129:["coverURI"],132:["regionMagnification"],201:["coverOffset","uint"],202:["thumbnailOffset","uint"],503:["title"],524:["language","string",!0],527:["pageProgressionDirection"]},Xt={1:["ar","ar-SA","ar-IQ","ar-EG","ar-LY","ar-DZ","ar-MA","ar-TN","ar-OM","ar-YE","ar-SY","ar-JO","ar-LB","ar-KW","ar-AE","ar-BH","ar-QA"],2:["bg"],3:["ca"],4:["zh","zh-TW","zh-CN","zh-HK","zh-SG"],5:["cs"],6:["da"],7:["de","de-DE","de-CH","de-AT","de-LU","de-LI"],8:["el"],9:["en","en-US","en-GB","en-AU","en-CA","en-NZ","en-IE","en-ZA","en-JM",null,"en-BZ","en-TT","en-ZW","en-PH"],10:["es","es-ES","es-MX",null,"es-GT","es-CR","es-PA","es-DO","es-VE","es-CO","es-PE","es-AR","es-EC","es-CL","es-UY","es-PY","es-BO","es-SV","es-HN","es-NI","es-PR"],11:["fi"],12:["fr","fr-FR","fr-BE","fr-CA","fr-CH","fr-LU","fr-MC"],13:["he"],14:["hu"],15:["is"],16:["it","it-IT","it-CH"],17:["ja"],18:["ko"],19:["nl","nl-NL","nl-BE"],20:["no","nb","nn"],21:["pl"],22:["pt","pt-BR","pt-PT"],23:["rm"],24:["ro"],25:["ru"],26:["hr",null,"sr"],27:["sk"],28:["sq"],29:["sv","sv-SE","sv-FI"],30:["th"],31:["tr"],32:["ur"],33:["id"],34:["uk"],35:["be"],36:["sl"],37:["et"],38:["lv"],39:["lt"],41:["fa"],42:["vi"],43:["hy"],44:["az"],45:["eu"],46:["hsb"],47:["mk"],48:["st"],49:["ts"],50:["tn"],52:["xh"],53:["zu"],54:["af"],55:["ka"],56:["fo"],57:["hi"],58:["mt"],59:["se"],62:["ms"],63:["kk"],65:["sw"],67:["uz",null,"uz-UZ"],68:["tt"],69:["bn"],70:["pa"],71:["gu"],72:["or"],73:["ta"],74:["te"],75:["kn"],76:["ml"],77:["as"],78:["mr"],79:["sa"],82:["cy","cy-GB"],83:["gl","gl-ES"],87:["kok"],97:["ne"],98:["fy"]},Kt=(t,e)=>{const i=new t.constructor(t.length+e.length);return i.set(t),i.set(e,t.length),i},Yt=(t,e,i)=>{const s=new t.constructor(t.length+e.length+i.length);return s.set(t),s.set(e,t.length),s.set(i,t.length+e.length),s},Qt=new TextDecoder,Jt=t=>Qt.decode(t),Zt=t=>{if(!t)return;const e=t.byteLength,i=4===e?"getUint32":2===e?"getUint16":"getUint8";return new DataView(t)[i](0)},te=(t,e)=>Object.fromEntries(Array.from(Object.entries(t)).map(([t,[i,s,n]])=>[t,("string"===n?Jt:Zt)(e.slice(i,i+s))])),ee=t=>new TextDecoder(Gt[t]),ie=(t,e=0)=>{let i=0,s=0;for(const n of t.subarray(e,e+4))if(i=i<<7|(127&n)>>>0,s++,128&n)break;return{value:i,length:s}},se=t=>{let e=0;for(const i of t.subarray(-4))128&i&&(e=0),e=e<<7|127&i;return e},ne=t=>{let e=0;for(;t>0;t>>=1)1&~t||e++;return