BiNgoViewer 2.3.2__tar.gz → 2.3.3__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (31) hide show
  1. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/BiNgoViewer.egg-info/PKG-INFO +1 -1
  2. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/BiNgoViewer.egg-info/SOURCES.txt +1 -1
  3. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/PKG-INFO +1 -1
  4. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/bingoviewer/__init__.py +1 -1
  5. bingoviewer-2.3.2/bingoviewer/frontend_dist/assets/index-LIiETdAH.js → bingoviewer-2.3.3/bingoviewer/frontend_dist/assets/index-r8ddmuu9.js +2 -2
  6. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/bingoviewer/frontend_dist/index.html +1 -1
  7. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/bingoviewer/server/api/data.py +1 -1
  8. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/bingoviewer/server/main.py +1 -1
  9. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/pyproject.toml +1 -1
  10. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/BiNgoViewer.egg-info/dependency_links.txt +0 -0
  11. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/BiNgoViewer.egg-info/entry_points.txt +0 -0
  12. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/BiNgoViewer.egg-info/requires.txt +0 -0
  13. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/BiNgoViewer.egg-info/top_level.txt +0 -0
  14. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/README.md +0 -0
  15. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/bingoviewer/__main__.py +0 -0
  16. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/bingoviewer/cli.py +0 -0
  17. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/bingoviewer/icon.py +0 -0
  18. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/bingoviewer/install_shortcut.py +0 -0
  19. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/bingoviewer/server/__init__.py +0 -0
  20. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/bingoviewer/server/api/__init__.py +0 -0
  21. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/bingoviewer/server/api/genome.py +0 -0
  22. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/bingoviewer/server/api/tracks.py +0 -0
  23. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/bingoviewer/server/readers/__init__.py +0 -0
  24. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/bingoviewer/server/readers/annotation_reader.py +0 -0
  25. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/bingoviewer/server/readers/bam_reader.py +0 -0
  26. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/bingoviewer/server/readers/bigwig_reader.py +0 -0
  27. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/bingoviewer/server/readers/genbank_reader.py +0 -0
  28. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/bingoviewer/server/readers/genome_reader.py +0 -0
  29. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/bingoviewer/server/readers/vcf_reader.py +0 -0
  30. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/bingoviewer/server/state.py +0 -0
  31. {bingoviewer-2.3.2 → bingoviewer-2.3.3}/setup.cfg +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: BiNgoViewer
3
- Version: 2.3.2
3
+ Version: 2.3.3
4
4
  Summary: BiNgo Genome Viewer — a lightweight browser-based genomics viewer
5
5
  Author-email: Billy M Ngo <billy.ngo0108@gmail.com>
6
6
  License: Proprietary
@@ -12,7 +12,7 @@ bingoviewer/cli.py
12
12
  bingoviewer/icon.py
13
13
  bingoviewer/install_shortcut.py
14
14
  bingoviewer/frontend_dist/index.html
15
- bingoviewer/frontend_dist/assets/index-LIiETdAH.js
15
+ bingoviewer/frontend_dist/assets/index-r8ddmuu9.js
16
16
  bingoviewer/server/__init__.py
17
17
  bingoviewer/server/main.py
18
18
  bingoviewer/server/state.py
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: BiNgoViewer
3
- Version: 2.3.2
3
+ Version: 2.3.3
4
4
  Summary: BiNgo Genome Viewer — a lightweight browser-based genomics viewer
5
5
  Author-email: Billy M Ngo <billy.ngo0108@gmail.com>
6
6
  License: Proprietary
@@ -1,3 +1,3 @@
1
1
  """BiNgo Genome Viewer — a lightweight browser-based genomics viewer."""
2
2
 
3
- __version__ = "2.3.2"
3
+ __version__ = "2.3.3"
@@ -42,7 +42,7 @@ Error generating stack: `+l.message+`
42
42
  `)}getSetCookie(){return this.get("set-cookie")||[]}get[Symbol.toStringTag](){return"AxiosHeaders"}static from(t){return t instanceof this?t:new this(t)}static concat(t,...n){const r=new this(t);return n.forEach(o=>r.set(o)),r}static accessor(t){const r=(this[oc]=this[oc]={accessors:{}}).accessors,o=this.prototype;function l(i){const a=Ar(i);r[a]||(d0(o,i),r[a]=!0)}return _.isArray(t)?t.forEach(l):l(t),this}};st.accessor(["Content-Type","Content-Length","Accept","Accept-Encoding","User-Agent","Authorization"]);_.reduceDescriptors(st.prototype,({value:e},t)=>{let n=t[0].toUpperCase()+t.slice(1);return{get:()=>e,set(r){this[n]=r}}});_.freezeMethods(st);function Pi(e,t){const n=this||Co,r=t||n,o=st.from(r.headers);let l=r.data;return _.forEach(e,function(a){l=a.call(n,l,o.normalize(),t?t.status:void 0)}),o.normalize(),l}function up(e){return!!(e&&e.__CANCEL__)}let To=class extends re{constructor(t,n,r){super(t??"canceled",re.ERR_CANCELED,n,r),this.name="CanceledError",this.__CANCEL__=!0}};function cp(e,t,n){const r=n.config.validateStatus;!n.status||!r||r(n.status)?e(n):t(new re("Request failed with status code "+n.status,[re.ERR_BAD_REQUEST,re.ERR_BAD_RESPONSE][Math.floor(n.status/100)-4],n.config,n.request,n))}function f0(e){const t=/^([-+\w]{1,25})(:?\/\/|:)/.exec(e);return t&&t[1]||""}function p0(e,t){e=e||10;const n=new Array(e),r=new Array(e);let o=0,l=0,i;return t=t!==void 0?t:1e3,function(u){const c=Date.now(),h=r[l];i||(i=c),n[o]=u,r[o]=c;let d=l,m=0;for(;d!==o;)m+=n[d++],d=d%e;if(o=(o+1)%e,o===l&&(l=(l+1)%e),c-i<t)return;const T=h&&c-h;return T?Math.round(m*1e3/T):void 0}}function h0(e,t){let n=0,r=1e3/t,o,l;const i=(c,h=Date.now())=>{n=h,o=null,l&&(clearTimeout(l),l=null),e(...c)};return[(...c)=>{const h=Date.now(),d=h-n;d>=r?i(c,h):(o=c,l||(l=setTimeout(()=>{l=null,i(o)},r-d)))},()=>o&&i(o)]}const Ll=(e,t,n=3)=>{let r=0;const o=p0(50,250);return h0(l=>{const i=l.loaded,a=l.lengthComputable?l.total:void 0,u=i-r,c=o(u),h=i<=a;r=i;const d={loaded:i,total:a,progress:a?i/a:void 0,bytes:u,rate:c||void 0,estimated:c&&a&&h?(a-i)/c:void 0,event:l,lengthComputable:a!=null,[t?"download":"upload"]:!0};e(d)},n)},lc=(e,t)=>{const n=e!=null;return[r=>t[0]({lengthComputable:n,total:e,loaded:r}),t[1]]},ic=e=>(...t)=>_.asap(()=>e(...t)),m0=Ye.hasStandardBrowserEnv?((e,t)=>n=>(n=new URL(n,Ye.origin),e.protocol===n.protocol&&e.host===n.host&&(t||e.port===n.port)))(new URL(Ye.origin),Ye.navigator&&/(msie|trident)/i.test(Ye.navigator.userAgent)):()=>!0,g0=Ye.hasStandardBrowserEnv?{write(e,t,n,r,o,l,i){if(typeof document>"u")return;const a=[`${e}=${encodeURIComponent(t)}`];_.isNumber(n)&&a.push(`expires=${new Date(n).toUTCString()}`),_.isString(r)&&a.push(`path=${r}`),_.isString(o)&&a.push(`domain=${o}`),l===!0&&a.push("secure"),_.isString(i)&&a.push(`SameSite=${i}`),document.cookie=a.join("; ")},read(e){if(typeof document>"u")return null;const t=document.cookie.match(new RegExp("(?:^|; )"+e+"=([^;]*)"));return t?decodeURIComponent(t[1]):null},remove(e){this.write(e,"",Date.now()-864e5,"/")}}:{write(){},read(){return null},remove(){}};function y0(e){return typeof e!="string"?!1:/^([a-z][a-z\d+\-.]*:)?\/\//i.test(e)}function x0(e,t){return t?e.replace(/\/?\/$/,"")+"/"+t.replace(/^\/+/,""):e}function dp(e,t,n){let r=!y0(t);return e&&(r||n==!1)?x0(e,t):t}const sc=e=>e instanceof st?{...e}:e;function Hn(e,t){t=t||{};const n={};function r(c,h,d,m){return _.isPlainObject(c)&&_.isPlainObject(h)?_.merge.call({caseless:m},c,h):_.isPlainObject(h)?_.merge({},h):_.isArray(h)?h.slice():h}function o(c,h,d,m){if(_.isUndefined(h)){if(!_.isUndefined(c))return r(void 0,c,d,m)}else return r(c,h,d,m)}function l(c,h){if(!_.isUndefined(h))return r(void 0,h)}function i(c,h){if(_.isUndefined(h)){if(!_.isUndefined(c))return r(void 0,c)}else return r(void 0,h)}function a(c,h,d){if(d in t)return r(c,h);if(d in e)return r(void 0,c)}const u={url:l,method:l,data:l,baseURL:i,transformRequest:i,transformResponse:i,paramsSerializer:i,timeout:i,timeoutMessage:i,withCredentials:i,withXSRFToken:i,adapter:i,responseType:i,xsrfCookieName:i,xsrfHeaderName:i,onUploadProgress:i,onDownloadProgress:i,decompress:i,maxContentLength:i,maxBodyLength:i,beforeRedirect:i,transport:i,httpAgent:i,httpsAgent:i,cancelToken:i,socketPath:i,responseEncoding:i,validateStatus:a,headers:(c,h,d)=>o(sc(c),sc(h),d,!0)};return _.forEach(Object.keys({...e,...t}),function(h){if(h==="__proto__"||h==="constructor"||h==="prototype")return;const d=_.hasOwnProp(u,h)?u[h]:o,m=d(e[h],t[h],h);_.isUndefined(m)&&d!==a||(n[h]=m)}),n}const fp=e=>{const t=Hn({},e);let{data:n,withXSRFToken:r,xsrfHeaderName:o,xsrfCookieName:l,headers:i,auth:a}=t;if(t.headers=i=st.from(i),t.url=sp(dp(t.baseURL,t.url,t.allowAbsoluteUrls),e.params,e.paramsSerializer),a&&i.set("Authorization","Basic "+btoa((a.username||"")+":"+(a.password?unescape(encodeURIComponent(a.password)):""))),_.isFormData(n)){if(Ye.hasStandardBrowserEnv||Ye.hasStandardBrowserWebWorkerEnv)i.setContentType(void 0);else if(_.isFunction(n.getHeaders)){const u=n.getHeaders(),c=["content-type","content-length"];Object.entries(u).forEach(([h,d])=>{c.includes(h.toLowerCase())&&i.set(h,d)})}}if(Ye.hasStandardBrowserEnv&&(r&&_.isFunction(r)&&(r=r(t)),r||r!==!1&&m0(t.url))){const u=o&&l&&g0.read(l);u&&i.set(o,u)}return t},v0=typeof XMLHttpRequest<"u",w0=v0&&function(e){return new Promise(function(n,r){const o=fp(e);let l=o.data;const i=st.from(o.headers).normalize();let{responseType:a,onUploadProgress:u,onDownloadProgress:c}=o,h,d,m,T,v;function y(){T&&T(),v&&v(),o.cancelToken&&o.cancelToken.unsubscribe(h),o.signal&&o.signal.removeEventListener("abort",h)}let x=new XMLHttpRequest;x.open(o.method.toUpperCase(),o.url,!0),x.timeout=o.timeout;function f(){if(!x)return;const g=st.from("getAllResponseHeaders"in x&&x.getAllResponseHeaders()),S={data:!a||a==="text"||a==="json"?x.responseText:x.response,status:x.status,statusText:x.statusText,headers:g,config:e,request:x};cp(function(b){n(b),y()},function(b){r(b),y()},S),x=null}"onloadend"in x?x.onloadend=f:x.onreadystatechange=function(){!x||x.readyState!==4||x.status===0&&!(x.responseURL&&x.responseURL.indexOf("file:")===0)||setTimeout(f)},x.onabort=function(){x&&(r(new re("Request aborted",re.ECONNABORTED,e,x)),x=null)},x.onerror=function(w){const S=w&&w.message?w.message:"Network Error",j=new re(S,re.ERR_NETWORK,e,x);j.event=w||null,r(j),x=null},x.ontimeout=function(){let w=o.timeout?"timeout of "+o.timeout+"ms exceeded":"timeout exceeded";const S=o.transitional||za;o.timeoutErrorMessage&&(w=o.timeoutErrorMessage),r(new re(w,S.clarifyTimeoutError?re.ETIMEDOUT:re.ECONNABORTED,e,x)),x=null},l===void 0&&i.setContentType(null),"setRequestHeader"in x&&_.forEach(i.toJSON(),function(w,S){x.setRequestHeader(S,w)}),_.isUndefined(o.withCredentials)||(x.withCredentials=!!o.withCredentials),a&&a!=="json"&&(x.responseType=o.responseType),c&&([m,v]=Ll(c,!0),x.addEventListener("progress",m)),u&&x.upload&&([d,T]=Ll(u),x.upload.addEventListener("progress",d),x.upload.addEventListener("loadend",T)),(o.cancelToken||o.signal)&&(h=g=>{x&&(r(!g||g.type?new To(null,e,x):g),x.abort(),x=null)},o.cancelToken&&o.cancelToken.subscribe(h),o.signal&&(o.signal.aborted?h():o.signal.addEventListener("abort",h)));const p=f0(o.url);if(p&&Ye.protocols.indexOf(p)===-1){r(new re("Unsupported protocol "+p+":",re.ERR_BAD_REQUEST,e));return}x.send(l||null)})},S0=(e,t)=>{const{length:n}=e=e?e.filter(Boolean):[];if(t||n){let r=new AbortController,o;const l=function(c){if(!o){o=!0,a();const h=c instanceof Error?c:this.reason;r.abort(h instanceof re?h:new To(h instanceof Error?h.message:h))}};let i=t&&setTimeout(()=>{i=null,l(new re(`timeout of ${t}ms exceeded`,re.ETIMEDOUT))},t);const a=()=>{e&&(i&&clearTimeout(i),i=null,e.forEach(c=>{c.unsubscribe?c.unsubscribe(l):c.removeEventListener("abort",l)}),e=null)};e.forEach(c=>c.addEventListener("abort",l));const{signal:u}=r;return u.unsubscribe=()=>_.asap(a),u}},b0=function*(e,t){let n=e.byteLength;if(n<t){yield e;return}let r=0,o;for(;r<n;)o=r+t,yield e.slice(r,o),r=o},k0=async function*(e,t){for await(const n of C0(e))yield*b0(n,t)},C0=async function*(e){if(e[Symbol.asyncIterator]){yield*e;return}const t=e.getReader();try{for(;;){const{done:n,value:r}=await t.read();if(n)break;yield r}}finally{await t.cancel()}},ac=(e,t,n,r)=>{const o=k0(e,t);let l=0,i,a=u=>{i||(i=!0,r&&r(u))};return new ReadableStream({async pull(u){try{const{done:c,value:h}=await o.next();if(c){a(),u.close();return}let d=h.byteLength;if(n){let m=l+=d;n(m)}u.enqueue(new Uint8Array(h))}catch(c){throw a(c),c}},cancel(u){return a(u),o.return()}},{highWaterMark:2})},uc=64*1024,{isFunction:Ho}=_,T0=(({Request:e,Response:t})=>({Request:e,Response:t}))(_.global),{ReadableStream:cc,TextEncoder:dc}=_.global,fc=(e,...t)=>{try{return!!e(...t)}catch{return!1}},j0=e=>{e=_.merge.call({skipUndefined:!0},T0,e);const{fetch:t,Request:n,Response:r}=e,o=t?Ho(t):typeof fetch=="function",l=Ho(n),i=Ho(r);if(!o)return!1;const a=o&&Ho(cc),u=o&&(typeof dc=="function"?(v=>y=>v.encode(y))(new dc):async v=>new Uint8Array(await new n(v).arrayBuffer())),c=l&&a&&fc(()=>{let v=!1;const y=new cc,x=new n(Ye.origin,{body:y,method:"POST",get duplex(){return v=!0,"half"}}).headers.has("Content-Type");return y.cancel(),v&&!x}),h=i&&a&&fc(()=>_.isReadableStream(new r("").body)),d={stream:h&&(v=>v.body)};o&&["text","arrayBuffer","blob","formData","stream"].forEach(v=>{!d[v]&&(d[v]=(y,x)=>{let f=y&&y[v];if(f)return f.call(y);throw new re(`Response type '${v}' is not supported`,re.ERR_NOT_SUPPORT,x)})});const m=async v=>{if(v==null)return 0;if(_.isBlob(v))return v.size;if(_.isSpecCompliantForm(v))return(await new n(Ye.origin,{method:"POST",body:v}).arrayBuffer()).byteLength;if(_.isArrayBufferView(v)||_.isArrayBuffer(v))return v.byteLength;if(_.isURLSearchParams(v)&&(v=v+""),_.isString(v))return(await u(v)).byteLength},T=async(v,y)=>{const x=_.toFiniteNumber(v.getContentLength());return x??m(y)};return async v=>{let{url:y,method:x,data:f,signal:p,cancelToken:g,timeout:w,onDownloadProgress:S,onUploadProgress:j,responseType:b,headers:E,withCredentials:O="same-origin",fetchOptions:z}=fp(v),P=t||fetch;b=b?(b+"").toLowerCase():"text";let H=S0([p,g&&g.toAbortSignal()],w),R=null;const U=H&&H.unsubscribe&&(()=>{H.unsubscribe()});let N;try{if(j&&c&&x!=="get"&&x!=="head"&&(N=await T(E,f))!==0){let A=new n(y,{method:"POST",body:f,duplex:"half"}),F;if(_.isFormData(f)&&(F=A.headers.get("content-type"))&&E.setContentType(F),A.body){const[V,M]=lc(N,Ll(ic(j)));f=ac(A.body,uc,V,M)}}_.isString(O)||(O=O?"include":"omit");const Y=l&&"credentials"in n.prototype,I={...z,signal:H,method:x.toUpperCase(),headers:E.normalize().toJSON(),body:f,duplex:"half",credentials:Y?O:void 0};R=l&&new n(y,I);let L=await(l?P(R,z):P(y,I));const $=h&&(b==="stream"||b==="response");if(h&&(S||$&&U)){const A={};["status","statusText","headers"].forEach(k=>{A[k]=L[k]});const F=_.toFiniteNumber(L.headers.get("content-length")),[V,M]=S&&lc(F,Ll(ic(S),!0))||[];L=new r(ac(L.body,uc,V,()=>{M&&M(),U&&U()}),A)}b=b||"text";let D=await d[_.findKey(d,b)||"text"](L,v);return!$&&U&&U(),await new Promise((A,F)=>{cp(A,F,{data:D,headers:st.from(L.headers),status:L.status,statusText:L.statusText,config:v,request:R})})}catch(Y){throw U&&U(),Y&&Y.name==="TypeError"&&/Load failed|fetch/i.test(Y.message)?Object.assign(new re("Network Error",re.ERR_NETWORK,v,R,Y&&Y.response),{cause:Y.cause||Y}):re.from(Y,Y&&Y.code,v,R,Y&&Y.response)}}},E0=new Map,pp=e=>{let t=e&&e.env||{};const{fetch:n,Request:r,Response:o}=t,l=[r,o,n];let i=l.length,a=i,u,c,h=E0;for(;a--;)u=l[a],c=h.get(u),c===void 0&&h.set(u,c=a?new Map:j0(t)),h=c;return c};pp();const Na={http:Hg,xhr:w0,fetch:{get:pp}};_.forEach(Na,(e,t)=>{if(e){try{Object.defineProperty(e,"name",{value:t})}catch{}Object.defineProperty(e,"adapterName",{value:t})}});const pc=e=>`- ${e}`,R0=e=>_.isFunction(e)||e===null||e===!1;function P0(e,t){e=_.isArray(e)?e:[e];const{length:n}=e;let r,o;const l={};for(let i=0;i<n;i++){r=e[i];let a;if(o=r,!R0(r)&&(o=Na[(a=String(r)).toLowerCase()],o===void 0))throw new re(`Unknown adapter '${a}'`);if(o&&(_.isFunction(o)||(o=o.get(t))))break;l[a||"#"+i]=o}if(!o){const i=Object.entries(l).map(([u,c])=>`adapter ${u} `+(c===!1?"is not supported by the environment":"is not available in the build"));let a=n?i.length>1?`since :
43
43
  `+i.map(pc).join(`
44
44
  `):" "+pc(i[0]):"as no adapter specified";throw new re("There is no suitable adapter to dispatch the request "+a,"ERR_NOT_SUPPORT")}return o}const hp={getAdapter:P0,adapters:Na};function _i(e){if(e.cancelToken&&e.cancelToken.throwIfRequested(),e.signal&&e.signal.aborted)throw new To(null,e)}function hc(e){return _i(e),e.headers=st.from(e.headers),e.data=Pi.call(e,e.transformRequest),["post","put","patch"].indexOf(e.method)!==-1&&e.headers.setContentType("application/x-www-form-urlencoded",!1),hp.getAdapter(e.adapter||Co.adapter,e)(e).then(function(r){return _i(e),r.data=Pi.call(e,e.transformResponse,r),r.headers=st.from(r.headers),r},function(r){return up(r)||(_i(e),r&&r.response&&(r.response.data=Pi.call(e,e.transformResponse,r.response),r.response.headers=st.from(r.response.headers))),Promise.reject(r)})}const mp="1.14.0",Zl={};["object","boolean","number","function","string","symbol"].forEach((e,t)=>{Zl[e]=function(r){return typeof r===e||"a"+(t<1?"n ":" ")+e}});const mc={};Zl.transitional=function(t,n,r){function o(l,i){return"[Axios v"+mp+"] Transitional option '"+l+"'"+i+(r?". "+r:"")}return(l,i,a)=>{if(t===!1)throw new re(o(i," has been removed"+(n?" in "+n:"")),re.ERR_DEPRECATED);return n&&!mc[i]&&(mc[i]=!0,console.warn(o(i," has been deprecated since v"+n+" and will be removed in the near future"))),t?t(l,i,a):!0}};Zl.spelling=function(t){return(n,r)=>(console.warn(`${r} is likely a misspelling of ${t}`),!0)};function _0(e,t,n){if(typeof e!="object")throw new re("options must be an object",re.ERR_BAD_OPTION_VALUE);const r=Object.keys(e);let o=r.length;for(;o-- >0;){const l=r[o],i=t[l];if(i){const a=e[l],u=a===void 0||i(a,l,e);if(u!==!0)throw new re("option "+l+" must be "+u,re.ERR_BAD_OPTION_VALUE);continue}if(n!==!0)throw new re("Unknown option "+l,re.ERR_BAD_OPTION)}}const il={assertOptions:_0,validators:Zl},xt=il.validators;let Nn=class{constructor(t){this.defaults=t||{},this.interceptors={request:new rc,response:new rc}}async request(t,n){try{return await this._request(t,n)}catch(r){if(r instanceof Error){let o={};Error.captureStackTrace?Error.captureStackTrace(o):o=new Error;const l=o.stack?o.stack.replace(/^.+\n/,""):"";try{r.stack?l&&!String(r.stack).endsWith(l.replace(/^.+\n.+\n/,""))&&(r.stack+=`
45
- `+l):r.stack=l}catch{}}throw r}}_request(t,n){typeof t=="string"?(n=n||{},n.url=t):n=t||{},n=Hn(this.defaults,n);const{transitional:r,paramsSerializer:o,headers:l}=n;r!==void 0&&il.assertOptions(r,{silentJSONParsing:xt.transitional(xt.boolean),forcedJSONParsing:xt.transitional(xt.boolean),clarifyTimeoutError:xt.transitional(xt.boolean),legacyInterceptorReqResOrdering:xt.transitional(xt.boolean)},!1),o!=null&&(_.isFunction(o)?n.paramsSerializer={serialize:o}:il.assertOptions(o,{encode:xt.function,serialize:xt.function},!0)),n.allowAbsoluteUrls!==void 0||(this.defaults.allowAbsoluteUrls!==void 0?n.allowAbsoluteUrls=this.defaults.allowAbsoluteUrls:n.allowAbsoluteUrls=!0),il.assertOptions(n,{baseUrl:xt.spelling("baseURL"),withXsrfToken:xt.spelling("withXSRFToken")},!0),n.method=(n.method||this.defaults.method||"get").toLowerCase();let i=l&&_.merge(l.common,l[n.method]);l&&_.forEach(["delete","get","head","post","put","patch","common"],v=>{delete l[v]}),n.headers=st.concat(i,l);const a=[];let u=!0;this.interceptors.request.forEach(function(y){if(typeof y.runWhen=="function"&&y.runWhen(n)===!1)return;u=u&&y.synchronous;const x=n.transitional||za;x&&x.legacyInterceptorReqResOrdering?a.unshift(y.fulfilled,y.rejected):a.push(y.fulfilled,y.rejected)});const c=[];this.interceptors.response.forEach(function(y){c.push(y.fulfilled,y.rejected)});let h,d=0,m;if(!u){const v=[hc.bind(this),void 0];for(v.unshift(...a),v.push(...c),m=v.length,h=Promise.resolve(n);d<m;)h=h.then(v[d++],v[d++]);return h}m=a.length;let T=n;for(;d<m;){const v=a[d++],y=a[d++];try{T=v(T)}catch(x){y.call(this,x);break}}try{h=hc.call(this,T)}catch(v){return Promise.reject(v)}for(d=0,m=c.length;d<m;)h=h.then(c[d++],c[d++]);return h}getUri(t){t=Hn(this.defaults,t);const n=dp(t.baseURL,t.url,t.allowAbsoluteUrls);return sp(n,t.params,t.paramsSerializer)}};_.forEach(["delete","get","head","options"],function(t){Nn.prototype[t]=function(n,r){return this.request(Hn(r||{},{method:t,url:n,data:(r||{}).data}))}});_.forEach(["post","put","patch"],function(t){function n(r){return function(l,i,a){return this.request(Hn(a||{},{method:t,headers:r?{"Content-Type":"multipart/form-data"}:{},url:l,data:i}))}}Nn.prototype[t]=n(),Nn.prototype[t+"Form"]=n(!0)});let L0=class gp{constructor(t){if(typeof t!="function")throw new TypeError("executor must be a function.");let n;this.promise=new Promise(function(l){n=l});const r=this;this.promise.then(o=>{if(!r._listeners)return;let l=r._listeners.length;for(;l-- >0;)r._listeners[l](o);r._listeners=null}),this.promise.then=o=>{let l;const i=new Promise(a=>{r.subscribe(a),l=a}).then(o);return i.cancel=function(){r.unsubscribe(l)},i},t(function(l,i,a){r.reason||(r.reason=new To(l,i,a),n(r.reason))})}throwIfRequested(){if(this.reason)throw this.reason}subscribe(t){if(this.reason){t(this.reason);return}this._listeners?this._listeners.push(t):this._listeners=[t]}unsubscribe(t){if(!this._listeners)return;const n=this._listeners.indexOf(t);n!==-1&&this._listeners.splice(n,1)}toAbortSignal(){const t=new AbortController,n=r=>{t.abort(r)};return this.subscribe(n),t.signal.unsubscribe=()=>this.unsubscribe(n),t.signal}static source(){let t;return{token:new gp(function(o){t=o}),cancel:t}}};function M0(e){return function(n){return e.apply(null,n)}}function B0(e){return _.isObject(e)&&e.isAxiosError===!0}const zs={Continue:100,SwitchingProtocols:101,Processing:102,EarlyHints:103,Ok:200,Created:201,Accepted:202,NonAuthoritativeInformation:203,NoContent:204,ResetContent:205,PartialContent:206,MultiStatus:207,AlreadyReported:208,ImUsed:226,MultipleChoices:300,MovedPermanently:301,Found:302,SeeOther:303,NotModified:304,UseProxy:305,Unused:306,TemporaryRedirect:307,PermanentRedirect:308,BadRequest:400,Unauthorized:401,PaymentRequired:402,Forbidden:403,NotFound:404,MethodNotAllowed:405,NotAcceptable:406,ProxyAuthenticationRequired:407,RequestTimeout:408,Conflict:409,Gone:410,LengthRequired:411,PreconditionFailed:412,PayloadTooLarge:413,UriTooLong:414,UnsupportedMediaType:415,RangeNotSatisfiable:416,ExpectationFailed:417,ImATeapot:418,MisdirectedRequest:421,UnprocessableEntity:422,Locked:423,FailedDependency:424,TooEarly:425,UpgradeRequired:426,PreconditionRequired:428,TooManyRequests:429,RequestHeaderFieldsTooLarge:431,UnavailableForLegalReasons:451,InternalServerError:500,NotImplemented:501,BadGateway:502,ServiceUnavailable:503,GatewayTimeout:504,HttpVersionNotSupported:505,VariantAlsoNegotiates:506,InsufficientStorage:507,LoopDetected:508,NotExtended:510,NetworkAuthenticationRequired:511,WebServerIsDown:521,ConnectionTimedOut:522,OriginIsUnreachable:523,TimeoutOccurred:524,SslHandshakeFailed:525,InvalidSslCertificate:526};Object.entries(zs).forEach(([e,t])=>{zs[t]=e});function yp(e){const t=new Nn(e),n=Kf(Nn.prototype.request,t);return _.extend(n,Nn.prototype,t,{allOwnKeys:!0}),_.extend(n,t,null,{allOwnKeys:!0}),n.create=function(o){return yp(Hn(e,o))},n}const Le=yp(Co);Le.Axios=Nn;Le.CanceledError=To;Le.CancelToken=L0;Le.isCancel=up;Le.VERSION=mp;Le.toFormData=Jl;Le.AxiosError=re;Le.Cancel=Le.CanceledError;Le.all=function(t){return Promise.all(t)};Le.spread=M0;Le.isAxiosError=B0;Le.mergeConfig=Hn;Le.AxiosHeaders=st;Le.formToJSON=e=>ap(_.isHTMLForm(e)?new FormData(e):e);Le.getAdapter=hp.getAdapter;Le.HttpStatusCode=zs;Le.default=Le;const{Axios:sx,AxiosError:ax,CanceledError:ux,isCancel:cx,CancelToken:dx,VERSION:fx,all:px,Cancel:hx,isAxiosError:mx,spread:gx,toFormData:yx,AxiosHeaders:xx,HttpStatusCode:vx,formToJSON:wx,getAdapter:Sx,mergeConfig:bx}=Le,rn=Le.create({baseURL:"/api"});function Kr(e,t,n){return new Promise((r,o)=>{const l=new XMLHttpRequest;l.open("POST",`/api${e}`),n&&l.upload.addEventListener("progress",i=>{i.lengthComputable&&n({loaded:i.loaded,total:i.total,percent:Math.round(i.loaded/i.total*100)})}),l.addEventListener("load",()=>{if(l.status>=200&&l.status<300)try{r({data:JSON.parse(l.responseText)})}catch{r({data:{}})}else{const i=new Error("Upload failed");try{i.response={status:l.status,data:JSON.parse(l.responseText)}}catch{i.response={status:l.status,data:{detail:l.statusText}}}o(i)}}),l.addEventListener("error",()=>{const i=new Error("Network error");i.response={status:0,data:{detail:"Network error — is the server running?"}},o(i)}),l.addEventListener("abort",()=>{const i=new Error("Upload aborted");i.name="CanceledError",o(i)}),l.send(t)})}const yn={load:(e,t)=>{const n=new FormData;return n.append("file",e),Kr("/genome/load",n,t)},loadPath:e=>{const t=new FormData;return t.append("path",e),Kr("/genome/load-path",t)},addChromosomes:(e,t)=>{const n=new FormData;return n.append("file",e),Kr("/genome/add-chromosomes",n,t)},chromosomes:()=>rn.get("/genome/chromosomes"),sequence:(e,t,n)=>rn.get("/genome/sequence",{params:{chrom:e,start:t,end:n}})},Ot={load:(e,t,n,r)=>{const o=new FormData;return o.append("file",e),t&&o.append("name",t),n&&o.append("index",n),Kr("/tracks/load",o,r)},loadPath:(e,t)=>{const n=new FormData;return n.append("path",e),t&&n.append("name",t),Kr("/tracks/load-path",n)},list:()=>rn.get("/tracks"),remove:e=>rn.delete(`/tracks/${e}`),coverage:(e,t,n,r,o=1e3)=>rn.get(`/tracks/${e}/coverage`,{params:{chrom:t,start:n,end:r,bins:o}}),reads:(e,t,n,r)=>rn.get(`/tracks/${e}/reads`,{params:{chrom:t,start:n,end:r}}),variants:(e,t,n,r)=>rn.get(`/tracks/${e}/variants`,{params:{chrom:t,start:n,end:r}}),features:(e,t,n,r)=>rn.get(`/tracks/${e}/features`,{params:{chrom:t,start:n,end:r}})},xp=C.createContext(null),gc=["#78909c","#81c784","#ffb74d","#f06292","#ce93d8","#80cbc4","#fff176","#ff8a65"],vp={cds:"#66bb6a",exon:"#42a5f5",gene:"#7e57c2",transcript:"#ab47bc",utr:"#26c6da",rrna:"#ffa726",trna:"#ef5350",repeat:"#8d6e63",default:"#80cbc4"};function Ft(e){return e&&e.replace(/\\u([0-9a-fA-F]{4})/g,(t,n)=>String.fromCharCode(parseInt(n,16)))}function A0({children:e}){const[t,n]=C.useState([]),[r,o]=C.useState(null),l=C.useRef(t);l.current=t;const i=C.useCallback(async(x,f,p,g)=>{var w,S;try{const b=(await Ot.load(x,f,p,g)).data;return b.name&&(b.name=Ft(b.name)),o(null),b}catch(j){const b=((S=(w=j.response)==null?void 0:w.data)==null?void 0:S.detail)||j.message||String(j);throw o(typeof b=="string"?b:JSON.stringify(b)),j}},[]),a=C.useCallback(x=>{n(f=>{const p=gc[f.length%gc.length],g=x.track_type==="annotations"||x.track_type==="genome_annotations";return[...f,{...x,color:p,height:z0(x.track_type),visible:!0,useArrows:!0,scaleMax:null,scaleMin:null,logScale:!1,barAutoWidth:!0,barWidth:2,showOutline:!1,outlineColor:null,outlineSmooth:0,showBars:!0,showNucleotides:!0,fwdColor:null,revColor:null,arrowStyle:"pointed",arrowSize:4,targetChromosomes:x.target_chromosomes||null,...g?{annotationColors:null}:{}}]})},[]),u=C.useCallback(async x=>{try{await Ot.remove(x)}catch{}},[]),c=C.useCallback(async(x,f)=>{const p=await i(x,f);return a(p),p},[i,a]),h=C.useCallback(async x=>{var p,g;const f=l.current.find(w=>w.id===x);if(f&&f.track_type==="genome_annotations"){n(w=>w.map(S=>S.id===x?{...S,visible:!1}:S));return}try{await Ot.remove(x),n(w=>w.filter(S=>S.id!==x))}catch(w){o(((g=(p=w.response)==null?void 0:p.data)==null?void 0:g.detail)||w.message)}},[]),d=C.useCallback(()=>{n(x=>x.map(f=>f.track_type==="genome_annotations"&&!f.visible?{...f,visible:!0}:f))},[]),m=C.useCallback((x,f)=>{n(p=>p.map(g=>g.id===x?{...g,...f}:g))},[]),T=C.useCallback((x,f)=>{n(p=>p.map(g=>x.includes(g.id)?{...g,...f}:g))},[]),v=C.useCallback((x,f)=>{n(p=>{const g=[...p],w=g.findIndex(b=>b.id===x),S=g.findIndex(b=>b.id===f);if(w===-1||S===-1)return p;const[j]=g.splice(w,1);return g.splice(S,0,j),g})},[]),y=C.useCallback(x=>{n(f=>{const p=f.findIndex(g=>g.id===x.id);if(p!==-1){const g=[...f];return g[p]={...g[p],name:Ft(x.name)||x.name,visible:!0,...x.targetChromosomes?{targetChromosomes:x.targetChromosomes}:{}},g}return[...f,{...x,name:Ft(x.name)||x.name,color:"#a5d6a7",height:80,visible:!0,useArrows:!0,annotationColors:null,targetChromosomes:x.targetChromosomes||null}]})},[]);return s.jsx(xp.Provider,{value:{tracks:t,setTracks:n,addTrack:c,uploadTrack:i,commitTrack:a,discardTrack:u,removeTrack:h,updateTrack:m,updateMultipleTracks:T,reorderTracks:v,addGenomeAnnotationTrack:y,restoreAnnotationTracks:d,error:r,setError:o},children:e})}function Jt(){return C.useContext(xp)}function z0(e){switch(e){case"reads":return 120;case"coverage":return 120;case"variants":return 60;case"annotations":case"genome_annotations":return 80;default:return 80}}const wp=C.createContext(null),yc={geneCds:"#66bb6a",geneExon:"#42a5f5",geneGene:"#7e57c2",geneTranscript:"#ab47bc",geneUtr:"#26c6da",geneRrna:"#ffa726",geneTrna:"#ef5350",geneRepeat:"#8d6e63",geneDefault:"#80cbc4"},vt={dark:{name:"Dark",appBg:"#1a1a1a",headerBg:"#2a2a2a",panelBg:"#252525",canvasBg:"#1a1a1a",inputBg:"#333",border:"#333",borderAccent:"#444",borderStrong:"#555",btnBg:"#555",btnText:"#fff",btnDanger:"#c62828",textPrimary:"#e0e0e0",textSecondary:"#999",textTertiary:"#777",textMuted:"#666",trackName:"#ccc",rulerTick:"#888",rulerLabel:"#ccc",tooltipBg:"#333",tooltipBorder:"#555",overlayBg:"rgba(0,0,0,0.55)",selectedRow:"#333",centerLine:"#555",...yc},light:{name:"Light",appBg:"#f5f5f5",headerBg:"#ffffff",panelBg:"#eee",canvasBg:"#ffffff",inputBg:"#fff",border:"#ddd",borderAccent:"#bbb",borderStrong:"#999",btnBg:"#e0e0e0",btnText:"#333",btnDanger:"#d32f2f",textPrimary:"#222",textSecondary:"#666",textTertiary:"#888",textMuted:"#aaa",trackName:"#333",rulerTick:"#666",rulerLabel:"#333",tooltipBg:"#fff",tooltipBorder:"#ccc",overlayBg:"rgba(0,0,0,0.25)",selectedRow:"#dde4ee",centerLine:"#ccc",...yc},colorblind:{name:"Colorblind Friendly",appBg:"#1a1a1a",headerBg:"#2a2a2a",panelBg:"#252525",canvasBg:"#1a1a1a",inputBg:"#333",border:"#333",borderAccent:"#444",borderStrong:"#555",btnBg:"#555",btnText:"#fff",btnDanger:"#cc4125",textPrimary:"#e0e0e0",textSecondary:"#999",textTertiary:"#777",textMuted:"#666",trackName:"#ccc",rulerTick:"#888",rulerLabel:"#ccc",tooltipBg:"#333",tooltipBorder:"#555",overlayBg:"rgba(0,0,0,0.55)",selectedRow:"#333",centerLine:"#555",geneCds:"#009e73",geneExon:"#0072b2",geneGene:"#cc79a7",geneTranscript:"#d55e00",geneUtr:"#56b4e9",geneRrna:"#e69f00",geneTrna:"#f0e442",geneRepeat:"#999999",geneDefault:"#56b4e9"},soft:{name:"Soft",appBg:"#f0ede8",headerBg:"#e4dfd8",panelBg:"#e9e5de",canvasBg:"#f5f2ed",inputBg:"#fff",border:"#d5cfc6",borderAccent:"#c4bdb2",borderStrong:"#a89f93",btnBg:"#d5cfc6",btnText:"#4a4540",btnDanger:"#c47066",textPrimary:"#3a3530",textSecondary:"#7a7468",textTertiary:"#9a9488",textMuted:"#b5ada2",trackName:"#4a4540",rulerTick:"#a89f93",rulerLabel:"#5a5550",tooltipBg:"#fff",tooltipBorder:"#d5cfc6",overlayBg:"rgba(0,0,0,0.2)",selectedRow:"#ddd8d0",centerLine:"#c4bdb2",geneCds:"#4caf50",geneExon:"#2e8bc0",geneGene:"#8e44ad",geneTranscript:"#c0392b",geneUtr:"#1abc9c",geneRrna:"#e67e22",geneTrna:"#e74c3c",geneRepeat:"#8d6e63",geneDefault:"#27ae60"},highContrast:{name:"High Contrast",appBg:"#000",headerBg:"#111",panelBg:"#111",canvasBg:"#000",inputBg:"#222",border:"#444",borderAccent:"#666",borderStrong:"#888",btnBg:"#444",btnText:"#fff",btnDanger:"#f44336",textPrimary:"#fff",textSecondary:"#ccc",textTertiary:"#aaa",textMuted:"#888",trackName:"#fff",rulerTick:"#aaa",rulerLabel:"#fff",tooltipBg:"#222",tooltipBorder:"#666",overlayBg:"rgba(0,0,0,0.7)",selectedRow:"#333",centerLine:"#555",geneCds:"#4caf50",geneExon:"#2196f3",geneGene:"#9c27b0",geneTranscript:"#e040fb",geneUtr:"#00e5ff",geneRrna:"#ff9800",geneTrna:"#ff1744",geneRepeat:"#ff6e40",geneDefault:"#69f0ae"}},Sp="genomics-viewer-theme",bp="genomics-viewer-custom-theme";function $0(){try{const e=localStorage.getItem(Sp),t=localStorage.getItem(bp);return{name:e&&(vt[e]||e==="custom")?e:"dark",custom:t?JSON.parse(t):null}}catch{return{name:"dark",custom:null}}}function N0({children:e}){const t=$0(),[n,r]=C.useState(t.name),[o,l]=C.useState(t.custom||{...vt.dark,name:"Custom"}),i=n==="custom"?o:vt[n]||vt.dark,a=C.useCallback(c=>{r(c),localStorage.setItem(Sp,c)},[]),u=C.useCallback(c=>{l(c),localStorage.setItem(bp,JSON.stringify(c))},[]);return C.useEffect(()=>{document.body.style.background=i.appBg,document.body.style.color=i.textPrimary},[i.appBg,i.textPrimary]),s.jsx(wp.Provider,{value:{theme:i,themeName:n,setThemeName:a,customTheme:o,setCustomTheme:u},children:e})}function Xe(){return C.useContext(wp)}function O0(e){const t=e==null?void 0:e.compatibility;return t&&t.status!=="ok"&&t.status!=="no_genome"}function xc(e){return e<1024?`${e} B`:e<1024*1024?`${(e/1024).toFixed(0)} KB`:`${(e/(1024*1024)).toFixed(1)} MB`}const $s=new Set([".gb",".gbk",".genbank",".fasta",".fa"]),Ns=new Set([".bam",".bw",".bigwig",".wig",".bedgraph",".bdg",".vcf",".bed",".gtf",".gff",".gff2",".gff3"]),vc=50*1024*1024;function Ml(e){if(!e)return"";const t=e.toLowerCase();if(t.endsWith(".vcf.gz"))return".vcf.gz";if(t.endsWith(".bam.bai"))return".bam.bai";const n=t.lastIndexOf(".");return n>=0?t.slice(n):""}function F0(e){const t=Ml(e);return t===".bai"||t===".bam.bai"}function I0(e){const t=[],n=[],r=[],o=[],l=[],i=[];for(const c of e){const h=Ml(c.name);$s.has(h)?t.push(c):h===".bam"?n.push(c):F0(c.name)?r.push(c):Ns.has(h)||h===".vcf.gz"?c.size>vc?i.push(c):o.push(c):l.push(c)}const a=[],u=[];for(const c of n){const h=c.name.replace(/\.bam$/i,""),d=r.find(m=>{const T=m.name.toLowerCase();return T===c.name.toLowerCase()+".bai"||T===h.toLowerCase()+".bai"});if(d){c.size>vc?i.push(c):a.push({file:c,indexFile:d});const m=r.indexOf(d);m!==-1&&r.splice(m,1)}else u.push(c)}for(const c of o)a.push({file:c,indexFile:null});for(const c of r)c._indexOrphan=!0;return l.push(...r),{genomeFiles:t,trackEntries:a,unpairedBams:u,largeFiles:i,unknownFiles:l}}function D0(){const{theme:e}=Xe(),{genome:t,setGenome:n,navigateTo:r}=at(),{addTrack:o,uploadTrack:l,commitTrack:i,discardTrack:a,addGenomeAnnotationTrack:u,error:c,setError:h}=Jt(),[d,m]=C.useState(!1),[T,v]=C.useState(null),[y,x]=C.useState(null),[f,p]=C.useState(null),[g,w]=C.useState(null),[S,j]=C.useState(null),[b,E]=C.useState(null),[O,z]=C.useState(""),[P,H]=C.useState(!1),R=C.useRef(null),U=C.useRef(null),N=C.useRef(null),Y=[...Array.from($s),...Array.from(Ns),".vcf.gz",".bai"].join(","),I={panel:{background:e.panelBg,borderBottom:`1px solid ${e.border}`,padding:"8px 12px",display:"flex",alignItems:"center",gap:12,flexWrap:"wrap",position:"relative"},group:{display:"flex",alignItems:"center",gap:6},label:{fontSize:11,color:e.textSecondary,textTransform:"uppercase",letterSpacing:1,whiteSpace:"nowrap"},fileInput:{background:e.inputBg,border:`1px solid ${e.borderAccent}`,borderRadius:4,color:e.textPrimary,padding:"4px 6px",fontSize:12,width:280,cursor:"pointer"},promptOverlay:{position:"fixed",inset:0,zIndex:9999,background:"rgba(0,0,0,0.35)",display:"flex",alignItems:"center",justifyContent:"center"},promptBox:{background:e.panelBg,border:`1px solid ${e.borderAccent}`,borderRadius:8,padding:"20px 24px",boxShadow:"0 8px 32px rgba(0,0,0,0.5)",maxWidth:440,width:"90%"},promptTitle:{fontSize:14,fontWeight:700,color:e.textPrimary,marginBottom:8},promptText:{fontSize:12,color:e.textSecondary,lineHeight:1.6,marginBottom:16},promptFile:{fontWeight:600,color:e.textPrimary},promptBtns:{display:"flex",gap:8,justifyContent:"flex-end",flexWrap:"wrap"},promptBtn:{background:e.btnBg,border:`1px solid ${e.borderStrong}`,borderRadius:4,color:e.btnText,padding:"5px 16px",cursor:"pointer",fontSize:12,fontWeight:600},promptBtnPrimary:{background:"#1976d2",border:"none",borderRadius:4,color:"#fff",padding:"5px 16px",cursor:"pointer",fontSize:12,fontWeight:600}};async function L(G){var J,te,B;m(!0),v(null),p(null),x(`Uploading genome: ${G.name}...`);try{const q=await yn.load(G,Z=>{p({...Z,label:G.name}),Z.percent>=100&&x(`Processing genome: ${G.name}...`)});p(null);const X=q.data;if(X.name&&(X.name=Ft(X.name)),n(X),((J=X.chromosomes)==null?void 0:J.length)>0){const Z=X.chromosomes[0];r(Z.name,0,Math.min(Z.length,5e4))}X.is_annotated&&u({id:"genome_annotations",name:`${X.name} (annotations)`,track_type:"genome_annotations",file_format:"genbank",targetChromosomes:X.annotated_chromosomes||null}),x(`Genome loaded: ${X.name}`),setTimeout(()=>x(null),3e3)}catch(q){v(((B=(te=q.response)==null?void 0:te.data)==null?void 0:B.detail)||q.message),x(null),p(null)}finally{m(!1)}}async function $(G){var te,B;m(!0),v(null),p(null);const J=[];for(const q of G){x(`Adding chromosomes from ${q.name}...`);try{const Z=(await yn.addChromosomes(q,le=>{p({...le,label:q.name})})).data;Z.name&&(Z.name=Ft(Z.name)),n(Z),Z.is_annotated&&u({id:"genome_annotations",name:`${Z.name} (annotations)`,track_type:"genome_annotations",file_format:"genbank",targetChromosomes:Z.annotated_chromosomes||null})}catch(X){J.push(`${q.name}: ${((B=(te=X.response)==null?void 0:te.data)==null?void 0:B.detail)||X.message}`)}}m(!1),J.length?(v(J.join("; ")),x(null)):(x(`Added chromosomes from ${G.length} file${G.length>1?"s":""}.`),setTimeout(()=>x(null),3e3))}async function D(G){var X,Z;if(!G.length)return;m(!0),v(null),h(null),p(null);const J=[],te=[],B=[],q=[];for(let le=0;le<G.length;le++){const{file:oe,indexFile:fe}=G[le];x(`Loading track ${le+1}/${G.length}: ${oe.name}...`);try{const we=await l(oe,void 0,fe,Ie=>{p({...Ie,label:oe.name}),Ie.percent>=100&&x(`Processing: ${oe.name}...`)});O0(we)?te.push(we):(i(we),J.push(we)),we.hint&&q.push(we.hint)}catch(we){B.push(`${oe.name}: ${((Z=(X=we.response)==null?void 0:X.data)==null?void 0:Z.detail)||we.message}`)}}if(m(!1),p(null),B.length)v(B.join("; ")),x(null);else if(J.length>0&&te.length===0){const le=`Added ${J.length} track${J.length>1?"s":""}.`;q.length?(x(le),setTimeout(()=>{x(q.join(" ")),setTimeout(()=>x(null),8e3)},2e3)):(x(le),setTimeout(()=>x(null),3e3))}else te.length===0&&x(null);te.length>0&&j({tracks:te})}async function A(G){const J=Array.from(G);if(!J.length)return;const{genomeFiles:te,trackEntries:B,unpairedBams:q,largeFiles:X,unknownFiles:Z}=I0(J);if(Z.length){const le=Z.filter(fe=>fe._indexOrphan),oe=Z.filter(fe=>!fe._indexOrphan);le.length&&E({bamFile:null,indexFile:le[0],bamPath:"",indexPath:"",error:null}),oe.length&&v(`Unsupported: ${oe.map(fe=>fe.name).join(", ")}`)}if(X.length>0){const le=X[0],oe=(le.size/(1024*1024)).toFixed(0),fe=le.name.toLowerCase().endsWith(".bam");E({bamFile:fe?le:null,indexFile:null,bamPath:"",indexPath:"",error:null,_largeFile:le,_largeWarning:`${le.name} is ${oe} MB. Large files load much faster via file path — the server reads directly from disk without uploading.`}),X.length>1&&v(`${X.length-1} additional large file(s) skipped — load one at a time via path.`)}if(q.length>0&&X.length===0&&E({bamFile:q[0],indexFile:null,bamPath:"",indexPath:"",error:null}),te.length>0&&!t){if(await L(te[0]),te.length>1){B.length>0&&await D(B),w({files:te.slice(1)}),R.current&&(R.current.value="");return}B.length>0&&await D(B)}else te.length>0&&t?(B.length>0&&await D(B),w({files:te})):B.length>0&&(t?await D(B):v("Load a genome file first (.fasta, .gb, .genbank)"));R.current&&(R.current.value="")}async function F(G){var X,Z,le,oe,fe;const J=G.trim();if(!J)return;v(null);const te=J.toLowerCase(),B=$s.has(Ml(J)),q=Ns.has(Ml(J))||te.endsWith(".vcf.gz")||te.endsWith(".bai");if(B&&!t){m(!0),x("Loading genome from path...");try{const Ie=(await yn.loadPath(J)).data;if(Ie.name&&(Ie.name=Ft(Ie.name)),n(Ie),((X=Ie.chromosomes)==null?void 0:X.length)>0){const ut=Ie.chromosomes[0];r(ut.name,0,Math.min(ut.length,5e4))}Ie.is_annotated&&u({id:"genome_annotations",name:`${Ie.name} (annotations)`,track_type:"genome_annotations",file_format:"genbank",targetChromosomes:Ie.annotated_chromosomes||null}),x(`Genome loaded: ${Ie.name}`),setTimeout(()=>x(null),3e3)}catch(we){v(((le=(Z=we.response)==null?void 0:Z.data)==null?void 0:le.detail)||we.message),x(null)}finally{m(!1)}}else if(q||B){if(!t){v("Load a genome file first");return}m(!0),x("Loading track from path...");try{const we=J.split(/[/\\]/).pop()||J,ut=(await Ot.loadPath(J,we)).data;ut.name&&(ut.name=Ft(ut.name)),i(ut),x(`Track loaded: ${ut.name}`),ut.hint?setTimeout(()=>{x(ut.hint),setTimeout(()=>x(null),8e3)},2e3):setTimeout(()=>x(null),3e3)}catch(we){v(((fe=(oe=we.response)==null?void 0:oe.data)==null?void 0:fe.detail)||we.message),x(null)}finally{m(!1)}}else v(`Unsupported file type: ${J.split(/[/\\]/).pop()}`);z("")}function V(G){G.preventDefault(),F(O)}function M(G){const J=G.target.files;J!=null&&J.length&&(v(null),A(J))}async function k(){if(!g)return;const{files:G}=g;w(null),await $(G)}async function Q(){if(!g)return;const{files:G}=g;w(null),await D(G.map(J=>({file:J,indexFile:null})))}function ee(){w(null)}function ce(){var G;(G=U.current)==null||G.click()}function he(){var G;(G=N.current)==null||G.click()}function pe(G){var te;const J=(te=G.target.files)==null?void 0:te[0];if(G.target.value="",!!J){if(!J.name.toLowerCase().endsWith(".bam")){E(B=>({...B,error:"Please select a .bam file"}));return}E(B=>({...B,bamFile:J,bamPath:"",error:null}))}}function ae(G){var te;const J=(te=G.target.files)==null?void 0:te[0];if(G.target.value="",!!J){if(!J.name.toLowerCase().endsWith(".bai")){E(B=>({...B,error:"Please select a .bai index file"}));return}E(B=>({...B,indexFile:J,indexPath:"",error:null}))}}function ie(G){return G&&(G.bamFile||G.bamPath.trim())}function ne(G){return G&&(G.indexFile||G.indexPath.trim())}function xe(G){return ie(G)&&ne(G)}async function Me(){if(!b)return;const{bamFile:G,indexFile:J,bamPath:te,indexPath:B,_largeFile:q}=b,X=te.trim(),Z=B.trim();if(q&&!q.name.toLowerCase().endsWith(".bam")){if(!X){E(oe=>({...oe,error:"File path is required"}));return}E(null),await F(X);return}if(!G&&!X){E(oe=>({...oe,error:"BAM file or path is required"}));return}if(!J&&!Z){E(oe=>({...oe,error:"BAM index (.bai) file or path is required"}));return}if(X&&!X.toLowerCase().endsWith(".bam")){E(oe=>({...oe,error:"BAM path must end with .bam"}));return}if(Z&&!Z.toLowerCase().endsWith(".bai")){E(oe=>({...oe,error:"Index path must end with .bai"}));return}if(E(null),!G&&X){await F(X);return}await D([{file:G,indexFile:J}])}function ve(){E(null)}async function Fe(){if(S){for(const G of S.tracks)await a(G.id);j(null)}}function et(){if(S){for(const G of S.tracks)i(G);j(null),x(`Added ${S.tracks.length} track${S.tracks.length>1?"s":""}.`),setTimeout(()=>x(null),3e3)}}const me=g?g.files.map(G=>G.name).join(", "):"",gt=g&&g.files.length>1;return s.jsxs("div",{style:I.panel,"data-tour":"file-loader",children:[s.jsxs("div",{style:I.group,title:"Select genome or track files",children:[s.jsx("span",{style:I.label,children:"Load Files"}),s.jsx("input",{ref:R,type:"file",multiple:!0,style:I.fileInput,disabled:d,accept:Y,onChange:M})]}),s.jsxs("button",{style:{...I.group,background:"none",border:`1px solid ${e.borderAccent}`,borderRadius:4,padding:"3px 8px",cursor:"pointer",color:e.textSecondary,fontSize:11},onClick:()=>H(G=>!G),title:"Load file by local path (recommended for large BAM files)",children:[P?"✕":"📂"," Path"]}),P&&s.jsxs("form",{onSubmit:V,style:{display:"flex",gap:4},children:[s.jsx("input",{type:"text",value:O,onChange:G=>z(G.target.value),placeholder:"/path/to/file.bam",disabled:d,style:{background:e.inputBg,border:`1px solid ${e.borderAccent}`,borderRadius:4,color:e.textPrimary,padding:"4px 8px",fontSize:11,width:260,fontFamily:"monospace"}}),s.jsx("button",{type:"submit",disabled:d||!O.trim(),style:{background:e.btnBg,border:"none",borderRadius:4,color:e.btnText,padding:"4px 10px",cursor:"pointer",fontSize:11,fontWeight:600},children:"Load"})]}),d?s.jsxs("div",{style:{display:"flex",alignItems:"center",gap:8,flex:1,minWidth:0},children:[s.jsx("span",{style:{fontSize:10,color:e.textMuted,fontStyle:"italic",whiteSpace:"nowrap",overflow:"hidden",textOverflow:"ellipsis"},children:y||"Loading…"}),f&&s.jsxs("div",{style:{display:"flex",alignItems:"center",gap:6,flex:1,minWidth:100},children:[s.jsx("div",{style:{flex:1,height:6,background:e.inputBg,borderRadius:3,overflow:"hidden",minWidth:60},children:s.jsx("div",{style:{width:`${f.percent}%`,height:"100%",background:f.percent>=100?"#66bb6a":"#42a5f5",borderRadius:3,transition:"width 0.2s ease"}})}),s.jsx("span",{style:{fontSize:10,color:e.textTertiary,whiteSpace:"nowrap"},children:f.percent<100?`${xc(f.loaded)} / ${xc(f.total)}`:"Processing..."})]})]}):s.jsx("span",{style:{fontSize:10,color:e.textMuted,fontStyle:"italic"},children:"or drag & drop anywhere"}),!d&&y&&s.jsx("span",{style:{color:"#81c784",fontSize:11},children:y}),(T||c)&&s.jsx("span",{style:{color:"#ef9a9a",fontSize:11},children:T||c}),g&&s.jsx("div",{style:I.promptOverlay,children:s.jsxs("div",{style:I.promptBox,onClick:G=>G.stopPropagation(),children:[s.jsxs("div",{style:I.promptTitle,children:["Genome file",gt?"s":""," detected"]}),s.jsxs("div",{style:I.promptText,children:[s.jsx("span",{style:I.promptFile,children:me}),gt?" appear to be genome files. A genome is already loaded.":" appears to be a genome file. A genome is already loaded.",s.jsx("br",{}),"How would you like to handle ",gt?"them":"it","?"]}),s.jsxs("div",{style:I.promptBtns,children:[s.jsx("button",{style:I.promptBtn,onClick:ee,children:"Skip"}),s.jsxs("button",{style:I.promptBtn,onClick:Q,children:["Add as Track",gt?"s":""]}),s.jsxs("button",{style:I.promptBtnPrimary,onClick:k,children:["Add as Chromosome",gt?"s":""]})]})]})}),S&&s.jsx("div",{style:I.promptOverlay,children:s.jsxs("div",{style:I.promptBox,onClick:G=>G.stopPropagation(),children:[s.jsx("div",{style:I.promptTitle,children:"Track compatibility warning"}),s.jsxs("div",{style:I.promptText,children:[S.tracks.map(G=>{var J;return s.jsxs("div",{style:{marginBottom:6},children:[s.jsx("span",{style:I.promptFile,children:G.name})," — ",((J=G.compatibility)==null?void 0:J.message)||"Possible mismatch with loaded genome"]},G.id)}),s.jsx("div",{style:{marginTop:8},children:S.tracks.length>1?"These tracks may not match the loaded genome.":"This track may not match the loaded genome."})]}),s.jsxs("div",{style:I.promptBtns,children:[s.jsx("button",{style:I.promptBtn,onClick:Fe,children:"Skip"}),s.jsx("button",{style:I.promptBtnPrimary,onClick:et,children:"Load Anyway"})]})]})}),b&&(()=>{const G=b._largeFile&&!b._largeFile.name.toLowerCase().endsWith(".bam"),J=G?!!b.bamPath.trim():xe(b),te=b.bamFile?b.bamFile.size/(1024*1024):0,B=b.bamFile&&te>50,q=ie(b),X=ne(b),Z={flex:1,padding:"5px 8px",borderRadius:4,fontSize:11,background:e.inputBg,color:e.textPrimary,fontFamily:"monospace"},le=G?`Load ${b._largeFile.name.split(".").pop().toUpperCase()} Track`:"Load BAM Track",oe=G?"Paste the local file path for the server to read directly from disk.":"BAM files require a matching .bai index. Browse for files or paste local paths.";return s.jsx("div",{style:I.promptOverlay,onClick:ve,children:s.jsxs("div",{style:{...I.promptBox,maxWidth:500},onClick:fe=>fe.stopPropagation(),children:[s.jsx("div",{style:I.promptTitle,children:le}),s.jsx("div",{style:{...I.promptText,marginBottom:12},children:oe}),s.jsxs("div",{style:{marginBottom:10},children:[s.jsxs("div",{style:{fontSize:11,color:e.textSecondary,marginBottom:4,fontWeight:600},children:[G?"File path":".bam file"," ",q&&s.jsx("span",{style:{color:"#66bb6a"},children:"✓"})]}),s.jsxs("div",{style:{display:"flex",gap:6,alignItems:"center"},children:[s.jsx("input",{type:"text",value:b.bamFile?b.bamFile.name:b.bamPath,onChange:fe=>E(we=>({...we,bamPath:fe.target.value,bamFile:null,error:null})),placeholder:G?"/path/to/file":"/path/to/reads.bam",style:{...Z,border:`1px solid ${q?"#66bb6a":e.borderAccent}`}}),!G&&s.jsx("button",{style:{...I.promptBtn,padding:"4px 12px",whiteSpace:"nowrap"},onClick:ce,children:"Browse"})]})]}),!G&&s.jsxs("div",{style:{marginBottom:12},children:[s.jsxs("div",{style:{fontSize:11,color:e.textSecondary,marginBottom:4,fontWeight:600},children:[".bai index ",X&&s.jsx("span",{style:{color:"#66bb6a"},children:"✓"})]}),s.jsxs("div",{style:{display:"flex",gap:6,alignItems:"center"},children:[s.jsx("input",{type:"text",value:b.indexFile?b.indexFile.name:b.indexPath,onChange:fe=>E(we=>({...we,indexPath:fe.target.value,indexFile:null,error:null})),placeholder:"/path/to/reads.bam.bai",style:{...Z,border:`1px solid ${X?"#66bb6a":e.borderAccent}`}}),s.jsx("button",{style:{...I.promptBtn,padding:"4px 12px",whiteSpace:"nowrap"},onClick:he,children:"Browse"})]})]}),s.jsx("input",{ref:U,type:"file",accept:".bam",style:{display:"none"},onChange:pe}),s.jsx("input",{ref:N,type:"file",accept:".bai,.bam.bai",style:{display:"none"},onChange:ae}),(B||b._largeWarning)&&s.jsx("div",{style:{fontSize:11,color:"#ffb74d",marginBottom:8,padding:"6px 10px",background:"rgba(255,183,77,0.1)",borderRadius:4,border:"1px solid rgba(255,183,77,0.3)"},children:b._largeWarning||s.jsxs(s.Fragment,{children:[s.jsxs("strong",{children:["Large file (",te.toFixed(0)," MB)"]})," — uploading may be slow. Paste the file path instead for instant loading."]})}),b.error&&s.jsx("div",{style:{fontSize:11,color:"#ef9a9a",marginBottom:8,padding:"4px 0"},children:b.error}),!B&&s.jsx("div",{style:{fontSize:10,color:e.textTertiary,marginBottom:10},children:"Tip: Paste a local file path to skip uploading — the server reads directly from disk. The .bai is auto-discovered if next to the .bam."}),s.jsxs("div",{style:I.promptBtns,children:[s.jsx("button",{style:I.promptBtn,onClick:ve,children:"Cancel"}),s.jsx("button",{style:{...I.promptBtnPrimary,opacity:J?1:.4,cursor:J?"pointer":"default"},disabled:!J,onClick:Me,children:"Open"})]})]})})})()]})}const U0=260,W0=180,H0=440,V0=.78,G0=1.4;function kp({title:e,onClose:t,theme:n,children:r,defaultWidth:o=440,defaultHeight:l=500}){const[i,a]=C.useState(()=>({x:Math.max(20,window.innerWidth-o-40),y:80})),[u,c]=C.useState({w:o,h:Math.min(l,window.innerHeight-120)}),h=C.useRef(null),d=C.useRef(null),m=C.useMemo(()=>{const f=u.w/H0;return Math.max(V0,Math.min(G0,f))},[u.w]),T=u.w/m,v=C.useCallback(f=>{if(f.target.closest("input, select, button, label, textarea"))return;f.preventDefault(),h.current={startX:f.clientX,startY:f.clientY,startPos:{...i}};function p(w){h.current&&a({x:Math.max(0,Math.min(window.innerWidth-100,h.current.startPos.x+w.clientX-h.current.startX)),y:Math.max(0,Math.min(window.innerHeight-40,h.current.startPos.y+w.clientY-h.current.startY))})}function g(){h.current=null,window.removeEventListener("mousemove",p),window.removeEventListener("mouseup",g)}window.addEventListener("mousemove",p),window.addEventListener("mouseup",g)},[i]),y=C.useCallback(f=>{f.preventDefault(),f.stopPropagation(),d.current={startX:f.clientX,startY:f.clientY,startSize:{...u}};function p(w){d.current&&c({w:Math.max(U0,d.current.startSize.w+w.clientX-d.current.startX),h:Math.max(W0,d.current.startSize.h+w.clientY-d.current.startY)})}function g(){d.current=null,window.removeEventListener("mousemove",p),window.removeEventListener("mouseup",g),document.body.style.cursor=""}document.body.style.cursor="nwse-resize",window.addEventListener("mousemove",p),window.addEventListener("mouseup",g)},[u]),x={panel:{position:"fixed",left:i.x,top:i.y,width:u.w,height:u.h,zIndex:1e3,background:n.panelBg,border:`1px solid ${n.borderAccent}`,borderRadius:8,display:"flex",flexDirection:"column",boxShadow:"0 8px 32px rgba(0,0,0,0.5)",overflow:"hidden"},header:{display:"flex",justifyContent:"space-between",alignItems:"center",padding:`${6*m+2}px ${12*m+2}px`,borderBottom:`1px solid ${n.border}`,cursor:"grab",userSelect:"none",flexShrink:0},title:{fontSize:Math.max(11,13*m),fontWeight:700,color:n.textPrimary},closeBtn:{background:"none",border:"none",color:n.textSecondary,cursor:"pointer",fontSize:Math.max(14,16*m),lineHeight:1,padding:"0 4px"},body:{flex:1,overflowY:"auto",overflowX:"hidden"},scaledContent:{transform:m!==1?`scale(${m})`:void 0,transformOrigin:"top left",width:m!==1?T:"100%"},resizeHandle:{position:"absolute",right:0,bottom:0,width:14,height:14,cursor:"nwse-resize",zIndex:1}};return s.jsxs("div",{style:x.panel,children:[s.jsxs("div",{style:x.header,onMouseDown:v,children:[s.jsx("span",{style:x.title,children:e}),s.jsx("button",{style:x.closeBtn,onClick:t,children:"✕"})]}),s.jsx("div",{style:x.body,children:s.jsx("div",{style:x.scaledContent,children:r})}),s.jsx("div",{style:x.resizeHandle,onMouseDown:y,title:"Drag to resize",children:s.jsx("svg",{width:"14",height:"14",viewBox:"0 0 14 14",style:{display:"block"},children:s.jsx("path",{d:"M12 2L2 12M12 6L6 12M12 10L10 12",stroke:n.textTertiary,strokeWidth:"1.5",fill:"none"})})})]})}const Y0=["#f44336","#e53935","#ef5350","#e57373","#ff5722","#ff8a65","#ff9800","#ffa726","#ffb74d","#ffc107","#ffd54f","#fff176","#4caf50","#66bb6a","#81c784","#aed581","#009688","#26c6da","#4dd0e1","#80cbc4","#2196f3","#42a5f5","#64b5f6","#3f51b5","#7e57c2","#9575cd","#9c27b0","#ab47bc","#ce93d8","#e91e63","#f06292","#795548","#8d6e63","#607d8b","#78909c"];function Q0({onClose:e}){const{theme:t}=Xe(),{tracks:n,updateTrack:r,updateMultipleTracks:o,removeTrack:l}=Jt(),[i,a]=C.useState(new Set);function u(k){a(Q=>{const ee=new Set(Q);return ee.has(k)?ee.delete(k):ee.add(k),ee})}function c(){a(new Set(n.map(k=>k.id)))}function h(){a(new Set)}const d=n.filter(k=>i.has(k.id)),m=d.some(k=>k.track_type==="annotations"||k.track_type==="genome_annotations"),T=d.some(k=>k.track_type==="coverage"||k.track_type==="reads"),v=d.some(k=>k.track_type==="reads"),y=d.some(k=>k.track_type==="variants"),x=d.some(k=>k.track_type==="coverage"||k.track_type==="reads"||k.track_type==="variants"),f=d.some(k=>k.track_type==="coverage"||k.track_type==="reads"),p=d.length>0&&d.every(k=>k.height===d[0].height)?d[0].height:"",g=d.length>0&&d.every(k=>k.color===d[0].color)?d[0].color:"#888888",w=d.length>0&&d.every(k=>k.visible===d[0].visible)?d[0].visible:null,S=d.length>0&&d.every(k=>k.useArrows===d[0].useArrows)?d[0].useArrows:null,j=d.length>0&&d.every(k=>k.scaleMax===d[0].scaleMax)?d[0].scaleMax:void 0,b=d.length>0&&d.every(k=>k.scaleMin===d[0].scaleMin)?d[0].scaleMin:void 0,E=j==null&&b==null,O=d.length>0&&d.every(k=>k.logScale===d[0].logScale)?d[0].logScale:null,z=d.length>0&&d.every(k=>k.barAutoWidth===d[0].barAutoWidth)?d[0].barAutoWidth:null,P=d.length>0&&d.every(k=>k.barWidth===d[0].barWidth)?d[0].barWidth:void 0,H=d.length>0&&d.every(k=>k.showOutline===d[0].showOutline)?d[0].showOutline:null,R=d.length>0&&d.every(k=>k.outlineColor===d[0].outlineColor)?d[0].outlineColor:void 0,U=d.length>0&&d.every(k=>k.outlineSmooth===d[0].outlineSmooth)?d[0].outlineSmooth:void 0,N=d.length>0&&d.every(k=>k.showBars===d[0].showBars)?d[0].showBars:null,Y=d.length>0&&d.every(k=>k.showNucleotides===d[0].showNucleotides)?d[0].showNucleotides:null,I=d.length>0&&d.every(k=>(k.fwdColor||"#90a4ae")===(d[0].fwdColor||"#90a4ae"))?d[0].fwdColor||"#90a4ae":void 0,L=d.length>0&&d.every(k=>(k.revColor||"#f06292")===(d[0].revColor||"#f06292"))?d[0].revColor||"#f06292":void 0,$=d.length>0&&d.every(k=>(k.arrowStyle||"pointed")===(d[0].arrowStyle||"pointed"))?d[0].arrowStyle||"pointed":void 0,D=d.length>0&&d.every(k=>(k.arrowSize||4)===(d[0].arrowSize||4))?d[0].arrowSize||4:void 0;function A(k){o([...i],k)}function F(){for(const k of i)l(k);a(new Set)}const V=t,M={body:{padding:"8px 0",overflowY:"auto",flex:1},trackRow:{display:"flex",alignItems:"center",gap:8,padding:"5px 16px",cursor:"pointer",transition:"background 0.1s"},trackRowSelected:{background:V.selectedRow},checkbox:{width:14,height:14,cursor:"pointer",flexShrink:0},trackLabel:{fontSize:12,color:V.textPrimary,flex:1,overflow:"hidden",textOverflow:"ellipsis",whiteSpace:"nowrap"},trackType:{fontSize:10,color:V.textTertiary,flexShrink:0},section:{padding:"12px 16px",borderTop:`1px solid ${V.border}`},sectionTitle:{fontSize:11,color:V.textSecondary,textTransform:"uppercase",letterSpacing:1,marginBottom:8},controlRow:{display:"flex",alignItems:"center",gap:10,marginBottom:6},subRow:{display:"flex",alignItems:"center",gap:10,marginBottom:6,paddingLeft:16,borderLeft:`2px solid ${V.border}`,marginLeft:4},controlLabel:{fontSize:12,color:V.textSecondary,width:90},subLabel:{fontSize:11,color:V.textTertiary,width:76},input:{background:V.inputBg,border:`1px solid ${V.borderAccent}`,borderRadius:4,color:V.textPrimary,padding:"3px 6px",fontSize:12,width:70},colorInput:{width:28,height:22,border:"none",background:"none",cursor:"pointer",padding:0},btn:{background:V.btnBg,color:V.btnText},btnDanger:{background:V.btnDanger,border:"none",borderRadius:4,color:"#fff",padding:"5px 14px",cursor:"pointer",fontSize:12,fontWeight:600},footer:{display:"flex",justifyContent:"space-between",alignItems:"center",padding:"10px 16px",borderTop:`1px solid ${V.border}`,gap:8},smallBtn:{background:"none",border:`1px solid ${V.borderAccent}`,borderRadius:3,color:V.textSecondary,cursor:"pointer",fontSize:10,padding:"2px 8px"},cbLabel:{fontSize:12,color:V.textSecondary,cursor:"pointer",display:"flex",alignItems:"center",gap:4}};return s.jsxs(kp,{title:"Track Settings",onClose:e,theme:V,defaultWidth:460,defaultHeight:520,children:[s.jsx("div",{style:M.body,children:n.length===0?s.jsx("div",{style:{padding:16,color:V.textTertiary,fontSize:12},children:"No tracks loaded."}):n.map(k=>s.jsxs("div",{style:{...M.trackRow,...i.has(k.id)?M.trackRowSelected:{}},onClick:()=>u(k.id),children:[s.jsx("input",{type:"checkbox",checked:i.has(k.id),onChange:()=>u(k.id),onClick:Q=>Q.stopPropagation(),style:M.checkbox}),s.jsx("span",{style:{width:10,height:10,borderRadius:2,background:k.color,flexShrink:0}}),s.jsx("span",{style:{...M.trackLabel,opacity:k.visible?1:.4},children:k.name}),s.jsx("span",{style:M.trackType,children:k.track_type})]},k.id))}),d.length>0&&s.jsxs("div",{style:M.section,children:[s.jsxs("div",{style:M.sectionTitle,children:["Edit ",d.length," selected track",d.length>1?"s":""]}),s.jsxs("div",{style:M.controlRow,children:[s.jsx("span",{style:M.controlLabel,children:"Height (px)"}),s.jsx("input",{type:"range",min:30,max:500,step:1,value:p||80,onChange:k=>A({height:parseInt(k.target.value)}),style:{flex:1,cursor:"pointer",accentColor:V.textSecondary}}),s.jsx("input",{type:"text",inputMode:"numeric",value:p,placeholder:"mixed",style:{...M.input,width:48},onChange:k=>{const Q=parseInt(k.target.value);Q>=30&&Q<=500&&A({height:Q})},onBlur:k=>{const Q=parseInt(k.target.value);(!Q||Q<30)&&A({height:30}),Q>500&&A({height:500})}})]}),s.jsxs("div",{style:M.controlRow,children:[s.jsx("span",{style:M.controlLabel,children:"Visible"}),s.jsxs("label",{style:M.cbLabel,children:[s.jsx("input",{type:"checkbox",checked:w===!0,ref:k=>{k&&(k.indeterminate=w===null)},onChange:k=>A({visible:k.target.checked}),style:{cursor:"pointer"}}),"Show"]})]}),f&&s.jsxs("div",{style:M.controlRow,children:[s.jsx("span",{style:M.controlLabel,children:"Fill bars"}),s.jsxs("label",{style:M.cbLabel,children:[s.jsx("input",{type:"checkbox",checked:N!==!1,ref:k=>{k&&(k.indeterminate=N===null)},onChange:k=>A({showBars:k.target.checked}),style:{cursor:"pointer"}}),"Show"]}),N!==!1&&s.jsx("input",{type:"color",value:g,style:M.colorInput,onChange:k=>A({color:k.target.value}),title:"Bar fill color"})]}),(y||!x&&!m)&&s.jsxs("div",{style:M.controlRow,children:[s.jsx("span",{style:M.controlLabel,children:"Color"}),s.jsx("input",{type:"color",value:g,style:M.colorInput,onChange:k=>A({color:k.target.value})})]}),x&&s.jsxs(s.Fragment,{children:[s.jsxs("div",{style:M.controlRow,children:[s.jsx("span",{style:M.controlLabel,children:"Bar width"}),s.jsxs("label",{style:M.cbLabel,children:[s.jsx("input",{type:"checkbox",checked:z!==!1,ref:k=>{k&&(k.indeterminate=z===null)},onChange:k=>A({barAutoWidth:k.target.checked}),style:{cursor:"pointer"}}),"Auto"]})]}),z===!1&&s.jsxs("div",{style:M.subRow,children:[s.jsx("span",{style:M.subLabel,children:"Width"}),s.jsx("input",{type:"range",min:1,max:50,step:1,value:P??2,onChange:k=>A({barWidth:parseInt(k.target.value)}),style:{flex:1,cursor:"pointer",accentColor:V.textSecondary}}),s.jsx("input",{type:"number",min:1,max:50,step:1,value:P??2,style:{...M.input,width:48},onChange:k=>{const Q=parseInt(k.target.value);Q>=1&&Q<=50&&A({barWidth:Q})}}),s.jsx("span",{style:{fontSize:11,color:V.textTertiary},children:"px"})]})]}),f&&s.jsxs(s.Fragment,{children:[s.jsxs("div",{style:M.controlRow,children:[s.jsx("span",{style:M.controlLabel,children:"Peak outline"}),s.jsxs("label",{style:M.cbLabel,children:[s.jsx("input",{type:"checkbox",checked:H===!0,ref:k=>{k&&(k.indeterminate=H===null)},onChange:k=>A({showOutline:k.target.checked}),style:{cursor:"pointer"}}),"Trace peaks"]}),H===!0&&s.jsx("input",{type:"color",value:R||g||"#ffffff",onChange:k=>A({outlineColor:k.target.value}),title:"Outline color",style:{width:22,height:18,border:"none",background:"none",cursor:"pointer",padding:0,marginLeft:4}})]}),H===!0&&s.jsxs("div",{style:M.subRow,children:[s.jsx("span",{style:M.subLabel,children:"Smoothness"}),s.jsx("input",{type:"range",min:0,max:10,step:1,value:U??0,onChange:k=>A({outlineSmooth:parseInt(k.target.value)}),style:{flex:1,cursor:"pointer",accentColor:V.textSecondary}}),s.jsx("span",{style:{fontSize:11,color:V.textTertiary,width:24,textAlign:"right"},children:U??0})]})]}),T&&s.jsxs("div",{style:M.controlRow,children:[s.jsx("span",{style:M.controlLabel,children:"Y Scale"}),s.jsxs("label",{style:M.cbLabel,children:[s.jsx("input",{type:"checkbox",checked:E,onChange:k=>A(k.target.checked?{scaleMax:null,scaleMin:null}:{scaleMax:100,scaleMin:100}),style:{cursor:"pointer"}}),"Auto"]})]}),T&&!E&&s.jsxs("div",{style:M.subRow,children:[s.jsx("span",{style:{fontSize:11,color:V.textTertiary,width:40},children:"+Ymax"}),s.jsx("input",{type:"number",min:1,step:10,value:j??"",placeholder:"max",style:M.input,onChange:k=>{const Q=parseFloat(k.target.value);Q>0&&A({scaleMax:Q})}}),s.jsxs("span",{style:{fontSize:11,color:V.textTertiary,width:40},children:["−","Ymax"]}),s.jsx("input",{type:"number",min:1,step:10,value:b??"",placeholder:"min",style:M.input,onChange:k=>{const Q=parseFloat(k.target.value);Q>0&&A({scaleMin:Q})}})]}),T&&s.jsxs("div",{style:M.controlRow,children:[s.jsx("span",{style:M.controlLabel,children:"Log scale"}),s.jsxs("label",{style:M.cbLabel,children:[s.jsx("input",{type:"checkbox",checked:O===!0,ref:k=>{k&&(k.indeterminate=O===null)},onChange:k=>A({logScale:k.target.checked}),style:{cursor:"pointer"}}),"log","₂"]})]}),m&&s.jsx(K0,{tracks:d,applyToSelected:A,theme:V}),m&&s.jsxs("div",{style:M.controlRow,children:[s.jsx("span",{style:M.controlLabel,children:"Gene style"}),s.jsxs("label",{style:M.cbLabel,children:[s.jsx("input",{type:"checkbox",checked:S===!0,ref:k=>{k&&(k.indeterminate=S===null)},onChange:k=>A({useArrows:k.target.checked}),style:{cursor:"pointer"}}),"Pointed arrows"]})]}),(v||m)&&s.jsxs("div",{style:M.controlRow,children:[s.jsx("span",{style:M.controlLabel,children:"Nucleotides"}),s.jsxs("label",{style:M.cbLabel,children:[s.jsx("input",{type:"checkbox",checked:Y!==!1,ref:k=>{k&&(k.indeterminate=Y===null)},onChange:k=>A({showNucleotides:k.target.checked}),style:{cursor:"pointer"}}),"Show when zoomed in"]})]}),v&&s.jsxs(s.Fragment,{children:[s.jsx("div",{style:{...M.sectionTitle,marginTop:12},children:"Read Appearance"}),s.jsxs("div",{style:M.controlRow,children:[s.jsx("span",{style:M.controlLabel,children:"Strand colors"}),s.jsx("span",{style:{fontSize:10,color:V.textTertiary,marginRight:2},children:"▶"}),s.jsx("input",{type:"color",value:I||"#90a4ae",onChange:k=>A({fwdColor:k.target.value}),title:"Forward strand color",style:{width:22,height:18,border:"none",background:"none",cursor:"pointer",padding:0}}),s.jsx("span",{style:{fontSize:10,color:V.textTertiary,marginLeft:6,marginRight:2},children:"◀"}),s.jsx("input",{type:"color",value:L||"#f06292",onChange:k=>A({revColor:k.target.value}),title:"Reverse strand color",style:{width:22,height:18,border:"none",background:"none",cursor:"pointer",padding:0}}),s.jsx("button",{style:{...M.smallBtn,marginLeft:"auto"},onClick:()=>A({fwdColor:null,revColor:null}),title:"Reset to defaults",children:"Reset"})]}),s.jsxs("div",{style:M.controlRow,children:[s.jsx("span",{style:M.controlLabel,children:"Arrow style"}),s.jsxs("select",{value:$||"pointed",onChange:k=>A({arrowStyle:k.target.value}),style:{background:V.inputBg,border:`1px solid ${V.borderAccent}`,borderRadius:4,color:V.textPrimary,padding:"2px 6px",fontSize:11,cursor:"pointer"},children:[s.jsx("option",{value:"pointed",children:"Pointed"}),s.jsx("option",{value:"chevron",children:"Chevron"}),s.jsx("option",{value:"fade",children:"Fade"}),s.jsx("option",{value:"flat",children:"Flat (none)"})]})]}),($||"pointed")!=="flat"&&s.jsxs("div",{style:M.subRow,children:[s.jsx("span",{style:M.subLabel,children:"Arrow size"}),s.jsx("input",{type:"range",min:2,max:12,step:1,value:D||4,onChange:k=>A({arrowSize:parseInt(k.target.value)}),style:{flex:1,cursor:"pointer",accentColor:V.textSecondary}}),s.jsx("span",{style:{fontSize:11,color:V.textTertiary,width:20,textAlign:"right"},children:D||4})]})]})]}),s.jsxs("div",{style:M.footer,children:[s.jsxs("div",{style:{display:"flex",gap:6},children:[s.jsx("button",{style:M.smallBtn,onClick:c,children:"Select all"}),s.jsx("button",{style:M.smallBtn,onClick:h,children:"Select none"})]}),s.jsx("div",{style:{display:"flex",gap:8},children:d.length>0&&s.jsxs("button",{style:M.btnDanger,onClick:F,children:["Remove (",d.length,")"]})})]})]})}const X0=[{key:"cds",label:"CDS"},{key:"exon",label:"Exon"},{key:"gene",label:"Gene"},{key:"transcript",label:"Transcript"},{key:"utr",label:"UTR"},{key:"rrna",label:"rRNA"},{key:"trna",label:"tRNA"},{key:"repeat",label:"Repeat"},{key:"default",label:"Other"}];function K0({tracks:e,applyToSelected:t,theme:n}){var T;const[r,o]=C.useState(null),l=C.useRef(null),[i,a]=C.useState(null),u=((T=e[0])==null?void 0:T.annotationColors)||{};function c(v){return u[v]||vp[v]||"#80cbc4"}function h(v,y){for(const x of e){const f={...x.annotationColors||{},[v]:y};t({annotationColors:f})}}function d(){t({annotationColors:null})}function m(v){a(v),l.current&&(l.current.value=c(v),l.current.click())}return s.jsxs("div",{style:{padding:"4px 0"},children:[s.jsxs("div",{style:{display:"flex",alignItems:"center",gap:8,marginBottom:6,padding:"0 0 0 0"},children:[s.jsx("span",{style:{fontSize:12,color:n.textSecondary,width:90},children:"Annotation colors"}),s.jsx("button",{style:{background:"none",border:`1px solid ${n.borderAccent}`,borderRadius:3,color:n.textTertiary,cursor:"pointer",fontSize:10,padding:"1px 6px"},onClick:d,children:"Reset"})]}),X0.map(({key:v,label:y})=>{const x=c(v);return s.jsxs("div",{children:[s.jsxs("div",{style:{display:"flex",alignItems:"center",gap:6,padding:"3px 4px",cursor:"pointer",fontSize:11,color:n.textPrimary,borderRadius:3},onMouseEnter:f=>f.currentTarget.style.background=n.selectedRow||"rgba(255,255,255,0.05)",onMouseLeave:f=>f.currentTarget.style.background="transparent",onClick:()=>o(r===v?null:v),children:[s.jsx("span",{style:{width:14,height:14,borderRadius:3,background:x,border:"1px solid rgba(255,255,255,0.15)",flexShrink:0,cursor:"pointer"},onDoubleClick:f=>{f.stopPropagation(),m(v)},title:"Click to expand swatches, double-click for full color picker"}),s.jsx("span",{style:{flex:1},children:y}),s.jsx("span",{style:{fontSize:9,color:n.textTertiary},children:r===v?"▲":"▼"})]}),r===v&&s.jsx("div",{style:{padding:"3px 4px 6px 24px",display:"flex",flexWrap:"wrap",gap:2},children:Y0.map(f=>s.jsx("span",{style:{width:16,height:16,borderRadius:3,background:f,cursor:"pointer",border:f===x?`2px solid ${n.textPrimary}`:"1px solid rgba(255,255,255,0.1)",boxSizing:"border-box"},onClick:()=>{h(v,f),o(null)}},f))})]},v)}),s.jsx("input",{ref:l,type:"color",style:{position:"absolute",left:-9999,top:-9999,opacity:0,width:0,height:0},onChange:v=>{i&&h(i,v.target.value)}})]})}const q0=["dark","light","colorblind","soft","highContrast"],wc=[{key:"appBg",label:"Background",group:"ui"},{key:"panelBg",label:"Panel",group:"ui"},{key:"canvasBg",label:"Canvas",group:"ui"},{key:"btnBg",label:"Buttons",group:"ui"},{key:"textPrimary",label:"Text",group:"ui"},{key:"textSecondary",label:"Text secondary",group:"ui"},{key:"border",label:"Borders",group:"ui"},{key:"geneCds",label:"CDS",group:"gene"},{key:"geneExon",label:"Exon",group:"gene"},{key:"geneGene",label:"Gene",group:"gene"},{key:"geneTranscript",label:"Transcript",group:"gene"},{key:"geneUtr",label:"UTR",group:"gene"},{key:"geneRrna",label:"rRNA",group:"gene"},{key:"geneTrna",label:"tRNA",group:"gene"},{key:"geneRepeat",label:"Repeat",group:"gene"},{key:"geneDefault",label:"Default feature",group:"gene"}],J0=["#000000","#1a1a1a","#333333","#4d4d4d","#666666","#808080","#999999","#b3b3b3","#cccccc","#e6e6e6","#f2f2f2","#ffffff","#4e0000","#7f0000","#b71c1c","#c62828","#d32f2f","#e53935","#ef5350","#f44336","#ef9a9a","#ffcdd2","#ffebee","#fff5f5","#4e2600","#7f3d00","#e65100","#ef6c00","#f57c00","#fb8c00","#ff9800","#ffa726","#ffb74d","#ffcc80","#ffe0b2","#fff3e0","#4e4400","#7f6f00","#f57f17","#f9a825","#fbc02d","#fdd835","#ffeb3b","#fff176","#fff59d","#fff9c4","#fffde7","#fffff0","#003300","#1b5e20","#2e7d32","#388e3c","#43a047","#4caf50","#66bb6a","#81c784","#a5d6a7","#c8e6c9","#e8f5e9","#f1f8e9","#003333","#004d40","#00695c","#00796b","#00897b","#009688","#26a69a","#4db6ac","#80cbc4","#b2dfdb","#e0f2f1","#e0f7fa","#001a33","#0d47a1","#1565c0","#1976d2","#1e88e5","#2196f3","#42a5f5","#64b5f6","#90caf9","#bbdefb","#e3f2fd","#e8eaf6","#1a0033","#311b92","#4527a0","#512da8","#5e35b1","#673ab7","#7e57c2","#9575cd","#b39ddb","#d1c4e9","#ede7f6","#f3e5f5","#330019","#880e4f","#ad1457","#c2185b","#d81b60","#e91e63","#ec407a","#f06292","#f48fb1","#f8bbd0","#fce4ec","#fff0f5","#1b0000","#3e2723","#4e342e","#5d4037","#6d4c41","#795548","#8d6e63","#a1887f","#bcaaa4","#d7ccc8","#efebe9","#fafafa"];function Z0({onClose:e}){const{theme:t,themeName:n,setThemeName:r,customTheme:o,setCustomTheme:l}=Xe(),[i,a]=C.useState(n==="custom"),[u,c]=C.useState(null),[h,d]=C.useState({left:0,top:0}),m=C.useRef(null),T=C.useRef(null);function v(b){r(b),a(!1)}function y(){const b=n==="custom"?o:vt[n]||vt.dark;l({...b,name:"Custom"}),r("custom"),a(!0)}function x(b,E){l({...o,[b]:E})}function f(b,E){const O=E.currentTarget.getBoundingClientRect(),z=window.innerWidth-O.right,P=290,H=260;let R,U;z>P+10?(R=O.right+6,U=Math.min(O.top,window.innerHeight-H-10)):(R=Math.max(10,O.left-P-6),U=Math.min(O.top,window.innerHeight-H-10)),d({left:R,top:U}),c(b)}function p(b){u&&x(u,b),c(null)}function g(b){T.current=b,m.current&&(m.current.value=j[b]||"#000000",m.current.click())}function w(b){T.current&&x(T.current,b.target.value)}const S=ey(t),j=n==="custom"?o:vt[n]||vt.dark;return s.jsxs(kp,{title:"Color Scheme",onClose:e,theme:t,defaultWidth:420,defaultHeight:480,children:[s.jsxs("div",{style:S.body,children:[s.jsxs("div",{style:S.section,children:[s.jsx("div",{style:S.sectionTitle,children:"Presets"}),s.jsx("div",{style:{display:"flex",gap:8,flexWrap:"wrap"},children:q0.map(b=>s.jsxs("button",{onClick:()=>v(b),style:{...S.presetBtn,border:n===b?`2px solid ${t.textPrimary}`:`1px solid ${t.borderAccent}`},children:[s.jsxs("div",{style:{display:"flex",gap:2,marginBottom:4},children:[s.jsx("span",{style:{width:14,height:14,borderRadius:2,background:vt[b].appBg,border:"1px solid #555"}}),s.jsx("span",{style:{width:14,height:14,borderRadius:2,background:vt[b].headerBg,border:"1px solid #555"}}),s.jsx("span",{style:{width:14,height:14,borderRadius:2,background:vt[b].btnBg,border:"1px solid #555"}})]}),s.jsx("span",{style:{fontSize:10,color:t.textSecondary},children:vt[b].name})]},b))})]}),s.jsxs("div",{style:S.section,children:[s.jsxs("div",{style:{display:"flex",alignItems:"center",justifyContent:"space-between",marginBottom:8},children:[s.jsx("div",{style:S.sectionTitle,children:"Custom Palette"}),i?s.jsx("button",{onClick:()=>a(!1),style:S.smallBtn,children:"Collapse"}):s.jsx("button",{onClick:y,style:S.btn,children:"Customize"})]}),i&&s.jsxs("div",{children:[s.jsx("div",{style:{fontSize:10,color:t.textTertiary,textTransform:"uppercase",letterSpacing:1,marginTop:4,marginBottom:6},children:"Interface"}),s.jsx("div",{style:{display:"grid",gridTemplateColumns:"1fr 1fr",gap:"4px 12px"},children:wc.filter(b=>b.group==="ui").map(({key:b,label:E})=>s.jsxs("div",{style:{display:"flex",alignItems:"center",gap:6},children:[s.jsx("span",{style:{display:"inline-block",width:20,height:16,borderRadius:3,background:j[b]||"#000",border:`1px solid ${t.borderAccent}`,cursor:"pointer",flexShrink:0},onMouseDown:O=>f(b,O),onDoubleClick:()=>{c(null),g(b)}}),s.jsx("span",{style:{fontSize:11,color:t.textSecondary},children:E})]},b))}),s.jsx("div",{style:{fontSize:10,color:t.textTertiary,textTransform:"uppercase",letterSpacing:1,marginTop:10,marginBottom:6},children:"Gene Features"}),s.jsx("div",{style:{display:"grid",gridTemplateColumns:"1fr 1fr 1fr",gap:"4px 12px"},children:wc.filter(b=>b.group==="gene").map(({key:b,label:E})=>s.jsxs("div",{style:{display:"flex",alignItems:"center",gap:6},children:[s.jsx("span",{style:{display:"inline-block",width:20,height:16,borderRadius:3,background:j[b]||"#000",border:`1px solid ${t.borderAccent}`,cursor:"pointer",flexShrink:0},onMouseDown:O=>f(b,O),onDoubleClick:()=>{c(null),g(b)}}),s.jsx("span",{style:{fontSize:11,color:t.textSecondary},children:E})]},b))})]})]})]}),s.jsx("div",{style:S.footer,children:s.jsx("button",{style:S.btn,onClick:e,children:"Close"})}),s.jsx("input",{ref:m,type:"color",onChange:w,style:{position:"fixed",left:-9999,top:-9999,opacity:0,width:0,height:0}}),u&&Wn.createPortal(s.jsx("div",{style:{position:"fixed",left:h.left,top:h.top,zIndex:10002,background:t.panelBg,border:`1px solid ${t.borderAccent}`,borderRadius:6,padding:8,boxShadow:"0 6px 20px rgba(0,0,0,0.6)",display:"grid",gridTemplateColumns:"repeat(12, 20px)",gap:2,maxHeight:300,overflowY:"auto"},onMouseLeave:()=>c(null),children:J0.map((b,E)=>s.jsx("span",{style:{width:20,height:20,borderRadius:3,background:b,cursor:"pointer",border:b===(j[u]||"")?`2px solid ${t.textPrimary}`:"1px solid rgba(128,128,128,0.3)",boxSizing:"border-box"},onMouseUp:()=>p(b)},E))}),document.body)]})}function ey(e){return{overlay:{position:"fixed",inset:0,background:e.overlayBg,display:"flex",alignItems:"center",justifyContent:"center",zIndex:1e3},panel:{background:e.panelBg,border:`1px solid ${e.borderAccent}`,borderRadius:8,padding:0,minWidth:440,maxWidth:560,maxHeight:"80vh",display:"flex",flexDirection:"column",boxShadow:"0 8px 32px rgba(0,0,0,0.5)"},header:{display:"flex",justifyContent:"space-between",alignItems:"center",padding:"10px 16px",borderBottom:`1px solid ${e.border}`},title:{fontSize:14,fontWeight:700,color:e.textPrimary},closeBtn:{background:"none",border:"none",color:e.textSecondary,cursor:"pointer",fontSize:18,lineHeight:1,padding:"0 4px"},body:{padding:"8px 0",overflowY:"auto",flex:1},section:{padding:"8px 16px"},sectionTitle:{fontSize:11,color:e.textSecondary,textTransform:"uppercase",letterSpacing:1,marginBottom:0},presetBtn:{background:e.panelBg,borderRadius:6,padding:"8px 10px",cursor:"pointer",display:"flex",flexDirection:"column",alignItems:"center",minWidth:70},smallBtn:{background:"none",border:`1px solid ${e.borderAccent}`,borderRadius:3,color:e.textSecondary,cursor:"pointer",fontSize:10,padding:"3px 8px"},btn:{background:e.btnBg,border:"none",borderRadius:4,color:e.btnText,padding:"5px 14px",cursor:"pointer",fontSize:12,fontWeight:600},footer:{display:"flex",justifyContent:"flex-end",padding:"10px 16px",borderTop:`1px solid ${e.border}`}}}const Li=5e4,ty=.5,ny=100,ry=800;function oy(e=200){const t=new Map;return{get(n){return t.get(n)},set(n,r){t.size>=e&&t.delete(t.keys().next().value),t.set(n,r)},findByPrefix(n){let r=null;for(const[o,l]of t)o.startsWith(n)&&(r=l);return r}}}const _n=oy(),Oa=new Map;function Sc(e,t){Oa.set(e,t)}function Cp(e){return Oa.get(e)||null}function ly(e,t){const n=Oa.get(e);return n||_n.findByPrefix(`${e}|coverage|${t}|`)||_n.findByPrefix(`${e}|reads|${t}|`)||_n.findByPrefix(`${e}|annotations|${t}|`)||_n.findByPrefix(`${e}|genome_annotations|${t}|`)||_n.findByPrefix(`${e}|variants|${t}|`)||null}function ei(e,t,n){const[r,o]=C.useState(null),[l,i]=C.useState(!1),[a,u]=C.useState(null),c=C.useRef(null),h=C.useRef(null),d=C.useRef(null),m=C.useRef(null),T=C.useRef(!1);C.useEffect(()=>{if(!e||!t||!n)return;const{chrom:y,start:x,end:f}=t,p=f-x,g=e.track_type;h.current&&h.current.trackId!==e.id&&(h.current=null,T.current=!1);const w=h.current;if(w&&w.trackId===e.id&&w.chrom===y&&x>=w.start&&f<=w.end){const j=p/(w.viewLen||p);if(j>.8&&j<1.2){m.current&&clearTimeout(m.current);return}m.current&&clearTimeout(m.current),m.current=setTimeout(()=>{v(e,y,x,f,p,g,n)},ry);return}return m.current&&clearTimeout(m.current),d.current&&clearTimeout(d.current),T.current&&(w==null?void 0:w.chrom)===y?d.current=setTimeout(()=>{v(e,y,x,f,p,g,n)},ny):v(e,y,x,f,p,g,n),()=>{d.current&&clearTimeout(d.current),m.current&&clearTimeout(m.current)}},[e==null?void 0:e.id,t==null?void 0:t.chrom,t==null?void 0:t.start,t==null?void 0:t.end,n]);function v(y,x,f,p,g,w,S){const b=w!=="reads"||g>Li?ty:0,E=Math.max(0,Math.floor(f-g*b)),O=Math.ceil(p+g*b),z=(O-E)/g,P=Math.min(Math.floor(S*z),Math.max(S*2,1e3)),H=`${y.id}|${w}|${x}|${E}|${O}|${P}`,R=_n.get(H);if(R){o(R),Sc(y.id,R),u(null),h.current={trackId:y.id,chrom:x,start:E,end:O,viewLen:g},T.current=!0;return}c.current&&c.current.abort();const U=new AbortController;c.current=U,T.current||i(!0),u(null);let N;if(w==="reads")g<=Li?N=Ot.reads(y.id,x,f,p):N=Ot.coverage(y.id,x,E,O,P);else if(w==="coverage")N=Ot.coverage(y.id,x,E,O,P);else if(w==="variants")N=Ot.variants(y.id,x,E,O);else if(w==="annotations"||w==="genome_annotations")N=Ot.features(y.id,x,E,O);else{i(!1);return}N.then(Y=>{if(U.signal.aborted)return;const I={...Y.data,mode:w==="reads"&&g<=Li?"reads":"coverage"};_n.set(H,I),h.current={trackId:y.id,chrom:x,start:E,end:O,viewLen:g},T.current=!0,o(I),Sc(y.id,I),u(null)}).catch(Y=>{var I,L;if(Y.name!=="CanceledError"&&!U.signal.aborted){const $=(L=(I=Y.response)==null?void 0:I.data)==null?void 0:L.detail,D=typeof $=="string"?$:Y.message||String(Y);u(D)}}).finally(()=>{U.signal.aborted||i(!1)})}return{data:r,loading:l,error:a}}const iy=["svg","png","jpg"],sy=140;function ay({onClose:e}){const{region:t}=at(),{tracks:n}=Jt(),{theme:r}=Xe(),o=t==null?void 0:t.chrom,l=n.filter(S=>S.visible&&(!S.targetChromosomes||!o||S.targetChromosomes.includes(o))),[i,a]=C.useState("svg"),[u,c]=C.useState(!0),[h,d]=C.useState(!0),[m,T]=C.useState(new Set(l.map(S=>S.id))),[v,y]=C.useState(1200),[x,f]=C.useState(!1);function p(S){T(j=>{const b=new Set(j);return b.has(S)?b.delete(S):b.add(S),b})}async function g(){if(t){f(!0);try{const S=l.filter(z=>m.has(z.id)),j=h?sy:0,b=v-j,E=u?30:0,O=E+S.reduce((z,P)=>z+P.height,0);if(i==="svg"){const z=uy(t,S,r,b,j,E,O,u,h);my(z,"genomics-export.svg","image/svg+xml")}else{const z=hy(t,S,r,b,j,E,O,v,u,h),P=i==="png"?"image/png":"image/jpeg";z.toBlob(H=>{const R=URL.createObjectURL(H),U=document.createElement("a");U.href=R,U.download=`genomics-export.${i}`,U.click(),URL.revokeObjectURL(R)},P,.95)}}finally{f(!1)}}}const w=vy(r);return s.jsx("div",{style:w.overlay,onClick:S=>{S.target===S.currentTarget&&e()},children:s.jsxs("div",{style:w.panel,children:[s.jsxs("div",{style:w.header,children:[s.jsx("span",{style:w.title,children:"Export Image"}),s.jsx("button",{style:w.closeBtn,onClick:e,children:"✕"})]}),s.jsxs("div",{style:w.body,children:[s.jsxs("div",{style:w.row,children:[s.jsx("span",{style:w.label,children:"Format"}),s.jsx("div",{style:{display:"flex",gap:6},children:iy.map(S=>s.jsx("button",{onClick:()=>a(S),style:{...w.fmtBtn,border:i===S?`2px solid ${r.textPrimary}`:`1px solid ${r.borderAccent}`},children:S.toUpperCase()},S))})]}),s.jsxs("div",{style:w.row,children:[s.jsx("span",{style:w.label,children:"Width (px)"}),s.jsx("input",{type:"number",min:400,max:4e3,step:100,value:v,onChange:S=>y(Math.max(400,parseInt(S.target.value)||1200)),style:w.input})]}),s.jsxs("div",{style:w.row,children:[s.jsxs("label",{style:w.cb,children:[s.jsx("input",{type:"checkbox",checked:u,onChange:S=>c(S.target.checked)})," Ruler"]}),s.jsxs("label",{style:w.cb,children:[s.jsx("input",{type:"checkbox",checked:h,onChange:S=>d(S.target.checked)})," Track labels"]})]}),s.jsxs("div",{style:{...w.row,flexDirection:"column",alignItems:"stretch",gap:4},children:[s.jsx("span",{style:w.label,children:"Include tracks"}),l.map(S=>s.jsxs("label",{style:{...w.cb,gap:6},children:[s.jsx("input",{type:"checkbox",checked:m.has(S.id),onChange:()=>p(S.id)}),s.jsx("span",{style:{width:8,height:8,borderRadius:2,background:S.color,flexShrink:0}}),s.jsx("span",{style:{fontSize:11},children:S.name})]},S.id))]}),i==="svg"&&s.jsx("div",{style:{padding:"4px 0",fontSize:10,color:r.textTertiary},children:"SVG output is fully vectorized — editable in Illustrator, Inkscape, etc."})]}),s.jsxs("div",{style:w.footer,children:[s.jsx("button",{style:w.btn,onClick:g,disabled:x||!t,children:x?"Exporting…":`Export ${i.toUpperCase()}`}),s.jsx("button",{style:{...w.btn,background:r.borderAccent},onClick:e,children:"Cancel"})]})]})})}function uy(e,t,n,r,o,l,i,a,u){const c=r+o;let h=`<?xml version="1.0" encoding="UTF-8"?>
45
+ `+l):r.stack=l}catch{}}throw r}}_request(t,n){typeof t=="string"?(n=n||{},n.url=t):n=t||{},n=Hn(this.defaults,n);const{transitional:r,paramsSerializer:o,headers:l}=n;r!==void 0&&il.assertOptions(r,{silentJSONParsing:xt.transitional(xt.boolean),forcedJSONParsing:xt.transitional(xt.boolean),clarifyTimeoutError:xt.transitional(xt.boolean),legacyInterceptorReqResOrdering:xt.transitional(xt.boolean)},!1),o!=null&&(_.isFunction(o)?n.paramsSerializer={serialize:o}:il.assertOptions(o,{encode:xt.function,serialize:xt.function},!0)),n.allowAbsoluteUrls!==void 0||(this.defaults.allowAbsoluteUrls!==void 0?n.allowAbsoluteUrls=this.defaults.allowAbsoluteUrls:n.allowAbsoluteUrls=!0),il.assertOptions(n,{baseUrl:xt.spelling("baseURL"),withXsrfToken:xt.spelling("withXSRFToken")},!0),n.method=(n.method||this.defaults.method||"get").toLowerCase();let i=l&&_.merge(l.common,l[n.method]);l&&_.forEach(["delete","get","head","post","put","patch","common"],v=>{delete l[v]}),n.headers=st.concat(i,l);const a=[];let u=!0;this.interceptors.request.forEach(function(y){if(typeof y.runWhen=="function"&&y.runWhen(n)===!1)return;u=u&&y.synchronous;const x=n.transitional||za;x&&x.legacyInterceptorReqResOrdering?a.unshift(y.fulfilled,y.rejected):a.push(y.fulfilled,y.rejected)});const c=[];this.interceptors.response.forEach(function(y){c.push(y.fulfilled,y.rejected)});let h,d=0,m;if(!u){const v=[hc.bind(this),void 0];for(v.unshift(...a),v.push(...c),m=v.length,h=Promise.resolve(n);d<m;)h=h.then(v[d++],v[d++]);return h}m=a.length;let T=n;for(;d<m;){const v=a[d++],y=a[d++];try{T=v(T)}catch(x){y.call(this,x);break}}try{h=hc.call(this,T)}catch(v){return Promise.reject(v)}for(d=0,m=c.length;d<m;)h=h.then(c[d++],c[d++]);return h}getUri(t){t=Hn(this.defaults,t);const n=dp(t.baseURL,t.url,t.allowAbsoluteUrls);return sp(n,t.params,t.paramsSerializer)}};_.forEach(["delete","get","head","options"],function(t){Nn.prototype[t]=function(n,r){return this.request(Hn(r||{},{method:t,url:n,data:(r||{}).data}))}});_.forEach(["post","put","patch"],function(t){function n(r){return function(l,i,a){return this.request(Hn(a||{},{method:t,headers:r?{"Content-Type":"multipart/form-data"}:{},url:l,data:i}))}}Nn.prototype[t]=n(),Nn.prototype[t+"Form"]=n(!0)});let L0=class gp{constructor(t){if(typeof t!="function")throw new TypeError("executor must be a function.");let n;this.promise=new Promise(function(l){n=l});const r=this;this.promise.then(o=>{if(!r._listeners)return;let l=r._listeners.length;for(;l-- >0;)r._listeners[l](o);r._listeners=null}),this.promise.then=o=>{let l;const i=new Promise(a=>{r.subscribe(a),l=a}).then(o);return i.cancel=function(){r.unsubscribe(l)},i},t(function(l,i,a){r.reason||(r.reason=new To(l,i,a),n(r.reason))})}throwIfRequested(){if(this.reason)throw this.reason}subscribe(t){if(this.reason){t(this.reason);return}this._listeners?this._listeners.push(t):this._listeners=[t]}unsubscribe(t){if(!this._listeners)return;const n=this._listeners.indexOf(t);n!==-1&&this._listeners.splice(n,1)}toAbortSignal(){const t=new AbortController,n=r=>{t.abort(r)};return this.subscribe(n),t.signal.unsubscribe=()=>this.unsubscribe(n),t.signal}static source(){let t;return{token:new gp(function(o){t=o}),cancel:t}}};function M0(e){return function(n){return e.apply(null,n)}}function B0(e){return _.isObject(e)&&e.isAxiosError===!0}const zs={Continue:100,SwitchingProtocols:101,Processing:102,EarlyHints:103,Ok:200,Created:201,Accepted:202,NonAuthoritativeInformation:203,NoContent:204,ResetContent:205,PartialContent:206,MultiStatus:207,AlreadyReported:208,ImUsed:226,MultipleChoices:300,MovedPermanently:301,Found:302,SeeOther:303,NotModified:304,UseProxy:305,Unused:306,TemporaryRedirect:307,PermanentRedirect:308,BadRequest:400,Unauthorized:401,PaymentRequired:402,Forbidden:403,NotFound:404,MethodNotAllowed:405,NotAcceptable:406,ProxyAuthenticationRequired:407,RequestTimeout:408,Conflict:409,Gone:410,LengthRequired:411,PreconditionFailed:412,PayloadTooLarge:413,UriTooLong:414,UnsupportedMediaType:415,RangeNotSatisfiable:416,ExpectationFailed:417,ImATeapot:418,MisdirectedRequest:421,UnprocessableEntity:422,Locked:423,FailedDependency:424,TooEarly:425,UpgradeRequired:426,PreconditionRequired:428,TooManyRequests:429,RequestHeaderFieldsTooLarge:431,UnavailableForLegalReasons:451,InternalServerError:500,NotImplemented:501,BadGateway:502,ServiceUnavailable:503,GatewayTimeout:504,HttpVersionNotSupported:505,VariantAlsoNegotiates:506,InsufficientStorage:507,LoopDetected:508,NotExtended:510,NetworkAuthenticationRequired:511,WebServerIsDown:521,ConnectionTimedOut:522,OriginIsUnreachable:523,TimeoutOccurred:524,SslHandshakeFailed:525,InvalidSslCertificate:526};Object.entries(zs).forEach(([e,t])=>{zs[t]=e});function yp(e){const t=new Nn(e),n=Kf(Nn.prototype.request,t);return _.extend(n,Nn.prototype,t,{allOwnKeys:!0}),_.extend(n,t,null,{allOwnKeys:!0}),n.create=function(o){return yp(Hn(e,o))},n}const Le=yp(Co);Le.Axios=Nn;Le.CanceledError=To;Le.CancelToken=L0;Le.isCancel=up;Le.VERSION=mp;Le.toFormData=Jl;Le.AxiosError=re;Le.Cancel=Le.CanceledError;Le.all=function(t){return Promise.all(t)};Le.spread=M0;Le.isAxiosError=B0;Le.mergeConfig=Hn;Le.AxiosHeaders=st;Le.formToJSON=e=>ap(_.isHTMLForm(e)?new FormData(e):e);Le.getAdapter=hp.getAdapter;Le.HttpStatusCode=zs;Le.default=Le;const{Axios:sx,AxiosError:ax,CanceledError:ux,isCancel:cx,CancelToken:dx,VERSION:fx,all:px,Cancel:hx,isAxiosError:mx,spread:gx,toFormData:yx,AxiosHeaders:xx,HttpStatusCode:vx,formToJSON:wx,getAdapter:Sx,mergeConfig:bx}=Le,rn=Le.create({baseURL:"/api"});function Kr(e,t,n){return new Promise((r,o)=>{const l=new XMLHttpRequest;l.open("POST",`/api${e}`),n&&l.upload.addEventListener("progress",i=>{i.lengthComputable&&n({loaded:i.loaded,total:i.total,percent:Math.round(i.loaded/i.total*100)})}),l.addEventListener("load",()=>{if(l.status>=200&&l.status<300)try{r({data:JSON.parse(l.responseText)})}catch{r({data:{}})}else{const i=new Error("Upload failed");try{i.response={status:l.status,data:JSON.parse(l.responseText)}}catch{i.response={status:l.status,data:{detail:l.statusText}}}o(i)}}),l.addEventListener("error",()=>{const i=new Error("Network error");i.response={status:0,data:{detail:"Network error — is the server running?"}},o(i)}),l.addEventListener("abort",()=>{const i=new Error("Upload aborted");i.name="CanceledError",o(i)}),l.send(t)})}const yn={load:(e,t)=>{const n=new FormData;return n.append("file",e),Kr("/genome/load",n,t)},loadPath:e=>{const t=new FormData;return t.append("path",e),Kr("/genome/load-path",t)},addChromosomes:(e,t)=>{const n=new FormData;return n.append("file",e),Kr("/genome/add-chromosomes",n,t)},chromosomes:()=>rn.get("/genome/chromosomes"),sequence:(e,t,n)=>rn.get("/genome/sequence",{params:{chrom:e,start:t,end:n}})},Ot={load:(e,t,n,r)=>{const o=new FormData;return o.append("file",e),t&&o.append("name",t),n&&o.append("index",n),Kr("/tracks/load",o,r)},loadPath:(e,t)=>{const n=new FormData;return n.append("path",e),t&&n.append("name",t),Kr("/tracks/load-path",n)},list:()=>rn.get("/tracks"),remove:e=>rn.delete(`/tracks/${e}`),coverage:(e,t,n,r,o=1e3)=>rn.get(`/tracks/${e}/coverage`,{params:{chrom:t,start:n,end:r,bins:o}}),reads:(e,t,n,r)=>rn.get(`/tracks/${e}/reads`,{params:{chrom:t,start:n,end:r}}),variants:(e,t,n,r)=>rn.get(`/tracks/${e}/variants`,{params:{chrom:t,start:n,end:r}}),features:(e,t,n,r)=>rn.get(`/tracks/${e}/features`,{params:{chrom:t,start:n,end:r}})},xp=C.createContext(null),gc=["#78909c","#81c784","#ffb74d","#f06292","#ce93d8","#80cbc4","#fff176","#ff8a65"],vp={cds:"#66bb6a",exon:"#42a5f5",gene:"#7e57c2",transcript:"#ab47bc",utr:"#26c6da",rrna:"#ffa726",trna:"#ef5350",repeat:"#8d6e63",default:"#80cbc4"};function Ft(e){return e&&e.replace(/\\u([0-9a-fA-F]{4})/g,(t,n)=>String.fromCharCode(parseInt(n,16)))}function A0({children:e}){const[t,n]=C.useState([]),[r,o]=C.useState(null),l=C.useRef(t);l.current=t;const i=C.useCallback(async(x,f,p,g)=>{var w,S;try{const b=(await Ot.load(x,f,p,g)).data;return b.name&&(b.name=Ft(b.name)),o(null),b}catch(j){const b=((S=(w=j.response)==null?void 0:w.data)==null?void 0:S.detail)||j.message||String(j);throw o(typeof b=="string"?b:JSON.stringify(b)),j}},[]),a=C.useCallback(x=>{n(f=>{const p=gc[f.length%gc.length],g=x.track_type==="annotations"||x.track_type==="genome_annotations";return[...f,{...x,color:p,height:z0(x.track_type),visible:!0,useArrows:!0,scaleMax:null,scaleMin:null,logScale:!1,barAutoWidth:!0,barWidth:2,showOutline:!1,outlineColor:null,outlineSmooth:0,showBars:!0,showNucleotides:!0,fwdColor:null,revColor:null,arrowStyle:"pointed",arrowSize:4,targetChromosomes:x.target_chromosomes||null,...g?{annotationColors:null}:{}}]})},[]),u=C.useCallback(async x=>{try{await Ot.remove(x)}catch{}},[]),c=C.useCallback(async(x,f)=>{const p=await i(x,f);return a(p),p},[i,a]),h=C.useCallback(async x=>{var p,g;const f=l.current.find(w=>w.id===x);if(f&&f.track_type==="genome_annotations"){n(w=>w.map(S=>S.id===x?{...S,visible:!1}:S));return}try{await Ot.remove(x),n(w=>w.filter(S=>S.id!==x))}catch(w){o(((g=(p=w.response)==null?void 0:p.data)==null?void 0:g.detail)||w.message)}},[]),d=C.useCallback(()=>{n(x=>x.map(f=>f.track_type==="genome_annotations"&&!f.visible?{...f,visible:!0}:f))},[]),m=C.useCallback((x,f)=>{n(p=>p.map(g=>g.id===x?{...g,...f}:g))},[]),T=C.useCallback((x,f)=>{n(p=>p.map(g=>x.includes(g.id)?{...g,...f}:g))},[]),v=C.useCallback((x,f)=>{n(p=>{const g=[...p],w=g.findIndex(b=>b.id===x),S=g.findIndex(b=>b.id===f);if(w===-1||S===-1)return p;const[j]=g.splice(w,1);return g.splice(S,0,j),g})},[]),y=C.useCallback(x=>{n(f=>{const p=f.findIndex(g=>g.id===x.id);if(p!==-1){const g=[...f];return g[p]={...g[p],name:Ft(x.name)||x.name,visible:!0,...x.targetChromosomes?{targetChromosomes:x.targetChromosomes}:{}},g}return[...f,{...x,name:Ft(x.name)||x.name,color:"#a5d6a7",height:80,visible:!0,useArrows:!0,annotationColors:null,targetChromosomes:x.targetChromosomes||null}]})},[]);return s.jsx(xp.Provider,{value:{tracks:t,setTracks:n,addTrack:c,uploadTrack:i,commitTrack:a,discardTrack:u,removeTrack:h,updateTrack:m,updateMultipleTracks:T,reorderTracks:v,addGenomeAnnotationTrack:y,restoreAnnotationTracks:d,error:r,setError:o},children:e})}function Jt(){return C.useContext(xp)}function z0(e){switch(e){case"reads":return 120;case"coverage":return 120;case"variants":return 60;case"annotations":case"genome_annotations":return 80;default:return 80}}const wp=C.createContext(null),yc={geneCds:"#66bb6a",geneExon:"#42a5f5",geneGene:"#7e57c2",geneTranscript:"#ab47bc",geneUtr:"#26c6da",geneRrna:"#ffa726",geneTrna:"#ef5350",geneRepeat:"#8d6e63",geneDefault:"#80cbc4"},vt={dark:{name:"Dark",appBg:"#1a1a1a",headerBg:"#2a2a2a",panelBg:"#252525",canvasBg:"#1a1a1a",inputBg:"#333",border:"#333",borderAccent:"#444",borderStrong:"#555",btnBg:"#555",btnText:"#fff",btnDanger:"#c62828",textPrimary:"#e0e0e0",textSecondary:"#999",textTertiary:"#777",textMuted:"#666",trackName:"#ccc",rulerTick:"#888",rulerLabel:"#ccc",tooltipBg:"#333",tooltipBorder:"#555",overlayBg:"rgba(0,0,0,0.55)",selectedRow:"#333",centerLine:"#555",...yc},light:{name:"Light",appBg:"#f5f5f5",headerBg:"#ffffff",panelBg:"#eee",canvasBg:"#ffffff",inputBg:"#fff",border:"#ddd",borderAccent:"#bbb",borderStrong:"#999",btnBg:"#e0e0e0",btnText:"#333",btnDanger:"#d32f2f",textPrimary:"#222",textSecondary:"#666",textTertiary:"#888",textMuted:"#aaa",trackName:"#333",rulerTick:"#666",rulerLabel:"#333",tooltipBg:"#fff",tooltipBorder:"#ccc",overlayBg:"rgba(0,0,0,0.25)",selectedRow:"#dde4ee",centerLine:"#ccc",...yc},colorblind:{name:"Colorblind Friendly",appBg:"#1a1a1a",headerBg:"#2a2a2a",panelBg:"#252525",canvasBg:"#1a1a1a",inputBg:"#333",border:"#333",borderAccent:"#444",borderStrong:"#555",btnBg:"#555",btnText:"#fff",btnDanger:"#cc4125",textPrimary:"#e0e0e0",textSecondary:"#999",textTertiary:"#777",textMuted:"#666",trackName:"#ccc",rulerTick:"#888",rulerLabel:"#ccc",tooltipBg:"#333",tooltipBorder:"#555",overlayBg:"rgba(0,0,0,0.55)",selectedRow:"#333",centerLine:"#555",geneCds:"#009e73",geneExon:"#0072b2",geneGene:"#cc79a7",geneTranscript:"#d55e00",geneUtr:"#56b4e9",geneRrna:"#e69f00",geneTrna:"#f0e442",geneRepeat:"#999999",geneDefault:"#56b4e9"},soft:{name:"Soft",appBg:"#f0ede8",headerBg:"#e4dfd8",panelBg:"#e9e5de",canvasBg:"#f5f2ed",inputBg:"#fff",border:"#d5cfc6",borderAccent:"#c4bdb2",borderStrong:"#a89f93",btnBg:"#d5cfc6",btnText:"#4a4540",btnDanger:"#c47066",textPrimary:"#3a3530",textSecondary:"#7a7468",textTertiary:"#9a9488",textMuted:"#b5ada2",trackName:"#4a4540",rulerTick:"#a89f93",rulerLabel:"#5a5550",tooltipBg:"#fff",tooltipBorder:"#d5cfc6",overlayBg:"rgba(0,0,0,0.2)",selectedRow:"#ddd8d0",centerLine:"#c4bdb2",geneCds:"#4caf50",geneExon:"#2e8bc0",geneGene:"#8e44ad",geneTranscript:"#c0392b",geneUtr:"#1abc9c",geneRrna:"#e67e22",geneTrna:"#e74c3c",geneRepeat:"#8d6e63",geneDefault:"#27ae60"},highContrast:{name:"High Contrast",appBg:"#000",headerBg:"#111",panelBg:"#111",canvasBg:"#000",inputBg:"#222",border:"#444",borderAccent:"#666",borderStrong:"#888",btnBg:"#444",btnText:"#fff",btnDanger:"#f44336",textPrimary:"#fff",textSecondary:"#ccc",textTertiary:"#aaa",textMuted:"#888",trackName:"#fff",rulerTick:"#aaa",rulerLabel:"#fff",tooltipBg:"#222",tooltipBorder:"#666",overlayBg:"rgba(0,0,0,0.7)",selectedRow:"#333",centerLine:"#555",geneCds:"#4caf50",geneExon:"#2196f3",geneGene:"#9c27b0",geneTranscript:"#e040fb",geneUtr:"#00e5ff",geneRrna:"#ff9800",geneTrna:"#ff1744",geneRepeat:"#ff6e40",geneDefault:"#69f0ae"}},Sp="genomics-viewer-theme",bp="genomics-viewer-custom-theme";function $0(){try{const e=localStorage.getItem(Sp),t=localStorage.getItem(bp);return{name:e&&(vt[e]||e==="custom")?e:"dark",custom:t?JSON.parse(t):null}}catch{return{name:"dark",custom:null}}}function N0({children:e}){const t=$0(),[n,r]=C.useState(t.name),[o,l]=C.useState(t.custom||{...vt.dark,name:"Custom"}),i=n==="custom"?o:vt[n]||vt.dark,a=C.useCallback(c=>{r(c),localStorage.setItem(Sp,c)},[]),u=C.useCallback(c=>{l(c),localStorage.setItem(bp,JSON.stringify(c))},[]);return C.useEffect(()=>{document.body.style.background=i.appBg,document.body.style.color=i.textPrimary},[i.appBg,i.textPrimary]),s.jsx(wp.Provider,{value:{theme:i,themeName:n,setThemeName:a,customTheme:o,setCustomTheme:u},children:e})}function Xe(){return C.useContext(wp)}function O0(e){const t=e==null?void 0:e.compatibility;return t&&t.status!=="ok"&&t.status!=="no_genome"}function xc(e){return e<1024?`${e} B`:e<1024*1024?`${(e/1024).toFixed(0)} KB`:`${(e/(1024*1024)).toFixed(1)} MB`}const $s=new Set([".gb",".gbk",".genbank",".fasta",".fa"]),Ns=new Set([".bam",".bw",".bigwig",".wig",".bedgraph",".bdg",".vcf",".bed",".gtf",".gff",".gff2",".gff3"]),vc=50*1024*1024;function Ml(e){if(!e)return"";const t=e.toLowerCase();if(t.endsWith(".vcf.gz"))return".vcf.gz";if(t.endsWith(".bam.bai"))return".bam.bai";const n=t.lastIndexOf(".");return n>=0?t.slice(n):""}function F0(e){const t=Ml(e);return t===".bai"||t===".bam.bai"}function I0(e){const t=[],n=[],r=[],o=[],l=[],i=[];for(const c of e){const h=Ml(c.name);$s.has(h)?t.push(c):h===".bam"?n.push(c):F0(c.name)?r.push(c):Ns.has(h)||h===".vcf.gz"?c.size>vc?i.push(c):o.push(c):l.push(c)}const a=[],u=[];for(const c of n){const h=c.name.replace(/\.bam$/i,""),d=r.find(m=>{const T=m.name.toLowerCase();return T===c.name.toLowerCase()+".bai"||T===h.toLowerCase()+".bai"});if(d){c.size>vc?i.push(c):a.push({file:c,indexFile:d});const m=r.indexOf(d);m!==-1&&r.splice(m,1)}else u.push(c)}for(const c of o)a.push({file:c,indexFile:null});for(const c of r)c._indexOrphan=!0;return l.push(...r),{genomeFiles:t,trackEntries:a,unpairedBams:u,largeFiles:i,unknownFiles:l}}function D0(){const{theme:e}=Xe(),{genome:t,setGenome:n,navigateTo:r}=at(),{addTrack:o,uploadTrack:l,commitTrack:i,discardTrack:a,addGenomeAnnotationTrack:u,error:c,setError:h}=Jt(),[d,m]=C.useState(!1),[T,v]=C.useState(null),[y,x]=C.useState(null),[f,p]=C.useState(null),[g,w]=C.useState(null),[S,j]=C.useState(null),[b,E]=C.useState(null),[O,z]=C.useState(""),[P,H]=C.useState(!1),R=C.useRef(null),U=C.useRef(null),N=C.useRef(null),Y=[...Array.from($s),...Array.from(Ns),".vcf.gz",".bai"].join(","),I={panel:{background:e.panelBg,borderBottom:`1px solid ${e.border}`,padding:"8px 12px",display:"flex",alignItems:"center",gap:12,flexWrap:"wrap",position:"relative"},group:{display:"flex",alignItems:"center",gap:6},label:{fontSize:11,color:e.textSecondary,textTransform:"uppercase",letterSpacing:1,whiteSpace:"nowrap"},fileInput:{background:e.inputBg,border:`1px solid ${e.borderAccent}`,borderRadius:4,color:e.textPrimary,padding:"4px 6px",fontSize:12,width:280,cursor:"pointer"},promptOverlay:{position:"fixed",inset:0,zIndex:9999,background:"rgba(0,0,0,0.35)",display:"flex",alignItems:"center",justifyContent:"center"},promptBox:{background:e.panelBg,border:`1px solid ${e.borderAccent}`,borderRadius:8,padding:"20px 24px",boxShadow:"0 8px 32px rgba(0,0,0,0.5)",maxWidth:440,width:"90%"},promptTitle:{fontSize:14,fontWeight:700,color:e.textPrimary,marginBottom:8},promptText:{fontSize:12,color:e.textSecondary,lineHeight:1.6,marginBottom:16},promptFile:{fontWeight:600,color:e.textPrimary},promptBtns:{display:"flex",gap:8,justifyContent:"flex-end",flexWrap:"wrap"},promptBtn:{background:e.btnBg,border:`1px solid ${e.borderStrong}`,borderRadius:4,color:e.btnText,padding:"5px 16px",cursor:"pointer",fontSize:12,fontWeight:600},promptBtnPrimary:{background:"#1976d2",border:"none",borderRadius:4,color:"#fff",padding:"5px 16px",cursor:"pointer",fontSize:12,fontWeight:600}};async function L(G){var J,te,B;m(!0),v(null),p(null),x(`Uploading genome: ${G.name}...`);try{const q=await yn.load(G,Z=>{p({...Z,label:G.name}),Z.percent>=100&&x(`Processing genome: ${G.name}...`)});p(null);const X=q.data;if(X.name&&(X.name=Ft(X.name)),n(X),((J=X.chromosomes)==null?void 0:J.length)>0){const Z=X.chromosomes[0];r(Z.name,0,Math.min(Z.length,5e4))}X.is_annotated&&u({id:"genome_annotations",name:`${X.name} (annotations)`,track_type:"genome_annotations",file_format:"genbank",targetChromosomes:X.annotated_chromosomes||null}),x(`Genome loaded: ${X.name}`),setTimeout(()=>x(null),3e3)}catch(q){v(((B=(te=q.response)==null?void 0:te.data)==null?void 0:B.detail)||q.message),x(null),p(null)}finally{m(!1)}}async function $(G){var te,B;m(!0),v(null),p(null);const J=[];for(const q of G){x(`Adding chromosomes from ${q.name}...`);try{const Z=(await yn.addChromosomes(q,le=>{p({...le,label:q.name})})).data;Z.name&&(Z.name=Ft(Z.name)),n(Z),Z.is_annotated&&u({id:"genome_annotations",name:`${Z.name} (annotations)`,track_type:"genome_annotations",file_format:"genbank",targetChromosomes:Z.annotated_chromosomes||null})}catch(X){J.push(`${q.name}: ${((B=(te=X.response)==null?void 0:te.data)==null?void 0:B.detail)||X.message}`)}}m(!1),J.length?(v(J.join("; ")),x(null)):(x(`Added chromosomes from ${G.length} file${G.length>1?"s":""}.`),setTimeout(()=>x(null),3e3))}async function D(G){var X,Z;if(!G.length)return;m(!0),v(null),h(null),p(null);const J=[],te=[],B=[],q=[];for(let le=0;le<G.length;le++){const{file:oe,indexFile:fe}=G[le];x(`Loading track ${le+1}/${G.length}: ${oe.name}...`);try{const we=await l(oe,void 0,fe,Ie=>{p({...Ie,label:oe.name}),Ie.percent>=100&&x(`Processing: ${oe.name}...`)});O0(we)?te.push(we):(i(we),J.push(we)),we.hint&&q.push(we.hint)}catch(we){B.push(`${oe.name}: ${((Z=(X=we.response)==null?void 0:X.data)==null?void 0:Z.detail)||we.message}`)}}if(m(!1),p(null),B.length)v(B.join("; ")),x(null);else if(J.length>0&&te.length===0){const le=`Added ${J.length} track${J.length>1?"s":""}.`;q.length?(x(le),setTimeout(()=>{x(q.join(" ")),setTimeout(()=>x(null),8e3)},2e3)):(x(le),setTimeout(()=>x(null),3e3))}else te.length===0&&x(null);te.length>0&&j({tracks:te})}async function A(G){const J=Array.from(G);if(!J.length)return;const{genomeFiles:te,trackEntries:B,unpairedBams:q,largeFiles:X,unknownFiles:Z}=I0(J);if(Z.length){const le=Z.filter(fe=>fe._indexOrphan),oe=Z.filter(fe=>!fe._indexOrphan);le.length&&E({bamFile:null,indexFile:le[0],bamPath:"",indexPath:"",error:null}),oe.length&&v(`Unsupported: ${oe.map(fe=>fe.name).join(", ")}`)}if(X.length>0){const le=X[0],oe=(le.size/(1024*1024)).toFixed(0),fe=le.name.toLowerCase().endsWith(".bam");E({bamFile:fe?le:null,indexFile:null,bamPath:"",indexPath:"",error:null,_largeFile:le,_largeWarning:`${le.name} is ${oe} MB. Large files load much faster via file path — the server reads directly from disk without uploading.`}),X.length>1&&v(`${X.length-1} additional large file(s) skipped — load one at a time via path.`)}if(q.length>0&&X.length===0&&E({bamFile:q[0],indexFile:null,bamPath:"",indexPath:"",error:null}),te.length>0&&!t){if(await L(te[0]),te.length>1){B.length>0&&await D(B),w({files:te.slice(1)}),R.current&&(R.current.value="");return}B.length>0&&await D(B)}else te.length>0&&t?(B.length>0&&await D(B),w({files:te})):B.length>0&&(t?await D(B):v("Load a genome file first (.fasta, .gb, .genbank)"));R.current&&(R.current.value="")}async function F(G){var X,Z,le,oe,fe;const J=G.trim();if(!J)return;v(null);const te=J.toLowerCase(),B=$s.has(Ml(J)),q=Ns.has(Ml(J))||te.endsWith(".vcf.gz")||te.endsWith(".bai");if(B&&!t){m(!0),x("Loading genome from path...");try{const Ie=(await yn.loadPath(J)).data;if(Ie.name&&(Ie.name=Ft(Ie.name)),n(Ie),((X=Ie.chromosomes)==null?void 0:X.length)>0){const ut=Ie.chromosomes[0];r(ut.name,0,Math.min(ut.length,5e4))}Ie.is_annotated&&u({id:"genome_annotations",name:`${Ie.name} (annotations)`,track_type:"genome_annotations",file_format:"genbank",targetChromosomes:Ie.annotated_chromosomes||null}),x(`Genome loaded: ${Ie.name}`),setTimeout(()=>x(null),3e3)}catch(we){v(((le=(Z=we.response)==null?void 0:Z.data)==null?void 0:le.detail)||we.message),x(null)}finally{m(!1)}}else if(q||B){if(!t){v("Load a genome file first");return}m(!0),x("Loading track from path...");try{const we=J.split(/[/\\]/).pop()||J,ut=(await Ot.loadPath(J,we)).data;ut.name&&(ut.name=Ft(ut.name)),i(ut),x(`Track loaded: ${ut.name}`),ut.hint?setTimeout(()=>{x(ut.hint),setTimeout(()=>x(null),8e3)},2e3):setTimeout(()=>x(null),3e3)}catch(we){v(((fe=(oe=we.response)==null?void 0:oe.data)==null?void 0:fe.detail)||we.message),x(null)}finally{m(!1)}}else v(`Unsupported file type: ${J.split(/[/\\]/).pop()}`);z("")}function V(G){G.preventDefault(),F(O)}function M(G){const J=G.target.files;J!=null&&J.length&&(v(null),A(J))}async function k(){if(!g)return;const{files:G}=g;w(null),await $(G)}async function Q(){if(!g)return;const{files:G}=g;w(null),await D(G.map(J=>({file:J,indexFile:null})))}function ee(){w(null)}function ce(){var G;(G=U.current)==null||G.click()}function he(){var G;(G=N.current)==null||G.click()}function pe(G){var te;const J=(te=G.target.files)==null?void 0:te[0];if(G.target.value="",!!J){if(!J.name.toLowerCase().endsWith(".bam")){E(B=>({...B,error:"Please select a .bam file"}));return}E(B=>({...B,bamFile:J,bamPath:"",error:null}))}}function ae(G){var te;const J=(te=G.target.files)==null?void 0:te[0];if(G.target.value="",!!J){if(!J.name.toLowerCase().endsWith(".bai")){E(B=>({...B,error:"Please select a .bai index file"}));return}E(B=>({...B,indexFile:J,indexPath:"",error:null}))}}function ie(G){return G&&(G.bamFile||G.bamPath.trim())}function ne(G){return G&&(G.indexFile||G.indexPath.trim())}function xe(G){return ie(G)&&ne(G)}async function Me(){if(!b)return;const{bamFile:G,indexFile:J,bamPath:te,indexPath:B,_largeFile:q}=b,X=te.trim(),Z=B.trim();if(q&&!q.name.toLowerCase().endsWith(".bam")){if(!X){E(oe=>({...oe,error:"File path is required"}));return}E(null),await F(X);return}if(!G&&!X){E(oe=>({...oe,error:"BAM file or path is required"}));return}if(!J&&!Z){E(oe=>({...oe,error:"BAM index (.bai) file or path is required"}));return}if(X&&!X.toLowerCase().endsWith(".bam")){E(oe=>({...oe,error:"BAM path must end with .bam"}));return}if(Z&&!Z.toLowerCase().endsWith(".bai")){E(oe=>({...oe,error:"Index path must end with .bai"}));return}if(E(null),!G&&X){await F(X);return}await D([{file:G,indexFile:J}])}function ve(){E(null)}async function Fe(){if(S){for(const G of S.tracks)await a(G.id);j(null)}}function et(){if(S){for(const G of S.tracks)i(G);j(null),x(`Added ${S.tracks.length} track${S.tracks.length>1?"s":""}.`),setTimeout(()=>x(null),3e3)}}const me=g?g.files.map(G=>G.name).join(", "):"",gt=g&&g.files.length>1;return s.jsxs("div",{style:I.panel,"data-tour":"file-loader",children:[s.jsxs("div",{style:I.group,title:"Select genome or track files",children:[s.jsx("span",{style:I.label,children:"Load Files"}),s.jsx("input",{ref:R,type:"file",multiple:!0,style:I.fileInput,disabled:d,accept:Y,onChange:M})]}),s.jsxs("button",{style:{...I.group,background:"none",border:`1px solid ${e.borderAccent}`,borderRadius:4,padding:"3px 8px",cursor:"pointer",color:e.textSecondary,fontSize:11},onClick:()=>H(G=>!G),title:"Load file by local path (recommended for large BAM files)",children:[P?"✕":"📂"," Path"]}),P&&s.jsxs("form",{onSubmit:V,style:{display:"flex",gap:4},children:[s.jsx("input",{type:"text",value:O,onChange:G=>z(G.target.value),placeholder:"/path/to/file.bam",disabled:d,style:{background:e.inputBg,border:`1px solid ${e.borderAccent}`,borderRadius:4,color:e.textPrimary,padding:"4px 8px",fontSize:11,width:260,fontFamily:"monospace"}}),s.jsx("button",{type:"submit",disabled:d||!O.trim(),style:{background:e.btnBg,border:"none",borderRadius:4,color:e.btnText,padding:"4px 10px",cursor:"pointer",fontSize:11,fontWeight:600},children:"Load"})]}),d?s.jsxs("div",{style:{display:"flex",alignItems:"center",gap:8,flex:1,minWidth:0},children:[s.jsx("span",{style:{fontSize:10,color:e.textMuted,fontStyle:"italic",whiteSpace:"nowrap",overflow:"hidden",textOverflow:"ellipsis"},children:y||"Loading…"}),f&&s.jsxs("div",{style:{display:"flex",alignItems:"center",gap:6,flex:1,minWidth:100},children:[s.jsx("div",{style:{flex:1,height:6,background:e.inputBg,borderRadius:3,overflow:"hidden",minWidth:60},children:s.jsx("div",{style:{width:`${f.percent}%`,height:"100%",background:f.percent>=100?"#66bb6a":"#42a5f5",borderRadius:3,transition:"width 0.2s ease"}})}),s.jsx("span",{style:{fontSize:10,color:e.textTertiary,whiteSpace:"nowrap"},children:f.percent<100?`${xc(f.loaded)} / ${xc(f.total)}`:"Processing..."})]})]}):s.jsx("span",{style:{fontSize:10,color:e.textMuted,fontStyle:"italic"},children:"or drag & drop anywhere"}),!d&&y&&s.jsx("span",{style:{color:"#81c784",fontSize:11},children:y}),(T||c)&&s.jsx("span",{style:{color:"#ef9a9a",fontSize:11},children:T||c}),g&&s.jsx("div",{style:I.promptOverlay,children:s.jsxs("div",{style:I.promptBox,onClick:G=>G.stopPropagation(),children:[s.jsxs("div",{style:I.promptTitle,children:["Genome file",gt?"s":""," detected"]}),s.jsxs("div",{style:I.promptText,children:[s.jsx("span",{style:I.promptFile,children:me}),gt?" appear to be genome files. A genome is already loaded.":" appears to be a genome file. A genome is already loaded.",s.jsx("br",{}),"How would you like to handle ",gt?"them":"it","?"]}),s.jsxs("div",{style:I.promptBtns,children:[s.jsx("button",{style:I.promptBtn,onClick:ee,children:"Skip"}),s.jsxs("button",{style:I.promptBtn,onClick:Q,children:["Add as Track",gt?"s":""]}),s.jsxs("button",{style:I.promptBtnPrimary,onClick:k,children:["Add as Chromosome",gt?"s":""]})]})]})}),S&&s.jsx("div",{style:I.promptOverlay,children:s.jsxs("div",{style:I.promptBox,onClick:G=>G.stopPropagation(),children:[s.jsx("div",{style:I.promptTitle,children:"Track compatibility warning"}),s.jsxs("div",{style:I.promptText,children:[S.tracks.map(G=>{var J;return s.jsxs("div",{style:{marginBottom:6},children:[s.jsx("span",{style:I.promptFile,children:G.name})," — ",((J=G.compatibility)==null?void 0:J.message)||"Possible mismatch with loaded genome"]},G.id)}),s.jsx("div",{style:{marginTop:8},children:S.tracks.length>1?"These tracks may not match the loaded genome.":"This track may not match the loaded genome."})]}),s.jsxs("div",{style:I.promptBtns,children:[s.jsx("button",{style:I.promptBtn,onClick:Fe,children:"Skip"}),s.jsx("button",{style:I.promptBtnPrimary,onClick:et,children:"Load Anyway"})]})]})}),b&&(()=>{const G=b._largeFile&&!b._largeFile.name.toLowerCase().endsWith(".bam"),J=G?!!b.bamPath.trim():xe(b),te=b.bamFile?b.bamFile.size/(1024*1024):0,B=b.bamFile&&te>50,q=ie(b),X=ne(b),Z={flex:1,padding:"5px 8px",borderRadius:4,fontSize:11,background:e.inputBg,color:e.textPrimary,fontFamily:"monospace"},le=G?`Load ${b._largeFile.name.split(".").pop().toUpperCase()} Track`:"Load BAM Track",oe=G?"Paste the local file path for the server to read directly from disk.":"BAM files require a matching .bai index. Browse for files or paste local paths.";return s.jsx("div",{style:I.promptOverlay,onClick:ve,children:s.jsxs("div",{style:{...I.promptBox,maxWidth:500},onClick:fe=>fe.stopPropagation(),children:[s.jsx("div",{style:I.promptTitle,children:le}),s.jsx("div",{style:{...I.promptText,marginBottom:12},children:oe}),s.jsxs("div",{style:{marginBottom:10},children:[s.jsxs("div",{style:{fontSize:11,color:e.textSecondary,marginBottom:4,fontWeight:600},children:[G?"File path":".bam file"," ",q&&s.jsx("span",{style:{color:"#66bb6a"},children:"✓"})]}),s.jsxs("div",{style:{display:"flex",gap:6,alignItems:"center"},children:[s.jsx("input",{type:"text",value:b.bamFile?b.bamFile.name:b.bamPath,onChange:fe=>E(we=>({...we,bamPath:fe.target.value,bamFile:null,error:null})),placeholder:G?"/path/to/file":"/path/to/reads.bam",style:{...Z,border:`1px solid ${q?"#66bb6a":e.borderAccent}`}}),!G&&s.jsx("button",{style:{...I.promptBtn,padding:"4px 12px",whiteSpace:"nowrap"},onClick:ce,children:"Browse"})]})]}),!G&&s.jsxs("div",{style:{marginBottom:12},children:[s.jsxs("div",{style:{fontSize:11,color:e.textSecondary,marginBottom:4,fontWeight:600},children:[".bai index ",X&&s.jsx("span",{style:{color:"#66bb6a"},children:"✓"})]}),s.jsxs("div",{style:{display:"flex",gap:6,alignItems:"center"},children:[s.jsx("input",{type:"text",value:b.indexFile?b.indexFile.name:b.indexPath,onChange:fe=>E(we=>({...we,indexPath:fe.target.value,indexFile:null,error:null})),placeholder:"/path/to/reads.bam.bai",style:{...Z,border:`1px solid ${X?"#66bb6a":e.borderAccent}`}}),s.jsx("button",{style:{...I.promptBtn,padding:"4px 12px",whiteSpace:"nowrap"},onClick:he,children:"Browse"})]})]}),s.jsx("input",{ref:U,type:"file",accept:".bam",style:{display:"none"},onChange:pe}),s.jsx("input",{ref:N,type:"file",accept:".bai,.bam.bai",style:{display:"none"},onChange:ae}),(B||b._largeWarning)&&s.jsx("div",{style:{fontSize:11,color:"#ffb74d",marginBottom:8,padding:"6px 10px",background:"rgba(255,183,77,0.1)",borderRadius:4,border:"1px solid rgba(255,183,77,0.3)"},children:b._largeWarning||s.jsxs(s.Fragment,{children:[s.jsxs("strong",{children:["Large file (",te.toFixed(0)," MB)"]})," — uploading may be slow. Paste the file path instead for instant loading."]})}),b.error&&s.jsx("div",{style:{fontSize:11,color:"#ef9a9a",marginBottom:8,padding:"4px 0"},children:b.error}),!B&&s.jsx("div",{style:{fontSize:10,color:e.textTertiary,marginBottom:10},children:"Tip: Paste a local file path to skip uploading — the server reads directly from disk. The .bai is auto-discovered if next to the .bam."}),s.jsxs("div",{style:I.promptBtns,children:[s.jsx("button",{style:I.promptBtn,onClick:ve,children:"Cancel"}),s.jsx("button",{style:{...I.promptBtnPrimary,opacity:J?1:.4,cursor:J?"pointer":"default"},disabled:!J,onClick:Me,children:"Open"})]})]})})})()]})}const U0=260,W0=180,H0=440,V0=.78,G0=1.4;function kp({title:e,onClose:t,theme:n,children:r,defaultWidth:o=440,defaultHeight:l=500}){const[i,a]=C.useState(()=>({x:Math.max(20,window.innerWidth-o-40),y:80})),[u,c]=C.useState({w:o,h:Math.min(l,window.innerHeight-120)}),h=C.useRef(null),d=C.useRef(null),m=C.useMemo(()=>{const f=u.w/H0;return Math.max(V0,Math.min(G0,f))},[u.w]),T=u.w/m,v=C.useCallback(f=>{if(f.target.closest("input, select, button, label, textarea"))return;f.preventDefault(),h.current={startX:f.clientX,startY:f.clientY,startPos:{...i}};function p(w){h.current&&a({x:Math.max(0,Math.min(window.innerWidth-100,h.current.startPos.x+w.clientX-h.current.startX)),y:Math.max(0,Math.min(window.innerHeight-40,h.current.startPos.y+w.clientY-h.current.startY))})}function g(){h.current=null,window.removeEventListener("mousemove",p),window.removeEventListener("mouseup",g)}window.addEventListener("mousemove",p),window.addEventListener("mouseup",g)},[i]),y=C.useCallback(f=>{f.preventDefault(),f.stopPropagation(),d.current={startX:f.clientX,startY:f.clientY,startSize:{...u}};function p(w){d.current&&c({w:Math.max(U0,d.current.startSize.w+w.clientX-d.current.startX),h:Math.max(W0,d.current.startSize.h+w.clientY-d.current.startY)})}function g(){d.current=null,window.removeEventListener("mousemove",p),window.removeEventListener("mouseup",g),document.body.style.cursor=""}document.body.style.cursor="nwse-resize",window.addEventListener("mousemove",p),window.addEventListener("mouseup",g)},[u]),x={panel:{position:"fixed",left:i.x,top:i.y,width:u.w,height:u.h,zIndex:1e3,background:n.panelBg,border:`1px solid ${n.borderAccent}`,borderRadius:8,display:"flex",flexDirection:"column",boxShadow:"0 8px 32px rgba(0,0,0,0.5)",overflow:"hidden"},header:{display:"flex",justifyContent:"space-between",alignItems:"center",padding:`${6*m+2}px ${12*m+2}px`,borderBottom:`1px solid ${n.border}`,cursor:"grab",userSelect:"none",flexShrink:0},title:{fontSize:Math.max(11,13*m),fontWeight:700,color:n.textPrimary},closeBtn:{background:"none",border:"none",color:n.textSecondary,cursor:"pointer",fontSize:Math.max(14,16*m),lineHeight:1,padding:"0 4px"},body:{flex:1,overflowY:"auto",overflowX:"hidden"},scaledContent:{transform:m!==1?`scale(${m})`:void 0,transformOrigin:"top left",width:m!==1?T:"100%"},resizeHandle:{position:"absolute",right:0,bottom:0,width:14,height:14,cursor:"nwse-resize",zIndex:1}};return s.jsxs("div",{style:x.panel,children:[s.jsxs("div",{style:x.header,onMouseDown:v,children:[s.jsx("span",{style:x.title,children:e}),s.jsx("button",{style:x.closeBtn,onClick:t,children:"✕"})]}),s.jsx("div",{style:x.body,children:s.jsx("div",{style:x.scaledContent,children:r})}),s.jsx("div",{style:x.resizeHandle,onMouseDown:y,title:"Drag to resize",children:s.jsx("svg",{width:"14",height:"14",viewBox:"0 0 14 14",style:{display:"block"},children:s.jsx("path",{d:"M12 2L2 12M12 6L6 12M12 10L10 12",stroke:n.textTertiary,strokeWidth:"1.5",fill:"none"})})})]})}const Y0=["#f44336","#e53935","#ef5350","#e57373","#ff5722","#ff8a65","#ff9800","#ffa726","#ffb74d","#ffc107","#ffd54f","#fff176","#4caf50","#66bb6a","#81c784","#aed581","#009688","#26c6da","#4dd0e1","#80cbc4","#2196f3","#42a5f5","#64b5f6","#3f51b5","#7e57c2","#9575cd","#9c27b0","#ab47bc","#ce93d8","#e91e63","#f06292","#795548","#8d6e63","#607d8b","#78909c"];function Q0({onClose:e}){const{theme:t}=Xe(),{tracks:n,updateTrack:r,updateMultipleTracks:o,removeTrack:l}=Jt(),[i,a]=C.useState(new Set);function u(k){a(Q=>{const ee=new Set(Q);return ee.has(k)?ee.delete(k):ee.add(k),ee})}function c(){a(new Set(n.map(k=>k.id)))}function h(){a(new Set)}const d=n.filter(k=>i.has(k.id)),m=d.some(k=>k.track_type==="annotations"||k.track_type==="genome_annotations"),T=d.some(k=>k.track_type==="coverage"||k.track_type==="reads"),v=d.some(k=>k.track_type==="reads"),y=d.some(k=>k.track_type==="variants"),x=d.some(k=>k.track_type==="coverage"||k.track_type==="reads"||k.track_type==="variants"),f=d.some(k=>k.track_type==="coverage"||k.track_type==="reads"),p=d.length>0&&d.every(k=>k.height===d[0].height)?d[0].height:"",g=d.length>0&&d.every(k=>k.color===d[0].color)?d[0].color:"#888888",w=d.length>0&&d.every(k=>k.visible===d[0].visible)?d[0].visible:null,S=d.length>0&&d.every(k=>k.useArrows===d[0].useArrows)?d[0].useArrows:null,j=d.length>0&&d.every(k=>k.scaleMax===d[0].scaleMax)?d[0].scaleMax:void 0,b=d.length>0&&d.every(k=>k.scaleMin===d[0].scaleMin)?d[0].scaleMin:void 0,E=j==null&&b==null,O=d.length>0&&d.every(k=>k.logScale===d[0].logScale)?d[0].logScale:null,z=d.length>0&&d.every(k=>k.barAutoWidth===d[0].barAutoWidth)?d[0].barAutoWidth:null,P=d.length>0&&d.every(k=>k.barWidth===d[0].barWidth)?d[0].barWidth:void 0,H=d.length>0&&d.every(k=>k.showOutline===d[0].showOutline)?d[0].showOutline:null,R=d.length>0&&d.every(k=>k.outlineColor===d[0].outlineColor)?d[0].outlineColor:void 0,U=d.length>0&&d.every(k=>k.outlineSmooth===d[0].outlineSmooth)?d[0].outlineSmooth:void 0,N=d.length>0&&d.every(k=>k.showBars===d[0].showBars)?d[0].showBars:null,Y=d.length>0&&d.every(k=>k.showNucleotides===d[0].showNucleotides)?d[0].showNucleotides:null,I=d.length>0&&d.every(k=>(k.fwdColor||"#90a4ae")===(d[0].fwdColor||"#90a4ae"))?d[0].fwdColor||"#90a4ae":void 0,L=d.length>0&&d.every(k=>(k.revColor||"#f06292")===(d[0].revColor||"#f06292"))?d[0].revColor||"#f06292":void 0,$=d.length>0&&d.every(k=>(k.arrowStyle||"pointed")===(d[0].arrowStyle||"pointed"))?d[0].arrowStyle||"pointed":void 0,D=d.length>0&&d.every(k=>(k.arrowSize||4)===(d[0].arrowSize||4))?d[0].arrowSize||4:void 0;function A(k){o([...i],k)}function F(){for(const k of i)l(k);a(new Set)}const V=t,M={body:{padding:"8px 0",overflowY:"auto",flex:1},trackRow:{display:"flex",alignItems:"center",gap:8,padding:"5px 16px",cursor:"pointer",transition:"background 0.1s"},trackRowSelected:{background:V.selectedRow},checkbox:{width:14,height:14,cursor:"pointer",flexShrink:0},trackLabel:{fontSize:12,color:V.textPrimary,flex:1,overflow:"hidden",textOverflow:"ellipsis",whiteSpace:"nowrap"},trackType:{fontSize:10,color:V.textTertiary,flexShrink:0},section:{padding:"12px 16px",borderTop:`1px solid ${V.border}`},sectionTitle:{fontSize:11,color:V.textSecondary,textTransform:"uppercase",letterSpacing:1,marginBottom:8},controlRow:{display:"flex",alignItems:"center",gap:10,marginBottom:6},subRow:{display:"flex",alignItems:"center",gap:10,marginBottom:6,paddingLeft:16,borderLeft:`2px solid ${V.border}`,marginLeft:4},controlLabel:{fontSize:12,color:V.textSecondary,width:90},subLabel:{fontSize:11,color:V.textTertiary,width:76},input:{background:V.inputBg,border:`1px solid ${V.borderAccent}`,borderRadius:4,color:V.textPrimary,padding:"3px 6px",fontSize:12,width:70},colorInput:{width:28,height:22,border:"none",background:"none",cursor:"pointer",padding:0},btn:{background:V.btnBg,color:V.btnText},btnDanger:{background:V.btnDanger,border:"none",borderRadius:4,color:"#fff",padding:"5px 14px",cursor:"pointer",fontSize:12,fontWeight:600},footer:{display:"flex",justifyContent:"space-between",alignItems:"center",padding:"10px 16px",borderTop:`1px solid ${V.border}`,gap:8},smallBtn:{background:"none",border:`1px solid ${V.borderAccent}`,borderRadius:3,color:V.textSecondary,cursor:"pointer",fontSize:10,padding:"2px 8px"},cbLabel:{fontSize:12,color:V.textSecondary,cursor:"pointer",display:"flex",alignItems:"center",gap:4}};return s.jsxs(kp,{title:"Track Settings",onClose:e,theme:V,defaultWidth:460,defaultHeight:520,children:[s.jsx("div",{style:M.body,children:n.length===0?s.jsx("div",{style:{padding:16,color:V.textTertiary,fontSize:12},children:"No tracks loaded."}):n.map(k=>s.jsxs("div",{style:{...M.trackRow,...i.has(k.id)?M.trackRowSelected:{}},onClick:()=>u(k.id),children:[s.jsx("input",{type:"checkbox",checked:i.has(k.id),onChange:()=>u(k.id),onClick:Q=>Q.stopPropagation(),style:M.checkbox}),s.jsx("span",{style:{width:10,height:10,borderRadius:2,background:k.color,flexShrink:0}}),s.jsx("span",{style:{...M.trackLabel,opacity:k.visible?1:.4},children:k.name}),s.jsx("span",{style:M.trackType,children:k.track_type})]},k.id))}),d.length>0&&s.jsxs("div",{style:M.section,children:[s.jsxs("div",{style:M.sectionTitle,children:["Edit ",d.length," selected track",d.length>1?"s":""]}),s.jsxs("div",{style:M.controlRow,children:[s.jsx("span",{style:M.controlLabel,children:"Height (px)"}),s.jsx("input",{type:"range",min:30,max:500,step:1,value:p||80,onChange:k=>A({height:parseInt(k.target.value)}),style:{flex:1,cursor:"pointer",accentColor:V.textSecondary}}),s.jsx("input",{type:"text",inputMode:"numeric",value:p,placeholder:"mixed",style:{...M.input,width:48},onChange:k=>{const Q=parseInt(k.target.value);Q>=30&&Q<=500&&A({height:Q})},onBlur:k=>{const Q=parseInt(k.target.value);(!Q||Q<30)&&A({height:30}),Q>500&&A({height:500})}})]}),s.jsxs("div",{style:M.controlRow,children:[s.jsx("span",{style:M.controlLabel,children:"Visible"}),s.jsxs("label",{style:M.cbLabel,children:[s.jsx("input",{type:"checkbox",checked:w===!0,ref:k=>{k&&(k.indeterminate=w===null)},onChange:k=>A({visible:k.target.checked}),style:{cursor:"pointer"}}),"Show"]})]}),f&&s.jsxs("div",{style:M.controlRow,children:[s.jsx("span",{style:M.controlLabel,children:"Fill bars"}),s.jsxs("label",{style:M.cbLabel,children:[s.jsx("input",{type:"checkbox",checked:N!==!1,ref:k=>{k&&(k.indeterminate=N===null)},onChange:k=>A({showBars:k.target.checked}),style:{cursor:"pointer"}}),"Show"]}),N!==!1&&s.jsx("input",{type:"color",value:g,style:M.colorInput,onChange:k=>A({color:k.target.value}),title:"Bar fill color"})]}),(y||!x&&!m)&&s.jsxs("div",{style:M.controlRow,children:[s.jsx("span",{style:M.controlLabel,children:"Color"}),s.jsx("input",{type:"color",value:g,style:M.colorInput,onChange:k=>A({color:k.target.value})})]}),x&&s.jsxs(s.Fragment,{children:[s.jsxs("div",{style:M.controlRow,children:[s.jsx("span",{style:M.controlLabel,children:"Bar width"}),s.jsxs("label",{style:M.cbLabel,children:[s.jsx("input",{type:"checkbox",checked:z!==!1,ref:k=>{k&&(k.indeterminate=z===null)},onChange:k=>A({barAutoWidth:k.target.checked}),style:{cursor:"pointer"}}),"Auto"]})]}),z===!1&&s.jsxs("div",{style:M.subRow,children:[s.jsx("span",{style:M.subLabel,children:"Width"}),s.jsx("input",{type:"range",min:1,max:50,step:1,value:P??2,onChange:k=>A({barWidth:parseInt(k.target.value)}),style:{flex:1,cursor:"pointer",accentColor:V.textSecondary}}),s.jsx("input",{type:"number",min:1,max:50,step:1,value:P??2,style:{...M.input,width:48},onChange:k=>{const Q=parseInt(k.target.value);Q>=1&&Q<=50&&A({barWidth:Q})}}),s.jsx("span",{style:{fontSize:11,color:V.textTertiary},children:"px"})]})]}),f&&s.jsxs(s.Fragment,{children:[s.jsxs("div",{style:M.controlRow,children:[s.jsx("span",{style:M.controlLabel,children:"Peak outline"}),s.jsxs("label",{style:M.cbLabel,children:[s.jsx("input",{type:"checkbox",checked:H===!0,ref:k=>{k&&(k.indeterminate=H===null)},onChange:k=>A({showOutline:k.target.checked}),style:{cursor:"pointer"}}),"Trace peaks"]}),H===!0&&s.jsx("input",{type:"color",value:R||g||"#ffffff",onChange:k=>A({outlineColor:k.target.value}),title:"Outline color",style:{width:22,height:18,border:"none",background:"none",cursor:"pointer",padding:0,marginLeft:4}})]}),H===!0&&s.jsxs("div",{style:M.subRow,children:[s.jsx("span",{style:M.subLabel,children:"Smoothness"}),s.jsx("input",{type:"range",min:0,max:10,step:1,value:U??0,onChange:k=>A({outlineSmooth:parseInt(k.target.value)}),style:{flex:1,cursor:"pointer",accentColor:V.textSecondary}}),s.jsx("span",{style:{fontSize:11,color:V.textTertiary,width:24,textAlign:"right"},children:U??0})]})]}),T&&s.jsxs("div",{style:M.controlRow,children:[s.jsx("span",{style:M.controlLabel,children:"Y Scale"}),s.jsxs("label",{style:M.cbLabel,children:[s.jsx("input",{type:"checkbox",checked:E,onChange:k=>A(k.target.checked?{scaleMax:null,scaleMin:null}:{scaleMax:100,scaleMin:100}),style:{cursor:"pointer"}}),"Auto"]})]}),T&&!E&&s.jsxs("div",{style:M.subRow,children:[s.jsx("span",{style:{fontSize:11,color:V.textTertiary,width:40},children:"+Ymax"}),s.jsx("input",{type:"number",min:1,step:10,value:j??"",placeholder:"max",style:M.input,onChange:k=>{const Q=parseFloat(k.target.value);Q>0&&A({scaleMax:Q})}}),s.jsxs("span",{style:{fontSize:11,color:V.textTertiary,width:40},children:["−","Ymax"]}),s.jsx("input",{type:"number",min:1,step:10,value:b??"",placeholder:"min",style:M.input,onChange:k=>{const Q=parseFloat(k.target.value);Q>0&&A({scaleMin:Q})}})]}),T&&s.jsxs("div",{style:M.controlRow,children:[s.jsx("span",{style:M.controlLabel,children:"Log scale"}),s.jsxs("label",{style:M.cbLabel,children:[s.jsx("input",{type:"checkbox",checked:O===!0,ref:k=>{k&&(k.indeterminate=O===null)},onChange:k=>A({logScale:k.target.checked}),style:{cursor:"pointer"}}),"log","₂"]})]}),m&&s.jsx(K0,{tracks:d,applyToSelected:A,theme:V}),m&&s.jsxs("div",{style:M.controlRow,children:[s.jsx("span",{style:M.controlLabel,children:"Gene style"}),s.jsxs("label",{style:M.cbLabel,children:[s.jsx("input",{type:"checkbox",checked:S===!0,ref:k=>{k&&(k.indeterminate=S===null)},onChange:k=>A({useArrows:k.target.checked}),style:{cursor:"pointer"}}),"Pointed arrows"]})]}),(v||m)&&s.jsxs("div",{style:M.controlRow,children:[s.jsx("span",{style:M.controlLabel,children:"Nucleotides"}),s.jsxs("label",{style:M.cbLabel,children:[s.jsx("input",{type:"checkbox",checked:Y!==!1,ref:k=>{k&&(k.indeterminate=Y===null)},onChange:k=>A({showNucleotides:k.target.checked}),style:{cursor:"pointer"}}),"Show when zoomed in"]})]}),v&&s.jsxs(s.Fragment,{children:[s.jsx("div",{style:{...M.sectionTitle,marginTop:12},children:"Read Appearance"}),s.jsxs("div",{style:M.controlRow,children:[s.jsx("span",{style:M.controlLabel,children:"Strand colors"}),s.jsx("span",{style:{fontSize:10,color:V.textTertiary,marginRight:2},children:"▶"}),s.jsx("input",{type:"color",value:I||"#90a4ae",onChange:k=>A({fwdColor:k.target.value}),title:"Forward strand color",style:{width:22,height:18,border:"none",background:"none",cursor:"pointer",padding:0}}),s.jsx("span",{style:{fontSize:10,color:V.textTertiary,marginLeft:6,marginRight:2},children:"◀"}),s.jsx("input",{type:"color",value:L||"#f06292",onChange:k=>A({revColor:k.target.value}),title:"Reverse strand color",style:{width:22,height:18,border:"none",background:"none",cursor:"pointer",padding:0}}),s.jsx("button",{style:{...M.smallBtn,marginLeft:"auto"},onClick:()=>A({fwdColor:null,revColor:null}),title:"Reset to defaults",children:"Reset"})]}),s.jsxs("div",{style:M.controlRow,children:[s.jsx("span",{style:M.controlLabel,children:"Arrow style"}),s.jsxs("select",{value:$||"pointed",onChange:k=>A({arrowStyle:k.target.value}),style:{background:V.inputBg,border:`1px solid ${V.borderAccent}`,borderRadius:4,color:V.textPrimary,padding:"2px 6px",fontSize:11,cursor:"pointer"},children:[s.jsx("option",{value:"pointed",children:"Pointed"}),s.jsx("option",{value:"chevron",children:"Chevron"}),s.jsx("option",{value:"fade",children:"Fade"}),s.jsx("option",{value:"flat",children:"Flat (none)"})]})]}),($||"pointed")!=="flat"&&s.jsxs("div",{style:M.subRow,children:[s.jsx("span",{style:M.subLabel,children:"Arrow size"}),s.jsx("input",{type:"range",min:2,max:12,step:1,value:D||4,onChange:k=>A({arrowSize:parseInt(k.target.value)}),style:{flex:1,cursor:"pointer",accentColor:V.textSecondary}}),s.jsx("span",{style:{fontSize:11,color:V.textTertiary,width:20,textAlign:"right"},children:D||4})]})]})]}),s.jsxs("div",{style:M.footer,children:[s.jsxs("div",{style:{display:"flex",gap:6},children:[s.jsx("button",{style:M.smallBtn,onClick:c,children:"Select all"}),s.jsx("button",{style:M.smallBtn,onClick:h,children:"Select none"})]}),s.jsx("div",{style:{display:"flex",gap:8},children:d.length>0&&s.jsxs("button",{style:M.btnDanger,onClick:F,children:["Remove (",d.length,")"]})})]})]})}const X0=[{key:"cds",label:"CDS"},{key:"exon",label:"Exon"},{key:"gene",label:"Gene"},{key:"transcript",label:"Transcript"},{key:"utr",label:"UTR"},{key:"rrna",label:"rRNA"},{key:"trna",label:"tRNA"},{key:"repeat",label:"Repeat"},{key:"default",label:"Other"}];function K0({tracks:e,applyToSelected:t,theme:n}){var T;const[r,o]=C.useState(null),l=C.useRef(null),[i,a]=C.useState(null),u=((T=e[0])==null?void 0:T.annotationColors)||{};function c(v){return u[v]||vp[v]||"#80cbc4"}function h(v,y){for(const x of e){const f={...x.annotationColors||{},[v]:y};t({annotationColors:f})}}function d(){t({annotationColors:null})}function m(v){a(v),l.current&&(l.current.value=c(v),l.current.click())}return s.jsxs("div",{style:{padding:"4px 0"},children:[s.jsxs("div",{style:{display:"flex",alignItems:"center",gap:8,marginBottom:6,padding:"0 0 0 0"},children:[s.jsx("span",{style:{fontSize:12,color:n.textSecondary,width:90},children:"Annotation colors"}),s.jsx("button",{style:{background:"none",border:`1px solid ${n.borderAccent}`,borderRadius:3,color:n.textTertiary,cursor:"pointer",fontSize:10,padding:"1px 6px"},onClick:d,children:"Reset"})]}),X0.map(({key:v,label:y})=>{const x=c(v);return s.jsxs("div",{children:[s.jsxs("div",{style:{display:"flex",alignItems:"center",gap:6,padding:"3px 4px",cursor:"pointer",fontSize:11,color:n.textPrimary,borderRadius:3},onMouseEnter:f=>f.currentTarget.style.background=n.selectedRow||"rgba(255,255,255,0.05)",onMouseLeave:f=>f.currentTarget.style.background="transparent",onClick:()=>o(r===v?null:v),children:[s.jsx("span",{style:{width:14,height:14,borderRadius:3,background:x,border:"1px solid rgba(255,255,255,0.15)",flexShrink:0,cursor:"pointer"},onDoubleClick:f=>{f.stopPropagation(),m(v)},title:"Click to expand swatches, double-click for full color picker"}),s.jsx("span",{style:{flex:1},children:y}),s.jsx("span",{style:{fontSize:9,color:n.textTertiary},children:r===v?"▲":"▼"})]}),r===v&&s.jsx("div",{style:{padding:"3px 4px 6px 24px",display:"flex",flexWrap:"wrap",gap:2},children:Y0.map(f=>s.jsx("span",{style:{width:16,height:16,borderRadius:3,background:f,cursor:"pointer",border:f===x?`2px solid ${n.textPrimary}`:"1px solid rgba(255,255,255,0.1)",boxSizing:"border-box"},onClick:()=>{h(v,f),o(null)}},f))})]},v)}),s.jsx("input",{ref:l,type:"color",style:{position:"absolute",left:-9999,top:-9999,opacity:0,width:0,height:0},onChange:v=>{i&&h(i,v.target.value)}})]})}const q0=["dark","light","colorblind","soft","highContrast"],wc=[{key:"appBg",label:"Background",group:"ui"},{key:"panelBg",label:"Panel",group:"ui"},{key:"canvasBg",label:"Canvas",group:"ui"},{key:"btnBg",label:"Buttons",group:"ui"},{key:"textPrimary",label:"Text",group:"ui"},{key:"textSecondary",label:"Text secondary",group:"ui"},{key:"border",label:"Borders",group:"ui"},{key:"geneCds",label:"CDS",group:"gene"},{key:"geneExon",label:"Exon",group:"gene"},{key:"geneGene",label:"Gene",group:"gene"},{key:"geneTranscript",label:"Transcript",group:"gene"},{key:"geneUtr",label:"UTR",group:"gene"},{key:"geneRrna",label:"rRNA",group:"gene"},{key:"geneTrna",label:"tRNA",group:"gene"},{key:"geneRepeat",label:"Repeat",group:"gene"},{key:"geneDefault",label:"Default feature",group:"gene"}],J0=["#000000","#1a1a1a","#333333","#4d4d4d","#666666","#808080","#999999","#b3b3b3","#cccccc","#e6e6e6","#f2f2f2","#ffffff","#4e0000","#7f0000","#b71c1c","#c62828","#d32f2f","#e53935","#ef5350","#f44336","#ef9a9a","#ffcdd2","#ffebee","#fff5f5","#4e2600","#7f3d00","#e65100","#ef6c00","#f57c00","#fb8c00","#ff9800","#ffa726","#ffb74d","#ffcc80","#ffe0b2","#fff3e0","#4e4400","#7f6f00","#f57f17","#f9a825","#fbc02d","#fdd835","#ffeb3b","#fff176","#fff59d","#fff9c4","#fffde7","#fffff0","#003300","#1b5e20","#2e7d32","#388e3c","#43a047","#4caf50","#66bb6a","#81c784","#a5d6a7","#c8e6c9","#e8f5e9","#f1f8e9","#003333","#004d40","#00695c","#00796b","#00897b","#009688","#26a69a","#4db6ac","#80cbc4","#b2dfdb","#e0f2f1","#e0f7fa","#001a33","#0d47a1","#1565c0","#1976d2","#1e88e5","#2196f3","#42a5f5","#64b5f6","#90caf9","#bbdefb","#e3f2fd","#e8eaf6","#1a0033","#311b92","#4527a0","#512da8","#5e35b1","#673ab7","#7e57c2","#9575cd","#b39ddb","#d1c4e9","#ede7f6","#f3e5f5","#330019","#880e4f","#ad1457","#c2185b","#d81b60","#e91e63","#ec407a","#f06292","#f48fb1","#f8bbd0","#fce4ec","#fff0f5","#1b0000","#3e2723","#4e342e","#5d4037","#6d4c41","#795548","#8d6e63","#a1887f","#bcaaa4","#d7ccc8","#efebe9","#fafafa"];function Z0({onClose:e}){const{theme:t,themeName:n,setThemeName:r,customTheme:o,setCustomTheme:l}=Xe(),[i,a]=C.useState(n==="custom"),[u,c]=C.useState(null),[h,d]=C.useState({left:0,top:0}),m=C.useRef(null),T=C.useRef(null);function v(b){r(b),a(!1)}function y(){const b=n==="custom"?o:vt[n]||vt.dark;l({...b,name:"Custom"}),r("custom"),a(!0)}function x(b,E){l({...o,[b]:E})}function f(b,E){const O=E.currentTarget.getBoundingClientRect(),z=window.innerWidth-O.right,P=290,H=260;let R,U;z>P+10?(R=O.right+6,U=Math.min(O.top,window.innerHeight-H-10)):(R=Math.max(10,O.left-P-6),U=Math.min(O.top,window.innerHeight-H-10)),d({left:R,top:U}),c(b)}function p(b){u&&x(u,b),c(null)}function g(b){T.current=b,m.current&&(m.current.value=j[b]||"#000000",m.current.click())}function w(b){T.current&&x(T.current,b.target.value)}const S=ey(t),j=n==="custom"?o:vt[n]||vt.dark;return s.jsxs(kp,{title:"Color Scheme",onClose:e,theme:t,defaultWidth:420,defaultHeight:480,children:[s.jsxs("div",{style:S.body,children:[s.jsxs("div",{style:S.section,children:[s.jsx("div",{style:S.sectionTitle,children:"Presets"}),s.jsx("div",{style:{display:"flex",gap:8,flexWrap:"wrap"},children:q0.map(b=>s.jsxs("button",{onClick:()=>v(b),style:{...S.presetBtn,border:n===b?`2px solid ${t.textPrimary}`:`1px solid ${t.borderAccent}`},children:[s.jsxs("div",{style:{display:"flex",gap:2,marginBottom:4},children:[s.jsx("span",{style:{width:14,height:14,borderRadius:2,background:vt[b].appBg,border:"1px solid #555"}}),s.jsx("span",{style:{width:14,height:14,borderRadius:2,background:vt[b].headerBg,border:"1px solid #555"}}),s.jsx("span",{style:{width:14,height:14,borderRadius:2,background:vt[b].btnBg,border:"1px solid #555"}})]}),s.jsx("span",{style:{fontSize:10,color:t.textSecondary},children:vt[b].name})]},b))})]}),s.jsxs("div",{style:S.section,children:[s.jsxs("div",{style:{display:"flex",alignItems:"center",justifyContent:"space-between",marginBottom:8},children:[s.jsx("div",{style:S.sectionTitle,children:"Custom Palette"}),i?s.jsx("button",{onClick:()=>a(!1),style:S.smallBtn,children:"Collapse"}):s.jsx("button",{onClick:y,style:S.btn,children:"Customize"})]}),i&&s.jsxs("div",{children:[s.jsx("div",{style:{fontSize:10,color:t.textTertiary,textTransform:"uppercase",letterSpacing:1,marginTop:4,marginBottom:6},children:"Interface"}),s.jsx("div",{style:{display:"grid",gridTemplateColumns:"1fr 1fr",gap:"4px 12px"},children:wc.filter(b=>b.group==="ui").map(({key:b,label:E})=>s.jsxs("div",{style:{display:"flex",alignItems:"center",gap:6},children:[s.jsx("span",{style:{display:"inline-block",width:20,height:16,borderRadius:3,background:j[b]||"#000",border:`1px solid ${t.borderAccent}`,cursor:"pointer",flexShrink:0},onMouseDown:O=>f(b,O),onDoubleClick:()=>{c(null),g(b)}}),s.jsx("span",{style:{fontSize:11,color:t.textSecondary},children:E})]},b))}),s.jsx("div",{style:{fontSize:10,color:t.textTertiary,textTransform:"uppercase",letterSpacing:1,marginTop:10,marginBottom:6},children:"Gene Features"}),s.jsx("div",{style:{display:"grid",gridTemplateColumns:"1fr 1fr 1fr",gap:"4px 12px"},children:wc.filter(b=>b.group==="gene").map(({key:b,label:E})=>s.jsxs("div",{style:{display:"flex",alignItems:"center",gap:6},children:[s.jsx("span",{style:{display:"inline-block",width:20,height:16,borderRadius:3,background:j[b]||"#000",border:`1px solid ${t.borderAccent}`,cursor:"pointer",flexShrink:0},onMouseDown:O=>f(b,O),onDoubleClick:()=>{c(null),g(b)}}),s.jsx("span",{style:{fontSize:11,color:t.textSecondary},children:E})]},b))})]})]})]}),s.jsx("div",{style:S.footer,children:s.jsx("button",{style:S.btn,onClick:e,children:"Close"})}),s.jsx("input",{ref:m,type:"color",onChange:w,style:{position:"fixed",left:-9999,top:-9999,opacity:0,width:0,height:0}}),u&&Wn.createPortal(s.jsx("div",{style:{position:"fixed",left:h.left,top:h.top,zIndex:10002,background:t.panelBg,border:`1px solid ${t.borderAccent}`,borderRadius:6,padding:8,boxShadow:"0 6px 20px rgba(0,0,0,0.6)",display:"grid",gridTemplateColumns:"repeat(12, 20px)",gap:2,maxHeight:300,overflowY:"auto"},onMouseLeave:()=>c(null),children:J0.map((b,E)=>s.jsx("span",{style:{width:20,height:20,borderRadius:3,background:b,cursor:"pointer",border:b===(j[u]||"")?`2px solid ${t.textPrimary}`:"1px solid rgba(128,128,128,0.3)",boxSizing:"border-box"},onMouseUp:()=>p(b)},E))}),document.body)]})}function ey(e){return{overlay:{position:"fixed",inset:0,background:e.overlayBg,display:"flex",alignItems:"center",justifyContent:"center",zIndex:1e3},panel:{background:e.panelBg,border:`1px solid ${e.borderAccent}`,borderRadius:8,padding:0,minWidth:440,maxWidth:560,maxHeight:"80vh",display:"flex",flexDirection:"column",boxShadow:"0 8px 32px rgba(0,0,0,0.5)"},header:{display:"flex",justifyContent:"space-between",alignItems:"center",padding:"10px 16px",borderBottom:`1px solid ${e.border}`},title:{fontSize:14,fontWeight:700,color:e.textPrimary},closeBtn:{background:"none",border:"none",color:e.textSecondary,cursor:"pointer",fontSize:18,lineHeight:1,padding:"0 4px"},body:{padding:"8px 0",overflowY:"auto",flex:1},section:{padding:"8px 16px"},sectionTitle:{fontSize:11,color:e.textSecondary,textTransform:"uppercase",letterSpacing:1,marginBottom:0},presetBtn:{background:e.panelBg,borderRadius:6,padding:"8px 10px",cursor:"pointer",display:"flex",flexDirection:"column",alignItems:"center",minWidth:70},smallBtn:{background:"none",border:`1px solid ${e.borderAccent}`,borderRadius:3,color:e.textSecondary,cursor:"pointer",fontSize:10,padding:"3px 8px"},btn:{background:e.btnBg,border:"none",borderRadius:4,color:e.btnText,padding:"5px 14px",cursor:"pointer",fontSize:12,fontWeight:600},footer:{display:"flex",justifyContent:"flex-end",padding:"10px 16px",borderTop:`1px solid ${e.border}`}}}const Li=5e4,ty=.5,ny=100,ry=800;function oy(e=200){const t=new Map;return{get(n){return t.get(n)},set(n,r){t.size>=e&&t.delete(t.keys().next().value),t.set(n,r)},findByPrefix(n){let r=null;for(const[o,l]of t)o.startsWith(n)&&(r=l);return r}}}const _n=oy(),Oa=new Map;function Sc(e,t){Oa.set(e,t)}function Cp(e){return Oa.get(e)||null}function ly(e,t){const n=Oa.get(e);return n||_n.findByPrefix(`${e}|coverage|${t}|`)||_n.findByPrefix(`${e}|reads|${t}|`)||_n.findByPrefix(`${e}|annotations|${t}|`)||_n.findByPrefix(`${e}|genome_annotations|${t}|`)||_n.findByPrefix(`${e}|variants|${t}|`)||null}function ei(e,t,n){const[r,o]=C.useState(null),[l,i]=C.useState(!1),[a,u]=C.useState(null),c=C.useRef(null),h=C.useRef(null),d=C.useRef(null),m=C.useRef(null),T=C.useRef(!1);C.useEffect(()=>{if(!e||!t||!n)return;const{chrom:y,start:x,end:f}=t,p=f-x,g=e.track_type;h.current&&h.current.trackId!==e.id&&(h.current=null,T.current=!1);const w=h.current;if(w&&w.trackId===e.id&&w.chrom===y&&x>=w.start&&f<=w.end){const j=p/(w.viewLen||p);if(j>.8&&j<1.2){m.current&&clearTimeout(m.current);return}m.current&&clearTimeout(m.current),m.current=setTimeout(()=>{v(e,y,x,f,p,g,n)},ry);return}return m.current&&clearTimeout(m.current),d.current&&clearTimeout(d.current),T.current&&(w==null?void 0:w.chrom)===y?d.current=setTimeout(()=>{v(e,y,x,f,p,g,n)},ny):v(e,y,x,f,p,g,n),()=>{d.current&&clearTimeout(d.current),m.current&&clearTimeout(m.current)}},[e==null?void 0:e.id,t==null?void 0:t.chrom,t==null?void 0:t.start,t==null?void 0:t.end,n]);function v(y,x,f,p,g,w,S){const b=w!=="reads"||g>Li?ty:0,E=Math.max(0,Math.floor(f-g*b)),O=Math.ceil(p+g*b),z=(O-E)/g,P=Math.max(500,Math.min(Math.floor(S*z),5e3)),H=`${y.id}|${w}|${x}|${E}|${O}|${P}`,R=_n.get(H);if(R){o(R),Sc(y.id,R),u(null),h.current={trackId:y.id,chrom:x,start:E,end:O,viewLen:g},T.current=!0;return}c.current&&c.current.abort();const U=new AbortController;c.current=U,T.current||i(!0),u(null);let N;if(w==="reads")g<=Li?N=Ot.reads(y.id,x,f,p):N=Ot.coverage(y.id,x,E,O,P);else if(w==="coverage")N=Ot.coverage(y.id,x,E,O,P);else if(w==="variants")N=Ot.variants(y.id,x,E,O);else if(w==="annotations"||w==="genome_annotations")N=Ot.features(y.id,x,E,O);else{i(!1);return}N.then(Y=>{if(U.signal.aborted)return;const I={...Y.data,mode:w==="reads"&&g<=Li?"reads":"coverage"};_n.set(H,I),h.current={trackId:y.id,chrom:x,start:E,end:O,viewLen:g},T.current=!0,o(I),Sc(y.id,I),u(null)}).catch(Y=>{var I,L;if(Y.name!=="CanceledError"&&!U.signal.aborted){const $=(L=(I=Y.response)==null?void 0:I.data)==null?void 0:L.detail,D=typeof $=="string"?$:Y.message||String(Y);u(D)}}).finally(()=>{U.signal.aborted||i(!1)})}return{data:r,loading:l,error:a}}const iy=["svg","png","jpg"],sy=140;function ay({onClose:e}){const{region:t}=at(),{tracks:n}=Jt(),{theme:r}=Xe(),o=t==null?void 0:t.chrom,l=n.filter(S=>S.visible&&(!S.targetChromosomes||!o||S.targetChromosomes.includes(o))),[i,a]=C.useState("svg"),[u,c]=C.useState(!0),[h,d]=C.useState(!0),[m,T]=C.useState(new Set(l.map(S=>S.id))),[v,y]=C.useState(1200),[x,f]=C.useState(!1);function p(S){T(j=>{const b=new Set(j);return b.has(S)?b.delete(S):b.add(S),b})}async function g(){if(t){f(!0);try{const S=l.filter(z=>m.has(z.id)),j=h?sy:0,b=v-j,E=u?30:0,O=E+S.reduce((z,P)=>z+P.height,0);if(i==="svg"){const z=uy(t,S,r,b,j,E,O,u,h);my(z,"genomics-export.svg","image/svg+xml")}else{const z=hy(t,S,r,b,j,E,O,v,u,h),P=i==="png"?"image/png":"image/jpeg";z.toBlob(H=>{const R=URL.createObjectURL(H),U=document.createElement("a");U.href=R,U.download=`genomics-export.${i}`,U.click(),URL.revokeObjectURL(R)},P,.95)}}finally{f(!1)}}}const w=vy(r);return s.jsx("div",{style:w.overlay,onClick:S=>{S.target===S.currentTarget&&e()},children:s.jsxs("div",{style:w.panel,children:[s.jsxs("div",{style:w.header,children:[s.jsx("span",{style:w.title,children:"Export Image"}),s.jsx("button",{style:w.closeBtn,onClick:e,children:"✕"})]}),s.jsxs("div",{style:w.body,children:[s.jsxs("div",{style:w.row,children:[s.jsx("span",{style:w.label,children:"Format"}),s.jsx("div",{style:{display:"flex",gap:6},children:iy.map(S=>s.jsx("button",{onClick:()=>a(S),style:{...w.fmtBtn,border:i===S?`2px solid ${r.textPrimary}`:`1px solid ${r.borderAccent}`},children:S.toUpperCase()},S))})]}),s.jsxs("div",{style:w.row,children:[s.jsx("span",{style:w.label,children:"Width (px)"}),s.jsx("input",{type:"number",min:400,max:4e3,step:100,value:v,onChange:S=>y(Math.max(400,parseInt(S.target.value)||1200)),style:w.input})]}),s.jsxs("div",{style:w.row,children:[s.jsxs("label",{style:w.cb,children:[s.jsx("input",{type:"checkbox",checked:u,onChange:S=>c(S.target.checked)})," Ruler"]}),s.jsxs("label",{style:w.cb,children:[s.jsx("input",{type:"checkbox",checked:h,onChange:S=>d(S.target.checked)})," Track labels"]})]}),s.jsxs("div",{style:{...w.row,flexDirection:"column",alignItems:"stretch",gap:4},children:[s.jsx("span",{style:w.label,children:"Include tracks"}),l.map(S=>s.jsxs("label",{style:{...w.cb,gap:6},children:[s.jsx("input",{type:"checkbox",checked:m.has(S.id),onChange:()=>p(S.id)}),s.jsx("span",{style:{width:8,height:8,borderRadius:2,background:S.color,flexShrink:0}}),s.jsx("span",{style:{fontSize:11},children:S.name})]},S.id))]}),i==="svg"&&s.jsx("div",{style:{padding:"4px 0",fontSize:10,color:r.textTertiary},children:"SVG output is fully vectorized — editable in Illustrator, Inkscape, etc."})]}),s.jsxs("div",{style:w.footer,children:[s.jsx("button",{style:w.btn,onClick:g,disabled:x||!t,children:x?"Exporting…":`Export ${i.toUpperCase()}`}),s.jsx("button",{style:{...w.btn,background:r.borderAccent},onClick:e,children:"Cancel"})]})]})})}function uy(e,t,n,r,o,l,i,a,u){const c=r+o;let h=`<?xml version="1.0" encoding="UTF-8"?>
46
46
  `;h+=`<svg xmlns="http://www.w3.org/2000/svg" width="${c}" height="${i}" viewBox="0 0 ${c} ${i}" font-family="Arial, Helvetica, sans-serif">
47
47
  `,h+=`<defs>
48
48
  `,h+=` <clipPath id="trackClip"><rect width="${r}" height="${i}"/></clipPath>
@@ -94,4 +94,4 @@ ${A.join(`
94
94
  `)}
95
95
 
96
96
  Tip: If files were moved, re-add them using the 📂 Path button.`):(y("Session restored"),setTimeout(()=>{y(null),e()},1200))}catch(Y){f(Y.message)}finally{g(!1)}}const z=Cc(),P=ky(c);return s.jsx("div",{style:P.overlay,onClick:H=>{H.target===H.currentTarget&&e()},children:s.jsxs("div",{style:P.panel,children:[s.jsxs("div",{style:P.header,children:[s.jsx("span",{style:P.title,children:"Session"}),s.jsx("button",{style:P.closeBtn,onClick:e,children:"✕"})]}),s.jsxs("div",{style:P.body,children:[s.jsxs("div",{style:P.section,children:[s.jsx("div",{style:P.sectionTitle,children:"Save"}),s.jsx("div",{style:{display:"flex",gap:8,flexWrap:"wrap"},children:s.jsx("button",{style:P.btn,onClick:S,disabled:!r||p,children:"Save to file"})}),s.jsx("div",{style:{fontSize:10,color:c.textTertiary,marginTop:4},children:"Session is also auto-saved to browser storage."})]}),s.jsxs("div",{style:P.section,children:[s.jsx("div",{style:P.sectionTitle,children:"Restore"}),s.jsxs("div",{style:{display:"flex",gap:8,flexWrap:"wrap"},children:[s.jsx("button",{style:P.btn,onClick:j,disabled:p,children:"Load from file"}),z&&s.jsx("button",{style:P.btn,onClick:E,disabled:p,children:"Restore last session"})]}),s.jsx("input",{ref:w,type:"file",accept:".json",style:{display:"none"},onChange:b}),z&&s.jsxs("div",{style:{fontSize:10,color:c.textTertiary,marginTop:4},children:["Last auto-save: ",new Date(z.savedAt).toLocaleString(),z.genome&&` — ${z.genome.name}`,z.tracks&&` — ${z.tracks.length} tracks`]})]}),v&&s.jsx("div",{style:{padding:"4px 16px",fontSize:11,color:"#81c784"},children:v}),x&&s.jsx("div",{style:{padding:"4px 16px",fontSize:11,color:"#ef9a9a",whiteSpace:"pre-wrap"},children:x})]}),s.jsx("div",{style:P.footer,children:s.jsx("button",{style:P.btn,onClick:e,children:"Close"})})]})})}function ky(e){return{overlay:{position:"fixed",inset:0,background:e.overlayBg,display:"flex",alignItems:"center",justifyContent:"center",zIndex:1e3},panel:{background:e.panelBg,border:`1px solid ${e.borderAccent}`,borderRadius:8,padding:0,minWidth:380,maxWidth:480,maxHeight:"80vh",display:"flex",flexDirection:"column",boxShadow:"0 8px 32px rgba(0,0,0,0.5)"},header:{display:"flex",justifyContent:"space-between",alignItems:"center",padding:"10px 16px",borderBottom:`1px solid ${e.border}`},title:{fontSize:14,fontWeight:700,color:e.textPrimary},closeBtn:{background:"none",border:"none",color:e.textSecondary,cursor:"pointer",fontSize:18,lineHeight:1,padding:"0 4px"},body:{padding:"8px 0",overflowY:"auto",flex:1},section:{padding:"8px 16px"},sectionTitle:{fontSize:11,color:e.textSecondary,textTransform:"uppercase",letterSpacing:1,marginBottom:6},btn:{background:e.btnBg,border:"none",borderRadius:4,color:e.btnText,padding:"5px 14px",cursor:"pointer",fontSize:12,fontWeight:600},footer:{display:"flex",justifyContent:"flex-end",padding:"10px 16px",borderTop:`1px solid ${e.border}`}}}const ye=e=>s.jsx("strong",{children:e}),ue=({children:e})=>s.jsxs("div",{style:{display:"flex",gap:6,marginTop:4},children:[s.jsx("span",{style:{opacity:.5},children:"•"}),s.jsx("span",{children:e})]}),jc=({children:e})=>s.jsx("span",{style:{background:"rgba(255,255,255,0.1)",borderRadius:3,padding:"0 4px",fontSize:11,fontFamily:"monospace"},children:e}),Cn=[{target:"file-loader",title:"Load Files",description:s.jsxs(s.Fragment,{children:["Upload genome and track files via:",s.jsxs(ue,{children:[ye("File picker"),' — click "Choose Files"']}),s.jsxs(ue,{children:[ye("Drag & drop")," — drop files anywhere on the app"]}),s.jsxs(ue,{children:[ye("Local path")," — paste a file path (best for large files)"]}),s.jsx("div",{style:{marginTop:8,opacity:.7},children:"Supported: FASTA, GenBank, BAM, BigWig, WIG, BedGraph, VCF, BED, GTF, GFF"})]}),position:"bottom"},{target:"nav-bar",title:"Navigation",description:s.jsxs(s.Fragment,{children:[s.jsxs(ue,{children:[ye("Chromosome selector")," — switch between chromosomes"]}),s.jsxs(ue,{children:[ye("Coordinate input")," — type ",s.jsx(jc,{children:"chr1:1000-5000"})," and press Go"]}),s.jsxs(ue,{children:[ye("- +")," — zoom out / zoom in"]}),s.jsxs(ue,{children:[ye("◀ ▶")," — pan left / pan right"]}),s.jsxs(ue,{children:[ye("Blue scrubber bar")," — click or drag to jump across the chromosome"]})]}),position:"bottom"},{target:"track-area",title:"Track Interaction",description:s.jsxs(s.Fragment,{children:[s.jsxs(ue,{children:[ye("Left-click drag")," — pan the viewport"]}),s.jsxs(ue,{children:[ye("Scroll wheel")," — zoom in/out at cursor position"]}),s.jsxs(ue,{children:[ye("Right-click drag")," — select a region (hover for stats)"]}),s.jsxs(ue,{children:[ye("Double-click gene")," — zoom to fit that gene with context"]}),s.jsxs(ue,{children:[ye("Hover features")," — view detailed tooltips"]})]}),position:"inside"},{target:"skeleton-track-label",title:"Track Labels",description:s.jsxs(s.Fragment,{children:[s.jsxs(ue,{children:[ye("≡ Drag handle")," — reorder tracks by dragging"]}),s.jsxs(ue,{children:[ye("Color swatch")," — click to pick a color"]}),s.jsxs(ue,{children:[ye("× Button")," — remove the track"]}),s.jsxs(ue,{children:[ye("Bottom edge")," — drag to resize track height"]})]}),position:"right"},{target:"btn-settings",title:"Track Settings",description:s.jsxs(s.Fragment,{children:["Select one or more tracks to adjust:",s.jsx(ue,{children:"Height, visibility, and fill color"}),s.jsx(ue,{children:"Bar width, peak outline trace + smoothness"}),s.jsxs(ue,{children:["Y-axis scale (auto / manual / log","₂",")"]}),s.jsx(ue,{children:"Annotation colors per feature type"}),s.jsx(ue,{children:"Read appearance — strand colors, arrow style & size"}),s.jsx(ue,{children:"Nucleotide display with mismatch highlighting"}),s.jsx("div",{style:{marginTop:6,opacity:.7},children:"The panel is draggable — adjust settings while viewing your data."})]}),position:"bottom",action:"open-settings"},{target:"header-btns",title:"Themes",description:s.jsxs(s.Fragment,{children:[s.jsxs(ue,{children:[ye("5 built-in themes")," — Dark, Light, Colorblind, Soft, High Contrast"]}),s.jsxs(ue,{children:[ye("Custom themes")," — clone any preset and edit every color"]}),s.jsx("div",{style:{marginTop:6,opacity:.7},children:"Theme preferences persist across sessions."})]}),position:"bottom",action:"open-theme"},{target:"btn-export",title:"Export Image",description:s.jsxs(s.Fragment,{children:["Export the current view as ",ye("SVG")," or ",ye("PNG"),".",s.jsx(ue,{children:"Background, bars, outlines, and labels are separate SVG groups"}),s.jsx(ue,{children:"All track settings (colors, outlines, visibility) are respected"}),s.jsx(ue,{children:"Edit exported SVGs in Illustrator, Inkscape, or Figma"})]}),position:"bottom"},{target:"header-btns",title:"Sessions",description:s.jsxs(s.Fragment,{children:[s.jsxs(ue,{children:[ye("Save to file")," — exports genome, tracks, region, zoom, colors, and all settings as JSON"]}),s.jsxs(ue,{children:[ye("Restore")," — reload a saved session or the last auto-save"]}),s.jsxs(ue,{children:[ye("Auto-save")," — your session saves to the browser automatically"]}),s.jsx("div",{style:{marginTop:6,opacity:.7},children:"An exit guard warns you before closing with unsaved work."})]}),position:"bottom"},{target:"file-loader",title:"Tips",description:s.jsxs(s.Fragment,{children:[s.jsxs(ue,{children:[ye("Large BAM files")," — use the ",s.jsxs(jc,{children:["📂"," Path"]})," button to load by file path (no upload needed)"]}),s.jsxs(ue,{children:[ye("Large WIG files")," — convert to BigWig for instant loading"]}),s.jsxs(ue,{children:[ye("BAM + BAI")," — select both together, or load by path (index auto-discovered)"]}),s.jsxs(ue,{children:[ye("Updates")," — the app checks for updates automatically on launch"]})]}),position:"bottom"}],Tn=8,jn=14,Et=340,Cy=230,zr="rgba(0,0,0,0.55)";function Ty({onClose:e,theme:t,onAction:n}){const[r,o]=C.useState(0),[l,i]=C.useState(null),[a,u]=C.useState(Cy),c=C.useRef(null),h=Cn[r],d=r===0,m=r===Cn.length-1;C.useEffect(()=>{var b;const j=(b=Cn[r])==null?void 0:b.action;j&&n&&n(j)},[r,n]);const T=C.useCallback(j=>{var E;((E=Cn[j])==null?void 0:E.action)&&n&&n(null)},[n]),v=C.useCallback(()=>{T(r),r<Cn.length-1?o(j=>j+1):e()},[r,e,T]),y=C.useCallback(()=>{T(r),r>0&&o(j=>j-1)},[r,T]);C.useEffect(()=>{function j(b){b.key==="Escape"?e():b.key==="ArrowRight"||b.key==="Enter"?v():b.key==="ArrowLeft"&&y()}return window.addEventListener("keydown",j),()=>window.removeEventListener("keydown",j)},[e,v,y]),C.useEffect(()=>{function j(){const b=document.querySelector(`[data-tour="${h.target}"]`);if(b){const E=b.getBoundingClientRect();i({top:E.top,left:E.left,width:E.width,height:E.height})}else i(null)}return j(),window.addEventListener("resize",j),window.addEventListener("scroll",j,!0),()=>{window.removeEventListener("resize",j),window.removeEventListener("scroll",j,!0)}},[h.target]),C.useEffect(()=>{c.current&&u(c.current.getBoundingClientRect().height)});const x=l?{top:l.top-Tn,left:l.left-Tn,width:l.width+Tn*2,height:l.height+Tn*2}:null;let f,p,g=null,w=Et/2;if(!l)f=(window.innerHeight-a)/2,p=(window.innerWidth-Et)/2;else{const j=h.position||"bottom",b=l.top+l.height+Tn,E=l.top-Tn,O=l.left+l.width+Tn,z=l.left+l.width/2;j==="inside"?(f=l.top+Math.max(20,(l.height-a)/2),p=l.left+Math.max(16,(l.width-Et)/2)):j==="right"?(f=l.top+l.height/2-a/2,p=O+jn,g="left",w=a/2,p+Et>window.innerWidth-12&&(f=b+jn,p=z-Et/2,g="up",w=Math.max(20,Math.min(Et-20,z-p)))):(b+jn+a<=window.innerHeight?(f=b+jn,g="up"):E-jn-a>=0?(f=E-jn-a,g="down"):(f=b+jn,g="up"),l.width<200?(p=Math.max(12,l.left+l.width-Et),p<12&&(p=12)):p=z-Et/2,w=Math.max(20,Math.min(Et-20,z-p))),p=Math.max(12,Math.min(window.innerWidth-Et-12,p)),f=Math.max(12,Math.min(window.innerHeight-a-12,f))}const S={card:{position:"fixed",top:f,left:p,width:Et,zIndex:10002,background:t.panelBg,border:`1px solid ${t.borderAccent}`,borderRadius:10,padding:"20px 24px 16px",color:t.textPrimary,boxShadow:"0 8px 32px rgba(0,0,0,0.5)"},stepCounter:{fontSize:11,fontWeight:600,color:t.textTertiary,textTransform:"uppercase",letterSpacing:1.2,marginBottom:10},title:{fontSize:16,fontWeight:700,marginBottom:6,color:t.textPrimary},description:{fontSize:13,lineHeight:1.6,color:t.textSecondary,marginBottom:20},dots:{display:"flex",justifyContent:"center",gap:8,marginBottom:14},dot:j=>({width:7,height:7,borderRadius:"50%",background:j?"#42a5f5":t.borderStrong,cursor:"pointer"}),nav:{display:"flex",alignItems:"center",justifyContent:"space-between"},btnPrimary:{background:"#1976d2",border:"none",borderRadius:5,color:"#fff",padding:"6px 18px",cursor:"pointer",fontSize:12,fontWeight:600},btnSecondary:{background:t.btnBg,border:`1px solid ${t.borderStrong}`,borderRadius:5,color:t.btnText,padding:"6px 14px",cursor:"pointer",fontSize:12,fontWeight:600},btnDisabled:{background:t.btnBg,border:`1px solid ${t.border}`,borderRadius:5,color:t.textMuted,padding:"6px 14px",fontSize:12,fontWeight:600,cursor:"default",opacity:.5},skip:{background:"none",border:"none",color:t.textTertiary,fontSize:11,cursor:"pointer",textDecoration:"underline",padding:0},arrowUp:{position:"absolute",top:-7,left:w-7,width:0,height:0,borderLeft:"7px solid transparent",borderRight:"7px solid transparent",borderBottom:`7px solid ${t.panelBg}`},arrowDown:{position:"absolute",bottom:-7,left:w-7,width:0,height:0,borderLeft:"7px solid transparent",borderRight:"7px solid transparent",borderTop:`7px solid ${t.panelBg}`},arrowLeft:{position:"absolute",left:-7,top:w-7,width:0,height:0,borderTop:"7px solid transparent",borderBottom:"7px solid transparent",borderRight:`7px solid ${t.panelBg}`}};return s.jsxs(s.Fragment,{children:[s.jsx("div",{style:{position:"fixed",inset:0,zIndex:1e4},onClick:e}),x?s.jsxs(s.Fragment,{children:[s.jsx("div",{style:{position:"fixed",top:0,left:0,right:0,height:Math.max(0,x.top),background:zr,zIndex:10001,pointerEvents:"none"}}),s.jsx("div",{style:{position:"fixed",top:x.top+x.height,left:0,right:0,bottom:0,background:zr,zIndex:10001,pointerEvents:"none"}}),s.jsx("div",{style:{position:"fixed",top:x.top,left:0,width:Math.max(0,x.left),height:x.height,background:zr,zIndex:10001,pointerEvents:"none"}}),s.jsx("div",{style:{position:"fixed",top:x.top,left:x.left+x.width,right:0,height:x.height,background:zr,zIndex:10001,pointerEvents:"none"}}),s.jsx("div",{style:{position:"fixed",top:x.top,left:x.left,width:x.width,height:x.height,borderRadius:6,border:"2px solid rgba(255,255,255,0.22)",zIndex:10001,pointerEvents:"none",boxSizing:"border-box"}})]}):s.jsx("div",{style:{position:"fixed",inset:0,background:zr,zIndex:10001,pointerEvents:"none"}}),s.jsxs("div",{ref:c,style:S.card,onClick:j=>j.stopPropagation(),children:[g==="up"&&s.jsx("div",{style:S.arrowUp}),g==="down"&&s.jsx("div",{style:S.arrowDown}),g==="left"&&s.jsx("div",{style:S.arrowLeft}),s.jsxs("div",{style:S.stepCounter,children:["Step ",r+1," of ",Cn.length]}),s.jsx("div",{style:S.title,children:h.title}),s.jsx("div",{style:S.description,children:h.description}),s.jsx("div",{style:S.dots,children:Cn.map((j,b)=>s.jsx("div",{style:S.dot(b===r),onClick:()=>o(b)},b))}),s.jsxs("div",{style:S.nav,children:[s.jsx("button",{style:S.skip,onClick:e,children:"Skip Tour"}),s.jsxs("div",{style:{display:"flex",gap:8},children:[s.jsx("button",{style:d?S.btnDisabled:S.btnSecondary,onClick:y,disabled:d,children:"Previous"}),s.jsx("button",{style:S.btnPrimary,onClick:v,children:m?"Finish":"Next"})]})]})]})]})}function jy(){const{theme:e}=Xe(),{genome:t,region:n,navigateTo:r,zoom:o,pan:l}=at(),[i,a]=C.useState(""),u=C.useRef(null),c=C.useRef(!1),h=C.useMemo(()=>{if(!t)return{toShort:{},toLong:{}};const w={},S={};return t.chromosomes.forEach((j,b)=>{const E=`chr${b+1}`;w[j.name]=E,S[E.toLowerCase()]=j.name,S[j.name.toLowerCase()]=j.name}),{toShort:w,toLong:S}},[t]);C.useEffect(()=>{if(n){const w=h.toShort[n.chrom]||n.chrom;a(`${w}:${n.start.toLocaleString()}-${n.end.toLocaleString()}`)}},[n,h]);const d=C.useMemo(()=>{if(!t||!n)return 0;const w=t.chromosomes.find(S=>S.name===n.chrom);return w?w.length:0},[t,n==null?void 0:n.chrom]),m=C.useCallback(w=>{if(!u.current||!n||!d)return;const S=u.current.getBoundingClientRect(),j=Math.max(0,Math.min(1,(w-S.left)/S.width)),b=n.end-n.start,E=j*d;r(n.chrom,E-b/2,E+b/2)},[n,d,r]),T=C.useCallback(w=>{w.preventDefault(),c.current=!0,m(w.clientX);function S(b){c.current&&m(b.clientX)}function j(){c.current=!1,window.removeEventListener("mousemove",S),window.removeEventListener("mouseup",j),document.body.style.cursor="",document.body.style.userSelect=""}document.body.style.cursor="grabbing",document.body.style.userSelect="none",window.addEventListener("mousemove",S),window.addEventListener("mouseup",j)},[m]),v={bar:{background:e.headerBg,borderBottom:`1px solid ${e.border}`,padding:"6px 12px",display:"flex",alignItems:"center",gap:10,flexWrap:"wrap"},select:{background:e.inputBg,border:`1px solid ${e.borderAccent}`,borderRadius:4,color:e.textPrimary,padding:"4px 6px",fontSize:12},coordInput:{background:e.inputBg,border:`1px solid ${e.borderAccent}`,borderRadius:4,color:e.textPrimary,padding:"4px 8px",fontSize:12,width:220,fontFamily:"monospace"},btn:{background:e.btnBg,border:"none",borderRadius:4,color:e.btnText,padding:"4px 10px",cursor:"pointer",fontSize:13},info:{color:e.textSecondary,fontSize:11,marginLeft:8},scrubberWrap:{flex:1,minWidth:120,height:14,position:"relative",background:e.inputBg,borderRadius:7,border:`1px solid ${e.borderAccent}`,cursor:"pointer",overflow:"hidden"}};function y(w){if(!t)return;const S=t.chromosomes.find(j=>j.name===w.target.value);S&&r(S.name,0,Math.min(S.length,5e4))}function x(w){w.preventDefault();const j=i.replace(/,/g,"").trim().match(/^(\S+):(\d+)-(\d+)$/);if(j){const b=h.toLong[j[1].toLowerCase()]||j[1];r(b,parseInt(j[2]),parseInt(j[3]))}}if(!t)return s.jsx("div",{style:{...v.bar,opacity:.4},"data-tour":"nav-bar",children:s.jsx("span",{style:{fontSize:12,color:e.textMuted,fontStyle:"italic"},children:"Load a genome to enable navigation"})});const f=n?n.end-n.start:0;let p=0,g=100;return n&&d>0&&(p=n.start/d*100,g=Math.max(1,f/d*100)),s.jsxs("div",{style:v.bar,"data-tour":"nav-bar",children:[s.jsx("select",{style:v.select,value:(n==null?void 0:n.chrom)||"",onChange:y,children:t.chromosomes.map((w,S)=>s.jsxs("option",{value:w.name,children:["chr",S+1," ","—"," ",w.name," (",(w.length/1e3).toFixed(0)," kbp)"]},w.name))}),s.jsxs("form",{onSubmit:x,style:{display:"flex",gap:4},children:[s.jsx("input",{style:v.coordInput,value:i,onChange:w=>a(w.target.value),placeholder:"chr1:start-end"}),s.jsx("button",{style:v.btn,type:"submit",children:"Go"})]}),s.jsx("button",{style:v.btn,onClick:()=>o(2),title:"Zoom out",children:"-"}),s.jsx("button",{style:v.btn,onClick:()=>o(.5),title:"Zoom in",children:"+"}),s.jsx("button",{style:v.btn,onClick:()=>l(-f*.5),title:"Pan left",children:"◀"}),s.jsx("button",{style:v.btn,onClick:()=>l(f*.5),title:"Pan right",children:"▶"}),n&&d>0&&s.jsx("div",{ref:u,style:v.scrubberWrap,onMouseDown:T,title:"Drag to scroll across the chromosome",children:s.jsx("div",{style:{position:"absolute",left:`${p}%`,width:`${g}%`,top:1,bottom:1,background:"#42a5f5",borderRadius:6,minWidth:8,opacity:.7,transition:c.current?"none":"left 0.1s ease"}})}),n&&s.jsxs("span",{style:v.info,children:[f.toLocaleString()," bp"]})]})}function Ep(e){const{region:t,zoom:n,navigateTo:r,setSelection:o,clearSelection:l}=at(),i=C.useRef(null),a=C.useRef(null),u=C.useRef(t);u.current=t,C.useEffect(()=>{const c=e.current;if(!c)return;function h(y){const x=u.current;if(x){if(y.button===2){y.preventDefault();const f=c.getBoundingClientRect(),p=(y.clientX-f.left)/f.width,g=x.start+p*(x.end-x.start);a.current={startX:y.clientX,startBp:g,region:{...x},containerWidth:f.width};return}y.button===0&&(l(),i.current={x:y.clientX,startRegion:{...x},containerWidth:c.offsetWidth||c.clientWidth||1})}}function d(y){if(a.current){const j=a.current,b=c.getBoundingClientRect(),E=Math.max(0,Math.min(1,(y.clientX-b.left)/b.width)),O=j.region.start+E*(j.region.end-j.region.start),z=Math.min(j.startBp,O),P=Math.max(j.startBp,O);Math.abs(P-z)>=1&&o({chrom:j.region.chrom,start:Math.floor(z),end:Math.ceil(P)});return}if(!i.current)return;const x=y.clientX-i.current.x,{chrom:f,start:p,end:g}=i.current.startRegion,w=(g-p)/i.current.containerWidth,S=-x*w;r(f,p+S,g+S)}function m(y){if(a.current){a.current=null;return}i.current=null}function T(y){y.preventDefault()}function v(y){y.preventDefault();const x=c.getBoundingClientRect(),f=(y.clientX-x.left)/x.width,p=y.deltaY>0?1.4:.7;n(p,f)}return c.addEventListener("mousedown",h),c.addEventListener("contextmenu",T),window.addEventListener("mousemove",d),window.addEventListener("mouseup",m),c.addEventListener("wheel",v,{passive:!1}),()=>{c.removeEventListener("mousedown",h),c.removeEventListener("contextmenu",T),window.removeEventListener("mousemove",d),window.removeEventListener("mouseup",m),c.removeEventListener("wheel",v)}},[n,r,o,l,e])}const En=30;function Ey({width:e}){const t=C.useRef(null),n=C.useRef(null),{region:r,selection:o}=at(),{theme:l}=Xe();return Ep(t),C.useEffect(()=>{const i=n.current;if(!i||!r)return;const a=window.devicePixelRatio||1;i.width=e*a,i.height=En*a;const u=i.getContext("2d");u.scale(a,a);const{start:c,end:h}=r,d=h-c;if(u.clearRect(0,0,e,En),u.fillStyle=l.canvasBg,u.fillRect(0,0,e,En),o&&o.chrom===r.chrom){const p=(o.start-c)/d,g=(o.end-c)/d,w=Math.max(0,p*e),S=Math.min(e,g*e);S-w>=1&&(u.fillStyle="rgba(100, 181, 246, 0.25)",u.fillRect(w,0,S-w,En),u.strokeStyle="rgba(100, 181, 246, 0.6)",u.lineWidth=1,u.beginPath(),u.moveTo(w,0),u.lineTo(w,En),u.moveTo(S,0),u.lineTo(S,En),u.stroke())}const m=Math.min(10,Math.floor(e/80)),T=d/m,v=Math.pow(10,Math.floor(Math.log10(T))),y=[1,2,5,10].map(p=>p*v),x=y.find(p=>p>=T)||y[y.length-1],f=Math.ceil(c/x)*x;u.strokeStyle=l.rulerTick,u.fillStyle=l.rulerLabel,u.font="10px Arial, Helvetica, sans-serif",u.textAlign="center",u.beginPath(),u.moveTo(0,20),u.lineTo(e,20),u.lineWidth=1,u.stroke();for(let p=f;p<=h;p+=x){const g=(p-c)/d*e;u.beginPath(),u.moveTo(g,14),u.lineTo(g,20),u.stroke(),u.fillText(Ry(p),g,11)}},[r,o,e,l]),s.jsx("div",{ref:t,style:{position:"relative"},children:s.jsx("canvas",{ref:n,style:{display:"block",width:"100%",height:En}})})}function Ry(e){return e>=1e6?`${(e/1e6).toFixed(2)}M`:e>=1e3?`${(e/1e3).toFixed(1)}k`:String(e)}function Ai(e,t){if(t<=0||e.length===0)return e;const n=new Array(e.length);for(let r=0;r<e.length;r++){let o=0,l=0;const i=Math.max(0,r-t),a=Math.min(e.length-1,r+t);for(let u=i;u<=a;u++)o+=e[u],l++;n[r]=o/l}return n}function Xn(e,t){return e<=0||t<=0?0:Math.log2(e+1)/Math.log2(t+1)}function Py({track:e,width:t,height:n,onWarning:r}){const o=C.useRef(null),{region:l}=at(),{theme:i}=Xe(),{data:a,loading:u,error:c}=ei(e,l,t);return C.useEffect(()=>{var Y,I;const h=o.current;if(!h)return;const d=window.devicePixelRatio||1;h.width=t*d,h.height=n*d;const m=h.getContext("2d");if(m.scale(d,d),m.clearRect(0,0,t,n),m.fillStyle=i.canvasBg,m.fillRect(0,0,t,n),u&&!((Y=a==null?void 0:a.bins)!=null&&Y.length)){m.fillStyle=i.textTertiary,m.font="11px Arial, Helvetica, sans-serif",m.fillText("Loading…",8,n/2+4),r&&r(null);return}if(c){m.fillStyle="#ef9a9a",m.font="11px Arial, Helvetica, sans-serif",m.fillText(typeof c=="string"?c:JSON.stringify(c),8,n/2+4),r&&r(null);return}if(!((I=a==null?void 0:a.bins)!=null&&I.length)){r&&r(null);return}const T=a.max_value||0,v=a.min_value||0,y=v<0,x=l.start,f=l.end-l.start,p=e.color||"#78909c",g=e.scaleMax!=null?e.scaleMax:null,w=e.scaleMin!=null?e.scaleMin:null,S=e.logScale===!0,j=e.barAutoWidth!==!1,b=e.barWidth||2,E=e.showOutline===!0,O=e.outlineColor||null,z=e.outlineSmooth||0,P=e.showBars!==!1,H=p,R=_y(p,-40),U=t/f;function N(L){return j?U>=1?Math.max(1,Math.min(U,L)):Math.max(1,L):Math.min(b,L)}if(y){const $=Math.round(n/2),D=$-12/2,A=n-$-12/2,F=g??(T||1),V=w??(Math.abs(v)||1);if(m.strokeStyle=i.centerLine,m.lineWidth=1,m.beginPath(),m.moveTo(0,$),m.lineTo(t,$),m.stroke(),P)for(const k of a.bins){const Q=(k.end-k.start)/f*t,ee=N(Q),ce=(k.start-x)/f*t,he=k.forward!=null?k.forward:Math.max(0,k.value),pe=k.reverse!=null?k.reverse:Math.min(0,k.value);if(he>0){const ae=S?Xn(he,F):he/F;m.fillStyle=H,m.fillRect(ce,$-ae*D,ee,ae*D)}if(pe<0){const ae=S?Xn(Math.abs(pe),V):Math.abs(pe)/V;m.fillStyle=R,m.fillRect(ce,$,ee,ae*A)}}if(E&&a.bins.length>0){const k=O||i.textPrimary||"#fff",Q=O||i.textPrimary||"#fff",ee=a.bins.map(ie=>{const ne=ie.forward!=null?ie.forward:Math.max(0,ie.value);return ne>0?S?Xn(ne,F):ne/F:0}),ce=a.bins.map(ie=>{const ne=ie.reverse!=null?ie.reverse:Math.min(0,ie.value);return ne<0?S?Xn(Math.abs(ne),V):Math.abs(ne)/V:0}),he=Ai(ee,z),pe=Ai(ce,z),ae=a.bins.map(ie=>((ie.start+ie.end)/2-x)/f*t);zi(m,ae,he.map(ie=>$-ie*D),k,z>0),zi(m,ae,pe.map(ie=>$+ie*A),Q,z>0)}const M=S?" log₂":"";$r(m,`+${F.toFixed(1)}${M}`,2,2,i),$r(m,`−${V.toFixed(1)}${M}`,2,n-12,i),$r(m,"0",2,$-6,i,!0)}else{const L=g??(T||1);if(P){m.fillStyle=H;for(const D of a.bins){const A=(D.end-D.start)/f*t,F=N(A),V=(D.start-x)/f*t,k=(S?Xn(D.value,L):D.value/L)*(n-14);m.fillRect(V,n-k-2,F,k)}}if(E&&a.bins.length>0){const D=a.bins.map(M=>S?Xn(M.value,L):M.value/L),A=Ai(D,z),F=a.bins.map(M=>((M.start+M.end)/2-x)/f*t),V=A.map(M=>n-M*(n-14)-2);zi(m,F,V,O||i.textPrimary||"#fff",z>0)}const $=S?" log₂":"";$r(m,`${L.toFixed(1)}${$}`,2,2,i),$r(m,"0",2,n-12,i,!0)}if(r){const L=[];g!=null&&T>g&&L.push(`Bars clipped: max value ${T.toFixed(1)} exceeds scale ${g.toFixed(1)}`),y&&w!=null&&Math.abs(v)>w&&L.push(`Negative bars clipped: min value ${Math.abs(v).toFixed(1)} exceeds scale ${w.toFixed(1)}`),r(L.length>0?L.join(`
97
- `):null)}},[a,u,c,t,n,l,e.color,e.scaleMax,e.scaleMin,e.logScale,e.barAutoWidth,e.barWidth,e.showOutline,e.outlineColor,e.outlineSmooth,e.showBars,i]),s.jsx("canvas",{ref:o,style:{display:"block",width:"100%",height:n}})}function zi(e,t,n,r,o){if(!(t.length<2)){if(e.beginPath(),e.moveTo(t[0],n[0]),o){for(let l=0;l<t.length-1;l++){const i=(t[l]+t[l+1])/2,a=(n[l]+n[l+1])/2;e.quadraticCurveTo(t[l],n[l],i,a)}e.lineTo(t[t.length-1],n[n.length-1])}else for(let l=0;l<t.length;l++)e.lineTo(t[l],n[l]);e.strokeStyle=r,e.lineWidth=1.5,e.stroke()}}function $r(e,t,n,r,o,l=!1){e.font="10px Arial, Helvetica, sans-serif",e.textAlign="left",e.textBaseline="top";const i=e.measureText(t),a=2,u=i.width+a*2,c=12;e.fillStyle=o.canvasBg||"#1e1e1e",e.globalAlpha=.75,e.fillRect(n,r,u,c),e.globalAlpha=1,e.fillStyle=l?o.textTertiary||"#666":o.textSecondary||"#aaa",e.fillText(t,n+a,r+1),e.textBaseline="alphabetic"}function _y(e,t){const n=e.match(/^#?([0-9a-f]{2})([0-9a-f]{2})([0-9a-f]{2})$/i);if(!n)return e;const r=o=>Math.max(0,Math.min(255,o+t));return`rgb(${r(parseInt(n[1],16))},${r(parseInt(n[2],16))},${r(parseInt(n[3],16))})`}const Ec=6,$i=8,Ni=14,Oi=2,Ly="#9c27b0",Vo=10,My={A:"#4caf50",T:"#f44336",C:"#2196f3",G:"#ff9800",N:"#9e9e9e"},By="#ffeb3b";function Rc(e,t){return e<=0||t<=0?0:Math.log2(e+1)/Math.log2(t+1)}function Ay({track:e,width:t,height:n,onWarning:r}){const o=C.useRef(null),{region:l}=at(),{theme:i}=Xe(),{data:a,loading:u}=ei(e,l,t),[c,h]=C.useState(null),d=C.useRef(null),[m,T]=C.useState(0),v=C.useRef(null),y=e.showNucleotides!==!1,x=e.useArrows!==!1,f=e.logScale===!0,p=e.fwdColor||"#90a4ae",g=e.revColor||"#f06292",w=e.arrowStyle||"pointed",S=e.arrowSize||4,j=C.useRef(null);C.useEffect(()=>{if(l&&j.current){const O=j.current;(O.chrom!==l.chrom||Math.abs(O.start-l.start)>O.end-O.start)&&T(0)}j.current=l},[l==null?void 0:l.chrom,l==null?void 0:l.start,l==null?void 0:l.end]),C.useEffect(()=>{if(!l||!y){h(null);return}const O=l.end-l.start;if(t/O<Ec||O>2e3){h(null);return}if(c&&c.chrom===l.chrom&&c.start<=l.start&&c.end>=l.end)return;const P=Math.max(0,l.start-500),H=l.end+500,R=`${l.chrom}:${P}-${H}`;d.current!==R&&(d.current=R,yn.sequence(l.chrom,P,H).then(U=>h({chrom:l.chrom,start:P,end:H,sequence:U.data.sequence})).catch(()=>{}))},[l==null?void 0:l.chrom,l==null?void 0:l.start,l==null?void 0:l.end,t,y]);const b=C.useCallback(O=>{var U;if(!((U=a==null?void 0:a.reads)!=null&&U.length)||!O.shiftKey&&Math.abs(O.deltaX)>Math.abs(O.deltaY))return;const z=y&&c?Ni:$i,P=Math.max(0,...a.reads.map(N=>N.row)),H=Math.floor(n/(z+Oi)),R=Math.max(0,P-H+2);R<=0||(O.preventDefault(),O.stopPropagation(),T(N=>Math.max(0,Math.min(R,N+Math.sign(O.deltaY)*3))))},[a,n,y,c]);C.useEffect(()=>{var k;const O=o.current;if(!O)return;const z=window.devicePixelRatio||1;O.width=t*z,O.height=n*z;const P=O.getContext("2d");if(P.scale(z,z),P.clearRect(0,0,t,n),P.fillStyle=i.canvasBg,P.fillRect(0,0,t,n),u&&!a){P.fillStyle=i.textTertiary,P.font="11px Arial, Helvetica, sans-serif",P.fillText("Loading…",8,n/2+4),r&&r(null);return}if(!a){r&&r(null);return}const H=l.start,R=l.end-l.start;if(a.bins){const Q=a.max_value||1,ee=e.scaleMax!=null?e.scaleMax:Q,ce=e.color||"#78909c",he=e.barAutoWidth!==!1,pe=e.barWidth||2,ae=t/R;if(e.showBars!==!1){P.fillStyle=ce;for(const ne of a.bins){const xe=(ne.end-ne.start)/R*t,Me=he?ae>=1?Math.max(1,Math.min(ae,xe)):Math.max(1,xe):Math.min(pe,xe),ve=(ne.start-H)/R*t,et=(f?Rc(ne.value,ee):Math.min(1,ne.value/ee))*(n-14);P.fillRect(ve,n-et-2,Me,et)}}if(e.showOutline&&a.bins.length>0){const ne=e.outlineSmooth||0,xe=a.bins.map(me=>f?Rc(me.value,ee):Math.min(1,me.value/ee)),Me=$y(xe,ne),ve=a.bins.map(me=>((me.start+me.end)/2-H)/R*t),Fe=Me.map(me=>n-me*(n-14)-2),et=e.outlineColor||i.textPrimary||"#fff";if(P.beginPath(),P.moveTo(ve[0],Fe[0]),ne>0){for(let me=0;me<ve.length-1;me++)P.quadraticCurveTo(ve[me],Fe[me],(ve[me]+ve[me+1])/2,(Fe[me]+Fe[me+1])/2);P.lineTo(ve[ve.length-1],Fe[Fe.length-1])}else for(let me=0;me<ve.length;me++)P.lineTo(ve[me],Fe[me]);P.strokeStyle=et,P.lineWidth=1.5,P.stroke()}const ie=f?" log₂":"";Pc(P,`${ee.toFixed(1)}${ie}`,2,2,i),Pc(P,"0",2,n-12,i,!0),P.fillStyle="#ffb74d",P.font="10px Arial, Helvetica, sans-serif",P.textAlign="right",P.fillText("zoom in for reads",t-4,10),r&&r(e.scaleMax!=null&&Q>e.scaleMax?`Bars clipped: max value ${Q.toFixed(1)} exceeds scale ${e.scaleMax.toFixed(1)}`:null);return}if(!((k=a.reads)!=null&&k.length)){P.fillStyle=i.textTertiary,P.font="11px Arial, Helvetica, sans-serif",P.fillText("No reads in region",8,n/2+4),r&&r(null);return}const U=Q=>(Q-H)/R*t,N=t/R,Y=y&&N>=Ec&&c!=null,I=Y?Ni:$i,L=Oi,D=Math.max(0,...a.reads.map(Q=>Q.row))+1,A=Math.floor(n/(I+L)),F=D>A,V=Math.min(m,Math.max(0,D-A+1));let M=0;for(const Q of a.reads){const ee=(Q.row-V)*(I+L)+2;if(ee+I<0||ee>n){M++;continue}const ce=Q.strand==="+"?p:g,he=Q.segments;if(he&&he.length>0){const pe=U(Q.start),ae=U(Q.end);P.strokeStyle=ce,P.lineWidth=1,P.beginPath(),P.moveTo(pe,ee+I/2),P.lineTo(ae,ee+I/2),P.stroke();let ie=0;for(const ne of he)if(ne.type==="M"){const xe=U(ne.start),Me=Math.max(1,U(ne.end)-xe);if(P.fillStyle=ce,P.fillRect(xe,ee,Me,I),Y&&Q.sequence){const ve=ne.end-ne.start;for(let Fe=0;Fe<ve;Fe++){const et=ne.start+Fe,me=U(et),gt=U(et+1)-me,G=(Q.sequence[ie+Fe]||"").toUpperCase();let J="";c&&et>=c.start&&et<c.end&&(J=(c.sequence[et-c.start]||"").toUpperCase());const te=J&&G&&G!==J&&G!=="N";te&&(P.fillStyle=By,P.fillRect(me,ee,gt,I)),gt>=6&&(P.fillStyle=te?"#000":My[G]||"#999",P.font=`bold ${Math.min(11,gt-1)}px monospace`,P.textAlign="center",P.textBaseline="middle",P.fillText(G,me+gt/2,ee+I/2))}ie+=ve}}else if(ne.type==="D"){const xe=U(ne.start),Me=U(ne.end)-xe;Me>=1&&(P.strokeStyle=ce,P.lineWidth=1,P.beginPath(),P.moveTo(xe,ee+I/2),P.lineTo(xe+Me,ee+I/2),P.stroke())}else if(ne.type==="N"){const xe=U(ne.start),Me=U(ne.end)-xe;Me>=2&&(P.setLineDash([2,2]),P.strokeStyle=ce,P.lineWidth=1,P.beginPath(),P.moveTo(xe,ee+I/2),P.lineTo(xe+Me,ee+I/2),P.stroke(),P.setLineDash([]))}else ne.type==="I"?(P.fillStyle=Ly,P.fillRect(U(ne.pos)-1,ee-1,2,I+2),Y&&(ie+=ne.length)):ne.type==="S"&&Y&&(ie+=ne.length)}else{const pe=U(Q.start),ae=Math.max(2,U(Q.end)-pe);P.fillStyle=Q.strand==="+"?p:g,P.fillRect(pe,ee,ae,I)}if(x&&w!=="flat"){const pe=U(Q.start),ae=Math.max(2,U(Q.end)-pe),ie=Math.min(S,ae/2);ie>=2&&zy(P,w,Q.strand,pe,ee,ae,I,ie,ce,i.canvasBg)}if(!Y&&!y){const pe=U(Q.start);Math.max(2,U(Q.end)-pe)>60&&(P.fillStyle=i.canvasBg,P.font="8px Arial, Helvetica, sans-serif",P.textAlign="left",P.fillText(Q.name.slice(0,20),pe+2,ee+I-1))}}if(F){const Q=t-Vo;P.fillStyle=i.inputBg||"#2a2a2a",P.fillRect(Q,0,Vo,n);const ee=A/D,ce=Math.max(20,ee*n),pe=(D>A?V/(D-A):0)*(n-ce);P.fillStyle="#555",P.fillRect(Q+1,pe,Vo-2,ce)}r&&(M>0&&!F?r(`${M} read${M>1?"s":""} hidden — increase track height to show all`):r(F?`${D} rows · Shift+scroll or drag scrollbar to navigate`:null))},[a,u,t,n,l,c,m,e.color,e.scaleMax,e.scaleMin,e.barAutoWidth,e.barWidth,e.showOutline,e.outlineColor,e.outlineSmooth,e.showBars,e.showNucleotides,e.useArrows,e.logScale,e.fwdColor,e.revColor,e.arrowStyle,e.arrowSize,i]);const E=C.useCallback(O=>{var D;if(!((D=a==null?void 0:a.reads)!=null&&D.length))return;const z=o.current;if(!z)return;const P=z.getBoundingClientRect();if((O.clientX-P.left)*(t/P.width)<t-Vo)return;const R=y&&c?Ni:$i,N=Math.max(0,...a.reads.map(A=>A.row))+1,Y=Math.floor(n/(R+Oi)),I=Math.max(0,N-Y+1);if(I<=0)return;O.preventDefault(),v.current={maxScroll:I,startY:O.clientY,startRow:m};function L(A){if(!v.current)return;const F=A.clientY-v.current.startY,V=Math.round(F/n*v.current.maxScroll);T(Math.max(0,Math.min(v.current.maxScroll,v.current.startRow+V)))}function $(){v.current=null,window.removeEventListener("mousemove",L),window.removeEventListener("mouseup",$)}window.addEventListener("mousemove",L),window.addEventListener("mouseup",$)},[a,t,n,m,y,c]);return s.jsx("canvas",{ref:o,style:{display:"block",width:"100%",height:n},onWheel:b,onMouseDown:E})}function zy(e,t,n,r,o,l,i,a,u,c){const h=n==="+";if(t==="pointed")e.fillStyle=c,h?(e.beginPath(),e.moveTo(r+l,o+i/2),e.lineTo(r+l-a,o),e.lineTo(r+l-a,o+i),e.fill()):(e.beginPath(),e.moveTo(r,o+i/2),e.lineTo(r+a,o),e.lineTo(r+a,o+i),e.fill());else if(t==="chevron")e.strokeStyle=c,e.lineWidth=1.5,h?(e.beginPath(),e.moveTo(r+l-a,o),e.lineTo(r+l,o+i/2),e.lineTo(r+l-a,o+i),e.stroke()):(e.beginPath(),e.moveTo(r+a,o),e.lineTo(r,o+i/2),e.lineTo(r+a,o+i),e.stroke());else if(t==="fade")if(h){const d=e.createLinearGradient(r+l-a*2,0,r+l,0);d.addColorStop(0,"rgba(0,0,0,0)"),d.addColorStop(1,c),e.fillStyle=d,e.fillRect(r+l-a*2,o,a*2,i)}else{const d=e.createLinearGradient(r,0,r+a*2,0);d.addColorStop(0,c),d.addColorStop(1,"rgba(0,0,0,0)"),e.fillStyle=d,e.fillRect(r,o,a*2,i)}}function $y(e,t){if(t<=0||e.length===0)return e;const n=new Array(e.length);for(let r=0;r<e.length;r++){let o=0,l=0;const i=Math.max(0,r-t),a=Math.min(e.length-1,r+t);for(let u=i;u<=a;u++)o+=e[u],l++;n[r]=o/l}return n}function Pc(e,t,n,r,o,l=!1){e.font="10px Arial, Helvetica, sans-serif",e.textAlign="left",e.textBaseline="top";const i=2,a=e.measureText(t).width+i*2;e.fillStyle=o.canvasBg||"#1e1e1e",e.globalAlpha=.75,e.fillRect(n,r,a,12),e.globalAlpha=1,e.fillStyle=l?o.textTertiary||"#666":o.textSecondary||"#aaa",e.fillText(t,n+i,r+1),e.textBaseline="alphabetic"}const Ny=16,Oy=22,Fy=4,Rp=8,_c=6,Lc={A:"#4caf50",T:"#f44336",C:"#2196f3",G:"#ff9800",N:"#9e9e9e"};function Iy({track:e,width:t,height:n,onWarning:r}){var O,z,P,H;const o=C.useRef(null),{region:l,navigateTo:i}=at(),{tracks:a}=Jt(),{theme:u}=Xe(),{data:c,loading:h,error:d}=ei(e,l,t),m=e.useArrows!==!1,T=e.showNucleotides!==!1,v=C.useRef([]),[y,x]=C.useState(null),[f,p]=C.useState(null),g=C.useRef(null);C.useEffect(()=>{if(!l||!T){p(null);return}const R=l.end-l.start;if(t/R<_c||R>2e3){p(null);return}if(f&&f.chrom===l.chrom&&f.start<=l.start&&f.end>=l.end)return;const N=Math.max(0,l.start-500),Y=l.end+500,I=`${l.chrom}:${N}-${Y}`;g.current!==I&&(g.current=I,yn.sequence(l.chrom,N,Y).then(L=>p({chrom:l.chrom,start:N,end:Y,sequence:L.data.sequence})).catch(()=>{}))},[l==null?void 0:l.chrom,l==null?void 0:l.start,l==null?void 0:l.end,t,T]),C.useEffect(()=>{var V,M;const R=o.current;if(!R)return;const U=window.devicePixelRatio||1;R.width=t*U,R.height=n*U;const N=R.getContext("2d");if(N.scale(U,U),N.clearRect(0,0,t,n),N.fillStyle=u.canvasBg,N.fillRect(0,0,t,n),v.current=[],h&&!((V=c==null?void 0:c.features)!=null&&V.length)){N.fillStyle=u.textTertiary,N.font="11px Arial, Helvetica, sans-serif",N.fillText("Loading…",8,n/2+4),r&&r(null);return}if(d){N.fillStyle="#ef9a9a",N.font="11px Arial, Helvetica, sans-serif",N.fillText(typeof d=="string"?d:JSON.stringify(d),8,n/2+4),r&&r(null);return}if(!((M=c==null?void 0:c.features)!=null&&M.length)){c&&(N.fillStyle=u.textTertiary,N.font="11px Arial, Helvetica, sans-serif",N.fillText("No features in region",8,n/2+4)),r&&r(null);return}const Y=l.end-l.start,I=t/Y,L=T&&I>=_c&&f!=null,$=L?Oy:Ny,D=[],A=[];let F=0;if(L){const Q=n-14;N.fillStyle=u.canvasBg,N.fillRect(0,Q,t,14),N.strokeStyle=u.border||"#333",N.lineWidth=.5,N.beginPath(),N.moveTo(0,Q),N.lineTo(t,Q),N.stroke();const ee=Math.min(10,I-1);if(ee>=5){N.font=`bold ${ee}px monospace`,N.textAlign="center",N.textBaseline="middle";for(let ce=Math.floor(l.start);ce<Math.ceil(l.end);ce++)if(f&&ce>=f.start&&ce<f.end){const he=(f.sequence[ce-f.start]||"").toUpperCase(),pe=(ce-l.start)/Y*t;N.fillStyle=Lc[he]||"#999",N.fillText(he,pe+I/2,Q+14/2)}}}for(const k of c.features){let Q=D.findIndex(ae=>k.start>=ae);Q===-1&&(Q=D.length),D[Q]=k.end;const ee=(k.start-l.start)/Y*t,ce=Math.max(2,(k.end-k.start)/Y*t),he=Q*($+Fy)+2;if(he+$>n){F++;continue}const pe=Bc(k.feature_type,e,u);if(k.sub_features&&k.sub_features.length>0){N.fillStyle=pe+"66",N.fillRect(ee,he+$/2-1,ce,2);for(const ae of k.sub_features){const ie=(ae.start-l.start)/Y*t,ne=Math.max(1,(ae.end-ae.start)/Y*t),xe=Bc(ae.feature_type,e,u),Me=ae.feature_type==="CDS"?$:$-6,ve=ae.feature_type==="CDS"?he:he+3;m?Mc(N,xe,ie,ve,ne,Me,ae.strand||k.strand):(N.fillStyle=xe,N.fillRect(ie,ve,ne,Me))}}else m?Mc(N,pe,ee,he,ce,$,k.strand):(N.fillStyle=pe,N.fillRect(ee,he,ce,$));if(L){const ae=Math.max(k.start,l.start),ie=Math.min(k.end,l.end);for(let ne=ae;ne<ie;ne++)if(f&&ne>=f.start&&ne<f.end){const xe=(f.sequence[ne-f.start]||"").toUpperCase(),Me=(ne-l.start)/Y*t,ve=I;ve>=6&&(N.fillStyle=Lc[xe]||"#999",N.font=`bold ${Math.min(10,ve-1)}px monospace`,N.textAlign="center",N.textBaseline="middle",N.fillText(xe,Me+ve/2,he+$/2))}}else if(ce>20){N.fillStyle="#fff",N.font="10px Arial, Helvetica, sans-serif",N.textAlign="left",N.textBaseline="alphabetic";const ae=k.name||k.feature_type,ie=Math.floor((ce-(m?Rp:0)-4)/6);ie>0&&N.fillText(ae.slice(0,ie),ee+3,he+$-4)}A.push({feat:k,x:ee,y:he,w:ce,h:$})}v.current=A,r&&r(F>0?`${F} feature${F>1?"s":""} hidden — increase track height to show all`:null)},[c,h,d,t,n,l,f,e.color,e.annotationColors,m,e.showNucleotides,u]);const w=C.useCallback(R=>{const U=o.current;if(!U)return;const N=U.getBoundingClientRect(),Y=(R.clientX-N.left)*(t/N.width),I=(R.clientY-N.top)*(n/N.height);for(const L of v.current)if(Y>=L.x&&Y<=L.x+L.w&&I>=L.y&&I<=L.y+L.h){const $=Math.min(R.clientX+14,window.innerWidth-300),D=Math.min(R.clientY+14,window.innerHeight-260);x({feat:L.feat,x:Math.max(4,$),y:Math.max(4,D)});return}x(null)},[t,n]),S=C.useCallback(()=>x(null),[]),j=C.useCallback(R=>{const U=o.current;if(!U||!l)return;const N=U.getBoundingClientRect(),Y=(R.clientX-N.left)*(t/N.width),I=(R.clientY-N.top)*(n/N.height);for(const L of v.current)if(Y>=L.x&&Y<=L.x+L.w&&I>=L.y&&I<=L.y+L.h){const $=L.feat,A=($.end-$.start)*.15/(1-.3),F=$.start-A,V=$.end+A;i(l.chrom,F,V),x(null);return}},[t,n,l,i]),b=y?Dy(y.feat,a,l==null?void 0:l.chrom):[],E=y?Wn.createPortal(s.jsxs("div",{style:{position:"fixed",left:y.x,top:y.y,background:u.tooltipBg,border:`1px solid ${u.tooltipBorder}`,borderRadius:4,padding:"6px 10px",color:u.textPrimary,fontSize:11,lineHeight:1.5,maxWidth:280,zIndex:1e4,pointerEvents:"none",boxShadow:"0 4px 12px rgba(0,0,0,0.5)",whiteSpace:"pre-wrap",wordBreak:"break-word"},children:[s.jsx("div",{style:{fontWeight:700,fontSize:12,marginBottom:2},children:y.feat.name||y.feat.feature_type}),s.jsx(en,{label:"Type",value:y.feat.feature_type}),s.jsx(en,{label:"Strand",value:y.feat.strand||"."}),s.jsx(en,{label:"Location",value:`${y.feat.start.toLocaleString()}–${y.feat.end.toLocaleString()}`}),s.jsx(en,{label:"Length",value:`${(y.feat.end-y.feat.start).toLocaleString()} bp`}),((O=y.feat.attributes)==null?void 0:O.gene)&&y.feat.attributes.gene!==y.feat.name&&s.jsx(en,{label:"Gene",value:y.feat.attributes.gene}),((z=y.feat.attributes)==null?void 0:z.locus_tag)&&s.jsx(en,{label:"Locus",value:y.feat.attributes.locus_tag}),((P=y.feat.attributes)==null?void 0:P.product)&&s.jsx(en,{label:"Product",value:y.feat.attributes.product}),((H=y.feat.attributes)==null?void 0:H.note)&&s.jsx(en,{label:"Note",value:String(y.feat.attributes.note).slice(0,120)}),b.length>0&&s.jsxs(s.Fragment,{children:[s.jsx("div",{style:{borderTop:`1px solid ${u.tooltipBorder}`,margin:"4px 0",paddingTop:4},children:s.jsx("span",{style:{color:u.textSecondary,fontWeight:600,fontSize:10,textTransform:"uppercase"},children:"Track totals in gene"})}),b.map(R=>s.jsxs("div",{style:{display:"flex",justifyContent:"space-between",gap:8},children:[s.jsx("span",{style:{color:u.textSecondary,overflow:"hidden",textOverflow:"ellipsis",whiteSpace:"nowrap",flex:1},children:R.name}),s.jsx("span",{style:{color:u.textPrimary,fontWeight:600,flexShrink:0},children:R.total.toFixed(1)})]},R.trackId))]})]}),document.body):null;return s.jsxs("div",{style:{position:"relative",width:"100%",height:n},children:[s.jsx("canvas",{ref:o,style:{display:"block",width:"100%",height:n},onMouseMove:w,onMouseLeave:S,onDoubleClick:j}),E]})}function en({label:e,value:t}){return t?s.jsxs("div",{style:{display:"flex",gap:6},children:[s.jsxs("span",{style:{opacity:.6,flexShrink:0},children:[e,":"]}),s.jsx("span",{children:t})]}):null}function Dy(e,t,n){var o;if(!e||!n)return[];const r=[];for(const l of t){if(l.track_type!=="coverage"&&l.track_type!=="reads")continue;const i=ly(l.id,n);if(!((o=i==null?void 0:i.bins)!=null&&o.length))continue;let a=0;for(const u of i.bins){if(u.end<=e.start||u.start>=e.end)continue;const c=u.forward!=null?u.forward:Math.max(0,u.value||0),h=u.reverse!=null?Math.abs(u.reverse):Math.abs(Math.min(0,u.value||0));a+=c+h}a>0&&r.push({trackId:l.id,name:l.name,total:a})}return r}function Mc(e,t,n,r,o,l,i){e.fillStyle=t;const a=Math.min(Rp,o*.4);e.beginPath(),i==="+"?(e.moveTo(n,r),e.lineTo(n+o-a,r),e.lineTo(n+o,r+l/2),e.lineTo(n+o-a,r+l),e.lineTo(n,r+l),e.closePath()):i==="-"?(e.moveTo(n+a,r),e.lineTo(n+o,r),e.lineTo(n+o,r+l),e.lineTo(n+a,r+l),e.lineTo(n,r+l/2),e.closePath()):e.rect(n,r,o,l),e.fill(),e.strokeStyle="rgba(0,0,0,0.25)",e.lineWidth=.5,e.stroke()}function Bc(e,t,n){const r=t.annotationColors;switch(e==null?void 0:e.toLowerCase()){case"cds":return(r==null?void 0:r.cds)||(n==null?void 0:n.geneCds)||"#66bb6a";case"exon":return(r==null?void 0:r.exon)||(n==null?void 0:n.geneExon)||"#42a5f5";case"gene":return(r==null?void 0:r.gene)||(n==null?void 0:n.geneGene)||"#7e57c2";case"mrna":case"transcript":return(r==null?void 0:r.transcript)||(n==null?void 0:n.geneTranscript)||"#ab47bc";case"utr":case"3utr":case"5utr":return(r==null?void 0:r.utr)||(n==null?void 0:n.geneUtr)||"#26c6da";case"rrna":return(r==null?void 0:r.rrna)||(n==null?void 0:n.geneRrna)||"#ffa726";case"trna":return(r==null?void 0:r.trna)||(n==null?void 0:n.geneTrna)||"#ef5350";case"repeat_region":return(r==null?void 0:r.repeat)||(n==null?void 0:n.geneRepeat)||"#8d6e63";default:return(r==null?void 0:r.default)||t.color||(n==null?void 0:n.geneDefault)||"#80cbc4"}}function Uy({track:e,width:t,height:n,onWarning:r}){const o=C.useRef(null),{region:l}=at(),{theme:i}=Xe(),{data:a,loading:u}=ei(e,l,t);return C.useEffect(()=>{var f,p;const c=o.current;if(!c)return;const h=window.devicePixelRatio||1;c.width=t*h,c.height=n*h;const d=c.getContext("2d");if(d.scale(h,h),d.clearRect(0,0,t,n),d.fillStyle=i.canvasBg,d.fillRect(0,0,t,n),u&&!((f=a==null?void 0:a.variants)!=null&&f.length)){d.fillStyle=i.textTertiary,d.font="11px Arial, Helvetica, sans-serif",d.fillText("Loading…",8,n/2+4),r&&r(null);return}if(!((p=a==null?void 0:a.variants)!=null&&p.length)){a&&(d.fillStyle=i.textTertiary,d.font="11px Arial, Helvetica, sans-serif",d.fillText("No variants in region",8,n/2+4)),r&&r(null);return}const m=l.end-l.start,T=e.barAutoWidth!==!1,v=e.barWidth||2,y=T?1:Math.max(.5,v),x=T?5:Math.max(2,v*2);for(const g of a.variants){const w=(g.pos-l.start)/m*t,S=Wy(g.ref,g.alt);d.strokeStyle=S,d.lineWidth=y,d.beginPath(),d.moveTo(w,n-4),d.lineTo(w,14),d.stroke(),d.fillStyle=S,d.beginPath(),d.arc(w,10,x,0,Math.PI*2),d.fill(),m<5e3&&(d.fillStyle=i.textPrimary,d.font="9px Arial, Helvetica, sans-serif",d.textAlign="center",d.fillText(`${g.ref}>${g.alt[0]||"?"}`,w,n-6))}if(r){const g=a.variants.filter(w=>w.pos>=l.start&&w.pos<=l.end).length;r(g>50?`${g} variants overlapping — zoom in for detail`:null)}},[a,u,t,n,l,e.color,e.barAutoWidth,e.barWidth,i]),s.jsx("canvas",{ref:o,style:{display:"block",width:"100%",height:n}})}function Wy(e,t){const n=t[0]||"";return e.length===1&&n.length===1?"#ffb74d":n.length>e.length?"#81c784":n.length<e.length?"#e57373":"#b0bec5"}function Hy({message:e,theme:t}){const[n,r]=C.useState(!1),o=C.useRef(null),l=o.current?o.current.getBoundingClientRect():null;return s.jsxs(s.Fragment,{children:[s.jsx("span",{ref:o,onMouseEnter:()=>r(!0),onMouseLeave:()=>r(!1),style:{display:"inline-flex",alignItems:"center",justifyContent:"center",width:12,height:12,borderRadius:"50%",background:"rgba(229, 57, 53, 0.85)",color:"#fff",fontSize:9,fontWeight:800,lineHeight:1,cursor:"default",flexShrink:0,fontFamily:"Arial, Helvetica, sans-serif"},children:"!"}),n&&l&&Wn.createPortal(s.jsx("div",{style:{position:"fixed",left:Math.min(l.right+6,window.innerWidth-220),top:l.top-4,background:t.tooltipBg||"#333",border:`1px solid ${t.tooltipBorder||"#555"}`,borderRadius:4,padding:"4px 8px",color:t.textPrimary||"#e0e0e0",fontSize:11,lineHeight:1.4,maxWidth:200,zIndex:10001,pointerEvents:"none",boxShadow:"0 3px 10px rgba(0,0,0,0.5)",whiteSpace:"pre-wrap",fontFamily:"Arial, Helvetica, sans-serif"},children:e}),document.body)]})}function Vy({width:e,height:t,trackData:n,trackType:r}){const{region:o,selection:l,clearSelection:i}=at(),{theme:a}=Xe(),[u,c]=C.useState(!1),[h,d]=C.useState({x:0,y:0}),m=C.useRef(null),T=C.useCallback(z=>{d({x:z.clientX,y:z.clientY}),c(!0)},[]),v=C.useCallback(()=>c(!1),[]);if(!l||!o||l.chrom!==o.chrom)return null;const y=o.end-o.start;if(y<=0)return null;const x=(l.start-o.start)/y,f=(l.end-o.start)/y,p=Math.max(0,x*e),w=Math.min(e,f*e)-p;if(w<1)return null;const S=Gy(l,n,r),j=l.end-l.start,b=260,E=Math.min(h.x+14,window.innerWidth-b-10),O=Math.min(h.y+14,window.innerHeight-200);return s.jsxs("div",{ref:m,style:{position:"absolute",top:0,left:0,width:e,height:t,pointerEvents:"none"},children:[s.jsx("div",{style:{position:"absolute",left:p,top:0,width:w,height:"100%",background:"rgba(100, 181, 246, 0.2)",borderLeft:"1px solid rgba(100, 181, 246, 0.6)",borderRight:"1px solid rgba(100, 181, 246, 0.6)",pointerEvents:"auto",cursor:"crosshair"},onMouseMove:T,onMouseLeave:v,onClick:z=>{z.stopPropagation(),i()}}),u&&Wn.createPortal(s.jsxs("div",{style:{position:"fixed",left:E,top:O,background:a.panelBg,border:`1px solid ${a.borderAccent}`,borderRadius:6,padding:"8px 12px",fontSize:11,color:a.textPrimary,lineHeight:1.6,pointerEvents:"none",zIndex:1e4,boxShadow:"0 4px 16px rgba(0,0,0,0.4)",minWidth:180,maxWidth:b},children:[s.jsx("div",{style:{fontWeight:700,marginBottom:4,fontSize:12},children:"Selected Region"}),s.jsxs("div",{children:[s.jsx("span",{style:{color:a.textSecondary},children:"Region:"})," ",l.chrom,":",l.start.toLocaleString(),"-",l.end.toLocaleString()]}),s.jsxs("div",{children:[s.jsx("span",{style:{color:a.textSecondary},children:"Length:"})," ",j.toLocaleString()," bp"]}),S.map((z,P)=>s.jsxs("div",{children:[s.jsxs("span",{style:{color:a.textSecondary},children:[z.label,":"]})," ",z.value]},P)),s.jsx("div",{style:{fontSize:9,color:a.textTertiary,marginTop:4},children:"Click to dismiss"})]}),document.body)]})}function Gy(e,t,n){const r=[];if(!t)return r;if(n==="reads"&&t.reads){const o=t.reads.filter(i=>i.end>e.start&&i.start<e.end);r.push({label:"Reads in region",value:o.length.toLocaleString()});let l=0;for(const i of o)if(i.cigar){const a=i.cigar.match(/(\d+)I/g);if(a)for(const u of a)l+=parseInt(u)}if(l>0&&r.push({label:"Insertion bases",value:l.toLocaleString()}),o.length>0){const i=o.reduce((a,u)=>a+(u.mapq||0),0)/o.length;r.push({label:"Avg MAPQ",value:i.toFixed(1)})}}if((n==="coverage"||n==="reads")&&t.bins){const o=t.bins.filter(l=>l.end>e.start&&l.start<e.end);if(o.length>0){const l=o.map(c=>c.value),i=l.reduce((c,h)=>c+h,0)/l.length,a=Math.max(...l),u=Math.min(...l);r.push({label:"Avg coverage",value:i.toFixed(1)}),r.push({label:"Max coverage",value:a.toFixed(1)}),u!==a&&r.push({label:"Min coverage",value:u.toFixed(1)})}}if(n==="variants"&&t.variants){const o=t.variants.filter(l=>l.pos>=e.start&&l.pos<e.end);r.push({label:"Variants in region",value:o.length.toLocaleString()})}if((n==="annotations"||n==="genome_annotations")&&t.features){const o=t.features.filter(l=>l.end>e.start&&l.start<e.end);r.push({label:"Features in region",value:o.length.toLocaleString()})}return r}class Yy extends C.Component{constructor(t){super(t),this.state={hasError:!1,error:null}}static getDerivedStateFromError(t){return{hasError:!0,error:t}}render(){var t;return this.state.hasError?s.jsxs("div",{style:{padding:8,color:"#ef9a9a",fontSize:11},children:["Track error: ",((t=this.state.error)==null?void 0:t.message)||"Unknown error"]}):this.props.children}}function Qy({track:e,containerWidth:t,labelWidth:n=140,onLabelResizeStart:r,isDragging:o,isDropTarget:l,onDragStart:i,onDragOver:a,onDrop:u,onDragEnd:c}){const{theme:h}=Xe(),{updateTrack:d,removeTrack:m}=Jt(),T=C.useRef(null),v=C.useRef(null),[y,x]=C.useState(!1),[f,p]=C.useState(!1),[g,w]=C.useState(null),S=C.useRef(null),j=C.useRef(null),b=e.track_type==="annotations"||e.track_type==="genome_annotations";Ep(T);const E=["#f44336","#ef5350","#e57373","#ff5722","#ff8a65","#ff9800","#ffa726","#ffb74d","#ffc107","#fff176","#4caf50","#66bb6a","#81c784","#aed581","#009688","#26c6da","#80cbc4","#2196f3","#42a5f5","#64b5f6","#7e57c2","#9575cd","#9c27b0","#ab47bc","#ce93d8","#e91e63","#f06292","#795548","#8d6e63","#607d8b","#78909c"],O=t-n,z={row:{display:"flex",borderBottom:`1px solid ${h.border}`,minHeight:40},label:{width:n,minWidth:n,background:h.panelBg,borderRight:`1px solid ${h.border}`,display:"flex",flexDirection:"column",justifyContent:"center",padding:"4px 8px",overflow:"hidden",position:"relative"},trackName:{fontSize:11,color:h.trackName,fontWeight:600,whiteSpace:"nowrap",overflow:"hidden",textOverflow:"ellipsis"},trackType:{fontSize:10,color:h.textTertiary,marginTop:2},trackArea:{flex:1,overflow:"hidden",position:"relative"}},P=C.useCallback(R=>{R.preventDefault(),R.stopPropagation();const U=R.clientY,N=e.height;function Y(L){const $=Math.max(30,Math.min(500,N+(L.clientY-U)));d(e.id,{height:$})}function I(){window.removeEventListener("mousemove",Y),window.removeEventListener("mouseup",I),document.body.style.cursor="",document.body.style.userSelect=""}document.body.style.cursor="ns-resize",document.body.style.userSelect="none",window.addEventListener("mousemove",Y),window.addEventListener("mouseup",I)},[e.id,e.height,d]);function H(){const R={track:e,width:O,height:e.height,onWarning:w};switch(e.track_type){case"reads":return s.jsx(Ay,{...R});case"coverage":return s.jsx(Py,{...R});case"variants":return s.jsx(Uy,{...R});case"annotations":case"genome_annotations":return s.jsx(Iy,{...R});default:return s.jsx("div",{style:{padding:8,color:h.textTertiary,fontSize:11},children:"Unknown track type"})}}return s.jsxs("div",{style:{...z.row,height:e.height,position:"relative",opacity:o?.4:1,borderTop:l?"2px solid #888":void 0},onDragOver:R=>{R.preventDefault(),R.dataTransfer.dropEffect="move",a==null||a()},onDrop:R=>{R.preventDefault(),u==null||u()},onDragEnd:c,children:[s.jsxs("div",{style:z.label,children:[s.jsxs("div",{style:{display:"flex",alignItems:"center",gap:4},children:[s.jsx("div",{draggable:!0,onDragStart:R=>{R.dataTransfer.effectAllowed="move",R.dataTransfer.setData("text/plain",e.id),i==null||i()},style:{cursor:"grab",color:h.textMuted,fontSize:14,lineHeight:1,userSelect:"none",flexShrink:0,padding:"0 2px"},title:"Drag to reorder tracks",children:"≡"}),s.jsx("div",{ref:S,children:b?s.jsxs(s.Fragment,{children:[s.jsx("span",{style:{display:"inline-block",width:10,height:10,borderRadius:2,background:"#888",cursor:"pointer",verticalAlign:"middle",border:"1px solid rgba(255,255,255,0.2)",backgroundImage:"linear-gradient(135deg, #ef5350 25%, #66bb6a 25%, #66bb6a 50%, #42a5f5 50%, #42a5f5 75%, #ffa726 75%)"},title:"Click to customize annotation colors",onMouseDown:R=>{R.stopPropagation(),p(U=>!U)}}),f&&Wn.createPortal(s.jsx(Jy,{track:e,theme:h,anchorRef:S,onClose:()=>p(!1),onChange:(R,U)=>{const N={...e.annotationColors||{},[R]:U};d(e.id,{annotationColors:N})},onReset:()=>d(e.id,{annotationColors:null})}),document.body)]}):s.jsxs(s.Fragment,{children:[s.jsx("span",{style:{display:"inline-block",width:10,height:10,borderRadius:2,background:e.color,cursor:"pointer",verticalAlign:"middle",border:"1px solid rgba(255,255,255,0.2)"},title:"Click to pick color, double-click for full palette",onMouseDown:R=>{R.stopPropagation(),x(!0)},onDoubleClick:R=>{var U;R.stopPropagation(),x(!1),(U=j.current)==null||U.click()}}),s.jsx("input",{ref:j,type:"color",value:e.color||"#78909c",onChange:R=>d(e.id,{color:R.target.value}),style:{position:"absolute",left:-9999,top:-9999,opacity:0,width:0,height:0}}),y&&Wn.createPortal(s.jsx("div",{style:{position:"fixed",left:S.current?S.current.getBoundingClientRect().left:0,top:S.current?S.current.getBoundingClientRect().bottom+4:0,zIndex:10001,background:h.panelBg,border:`1px solid ${h.borderAccent}`,borderRadius:4,padding:6,boxShadow:"0 4px 12px rgba(0,0,0,0.5)",display:"grid",gridTemplateColumns:"repeat(5, 18px)",gap:3},onMouseLeave:()=>x(!1),children:E.map(R=>s.jsx("span",{style:{width:18,height:18,borderRadius:3,background:R,cursor:"pointer",border:R===e.color?`2px solid ${h.textPrimary}`:"1px solid rgba(255,255,255,0.15)",boxSizing:"border-box"},onMouseUp:()=>{d(e.id,{color:R}),x(!1)}},R))}),document.body)]})}),s.jsx("div",{style:{...z.trackName,flex:1},title:e.name,children:e.name}),s.jsx("span",{title:"Remove track",onClick:R=>{R.stopPropagation(),m(e.id)},style:{color:"#e53935",fontSize:13,fontWeight:700,cursor:"pointer",lineHeight:1,flexShrink:0,padding:"0 2px",opacity:.7,transition:"opacity 0.15s"},onMouseEnter:R=>R.currentTarget.style.opacity="1",onMouseLeave:R=>R.currentTarget.style.opacity="0.7",children:"×"})]}),s.jsxs("div",{style:{display:"flex",alignItems:"center",gap:4},children:[s.jsxs("div",{style:z.trackType,children:[e.file_format," · ",e.track_type]}),g&&s.jsx(Hy,{message:g,theme:h})]}),r&&s.jsx("div",{onMouseDown:r,style:{position:"absolute",right:-3,top:0,bottom:0,width:6,cursor:"ew-resize",zIndex:10},onMouseEnter:R=>R.currentTarget.style.background="rgba(255,255,255,0.15)",onMouseLeave:R=>R.currentTarget.style.background="transparent"})]}),s.jsxs("div",{style:z.trackArea,ref:T,children:[s.jsx(Yy,{children:H()}),s.jsx(Vy,{width:O,height:e.height,trackData:Cp(e.id),trackType:e.track_type})]}),s.jsx("div",{ref:v,onMouseDown:P,title:"Drag to resize track height",style:{position:"absolute",left:0,right:0,bottom:-2,height:5,cursor:"ns-resize",zIndex:10,background:"transparent"},onMouseEnter:R=>R.currentTarget.style.background="rgba(255,255,255,0.15)",onMouseLeave:R=>R.currentTarget.style.background="transparent"})]})}const Xy=[{key:"cds",label:"CDS"},{key:"exon",label:"Exon"},{key:"gene",label:"Gene"},{key:"transcript",label:"Transcript"},{key:"utr",label:"UTR"},{key:"rrna",label:"rRNA"},{key:"trna",label:"tRNA"},{key:"repeat",label:"Repeat"},{key:"default",label:"Other"}],Ky=["#f44336","#ef5350","#e57373","#ff5722","#ff8a65","#ff9800","#ffa726","#ffb74d","#ffc107","#fff176","#4caf50","#66bb6a","#81c784","#aed581","#009688","#26c6da","#80cbc4","#2196f3","#42a5f5","#64b5f6","#7e57c2","#9575cd","#9c27b0","#ab47bc","#ce93d8","#e91e63","#f06292","#795548","#8d6e63","#607d8b","#78909c"],qy={cds:"geneCds",exon:"geneExon",gene:"geneGene",transcript:"geneTranscript",utr:"geneUtr",rrna:"geneRrna",trna:"geneTrna",repeat:"geneRepeat",default:"geneDefault"};function Jy({track:e,theme:t,anchorRef:n,onClose:r,onChange:o,onReset:l}){var d;const[i,a]=C.useState(null),u=e.annotationColors||{},c=(d=n.current)==null?void 0:d.getBoundingClientRect();function h(m){return u[m]||t[qy[m]]||vp[m]}return s.jsxs("div",{style:{position:"fixed",left:c?Math.min(c.left,window.innerWidth-220):0,top:c?c.bottom+4:0,zIndex:10001,background:t.panelBg,border:`1px solid ${t.borderAccent}`,borderRadius:6,padding:"8px 0",boxShadow:"0 6px 20px rgba(0,0,0,0.5)",width:210,maxHeight:340,overflowY:"auto"},onMouseLeave:r,children:[s.jsx("div",{style:{fontSize:10,fontWeight:700,color:t.textSecondary,textTransform:"uppercase",letterSpacing:1,padding:"0 10px 6px",borderBottom:`1px solid ${t.border}`,marginBottom:4},children:"Annotation Colors"}),Xy.map(({key:m,label:T})=>{const v=h(m);return s.jsxs("div",{children:[s.jsxs("div",{style:{display:"flex",alignItems:"center",gap:8,padding:"4px 10px",cursor:"pointer",fontSize:11,color:t.textPrimary},onMouseEnter:y=>y.currentTarget.style.background=t.selectedRow,onMouseLeave:y=>y.currentTarget.style.background="transparent",onClick:()=>a(i===m?null:m),children:[s.jsx("span",{style:{display:"inline-block",width:14,height:14,borderRadius:3,background:v,border:"1px solid rgba(255,255,255,0.15)",flexShrink:0}}),s.jsx("span",{style:{flex:1},children:T}),s.jsx("span",{style:{fontSize:9,color:t.textTertiary},children:i===m?"▲":"▼"})]}),i===m&&s.jsx("div",{style:{padding:"4px 10px 6px 32px",display:"grid",gridTemplateColumns:"repeat(5, 18px)",gap:3},children:Ky.map(y=>s.jsx("span",{style:{width:18,height:18,borderRadius:3,background:y,cursor:"pointer",border:y===v?`2px solid ${t.textPrimary}`:"1px solid rgba(255,255,255,0.15)",boxSizing:"border-box"},onClick:()=>{o(m,y),a(null)}},y))})]},m)}),s.jsx("div",{style:{borderTop:`1px solid ${t.border}`,marginTop:4,paddingTop:4},children:s.jsx("div",{style:{padding:"4px 10px",fontSize:10,color:t.textTertiary,cursor:"pointer",textAlign:"center"},onMouseEnter:m=>{m.currentTarget.style.color=t.textPrimary},onMouseLeave:m=>{m.currentTarget.style.color=t.textTertiary},onClick:l,children:"Reset to defaults"})})]})}function Zy({labelWidth:e}){const{genome:t,region:n}=at(),{tracks:r}=Jt(),{theme:o,themeName:l,customTheme:i}=Xe(),[a,u]=C.useState(!1),[c,h]=C.useState(!1),d=!!t;C.useEffect(()=>{if(!d)return;function y(x){x.preventDefault(),x.returnValue=""}return window.addEventListener("beforeunload",y),()=>window.removeEventListener("beforeunload",y)},[d]),C.useEffect(()=>{if(!d)return;function y(x){(x.ctrlKey||x.metaKey)&&x.key==="w"&&(x.preventDefault(),u(!0))}return window.addEventListener("keydown",y),()=>window.removeEventListener("keydown",y)},[d]);const m=C.useCallback(()=>u(!1),[]),T=C.useCallback(()=>{window.onbeforeunload=null,window.close(),window.location.href="about:blank"},[]),v=C.useCallback(()=>{h(!0);try{const y=Fa(t,n,r,l,i,e);Ia(y),jp(y)}catch{}h(!1),window.onbeforeunload=null,window.close(),window.location.href="about:blank"},[t,n,r,l,i,e]);return a?s.jsx("div",{style:{position:"fixed",inset:0,zIndex:1e4,background:"rgba(0,0,0,0.5)",display:"flex",alignItems:"center",justifyContent:"center"},onClick:m,children:s.jsxs("div",{style:{background:o.panelBg,border:`1px solid ${o.borderAccent}`,borderRadius:8,padding:"24px 28px",maxWidth:400,width:"90%",boxShadow:"0 8px 32px rgba(0,0,0,0.6)"},onClick:y=>y.stopPropagation(),children:[s.jsx("div",{style:{fontSize:16,fontWeight:700,color:o.textPrimary,marginBottom:8},children:"Leave BiNgo Genome Viewer?"}),s.jsxs("div",{style:{fontSize:12,color:o.textSecondary,lineHeight:1.7,marginBottom:20},children:["You have an active session with"," ",s.jsxs("strong",{style:{color:o.textPrimary},children:[r.length," track",r.length!==1?"s":""]})," loaded. Unsaved changes will be lost."]}),s.jsxs("div",{style:{display:"flex",flexDirection:"column",gap:8},children:[s.jsx("button",{onClick:m,style:{background:"#1976d2",border:"none",borderRadius:4,color:"#fff",padding:"8px 16px",cursor:"pointer",fontSize:13,fontWeight:600,width:"100%"},children:"Return to App"}),s.jsx("button",{onClick:v,disabled:c,style:{background:o.btnBg,border:`1px solid ${o.borderStrong}`,borderRadius:4,color:o.btnText,padding:"8px 16px",cursor:"pointer",fontSize:13,fontWeight:600,width:"100%"},children:c?"Saving...":"Save Session & Exit"}),s.jsx("button",{onClick:T,style:{background:"transparent",border:`1px solid ${o.border}`,borderRadius:4,color:"#e57373",padding:"8px 16px",cursor:"pointer",fontSize:13,fontWeight:600,width:"100%"},children:"Exit Without Saving"})]})]})}):null}const Ac="2.3.2";let ex=0;function zc({size:e=32}){const[t]=Us.useState(()=>`blogo${++ex}`);return s.jsxs("svg",{width:e,height:e,viewBox:"0 0 100 100",style:{flexShrink:0},xmlns:"http://www.w3.org/2000/svg",children:[s.jsxs("defs",{children:[s.jsxs("radialGradient",{id:`${t}_bg`,cx:"35%",cy:"30%",r:"65%",children:[s.jsx("stop",{offset:"0%",stopColor:"#5eb8ff"}),s.jsx("stop",{offset:"50%",stopColor:"#1976d2"}),s.jsx("stop",{offset:"100%",stopColor:"#0d47a1"})]}),s.jsxs("radialGradient",{id:`${t}_sh`,cx:"30%",cy:"25%",r:"30%",children:[s.jsx("stop",{offset:"0%",stopColor:"#ffffff",stopOpacity:"0.7"}),s.jsx("stop",{offset:"100%",stopColor:"#ffffff",stopOpacity:"0"})]})]}),s.jsx("circle",{cx:"50",cy:"50",r:"48",fill:`url(#${t}_bg)`}),s.jsx("circle",{cx:"50",cy:"48",r:"28",fill:"white"}),s.jsx("circle",{cx:"50",cy:"48",r:"28",fill:"none",stroke:"#1565c0",strokeWidth:"2.5"}),s.jsx("text",{x:"50",y:"39",textAnchor:"middle",fontSize:"13",fontWeight:"800",fontFamily:"Arial, sans-serif",fill:"#0d47a1",children:"BN"}),s.jsx("text",{x:"50",y:"64",textAnchor:"middle",fontSize:"30",fontWeight:"900",fontFamily:"Arial, sans-serif",fill:"#0d47a1",children:"1"}),s.jsx("circle",{cx:"50",cy:"50",r:"48",fill:`url(#${t}_sh)`})]})}function tx({theme:e,labelWidth:t}){return s.jsxs("div",{style:{display:"flex",borderBottom:`1px solid ${e.border}`,height:60,opacity:.45},children:[s.jsx("div",{"data-tour":"skeleton-track-label",style:{width:t,minWidth:t,background:e.panelBg,borderRight:`1px solid ${e.border}`,padding:"6px 8px",display:"flex",flexDirection:"column",justifyContent:"center",gap:4},children:s.jsxs("div",{style:{display:"flex",alignItems:"center",gap:6},children:[s.jsx("span",{style:{fontSize:14,color:e.textTertiary,userSelect:"none",lineHeight:1},children:"≡"}),s.jsx("span",{style:{width:10,height:10,borderRadius:2,background:"#78909c",flexShrink:0}}),s.jsx("span",{style:{fontSize:11,fontWeight:600,color:e.textSecondary,flex:1,overflow:"hidden",textOverflow:"ellipsis",whiteSpace:"nowrap"},children:"Track Name"}),s.jsx("span",{style:{fontSize:13,color:e.textTertiary,lineHeight:1,padding:"0 2px"},children:"×"})]})}),s.jsx("div",{style:{flex:1,background:e.canvasBg}})]})}function nx(){const{theme:e}=Xe(),{genome:t,region:n,setGenome:r,navigateTo:o}=at(),{tracks:l,reorderTracks:i,addTrack:a,uploadTrack:u,commitTrack:c,discardTrack:h,addGenomeAnnotationTrack:d,restoreAnnotationTracks:m}=Jt(),T=C.useRef(null),[v,y]=C.useState(800),[x,f]=C.useState(!1),[p,g]=C.useState(!1),[w,S]=C.useState(!1),[j,b]=C.useState(!1),[E,O]=C.useState(!1),[z,P]=C.useState(!1),[H,R]=C.useState(140),[U,N]=C.useState(null),[Y,I]=C.useState(null),[L,$]=C.useState(!1),[D,A]=C.useState(null),[F,V]=C.useState(null),[M,k]=C.useState(null),Q=C.useRef(0);Sy(H),C.useEffect(()=>{const B=()=>fetch("/api/heartbeat").catch(()=>{});B();const q=setInterval(B,1e4);return()=>clearInterval(q)},[]);const ee=C.useRef(n==null?void 0:n.chrom);C.useEffect(()=>{n!=null&&n.chrom&&n.chrom!==ee.current&&(ee.current=n.chrom,m())},[n==null?void 0:n.chrom,m]);const ce=new Set([".gb",".gbk",".genbank",".fasta",".fa"]),he=new Set([".bam",".bw",".bigwig",".wig",".bedgraph",".bdg",".vcf",".bed",".gtf",".gff",".gff2",".gff3"]),pe=new Set([".bai"]);function ae(B){if(!B)return"";if(B.toLowerCase().endsWith(".vcf.gz"))return".vcf.gz";const q=B.lastIndexOf(".");return q>=0?B.slice(q).toLowerCase():""}const ie=C.useCallback(B=>{var q,X;B.preventDefault(),B.stopPropagation(),(X=(q=B.dataTransfer)==null?void 0:q.types)!=null&&X.includes("Files")&&(Q.current++,Q.current===1&&$(!0))},[]),ne=C.useCallback(B=>{var q,X;B.preventDefault(),B.stopPropagation(),(X=(q=B.dataTransfer)==null?void 0:q.types)!=null&&X.includes("Files")&&(Q.current--,Q.current<=0&&(Q.current=0,$(!1)))},[]),xe=C.useCallback(B=>{B.preventDefault(),B.stopPropagation()},[]);function Me(B){const q=B==null?void 0:B.compatibility;return q&&q.status!=="ok"&&q.status!=="no_genome"}const ve=C.useCallback(async B=>{var Ie,ut,Da,Ua,Wa;if(B.preventDefault(),B.stopPropagation(),Q.current=0,$(!1),!((ut=(Ie=B.dataTransfer)==null?void 0:Ie.types)!=null&&ut.includes("Files")))return;const q=Array.from(B.dataTransfer.files);if(!q.length)return;const X=[],Z=[],le=[],oe=[];for(const Re of q){const Be=ae(Re.name),yt=Re.name.toLowerCase();ce.has(Be)?X.push(Re):he.has(Be)||Be===".vcf.gz"?Z.push(Re):pe.has(Be)||yt.endsWith(".bam.bai")?le.push(Re):oe.push(Re)}const fe=Z.filter(Re=>Re.name.toLowerCase().endsWith(".bam")&&Re.size>50*1024*1024),we=le.filter(Re=>Re.size>10*1024*1024);if(fe.length||we.length){const Re=[...fe,...we].map(yt=>yt.name).join(", "),Be=[...fe,...we].reduce((yt,jo)=>yt+jo.size,0)/(1024*1024);A({error:`${Re} (${Be.toFixed(0)} MB) — large files load faster via the Path button. Click 📂 Path in the toolbar and paste the file path instead of uploading.`}),setTimeout(()=>A(null),1e4);return}if(oe.length&&!X.length&&!Z.length&&!le.length){A({error:`Unsupported file${oe.length>1?"s":""}: ${oe.map(Re=>Re.name).join(", ")}`}),setTimeout(()=>A(null),4e3);return}try{if(X.length>0&&!t){A({msg:`Loading genome: ${X[0].name}...`});const Be=(await yn.load(X[0])).data;if(Be.name&&(Be.name=Ft(Be.name)),r(Be),((Da=Be.chromosomes)==null?void 0:Da.length)>0){const yt=Be.chromosomes[0];o(yt.name,0,Math.min(yt.length,5e4))}Be.is_annotated&&d({id:"genome_annotations",name:`${Be.name} (annotations)`,track_type:"genome_annotations",file_format:"genbank",targetChromosomes:Be.annotated_chromosomes||null})}else X.length>0&&t&&V({files:X});if(Z.length>0){if(!t&&X.length===0){A({error:"Load a genome file first (.fasta, .gb, .genbank)"}),setTimeout(()=>A(null),4e3);return}A({msg:`Loading ${Z.length} track${Z.length>1?"s":""}...`});const Re=[],Be=[],yt=[];for(const jo of Z)try{const kn=await u(jo,void 0);Me(kn)?Be.push(kn):(c(kn),Re.push(kn))}catch(kn){yt.push(`${jo.name}: ${((Wa=(Ua=kn.response)==null?void 0:Ua.data)==null?void 0:Wa.detail)||kn.message}`)}if(yt.length){A({error:yt.join("; ")}),setTimeout(()=>A(null),5e3);return}Be.length>0&&k({tracks:Be})}oe.length?(A({error:`Skipped unsupported: ${oe.map(Re=>Re.name).join(", ")}`}),setTimeout(()=>A(null),4e3)):(A({msg:"Files loaded"}),setTimeout(()=>A(null),2e3))}catch(Re){A({error:Re.message||"Drop failed"}),setTimeout(()=>A(null),5e3)}},[t,r,o,a,d]),Fe=C.useCallback(async()=>{var q,X;if(!F)return;const B=F.files;V(null);try{const Z=[];for(const le of B){A({msg:`Adding chromosomes from ${le.name}...`});try{const fe=(await yn.addChromosomes(le)).data;fe.name&&(fe.name=Ft(fe.name)),r(fe),fe.is_annotated&&d({id:"genome_annotations",name:`${fe.name} (annotations)`,track_type:"genome_annotations",file_format:"genbank",targetChromosomes:fe.annotated_chromosomes||null})}catch(oe){Z.push(`${le.name}: ${((X=(q=oe.response)==null?void 0:q.data)==null?void 0:X.detail)||oe.message}`)}}Z.length?(A({error:Z.join("; ")}),setTimeout(()=>A(null),5e3)):(A({msg:`Added chromosomes from ${B.length} file${B.length>1?"s":""}`}),setTimeout(()=>A(null),3e3))}catch(Z){A({error:Z.message||"Failed to add chromosomes"}),setTimeout(()=>A(null),5e3)}},[F,r,d]),et=C.useCallback(async()=>{var q,X;if(!F)return;const B=F.files;V(null);try{A({msg:`Loading ${B.length} track${B.length>1?"s":""}...`});const Z=[];for(const le of B)try{await a(le,void 0)}catch(oe){Z.push(`${le.name}: ${((X=(q=oe.response)==null?void 0:q.data)==null?void 0:X.detail)||oe.message}`)}Z.length?(A({error:Z.join("; ")}),setTimeout(()=>A(null),5e3)):(A({msg:`Added ${B.length} track${B.length>1?"s":""}`}),setTimeout(()=>A(null),3e3))}catch(Z){A({error:Z.message||"Failed to load tracks"}),setTimeout(()=>A(null),5e3)}},[F,a]),me=C.useCallback(async()=>{if(M){for(const B of M.tracks)await h(B.id);k(null)}},[M,h]),gt=C.useCallback(()=>{if(M){for(const B of M.tracks)c(B);k(null),A({msg:`Added ${M.tracks.length} track${M.tracks.length>1?"s":""}`}),setTimeout(()=>A(null),3e3)}},[M,c]),G=C.useCallback(B=>{B.preventDefault();const q=B.clientX,X=H;function Z(oe){R(Math.max(60,Math.min(400,X+(oe.clientX-q))))}function le(){window.removeEventListener("mousemove",Z),window.removeEventListener("mouseup",le),document.body.style.cursor="",document.body.style.userSelect=""}document.body.style.cursor="ew-resize",document.body.style.userSelect="none",window.addEventListener("mousemove",Z),window.addEventListener("mouseup",le)},[H]);C.useEffect(()=>{if(!T.current)return;const B=new ResizeObserver(q=>{for(const X of q)y(X.contentRect.width)});return B.observe(T.current),()=>B.disconnect()},[]);const J=C.useCallback(B=>B.visible?!B.targetChromosomes||!(n!=null&&n.chrom)?!0:B.targetChromosomes.includes(n.chrom):!1,[n==null?void 0:n.chrom]),te={app:{display:"flex",flexDirection:"column",height:"100vh",background:e.appBg,color:e.textPrimary},header:{background:e.headerBg,borderBottom:`2px solid ${e.borderAccent}`,padding:"8px 16px",display:"flex",alignItems:"center",justifyContent:"space-between"},headerLeft:{display:"flex",alignItems:"center",gap:12},title:{fontSize:18,fontWeight:700,color:e.textPrimary,letterSpacing:1},subtitle:{fontSize:11,color:e.textTertiary},headerBtns:{display:"flex",gap:8},btn:{background:e.btnBg,border:`1px solid ${e.borderStrong}`,borderRadius:4,color:e.btnText,padding:"5px 14px",cursor:"pointer",fontSize:12,fontWeight:600,display:"flex",alignItems:"center",gap:6},trackArea:{flex:1,overflowY:"auto",overflowX:"hidden",display:"flex",flexDirection:"column"},emptyState:{display:"flex",flexDirection:"column",alignItems:"center",justifyContent:"center",flex:1,color:e.textMuted,gap:12},emptyTitle:{fontSize:22,fontWeight:300},emptyHint:{fontSize:13}};return s.jsxs("div",{style:te.app,onDragEnter:ie,onDragLeave:ne,onDragOver:xe,onDrop:ve,children:[s.jsxs("div",{style:te.header,children:[s.jsxs("div",{style:te.headerLeft,children:[s.jsx(zc,{size:34}),s.jsxs("div",{children:[s.jsx("div",{style:te.title,children:"BiNgo Genome Viewer"}),t&&s.jsxs("div",{style:te.subtitle,children:[t.name," · ",t.chromosomes.length," chr"]})]}),s.jsxs("button",{onClick:()=>O(!0),title:"About / References",style:{background:"none",border:`1px solid ${e.border}`,borderRadius:10,padding:"2px 8px",display:"flex",alignItems:"center",gap:4,cursor:"pointer",color:e.textSecondary,fontSize:11,fontWeight:600,lineHeight:1,flexShrink:0},onMouseEnter:B=>{B.currentTarget.style.color=e.textPrimary,B.currentTarget.style.borderColor=e.textSecondary},onMouseLeave:B=>{B.currentTarget.style.color=e.textSecondary,B.currentTarget.style.borderColor=e.border},children:[s.jsxs("svg",{width:"12",height:"12",viewBox:"0 0 16 16",fill:"currentColor",style:{flexShrink:0},children:[s.jsx("path",{d:"M8 15A7 7 0 1 1 8 1a7 7 0 0 1 0 14zm0 1A8 8 0 1 0 8 0a8 8 0 0 0 0 16z"}),s.jsx("circle",{cx:"8",cy:"4.5",r:"1.2"}),s.jsx("rect",{x:"7",y:"6.5",width:"2",height:"5.5",rx:"0.8"})]}),"Info"]}),s.jsxs("button",{onClick:()=>P(!0),title:"Guided Tour",style:{background:"none",border:`1px solid ${e.border}`,borderRadius:10,padding:"2px 8px",display:"flex",alignItems:"center",gap:4,cursor:"pointer",color:e.textSecondary,fontSize:11,fontWeight:600,lineHeight:1,flexShrink:0},onMouseEnter:B=>{B.currentTarget.style.color=e.textPrimary,B.currentTarget.style.borderColor=e.textSecondary},onMouseLeave:B=>{B.currentTarget.style.color=e.textSecondary,B.currentTarget.style.borderColor=e.border},children:[s.jsxs("svg",{width:"12",height:"12",viewBox:"0 0 16 16",fill:"currentColor",style:{flexShrink:0},children:[s.jsx("path",{d:"M8 15A7 7 0 1 1 8 1a7 7 0 0 1 0 14zm0 1A8 8 0 1 0 8 0a8 8 0 0 0 0 16z"}),s.jsx("path",{d:"M5.255 5.786a.237.237 0 0 0 .241.247h.825c.138 0 .248-.113.266-.25.09-.656.54-1.134 1.342-1.134.686 0 1.314.343 1.314 1.168 0 .635-.374.927-.965 1.371-.673.489-1.206 1.06-1.168 1.987l.003.217a.25.25 0 0 0 .25.246h.811a.25.25 0 0 0 .25-.25v-.105c0-.718.273-.927 1.01-1.486.609-.463 1.244-.977 1.244-2.056 0-1.511-1.276-2.241-2.673-2.241-1.267 0-2.655.59-2.75 2.286zM8 13.5a1 1 0 1 0 0-2 1 1 0 0 0 0 2z"})]}),"Help"]})]}),s.jsxs("div",{style:te.headerBtns,"data-tour":"header-btns",children:[s.jsxs("button",{style:te.btn,onClick:()=>b(!0),title:"Save or restore a session",children:[s.jsxs("svg",{width:"12",height:"12",viewBox:"0 0 12 12",fill:"none",stroke:"currentColor",strokeWidth:"1.3",strokeLinecap:"round",strokeLinejoin:"round",style:{flexShrink:0},children:[s.jsx("path",{d:"M2 2h8v8H2z"}),s.jsx("path",{d:"M4 2v4h4V2"}),s.jsx("path",{d:"M5 3h2"})]}),"Save Session"]}),s.jsxs("button",{style:te.btn,onClick:()=>g(!0),title:"Customize color theme",children:[s.jsxs("svg",{width:"12",height:"12",viewBox:"0 0 12 12",style:{flexShrink:0},children:[s.jsx("rect",{x:"0",y:"0",width:"5.5",height:"5.5",rx:"1",fill:"#66bb6a"}),s.jsx("rect",{x:"6.5",y:"0",width:"5.5",height:"5.5",rx:"1",fill:"#42a5f5"}),s.jsx("rect",{x:"0",y:"6.5",width:"5.5",height:"5.5",rx:"1",fill:"#ffa726"}),s.jsx("rect",{x:"6.5",y:"6.5",width:"5.5",height:"5.5",rx:"1",fill:"#ab47bc"})]}),"Theme"]}),s.jsxs("button",{"data-tour":"btn-export",style:{...te.btn,...n&&l.length>0?{}:{opacity:.35,cursor:"default"}},onClick:()=>{n&&l.length>0&&S(!0)},title:"Export current view as SVG or PNG",children:[s.jsx("svg",{width:"12",height:"12",viewBox:"0 0 12 12",fill:"none",stroke:"currentColor",strokeWidth:"1.5",strokeLinecap:"round",strokeLinejoin:"round",style:{flexShrink:0},children:s.jsx("path",{d:"M6 1v7M3 5.5L6 8.5 9 5.5M2 11h8"})}),"Export Image"]}),s.jsxs("button",{"data-tour":"btn-settings",style:{...te.btn,...l.length===0?{opacity:.35,cursor:"default"}:{}},onClick:()=>{l.length>0&&f(!0)},title:"Adjust height, scale, color, and bar width for tracks",children:["⚙"," Track Settings"]})]})]}),s.jsx(D0,{}),s.jsx(jy,{}),s.jsxs("div",{style:te.trackArea,ref:T,"data-tour":"track-area",children:[l.filter(J).length===0&&s.jsx(tx,{theme:e,labelWidth:H}),t?n?s.jsxs(s.Fragment,{children:[s.jsxs("div",{style:{display:"flex"},children:[s.jsx("div",{style:{width:H,minWidth:H,background:e.panelBg,borderRight:`1px solid ${e.border}`,position:"relative"},children:s.jsx("div",{onMouseDown:G,style:{position:"absolute",right:-3,top:0,bottom:0,width:6,cursor:"ew-resize",zIndex:10},onMouseEnter:B=>B.currentTarget.style.background="rgba(255,255,255,0.15)",onMouseLeave:B=>B.currentTarget.style.background="transparent"})}),s.jsx(Ey,{width:v-H})]}),l.filter(J).map(B=>s.jsx(Qy,{track:B,containerWidth:v,labelWidth:H,onLabelResizeStart:G,isDragging:U===B.id,isDropTarget:Y===B.id,onDragStart:()=>N(B.id),onDragOver:()=>I(B.id),onDrop:()=>{U&&U!==B.id&&i(U,B.id),N(null),I(null)},onDragEnd:()=>{N(null),I(null)}},B.id)),l.length===0&&s.jsx("div",{style:{padding:24,color:e.textMuted,fontSize:13},children:"Add tracks above — BAM, VCF, BigWig, BED, GTF, GFF, WIG..."})]}):s.jsx("div",{style:te.emptyState,children:s.jsx("div",{style:te.emptyHint,children:"Select a chromosome to begin"})}):s.jsxs("div",{style:te.emptyState,children:[s.jsx("div",{style:te.emptyTitle,children:"No genome loaded"}),s.jsx("div",{style:te.emptyHint,children:"Load a FASTA or GenBank file above to get started"})]})]}),x&&s.jsx(Q0,{onClose:()=>f(!1)}),p&&s.jsx(Z0,{onClose:()=>g(!1)}),w&&s.jsx(ay,{onClose:()=>S(!1)}),j&&s.jsx(by,{onClose:()=>b(!1),labelWidth:H,setLabelWidth:R}),z&&s.jsx(Ty,{onClose:()=>{P(!1),f(!1),g(!1)},theme:e,onAction:B=>{B==="open-settings"?(f(!0),g(!1)):B==="open-theme"?(g(!0),f(!1)):(f(!1),g(!1))}}),E&&s.jsx("div",{style:{position:"fixed",inset:0,background:"rgba(0,0,0,0.6)",display:"flex",alignItems:"center",justifyContent:"center",zIndex:9999},onClick:()=>O(!1),children:s.jsxs("div",{style:{background:e.panelBg,border:`1px solid ${e.border}`,borderRadius:8,padding:"28px 36px",maxWidth:520,maxHeight:"85vh",overflowY:"auto",color:e.textPrimary,lineHeight:1.7},onClick:B=>B.stopPropagation(),children:[s.jsxs("div",{style:{display:"flex",alignItems:"center",gap:12,marginBottom:16},children:[s.jsx(zc,{size:44}),s.jsx("div",{style:{fontSize:20,fontWeight:700},children:"BiNgo Genome Viewer"})]}),s.jsxs("div",{style:{fontSize:13,color:e.textSecondary,marginBottom:12},children:[s.jsx("strong",{style:{color:e.textPrimary},children:"Version:"})," ",Ac]}),s.jsxs("div",{style:{fontSize:13,color:e.textSecondary,marginBottom:12},children:[s.jsx("strong",{style:{color:e.textPrimary},children:"Publisher:"})," Billy M Ngo"]}),s.jsxs("div",{style:{fontSize:13,color:e.textSecondary,marginBottom:20},children:[s.jsx("strong",{style:{color:e.textPrimary},children:"Published:"})," April 2026"]}),s.jsxs("div",{style:{fontSize:12,color:e.textSecondary,background:e.canvasBg,border:`1px solid ${e.border}`,borderRadius:4,padding:"10px 14px",fontFamily:"monospace",lineHeight:1.6,marginBottom:20,userSelect:"all"},children:["Ngo, B.M. (2026). BiNgo Genome Viewer (v",Ac,") [Software]."]}),s.jsxs("details",{style:{marginBottom:20},children:[s.jsx("summary",{style:{cursor:"pointer",fontSize:13,fontWeight:600,color:e.textPrimary,marginBottom:8},children:"References & Acknowledgments"}),s.jsxs("div",{style:{fontSize:11,color:e.textSecondary,lineHeight:1.8,paddingTop:8},children:[s.jsx("div",{style:{fontWeight:600,color:e.textPrimary,marginBottom:4},children:"Software Dependencies"}),s.jsxs("div",{children:[s.jsx("strong",{children:"FastAPI"})," ","—"," Ram","í","rez, S. (2018). A modern web framework for building APIs with Python."]}),s.jsxs("div",{children:[s.jsx("strong",{children:"Uvicorn"})," ","—"," Encode OSS. ASGI server implementation for Python."]}),s.jsxs("div",{children:[s.jsx("strong",{children:"BioPython"})," ","—"," Cock, P.J.A. et al. (2009). ",s.jsx("em",{children:"Bioinformatics"}),", 25(11), 1422","–","1423."]}),s.jsxs("div",{children:[s.jsx("strong",{children:"pyfaidx"})," ","—"," Shirley, M.D. et al. (2015). ",s.jsx("em",{children:"PeerJ PrePrints"}),", 3:e1196."]}),s.jsxs("div",{children:[s.jsx("strong",{children:"bamnostic"})," ","—"," Sherman, M.A. & Mills, R.E. (2019). Pure Python BAM parser."]}),s.jsxs("div",{children:[s.jsx("strong",{children:"React"})," ","—"," Meta Platforms, Inc. JavaScript UI library."]}),s.jsxs("div",{children:[s.jsx("strong",{children:"Vite"})," ","—"," You, E. (2020). Next generation frontend tooling."]}),s.jsx("div",{style:{fontWeight:600,color:e.textPrimary,marginTop:12,marginBottom:4},children:"File Format Specifications"}),s.jsxs("div",{children:[s.jsx("strong",{children:"SAM/BAM"})," ","—"," Li, H. et al. (2009). ",s.jsx("em",{children:"Bioinformatics"}),", 25(16), 2078","–","2079."]}),s.jsxs("div",{children:[s.jsx("strong",{children:"VCF"})," ","—"," Danecek, P. et al. (2011). ",s.jsx("em",{children:"Bioinformatics"}),", 27(15), 2156","–","2158."]}),s.jsxs("div",{children:[s.jsx("strong",{children:"BigWig/WIG"})," ","—"," Kent, W.J. et al. (2010). ",s.jsx("em",{children:"Bioinformatics"}),", 26(17), 2204","–","2207."]}),s.jsxs("div",{children:[s.jsx("strong",{children:"BED"})," ","—"," UCSC Genome Browser, UC Santa Cruz."]}),s.jsxs("div",{children:[s.jsx("strong",{children:"GFF3"})," ","—"," Sequence Ontology Project."]}),s.jsxs("div",{children:[s.jsx("strong",{children:"GTF"})," ","—"," Ensembl genome database project."]}),s.jsxs("div",{children:[s.jsx("strong",{children:"GenBank"})," ","—"," Benson, D.A. et al. (2013). ",s.jsx("em",{children:"Nucleic Acids Res."}),", 41(D1), D36","–","D42."]}),s.jsx("div",{style:{fontWeight:600,color:e.textPrimary,marginTop:12,marginBottom:4},children:"Inspiration"}),s.jsxs("div",{children:[s.jsx("strong",{children:"IGV"})," ","—"," Robinson, J.T. et al. (2011). ",s.jsx("em",{children:"Nature Biotechnology"}),", 29(1), 24","–","26."]}),s.jsx("div",{style:{fontWeight:600,color:e.textPrimary,marginTop:12,marginBottom:4},children:"Acknowledgments"}),s.jsx("div",{children:"Early version testing and feedback:"}),s.jsx("div",{children:"Amanda Antoch, Isaac Poarch, Otto Chipashvili, Jake Colautti"})]})]}),s.jsx("div",{style:{textAlign:"right"},children:s.jsx("button",{onClick:()=>O(!1),style:{background:e.btnBg,border:`1px solid ${e.borderStrong}`,borderRadius:4,color:e.btnText,padding:"5px 18px",cursor:"pointer",fontSize:12,fontWeight:600},children:"Close"})})]})}),F&&(()=>{const B=F.files.length>1,q=F.files.map(X=>X.name).join(", ");return s.jsx("div",{style:{position:"fixed",inset:0,background:"rgba(0,0,0,0.45)",display:"flex",alignItems:"center",justifyContent:"center",zIndex:9999},children:s.jsxs("div",{style:{background:e.panelBg,border:`1px solid ${e.borderAccent}`,borderRadius:8,padding:"20px 24px",maxWidth:440,width:"90%",boxShadow:"0 8px 32px rgba(0,0,0,0.5)"},onClick:X=>X.stopPropagation(),children:[s.jsxs("div",{style:{fontSize:14,fontWeight:700,color:e.textPrimary,marginBottom:8},children:["Genome file",B?"s":""," detected"]}),s.jsxs("div",{style:{fontSize:12,color:e.textSecondary,lineHeight:1.6,marginBottom:16},children:[s.jsx("strong",{style:{color:e.textPrimary},children:q}),B?" appear to be genome files. A genome is already loaded.":" appears to be a genome file. A genome is already loaded.",s.jsx("br",{}),"How would you like to handle ",B?"them":"it","?"]}),s.jsxs("div",{style:{display:"flex",gap:8,justifyContent:"flex-end",flexWrap:"wrap"},children:[s.jsx("button",{onClick:()=>V(null),style:{background:e.btnBg,border:`1px solid ${e.borderStrong}`,borderRadius:4,color:e.btnText,padding:"5px 16px",cursor:"pointer",fontSize:12,fontWeight:600},children:"Skip"}),s.jsxs("button",{onClick:et,style:{background:e.btnBg,border:`1px solid ${e.borderStrong}`,borderRadius:4,color:e.btnText,padding:"5px 16px",cursor:"pointer",fontSize:12,fontWeight:600},children:["Add as Track",B?"s":""]}),s.jsxs("button",{onClick:Fe,style:{background:"#1976d2",border:"none",borderRadius:4,color:"#fff",padding:"5px 16px",cursor:"pointer",fontSize:12,fontWeight:600},children:["Add as Chromosome",B?"s":""]})]})]})})})(),M&&s.jsx("div",{style:{position:"fixed",inset:0,background:"rgba(0,0,0,0.45)",display:"flex",alignItems:"center",justifyContent:"center",zIndex:9999},children:s.jsxs("div",{style:{background:e.panelBg,border:`1px solid ${e.borderAccent}`,borderRadius:8,padding:"20px 24px",maxWidth:480,width:"90%",boxShadow:"0 8px 32px rgba(0,0,0,0.5)"},onClick:B=>B.stopPropagation(),children:[s.jsx("div",{style:{fontSize:14,fontWeight:700,color:e.textPrimary,marginBottom:8},children:"Track compatibility warning"}),s.jsxs("div",{style:{fontSize:12,color:e.textSecondary,lineHeight:1.6,marginBottom:16},children:[M.tracks.map(B=>{var q;return s.jsxs("div",{style:{marginBottom:6},children:[s.jsx("strong",{style:{color:e.textPrimary},children:B.name})," — ",((q=B.compatibility)==null?void 0:q.message)||"Possible mismatch with loaded genome"]},B.id)}),s.jsx("div",{style:{marginTop:8},children:M.tracks.length>1?"These tracks may not match the loaded genome.":"This track may not match the loaded genome."})]}),s.jsxs("div",{style:{display:"flex",gap:8,justifyContent:"flex-end",flexWrap:"wrap"},children:[s.jsx("button",{onClick:me,style:{background:e.btnBg,border:`1px solid ${e.borderStrong}`,borderRadius:4,color:e.btnText,padding:"5px 16px",cursor:"pointer",fontSize:12,fontWeight:600},children:"Skip"}),s.jsx("button",{onClick:gt,style:{background:"#1976d2",border:"none",borderRadius:4,color:"#fff",padding:"5px 16px",cursor:"pointer",fontSize:12,fontWeight:600},children:"Load Anyway"})]})]})}),L&&s.jsx("div",{style:{position:"fixed",inset:0,zIndex:9998,background:"rgba(0,0,0,0.45)",display:"flex",alignItems:"center",justifyContent:"center",pointerEvents:"none"},children:s.jsxs("div",{style:{border:`3px dashed ${e.textSecondary}`,borderRadius:16,padding:"40px 60px",textAlign:"center"},children:[s.jsx("div",{style:{fontSize:28,fontWeight:300,color:e.textPrimary,marginBottom:8},children:"Drop files here"}),s.jsx("div",{style:{fontSize:13,color:e.textSecondary},children:"Genome (.gb, .fasta) or track files (.bam, .bw, .wig, .vcf, .bed, .gff, .gtf)"})]})}),D&&s.jsx("div",{style:{position:"fixed",bottom:20,left:"50%",transform:"translateX(-50%)",zIndex:10001,padding:"8px 20px",borderRadius:6,background:D.error?"#c62828":e.panelBg,border:`1px solid ${D.error?"#e53935":e.borderAccent}`,color:D.error?"#fff":"#81c784",fontSize:12,fontWeight:600,boxShadow:"0 4px 16px rgba(0,0,0,0.5)"},children:D.error||D.msg}),t&&s.jsx(Zy,{labelWidth:H})]})}function rx(){return s.jsx(N0,{children:s.jsx(tg,{children:s.jsx(A0,{children:s.jsx(nx,{})})})})}Fi.createRoot(document.getElementById("root")).render(s.jsx(Us.StrictMode,{children:s.jsx(rx,{})}));
97
+ `):null)}},[a,u,c,t,n,l,e.color,e.scaleMax,e.scaleMin,e.logScale,e.barAutoWidth,e.barWidth,e.showOutline,e.outlineColor,e.outlineSmooth,e.showBars,i]),s.jsx("canvas",{ref:o,style:{display:"block",width:"100%",height:n}})}function zi(e,t,n,r,o){if(!(t.length<2)){if(e.beginPath(),e.moveTo(t[0],n[0]),o){for(let l=0;l<t.length-1;l++){const i=(t[l]+t[l+1])/2,a=(n[l]+n[l+1])/2;e.quadraticCurveTo(t[l],n[l],i,a)}e.lineTo(t[t.length-1],n[n.length-1])}else for(let l=0;l<t.length;l++)e.lineTo(t[l],n[l]);e.strokeStyle=r,e.lineWidth=1.5,e.stroke()}}function $r(e,t,n,r,o,l=!1){e.font="10px Arial, Helvetica, sans-serif",e.textAlign="left",e.textBaseline="top";const i=e.measureText(t),a=2,u=i.width+a*2,c=12;e.fillStyle=o.canvasBg||"#1e1e1e",e.globalAlpha=.75,e.fillRect(n,r,u,c),e.globalAlpha=1,e.fillStyle=l?o.textTertiary||"#666":o.textSecondary||"#aaa",e.fillText(t,n+a,r+1),e.textBaseline="alphabetic"}function _y(e,t){const n=e.match(/^#?([0-9a-f]{2})([0-9a-f]{2})([0-9a-f]{2})$/i);if(!n)return e;const r=o=>Math.max(0,Math.min(255,o+t));return`rgb(${r(parseInt(n[1],16))},${r(parseInt(n[2],16))},${r(parseInt(n[3],16))})`}const Ec=6,$i=8,Ni=14,Oi=2,Ly="#9c27b0",Vo=10,My={A:"#4caf50",T:"#f44336",C:"#2196f3",G:"#ff9800",N:"#9e9e9e"},By="#ffeb3b";function Rc(e,t){return e<=0||t<=0?0:Math.log2(e+1)/Math.log2(t+1)}function Ay({track:e,width:t,height:n,onWarning:r}){const o=C.useRef(null),{region:l}=at(),{theme:i}=Xe(),{data:a,loading:u}=ei(e,l,t),[c,h]=C.useState(null),d=C.useRef(null),[m,T]=C.useState(0),v=C.useRef(null),y=e.showNucleotides!==!1,x=e.useArrows!==!1,f=e.logScale===!0,p=e.fwdColor||"#90a4ae",g=e.revColor||"#f06292",w=e.arrowStyle||"pointed",S=e.arrowSize||4,j=C.useRef(null);C.useEffect(()=>{if(l&&j.current){const O=j.current;(O.chrom!==l.chrom||Math.abs(O.start-l.start)>O.end-O.start)&&T(0)}j.current=l},[l==null?void 0:l.chrom,l==null?void 0:l.start,l==null?void 0:l.end]),C.useEffect(()=>{if(!l||!y){h(null);return}const O=l.end-l.start;if(t/O<Ec||O>2e3){h(null);return}if(c&&c.chrom===l.chrom&&c.start<=l.start&&c.end>=l.end)return;const P=Math.max(0,l.start-500),H=l.end+500,R=`${l.chrom}:${P}-${H}`;d.current!==R&&(d.current=R,yn.sequence(l.chrom,P,H).then(U=>h({chrom:l.chrom,start:P,end:H,sequence:U.data.sequence})).catch(()=>{}))},[l==null?void 0:l.chrom,l==null?void 0:l.start,l==null?void 0:l.end,t,y]);const b=C.useCallback(O=>{var U;if(!((U=a==null?void 0:a.reads)!=null&&U.length)||!O.shiftKey&&Math.abs(O.deltaX)>Math.abs(O.deltaY))return;const z=y&&c?Ni:$i,P=Math.max(0,...a.reads.map(N=>N.row)),H=Math.floor(n/(z+Oi)),R=Math.max(0,P-H+2);R<=0||(O.preventDefault(),O.stopPropagation(),T(N=>Math.max(0,Math.min(R,N+Math.sign(O.deltaY)*3))))},[a,n,y,c]);C.useEffect(()=>{var k;const O=o.current;if(!O)return;const z=window.devicePixelRatio||1;O.width=t*z,O.height=n*z;const P=O.getContext("2d");if(P.scale(z,z),P.clearRect(0,0,t,n),P.fillStyle=i.canvasBg,P.fillRect(0,0,t,n),u&&!a){P.fillStyle=i.textTertiary,P.font="11px Arial, Helvetica, sans-serif",P.fillText("Loading…",8,n/2+4),r&&r(null);return}if(!a){r&&r(null);return}const H=l.start,R=l.end-l.start;if(a.bins){const Q=a.max_value||1,ee=e.scaleMax!=null?e.scaleMax:Q,ce=e.color||"#78909c",he=e.barAutoWidth!==!1,pe=e.barWidth||2,ae=t/R;if(e.showBars!==!1){P.fillStyle=ce;for(const ne of a.bins){const xe=(ne.end-ne.start)/R*t,Me=he?ae>=1?Math.max(1,Math.min(ae,xe)):Math.max(1,xe):Math.min(pe,xe),ve=(ne.start-H)/R*t,et=(f?Rc(ne.value,ee):Math.min(1,ne.value/ee))*(n-14);P.fillRect(ve,n-et-2,Me,et)}}if(e.showOutline&&a.bins.length>0){const ne=e.outlineSmooth||0,xe=a.bins.map(me=>f?Rc(me.value,ee):Math.min(1,me.value/ee)),Me=$y(xe,ne),ve=a.bins.map(me=>((me.start+me.end)/2-H)/R*t),Fe=Me.map(me=>n-me*(n-14)-2),et=e.outlineColor||i.textPrimary||"#fff";if(P.beginPath(),P.moveTo(ve[0],Fe[0]),ne>0){for(let me=0;me<ve.length-1;me++)P.quadraticCurveTo(ve[me],Fe[me],(ve[me]+ve[me+1])/2,(Fe[me]+Fe[me+1])/2);P.lineTo(ve[ve.length-1],Fe[Fe.length-1])}else for(let me=0;me<ve.length;me++)P.lineTo(ve[me],Fe[me]);P.strokeStyle=et,P.lineWidth=1.5,P.stroke()}const ie=f?" log₂":"";Pc(P,`${ee.toFixed(1)}${ie}`,2,2,i),Pc(P,"0",2,n-12,i,!0),P.fillStyle="#ffb74d",P.font="10px Arial, Helvetica, sans-serif",P.textAlign="right",P.fillText("zoom in for reads",t-4,10),r&&r(e.scaleMax!=null&&Q>e.scaleMax?`Bars clipped: max value ${Q.toFixed(1)} exceeds scale ${e.scaleMax.toFixed(1)}`:null);return}if(!((k=a.reads)!=null&&k.length)){P.fillStyle=i.textTertiary,P.font="11px Arial, Helvetica, sans-serif",P.fillText("No reads in region",8,n/2+4),r&&r(null);return}const U=Q=>(Q-H)/R*t,N=t/R,Y=y&&N>=Ec&&c!=null,I=Y?Ni:$i,L=Oi,D=Math.max(0,...a.reads.map(Q=>Q.row))+1,A=Math.floor(n/(I+L)),F=D>A,V=Math.min(m,Math.max(0,D-A+1));let M=0;for(const Q of a.reads){const ee=(Q.row-V)*(I+L)+2;if(ee+I<0||ee>n){M++;continue}const ce=Q.strand==="+"?p:g,he=Q.segments;if(he&&he.length>0){const pe=U(Q.start),ae=U(Q.end);P.strokeStyle=ce,P.lineWidth=1,P.beginPath(),P.moveTo(pe,ee+I/2),P.lineTo(ae,ee+I/2),P.stroke();let ie=0;for(const ne of he)if(ne.type==="M"){const xe=U(ne.start),Me=Math.max(1,U(ne.end)-xe);if(P.fillStyle=ce,P.fillRect(xe,ee,Me,I),Y&&Q.sequence){const ve=ne.end-ne.start;for(let Fe=0;Fe<ve;Fe++){const et=ne.start+Fe,me=U(et),gt=U(et+1)-me,G=(Q.sequence[ie+Fe]||"").toUpperCase();let J="";c&&et>=c.start&&et<c.end&&(J=(c.sequence[et-c.start]||"").toUpperCase());const te=J&&G&&G!==J&&G!=="N";te&&(P.fillStyle=By,P.fillRect(me,ee,gt,I)),gt>=6&&(P.fillStyle=te?"#000":My[G]||"#999",P.font=`bold ${Math.min(11,gt-1)}px monospace`,P.textAlign="center",P.textBaseline="middle",P.fillText(G,me+gt/2,ee+I/2))}ie+=ve}}else if(ne.type==="D"){const xe=U(ne.start),Me=U(ne.end)-xe;Me>=1&&(P.strokeStyle=ce,P.lineWidth=1,P.beginPath(),P.moveTo(xe,ee+I/2),P.lineTo(xe+Me,ee+I/2),P.stroke())}else if(ne.type==="N"){const xe=U(ne.start),Me=U(ne.end)-xe;Me>=2&&(P.setLineDash([2,2]),P.strokeStyle=ce,P.lineWidth=1,P.beginPath(),P.moveTo(xe,ee+I/2),P.lineTo(xe+Me,ee+I/2),P.stroke(),P.setLineDash([]))}else ne.type==="I"?(P.fillStyle=Ly,P.fillRect(U(ne.pos)-1,ee-1,2,I+2),Y&&(ie+=ne.length)):ne.type==="S"&&Y&&(ie+=ne.length)}else{const pe=U(Q.start),ae=Math.max(2,U(Q.end)-pe);P.fillStyle=Q.strand==="+"?p:g,P.fillRect(pe,ee,ae,I)}if(x&&w!=="flat"){const pe=U(Q.start),ae=Math.max(2,U(Q.end)-pe),ie=Math.min(S,ae/2);ie>=2&&zy(P,w,Q.strand,pe,ee,ae,I,ie,ce,i.canvasBg)}if(!Y&&!y){const pe=U(Q.start);Math.max(2,U(Q.end)-pe)>60&&(P.fillStyle=i.canvasBg,P.font="8px Arial, Helvetica, sans-serif",P.textAlign="left",P.fillText(Q.name.slice(0,20),pe+2,ee+I-1))}}if(F){const Q=t-Vo;P.fillStyle=i.inputBg||"#2a2a2a",P.fillRect(Q,0,Vo,n);const ee=A/D,ce=Math.max(20,ee*n),pe=(D>A?V/(D-A):0)*(n-ce);P.fillStyle="#555",P.fillRect(Q+1,pe,Vo-2,ce)}r&&(M>0&&!F?r(`${M} read${M>1?"s":""} hidden — increase track height to show all`):r(F?`${D} rows · Shift+scroll or drag scrollbar to navigate`:null))},[a,u,t,n,l,c,m,e.color,e.scaleMax,e.scaleMin,e.barAutoWidth,e.barWidth,e.showOutline,e.outlineColor,e.outlineSmooth,e.showBars,e.showNucleotides,e.useArrows,e.logScale,e.fwdColor,e.revColor,e.arrowStyle,e.arrowSize,i]);const E=C.useCallback(O=>{var D;if(!((D=a==null?void 0:a.reads)!=null&&D.length))return;const z=o.current;if(!z)return;const P=z.getBoundingClientRect();if((O.clientX-P.left)*(t/P.width)<t-Vo)return;const R=y&&c?Ni:$i,N=Math.max(0,...a.reads.map(A=>A.row))+1,Y=Math.floor(n/(R+Oi)),I=Math.max(0,N-Y+1);if(I<=0)return;O.preventDefault(),v.current={maxScroll:I,startY:O.clientY,startRow:m};function L(A){if(!v.current)return;const F=A.clientY-v.current.startY,V=Math.round(F/n*v.current.maxScroll);T(Math.max(0,Math.min(v.current.maxScroll,v.current.startRow+V)))}function $(){v.current=null,window.removeEventListener("mousemove",L),window.removeEventListener("mouseup",$)}window.addEventListener("mousemove",L),window.addEventListener("mouseup",$)},[a,t,n,m,y,c]);return s.jsx("canvas",{ref:o,style:{display:"block",width:"100%",height:n},onWheel:b,onMouseDown:E})}function zy(e,t,n,r,o,l,i,a,u,c){const h=n==="+";if(t==="pointed")e.fillStyle=c,h?(e.beginPath(),e.moveTo(r+l,o+i/2),e.lineTo(r+l-a,o),e.lineTo(r+l-a,o+i),e.fill()):(e.beginPath(),e.moveTo(r,o+i/2),e.lineTo(r+a,o),e.lineTo(r+a,o+i),e.fill());else if(t==="chevron")e.strokeStyle=c,e.lineWidth=1.5,h?(e.beginPath(),e.moveTo(r+l-a,o),e.lineTo(r+l,o+i/2),e.lineTo(r+l-a,o+i),e.stroke()):(e.beginPath(),e.moveTo(r+a,o),e.lineTo(r,o+i/2),e.lineTo(r+a,o+i),e.stroke());else if(t==="fade")if(h){const d=e.createLinearGradient(r+l-a*2,0,r+l,0);d.addColorStop(0,"rgba(0,0,0,0)"),d.addColorStop(1,c),e.fillStyle=d,e.fillRect(r+l-a*2,o,a*2,i)}else{const d=e.createLinearGradient(r,0,r+a*2,0);d.addColorStop(0,c),d.addColorStop(1,"rgba(0,0,0,0)"),e.fillStyle=d,e.fillRect(r,o,a*2,i)}}function $y(e,t){if(t<=0||e.length===0)return e;const n=new Array(e.length);for(let r=0;r<e.length;r++){let o=0,l=0;const i=Math.max(0,r-t),a=Math.min(e.length-1,r+t);for(let u=i;u<=a;u++)o+=e[u],l++;n[r]=o/l}return n}function Pc(e,t,n,r,o,l=!1){e.font="10px Arial, Helvetica, sans-serif",e.textAlign="left",e.textBaseline="top";const i=2,a=e.measureText(t).width+i*2;e.fillStyle=o.canvasBg||"#1e1e1e",e.globalAlpha=.75,e.fillRect(n,r,a,12),e.globalAlpha=1,e.fillStyle=l?o.textTertiary||"#666":o.textSecondary||"#aaa",e.fillText(t,n+i,r+1),e.textBaseline="alphabetic"}const Ny=16,Oy=22,Fy=4,Rp=8,_c=6,Lc={A:"#4caf50",T:"#f44336",C:"#2196f3",G:"#ff9800",N:"#9e9e9e"};function Iy({track:e,width:t,height:n,onWarning:r}){var O,z,P,H;const o=C.useRef(null),{region:l,navigateTo:i}=at(),{tracks:a}=Jt(),{theme:u}=Xe(),{data:c,loading:h,error:d}=ei(e,l,t),m=e.useArrows!==!1,T=e.showNucleotides!==!1,v=C.useRef([]),[y,x]=C.useState(null),[f,p]=C.useState(null),g=C.useRef(null);C.useEffect(()=>{if(!l||!T){p(null);return}const R=l.end-l.start;if(t/R<_c||R>2e3){p(null);return}if(f&&f.chrom===l.chrom&&f.start<=l.start&&f.end>=l.end)return;const N=Math.max(0,l.start-500),Y=l.end+500,I=`${l.chrom}:${N}-${Y}`;g.current!==I&&(g.current=I,yn.sequence(l.chrom,N,Y).then(L=>p({chrom:l.chrom,start:N,end:Y,sequence:L.data.sequence})).catch(()=>{}))},[l==null?void 0:l.chrom,l==null?void 0:l.start,l==null?void 0:l.end,t,T]),C.useEffect(()=>{var V,M;const R=o.current;if(!R)return;const U=window.devicePixelRatio||1;R.width=t*U,R.height=n*U;const N=R.getContext("2d");if(N.scale(U,U),N.clearRect(0,0,t,n),N.fillStyle=u.canvasBg,N.fillRect(0,0,t,n),v.current=[],h&&!((V=c==null?void 0:c.features)!=null&&V.length)){N.fillStyle=u.textTertiary,N.font="11px Arial, Helvetica, sans-serif",N.fillText("Loading…",8,n/2+4),r&&r(null);return}if(d){N.fillStyle="#ef9a9a",N.font="11px Arial, Helvetica, sans-serif",N.fillText(typeof d=="string"?d:JSON.stringify(d),8,n/2+4),r&&r(null);return}if(!((M=c==null?void 0:c.features)!=null&&M.length)){c&&(N.fillStyle=u.textTertiary,N.font="11px Arial, Helvetica, sans-serif",N.fillText("No features in region",8,n/2+4)),r&&r(null);return}const Y=l.end-l.start,I=t/Y,L=T&&I>=_c&&f!=null,$=L?Oy:Ny,D=[],A=[];let F=0;if(L){const Q=n-14;N.fillStyle=u.canvasBg,N.fillRect(0,Q,t,14),N.strokeStyle=u.border||"#333",N.lineWidth=.5,N.beginPath(),N.moveTo(0,Q),N.lineTo(t,Q),N.stroke();const ee=Math.min(10,I-1);if(ee>=5){N.font=`bold ${ee}px monospace`,N.textAlign="center",N.textBaseline="middle";for(let ce=Math.floor(l.start);ce<Math.ceil(l.end);ce++)if(f&&ce>=f.start&&ce<f.end){const he=(f.sequence[ce-f.start]||"").toUpperCase(),pe=(ce-l.start)/Y*t;N.fillStyle=Lc[he]||"#999",N.fillText(he,pe+I/2,Q+14/2)}}}for(const k of c.features){let Q=D.findIndex(ae=>k.start>=ae);Q===-1&&(Q=D.length),D[Q]=k.end;const ee=(k.start-l.start)/Y*t,ce=Math.max(2,(k.end-k.start)/Y*t),he=Q*($+Fy)+2;if(he+$>n){F++;continue}const pe=Bc(k.feature_type,e,u);if(k.sub_features&&k.sub_features.length>0){N.fillStyle=pe+"66",N.fillRect(ee,he+$/2-1,ce,2);for(const ae of k.sub_features){const ie=(ae.start-l.start)/Y*t,ne=Math.max(1,(ae.end-ae.start)/Y*t),xe=Bc(ae.feature_type,e,u),Me=ae.feature_type==="CDS"?$:$-6,ve=ae.feature_type==="CDS"?he:he+3;m?Mc(N,xe,ie,ve,ne,Me,ae.strand||k.strand):(N.fillStyle=xe,N.fillRect(ie,ve,ne,Me))}}else m?Mc(N,pe,ee,he,ce,$,k.strand):(N.fillStyle=pe,N.fillRect(ee,he,ce,$));if(L){const ae=Math.max(k.start,l.start),ie=Math.min(k.end,l.end);for(let ne=ae;ne<ie;ne++)if(f&&ne>=f.start&&ne<f.end){const xe=(f.sequence[ne-f.start]||"").toUpperCase(),Me=(ne-l.start)/Y*t,ve=I;ve>=6&&(N.fillStyle=Lc[xe]||"#999",N.font=`bold ${Math.min(10,ve-1)}px monospace`,N.textAlign="center",N.textBaseline="middle",N.fillText(xe,Me+ve/2,he+$/2))}}else if(ce>20){N.fillStyle="#fff",N.font="10px Arial, Helvetica, sans-serif",N.textAlign="left",N.textBaseline="alphabetic";const ae=k.name||k.feature_type,ie=Math.floor((ce-(m?Rp:0)-4)/6);ie>0&&N.fillText(ae.slice(0,ie),ee+3,he+$-4)}A.push({feat:k,x:ee,y:he,w:ce,h:$})}v.current=A,r&&r(F>0?`${F} feature${F>1?"s":""} hidden — increase track height to show all`:null)},[c,h,d,t,n,l,f,e.color,e.annotationColors,m,e.showNucleotides,u]);const w=C.useCallback(R=>{const U=o.current;if(!U)return;const N=U.getBoundingClientRect(),Y=(R.clientX-N.left)*(t/N.width),I=(R.clientY-N.top)*(n/N.height);for(const L of v.current)if(Y>=L.x&&Y<=L.x+L.w&&I>=L.y&&I<=L.y+L.h){const $=Math.min(R.clientX+14,window.innerWidth-300),D=Math.min(R.clientY+14,window.innerHeight-260);x({feat:L.feat,x:Math.max(4,$),y:Math.max(4,D)});return}x(null)},[t,n]),S=C.useCallback(()=>x(null),[]),j=C.useCallback(R=>{const U=o.current;if(!U||!l)return;const N=U.getBoundingClientRect(),Y=(R.clientX-N.left)*(t/N.width),I=(R.clientY-N.top)*(n/N.height);for(const L of v.current)if(Y>=L.x&&Y<=L.x+L.w&&I>=L.y&&I<=L.y+L.h){const $=L.feat,A=($.end-$.start)*.15/(1-.3),F=$.start-A,V=$.end+A;i(l.chrom,F,V),x(null);return}},[t,n,l,i]),b=y?Dy(y.feat,a,l==null?void 0:l.chrom):[],E=y?Wn.createPortal(s.jsxs("div",{style:{position:"fixed",left:y.x,top:y.y,background:u.tooltipBg,border:`1px solid ${u.tooltipBorder}`,borderRadius:4,padding:"6px 10px",color:u.textPrimary,fontSize:11,lineHeight:1.5,maxWidth:280,zIndex:1e4,pointerEvents:"none",boxShadow:"0 4px 12px rgba(0,0,0,0.5)",whiteSpace:"pre-wrap",wordBreak:"break-word"},children:[s.jsx("div",{style:{fontWeight:700,fontSize:12,marginBottom:2},children:y.feat.name||y.feat.feature_type}),s.jsx(en,{label:"Type",value:y.feat.feature_type}),s.jsx(en,{label:"Strand",value:y.feat.strand||"."}),s.jsx(en,{label:"Location",value:`${y.feat.start.toLocaleString()}–${y.feat.end.toLocaleString()}`}),s.jsx(en,{label:"Length",value:`${(y.feat.end-y.feat.start).toLocaleString()} bp`}),((O=y.feat.attributes)==null?void 0:O.gene)&&y.feat.attributes.gene!==y.feat.name&&s.jsx(en,{label:"Gene",value:y.feat.attributes.gene}),((z=y.feat.attributes)==null?void 0:z.locus_tag)&&s.jsx(en,{label:"Locus",value:y.feat.attributes.locus_tag}),((P=y.feat.attributes)==null?void 0:P.product)&&s.jsx(en,{label:"Product",value:y.feat.attributes.product}),((H=y.feat.attributes)==null?void 0:H.note)&&s.jsx(en,{label:"Note",value:String(y.feat.attributes.note).slice(0,120)}),b.length>0&&s.jsxs(s.Fragment,{children:[s.jsx("div",{style:{borderTop:`1px solid ${u.tooltipBorder}`,margin:"4px 0",paddingTop:4},children:s.jsx("span",{style:{color:u.textSecondary,fontWeight:600,fontSize:10,textTransform:"uppercase"},children:"Track totals in gene"})}),b.map(R=>s.jsxs("div",{style:{display:"flex",justifyContent:"space-between",gap:8},children:[s.jsx("span",{style:{color:u.textSecondary,overflow:"hidden",textOverflow:"ellipsis",whiteSpace:"nowrap",flex:1},children:R.name}),s.jsx("span",{style:{color:u.textPrimary,fontWeight:600,flexShrink:0},children:R.total.toFixed(1)})]},R.trackId))]})]}),document.body):null;return s.jsxs("div",{style:{position:"relative",width:"100%",height:n},children:[s.jsx("canvas",{ref:o,style:{display:"block",width:"100%",height:n},onMouseMove:w,onMouseLeave:S,onDoubleClick:j}),E]})}function en({label:e,value:t}){return t?s.jsxs("div",{style:{display:"flex",gap:6},children:[s.jsxs("span",{style:{opacity:.6,flexShrink:0},children:[e,":"]}),s.jsx("span",{children:t})]}):null}function Dy(e,t,n){var o;if(!e||!n)return[];const r=[];for(const l of t){if(l.track_type!=="coverage"&&l.track_type!=="reads")continue;const i=ly(l.id,n);if(!((o=i==null?void 0:i.bins)!=null&&o.length))continue;let a=0;for(const u of i.bins){if(u.end<=e.start||u.start>=e.end)continue;const c=u.forward!=null?u.forward:Math.max(0,u.value||0),h=u.reverse!=null?Math.abs(u.reverse):Math.abs(Math.min(0,u.value||0));a+=c+h}a>0&&r.push({trackId:l.id,name:l.name,total:a})}return r}function Mc(e,t,n,r,o,l,i){e.fillStyle=t;const a=Math.min(Rp,o*.4);e.beginPath(),i==="+"?(e.moveTo(n,r),e.lineTo(n+o-a,r),e.lineTo(n+o,r+l/2),e.lineTo(n+o-a,r+l),e.lineTo(n,r+l),e.closePath()):i==="-"?(e.moveTo(n+a,r),e.lineTo(n+o,r),e.lineTo(n+o,r+l),e.lineTo(n+a,r+l),e.lineTo(n,r+l/2),e.closePath()):e.rect(n,r,o,l),e.fill(),e.strokeStyle="rgba(0,0,0,0.25)",e.lineWidth=.5,e.stroke()}function Bc(e,t,n){const r=t.annotationColors;switch(e==null?void 0:e.toLowerCase()){case"cds":return(r==null?void 0:r.cds)||(n==null?void 0:n.geneCds)||"#66bb6a";case"exon":return(r==null?void 0:r.exon)||(n==null?void 0:n.geneExon)||"#42a5f5";case"gene":return(r==null?void 0:r.gene)||(n==null?void 0:n.geneGene)||"#7e57c2";case"mrna":case"transcript":return(r==null?void 0:r.transcript)||(n==null?void 0:n.geneTranscript)||"#ab47bc";case"utr":case"3utr":case"5utr":return(r==null?void 0:r.utr)||(n==null?void 0:n.geneUtr)||"#26c6da";case"rrna":return(r==null?void 0:r.rrna)||(n==null?void 0:n.geneRrna)||"#ffa726";case"trna":return(r==null?void 0:r.trna)||(n==null?void 0:n.geneTrna)||"#ef5350";case"repeat_region":return(r==null?void 0:r.repeat)||(n==null?void 0:n.geneRepeat)||"#8d6e63";default:return(r==null?void 0:r.default)||t.color||(n==null?void 0:n.geneDefault)||"#80cbc4"}}function Uy({track:e,width:t,height:n,onWarning:r}){const o=C.useRef(null),{region:l}=at(),{theme:i}=Xe(),{data:a,loading:u}=ei(e,l,t);return C.useEffect(()=>{var f,p;const c=o.current;if(!c)return;const h=window.devicePixelRatio||1;c.width=t*h,c.height=n*h;const d=c.getContext("2d");if(d.scale(h,h),d.clearRect(0,0,t,n),d.fillStyle=i.canvasBg,d.fillRect(0,0,t,n),u&&!((f=a==null?void 0:a.variants)!=null&&f.length)){d.fillStyle=i.textTertiary,d.font="11px Arial, Helvetica, sans-serif",d.fillText("Loading…",8,n/2+4),r&&r(null);return}if(!((p=a==null?void 0:a.variants)!=null&&p.length)){a&&(d.fillStyle=i.textTertiary,d.font="11px Arial, Helvetica, sans-serif",d.fillText("No variants in region",8,n/2+4)),r&&r(null);return}const m=l.end-l.start,T=e.barAutoWidth!==!1,v=e.barWidth||2,y=T?1:Math.max(.5,v),x=T?5:Math.max(2,v*2);for(const g of a.variants){const w=(g.pos-l.start)/m*t,S=Wy(g.ref,g.alt);d.strokeStyle=S,d.lineWidth=y,d.beginPath(),d.moveTo(w,n-4),d.lineTo(w,14),d.stroke(),d.fillStyle=S,d.beginPath(),d.arc(w,10,x,0,Math.PI*2),d.fill(),m<5e3&&(d.fillStyle=i.textPrimary,d.font="9px Arial, Helvetica, sans-serif",d.textAlign="center",d.fillText(`${g.ref}>${g.alt[0]||"?"}`,w,n-6))}if(r){const g=a.variants.filter(w=>w.pos>=l.start&&w.pos<=l.end).length;r(g>50?`${g} variants overlapping — zoom in for detail`:null)}},[a,u,t,n,l,e.color,e.barAutoWidth,e.barWidth,i]),s.jsx("canvas",{ref:o,style:{display:"block",width:"100%",height:n}})}function Wy(e,t){const n=t[0]||"";return e.length===1&&n.length===1?"#ffb74d":n.length>e.length?"#81c784":n.length<e.length?"#e57373":"#b0bec5"}function Hy({message:e,theme:t}){const[n,r]=C.useState(!1),o=C.useRef(null),l=o.current?o.current.getBoundingClientRect():null;return s.jsxs(s.Fragment,{children:[s.jsx("span",{ref:o,onMouseEnter:()=>r(!0),onMouseLeave:()=>r(!1),style:{display:"inline-flex",alignItems:"center",justifyContent:"center",width:12,height:12,borderRadius:"50%",background:"rgba(229, 57, 53, 0.85)",color:"#fff",fontSize:9,fontWeight:800,lineHeight:1,cursor:"default",flexShrink:0,fontFamily:"Arial, Helvetica, sans-serif"},children:"!"}),n&&l&&Wn.createPortal(s.jsx("div",{style:{position:"fixed",left:Math.min(l.right+6,window.innerWidth-220),top:l.top-4,background:t.tooltipBg||"#333",border:`1px solid ${t.tooltipBorder||"#555"}`,borderRadius:4,padding:"4px 8px",color:t.textPrimary||"#e0e0e0",fontSize:11,lineHeight:1.4,maxWidth:200,zIndex:10001,pointerEvents:"none",boxShadow:"0 3px 10px rgba(0,0,0,0.5)",whiteSpace:"pre-wrap",fontFamily:"Arial, Helvetica, sans-serif"},children:e}),document.body)]})}function Vy({width:e,height:t,trackData:n,trackType:r}){const{region:o,selection:l,clearSelection:i}=at(),{theme:a}=Xe(),[u,c]=C.useState(!1),[h,d]=C.useState({x:0,y:0}),m=C.useRef(null),T=C.useCallback(z=>{d({x:z.clientX,y:z.clientY}),c(!0)},[]),v=C.useCallback(()=>c(!1),[]);if(!l||!o||l.chrom!==o.chrom)return null;const y=o.end-o.start;if(y<=0)return null;const x=(l.start-o.start)/y,f=(l.end-o.start)/y,p=Math.max(0,x*e),w=Math.min(e,f*e)-p;if(w<1)return null;const S=Gy(l,n,r),j=l.end-l.start,b=260,E=Math.min(h.x+14,window.innerWidth-b-10),O=Math.min(h.y+14,window.innerHeight-200);return s.jsxs("div",{ref:m,style:{position:"absolute",top:0,left:0,width:e,height:t,pointerEvents:"none"},children:[s.jsx("div",{style:{position:"absolute",left:p,top:0,width:w,height:"100%",background:"rgba(100, 181, 246, 0.2)",borderLeft:"1px solid rgba(100, 181, 246, 0.6)",borderRight:"1px solid rgba(100, 181, 246, 0.6)",pointerEvents:"auto",cursor:"crosshair"},onMouseMove:T,onMouseLeave:v,onClick:z=>{z.stopPropagation(),i()}}),u&&Wn.createPortal(s.jsxs("div",{style:{position:"fixed",left:E,top:O,background:a.panelBg,border:`1px solid ${a.borderAccent}`,borderRadius:6,padding:"8px 12px",fontSize:11,color:a.textPrimary,lineHeight:1.6,pointerEvents:"none",zIndex:1e4,boxShadow:"0 4px 16px rgba(0,0,0,0.4)",minWidth:180,maxWidth:b},children:[s.jsx("div",{style:{fontWeight:700,marginBottom:4,fontSize:12},children:"Selected Region"}),s.jsxs("div",{children:[s.jsx("span",{style:{color:a.textSecondary},children:"Region:"})," ",l.chrom,":",l.start.toLocaleString(),"-",l.end.toLocaleString()]}),s.jsxs("div",{children:[s.jsx("span",{style:{color:a.textSecondary},children:"Length:"})," ",j.toLocaleString()," bp"]}),S.map((z,P)=>s.jsxs("div",{children:[s.jsxs("span",{style:{color:a.textSecondary},children:[z.label,":"]})," ",z.value]},P)),s.jsx("div",{style:{fontSize:9,color:a.textTertiary,marginTop:4},children:"Click to dismiss"})]}),document.body)]})}function Gy(e,t,n){const r=[];if(!t)return r;if(n==="reads"&&t.reads){const o=t.reads.filter(i=>i.end>e.start&&i.start<e.end);r.push({label:"Reads in region",value:o.length.toLocaleString()});let l=0;for(const i of o)if(i.cigar){const a=i.cigar.match(/(\d+)I/g);if(a)for(const u of a)l+=parseInt(u)}if(l>0&&r.push({label:"Insertion bases",value:l.toLocaleString()}),o.length>0){const i=o.reduce((a,u)=>a+(u.mapq||0),0)/o.length;r.push({label:"Avg MAPQ",value:i.toFixed(1)})}}if((n==="coverage"||n==="reads")&&t.bins){const o=t.bins.filter(l=>l.end>e.start&&l.start<e.end);if(o.length>0){const l=o.map(c=>c.value),i=l.reduce((c,h)=>c+h,0)/l.length,a=Math.max(...l),u=Math.min(...l);r.push({label:"Avg coverage",value:i.toFixed(1)}),r.push({label:"Max coverage",value:a.toFixed(1)}),u!==a&&r.push({label:"Min coverage",value:u.toFixed(1)})}}if(n==="variants"&&t.variants){const o=t.variants.filter(l=>l.pos>=e.start&&l.pos<e.end);r.push({label:"Variants in region",value:o.length.toLocaleString()})}if((n==="annotations"||n==="genome_annotations")&&t.features){const o=t.features.filter(l=>l.end>e.start&&l.start<e.end);r.push({label:"Features in region",value:o.length.toLocaleString()})}return r}class Yy extends C.Component{constructor(t){super(t),this.state={hasError:!1,error:null}}static getDerivedStateFromError(t){return{hasError:!0,error:t}}render(){var t;return this.state.hasError?s.jsxs("div",{style:{padding:8,color:"#ef9a9a",fontSize:11},children:["Track error: ",((t=this.state.error)==null?void 0:t.message)||"Unknown error"]}):this.props.children}}function Qy({track:e,containerWidth:t,labelWidth:n=140,onLabelResizeStart:r,isDragging:o,isDropTarget:l,onDragStart:i,onDragOver:a,onDrop:u,onDragEnd:c}){const{theme:h}=Xe(),{updateTrack:d,removeTrack:m}=Jt(),T=C.useRef(null),v=C.useRef(null),[y,x]=C.useState(!1),[f,p]=C.useState(!1),[g,w]=C.useState(null),S=C.useRef(null),j=C.useRef(null),b=e.track_type==="annotations"||e.track_type==="genome_annotations";Ep(T);const E=["#f44336","#ef5350","#e57373","#ff5722","#ff8a65","#ff9800","#ffa726","#ffb74d","#ffc107","#fff176","#4caf50","#66bb6a","#81c784","#aed581","#009688","#26c6da","#80cbc4","#2196f3","#42a5f5","#64b5f6","#7e57c2","#9575cd","#9c27b0","#ab47bc","#ce93d8","#e91e63","#f06292","#795548","#8d6e63","#607d8b","#78909c"],O=t-n,z={row:{display:"flex",borderBottom:`1px solid ${h.border}`,minHeight:40},label:{width:n,minWidth:n,background:h.panelBg,borderRight:`1px solid ${h.border}`,display:"flex",flexDirection:"column",justifyContent:"center",padding:"4px 8px",overflow:"hidden",position:"relative"},trackName:{fontSize:11,color:h.trackName,fontWeight:600,whiteSpace:"nowrap",overflow:"hidden",textOverflow:"ellipsis"},trackType:{fontSize:10,color:h.textTertiary,marginTop:2},trackArea:{flex:1,overflow:"hidden",position:"relative"}},P=C.useCallback(R=>{R.preventDefault(),R.stopPropagation();const U=R.clientY,N=e.height;function Y(L){const $=Math.max(30,Math.min(500,N+(L.clientY-U)));d(e.id,{height:$})}function I(){window.removeEventListener("mousemove",Y),window.removeEventListener("mouseup",I),document.body.style.cursor="",document.body.style.userSelect=""}document.body.style.cursor="ns-resize",document.body.style.userSelect="none",window.addEventListener("mousemove",Y),window.addEventListener("mouseup",I)},[e.id,e.height,d]);function H(){const R={track:e,width:O,height:e.height,onWarning:w};switch(e.track_type){case"reads":return s.jsx(Ay,{...R});case"coverage":return s.jsx(Py,{...R});case"variants":return s.jsx(Uy,{...R});case"annotations":case"genome_annotations":return s.jsx(Iy,{...R});default:return s.jsx("div",{style:{padding:8,color:h.textTertiary,fontSize:11},children:"Unknown track type"})}}return s.jsxs("div",{style:{...z.row,height:e.height,position:"relative",opacity:o?.4:1,borderTop:l?"2px solid #888":void 0},onDragOver:R=>{R.preventDefault(),R.dataTransfer.dropEffect="move",a==null||a()},onDrop:R=>{R.preventDefault(),u==null||u()},onDragEnd:c,children:[s.jsxs("div",{style:z.label,children:[s.jsxs("div",{style:{display:"flex",alignItems:"center",gap:4},children:[s.jsx("div",{draggable:!0,onDragStart:R=>{R.dataTransfer.effectAllowed="move",R.dataTransfer.setData("text/plain",e.id),i==null||i()},style:{cursor:"grab",color:h.textMuted,fontSize:14,lineHeight:1,userSelect:"none",flexShrink:0,padding:"0 2px"},title:"Drag to reorder tracks",children:"≡"}),s.jsx("div",{ref:S,children:b?s.jsxs(s.Fragment,{children:[s.jsx("span",{style:{display:"inline-block",width:10,height:10,borderRadius:2,background:"#888",cursor:"pointer",verticalAlign:"middle",border:"1px solid rgba(255,255,255,0.2)",backgroundImage:"linear-gradient(135deg, #ef5350 25%, #66bb6a 25%, #66bb6a 50%, #42a5f5 50%, #42a5f5 75%, #ffa726 75%)"},title:"Click to customize annotation colors",onMouseDown:R=>{R.stopPropagation(),p(U=>!U)}}),f&&Wn.createPortal(s.jsx(Jy,{track:e,theme:h,anchorRef:S,onClose:()=>p(!1),onChange:(R,U)=>{const N={...e.annotationColors||{},[R]:U};d(e.id,{annotationColors:N})},onReset:()=>d(e.id,{annotationColors:null})}),document.body)]}):s.jsxs(s.Fragment,{children:[s.jsx("span",{style:{display:"inline-block",width:10,height:10,borderRadius:2,background:e.color,cursor:"pointer",verticalAlign:"middle",border:"1px solid rgba(255,255,255,0.2)"},title:"Click to pick color, double-click for full palette",onMouseDown:R=>{R.stopPropagation(),x(!0)},onDoubleClick:R=>{var U;R.stopPropagation(),x(!1),(U=j.current)==null||U.click()}}),s.jsx("input",{ref:j,type:"color",value:e.color||"#78909c",onChange:R=>d(e.id,{color:R.target.value}),style:{position:"absolute",left:-9999,top:-9999,opacity:0,width:0,height:0}}),y&&Wn.createPortal(s.jsx("div",{style:{position:"fixed",left:S.current?S.current.getBoundingClientRect().left:0,top:S.current?S.current.getBoundingClientRect().bottom+4:0,zIndex:10001,background:h.panelBg,border:`1px solid ${h.borderAccent}`,borderRadius:4,padding:6,boxShadow:"0 4px 12px rgba(0,0,0,0.5)",display:"grid",gridTemplateColumns:"repeat(5, 18px)",gap:3},onMouseLeave:()=>x(!1),children:E.map(R=>s.jsx("span",{style:{width:18,height:18,borderRadius:3,background:R,cursor:"pointer",border:R===e.color?`2px solid ${h.textPrimary}`:"1px solid rgba(255,255,255,0.15)",boxSizing:"border-box"},onMouseUp:()=>{d(e.id,{color:R}),x(!1)}},R))}),document.body)]})}),s.jsx("div",{style:{...z.trackName,flex:1},title:e.name,children:e.name}),s.jsx("span",{title:"Remove track",onClick:R=>{R.stopPropagation(),m(e.id)},style:{color:"#e53935",fontSize:13,fontWeight:700,cursor:"pointer",lineHeight:1,flexShrink:0,padding:"0 2px",opacity:.7,transition:"opacity 0.15s"},onMouseEnter:R=>R.currentTarget.style.opacity="1",onMouseLeave:R=>R.currentTarget.style.opacity="0.7",children:"×"})]}),s.jsxs("div",{style:{display:"flex",alignItems:"center",gap:4},children:[s.jsxs("div",{style:z.trackType,children:[e.file_format," · ",e.track_type]}),g&&s.jsx(Hy,{message:g,theme:h})]}),r&&s.jsx("div",{onMouseDown:r,style:{position:"absolute",right:-3,top:0,bottom:0,width:6,cursor:"ew-resize",zIndex:10},onMouseEnter:R=>R.currentTarget.style.background="rgba(255,255,255,0.15)",onMouseLeave:R=>R.currentTarget.style.background="transparent"})]}),s.jsxs("div",{style:z.trackArea,ref:T,children:[s.jsx(Yy,{children:H()}),s.jsx(Vy,{width:O,height:e.height,trackData:Cp(e.id),trackType:e.track_type})]}),s.jsx("div",{ref:v,onMouseDown:P,title:"Drag to resize track height",style:{position:"absolute",left:0,right:0,bottom:-2,height:5,cursor:"ns-resize",zIndex:10,background:"transparent"},onMouseEnter:R=>R.currentTarget.style.background="rgba(255,255,255,0.15)",onMouseLeave:R=>R.currentTarget.style.background="transparent"})]})}const Xy=[{key:"cds",label:"CDS"},{key:"exon",label:"Exon"},{key:"gene",label:"Gene"},{key:"transcript",label:"Transcript"},{key:"utr",label:"UTR"},{key:"rrna",label:"rRNA"},{key:"trna",label:"tRNA"},{key:"repeat",label:"Repeat"},{key:"default",label:"Other"}],Ky=["#f44336","#ef5350","#e57373","#ff5722","#ff8a65","#ff9800","#ffa726","#ffb74d","#ffc107","#fff176","#4caf50","#66bb6a","#81c784","#aed581","#009688","#26c6da","#80cbc4","#2196f3","#42a5f5","#64b5f6","#7e57c2","#9575cd","#9c27b0","#ab47bc","#ce93d8","#e91e63","#f06292","#795548","#8d6e63","#607d8b","#78909c"],qy={cds:"geneCds",exon:"geneExon",gene:"geneGene",transcript:"geneTranscript",utr:"geneUtr",rrna:"geneRrna",trna:"geneTrna",repeat:"geneRepeat",default:"geneDefault"};function Jy({track:e,theme:t,anchorRef:n,onClose:r,onChange:o,onReset:l}){var d;const[i,a]=C.useState(null),u=e.annotationColors||{},c=(d=n.current)==null?void 0:d.getBoundingClientRect();function h(m){return u[m]||t[qy[m]]||vp[m]}return s.jsxs("div",{style:{position:"fixed",left:c?Math.min(c.left,window.innerWidth-220):0,top:c?c.bottom+4:0,zIndex:10001,background:t.panelBg,border:`1px solid ${t.borderAccent}`,borderRadius:6,padding:"8px 0",boxShadow:"0 6px 20px rgba(0,0,0,0.5)",width:210,maxHeight:340,overflowY:"auto"},onMouseLeave:r,children:[s.jsx("div",{style:{fontSize:10,fontWeight:700,color:t.textSecondary,textTransform:"uppercase",letterSpacing:1,padding:"0 10px 6px",borderBottom:`1px solid ${t.border}`,marginBottom:4},children:"Annotation Colors"}),Xy.map(({key:m,label:T})=>{const v=h(m);return s.jsxs("div",{children:[s.jsxs("div",{style:{display:"flex",alignItems:"center",gap:8,padding:"4px 10px",cursor:"pointer",fontSize:11,color:t.textPrimary},onMouseEnter:y=>y.currentTarget.style.background=t.selectedRow,onMouseLeave:y=>y.currentTarget.style.background="transparent",onClick:()=>a(i===m?null:m),children:[s.jsx("span",{style:{display:"inline-block",width:14,height:14,borderRadius:3,background:v,border:"1px solid rgba(255,255,255,0.15)",flexShrink:0}}),s.jsx("span",{style:{flex:1},children:T}),s.jsx("span",{style:{fontSize:9,color:t.textTertiary},children:i===m?"▲":"▼"})]}),i===m&&s.jsx("div",{style:{padding:"4px 10px 6px 32px",display:"grid",gridTemplateColumns:"repeat(5, 18px)",gap:3},children:Ky.map(y=>s.jsx("span",{style:{width:18,height:18,borderRadius:3,background:y,cursor:"pointer",border:y===v?`2px solid ${t.textPrimary}`:"1px solid rgba(255,255,255,0.15)",boxSizing:"border-box"},onClick:()=>{o(m,y),a(null)}},y))})]},m)}),s.jsx("div",{style:{borderTop:`1px solid ${t.border}`,marginTop:4,paddingTop:4},children:s.jsx("div",{style:{padding:"4px 10px",fontSize:10,color:t.textTertiary,cursor:"pointer",textAlign:"center"},onMouseEnter:m=>{m.currentTarget.style.color=t.textPrimary},onMouseLeave:m=>{m.currentTarget.style.color=t.textTertiary},onClick:l,children:"Reset to defaults"})})]})}function Zy({labelWidth:e}){const{genome:t,region:n}=at(),{tracks:r}=Jt(),{theme:o,themeName:l,customTheme:i}=Xe(),[a,u]=C.useState(!1),[c,h]=C.useState(!1),d=!!t;C.useEffect(()=>{if(!d)return;function y(x){x.preventDefault(),x.returnValue=""}return window.addEventListener("beforeunload",y),()=>window.removeEventListener("beforeunload",y)},[d]),C.useEffect(()=>{if(!d)return;function y(x){(x.ctrlKey||x.metaKey)&&x.key==="w"&&(x.preventDefault(),u(!0))}return window.addEventListener("keydown",y),()=>window.removeEventListener("keydown",y)},[d]);const m=C.useCallback(()=>u(!1),[]),T=C.useCallback(()=>{window.onbeforeunload=null,window.close(),window.location.href="about:blank"},[]),v=C.useCallback(()=>{h(!0);try{const y=Fa(t,n,r,l,i,e);Ia(y),jp(y)}catch{}h(!1),window.onbeforeunload=null,window.close(),window.location.href="about:blank"},[t,n,r,l,i,e]);return a?s.jsx("div",{style:{position:"fixed",inset:0,zIndex:1e4,background:"rgba(0,0,0,0.5)",display:"flex",alignItems:"center",justifyContent:"center"},onClick:m,children:s.jsxs("div",{style:{background:o.panelBg,border:`1px solid ${o.borderAccent}`,borderRadius:8,padding:"24px 28px",maxWidth:400,width:"90%",boxShadow:"0 8px 32px rgba(0,0,0,0.6)"},onClick:y=>y.stopPropagation(),children:[s.jsx("div",{style:{fontSize:16,fontWeight:700,color:o.textPrimary,marginBottom:8},children:"Leave BiNgo Genome Viewer?"}),s.jsxs("div",{style:{fontSize:12,color:o.textSecondary,lineHeight:1.7,marginBottom:20},children:["You have an active session with"," ",s.jsxs("strong",{style:{color:o.textPrimary},children:[r.length," track",r.length!==1?"s":""]})," loaded. Unsaved changes will be lost."]}),s.jsxs("div",{style:{display:"flex",flexDirection:"column",gap:8},children:[s.jsx("button",{onClick:m,style:{background:"#1976d2",border:"none",borderRadius:4,color:"#fff",padding:"8px 16px",cursor:"pointer",fontSize:13,fontWeight:600,width:"100%"},children:"Return to App"}),s.jsx("button",{onClick:v,disabled:c,style:{background:o.btnBg,border:`1px solid ${o.borderStrong}`,borderRadius:4,color:o.btnText,padding:"8px 16px",cursor:"pointer",fontSize:13,fontWeight:600,width:"100%"},children:c?"Saving...":"Save Session & Exit"}),s.jsx("button",{onClick:T,style:{background:"transparent",border:`1px solid ${o.border}`,borderRadius:4,color:"#e57373",padding:"8px 16px",cursor:"pointer",fontSize:13,fontWeight:600,width:"100%"},children:"Exit Without Saving"})]})]})}):null}const Ac="2.3.3";let ex=0;function zc({size:e=32}){const[t]=Us.useState(()=>`blogo${++ex}`);return s.jsxs("svg",{width:e,height:e,viewBox:"0 0 100 100",style:{flexShrink:0},xmlns:"http://www.w3.org/2000/svg",children:[s.jsxs("defs",{children:[s.jsxs("radialGradient",{id:`${t}_bg`,cx:"35%",cy:"30%",r:"65%",children:[s.jsx("stop",{offset:"0%",stopColor:"#5eb8ff"}),s.jsx("stop",{offset:"50%",stopColor:"#1976d2"}),s.jsx("stop",{offset:"100%",stopColor:"#0d47a1"})]}),s.jsxs("radialGradient",{id:`${t}_sh`,cx:"30%",cy:"25%",r:"30%",children:[s.jsx("stop",{offset:"0%",stopColor:"#ffffff",stopOpacity:"0.7"}),s.jsx("stop",{offset:"100%",stopColor:"#ffffff",stopOpacity:"0"})]})]}),s.jsx("circle",{cx:"50",cy:"50",r:"48",fill:`url(#${t}_bg)`}),s.jsx("circle",{cx:"50",cy:"48",r:"28",fill:"white"}),s.jsx("circle",{cx:"50",cy:"48",r:"28",fill:"none",stroke:"#1565c0",strokeWidth:"2.5"}),s.jsx("text",{x:"50",y:"39",textAnchor:"middle",fontSize:"13",fontWeight:"800",fontFamily:"Arial, sans-serif",fill:"#0d47a1",children:"BN"}),s.jsx("text",{x:"50",y:"64",textAnchor:"middle",fontSize:"30",fontWeight:"900",fontFamily:"Arial, sans-serif",fill:"#0d47a1",children:"1"}),s.jsx("circle",{cx:"50",cy:"50",r:"48",fill:`url(#${t}_sh)`})]})}function tx({theme:e,labelWidth:t}){return s.jsxs("div",{style:{display:"flex",borderBottom:`1px solid ${e.border}`,height:60,opacity:.45},children:[s.jsx("div",{"data-tour":"skeleton-track-label",style:{width:t,minWidth:t,background:e.panelBg,borderRight:`1px solid ${e.border}`,padding:"6px 8px",display:"flex",flexDirection:"column",justifyContent:"center",gap:4},children:s.jsxs("div",{style:{display:"flex",alignItems:"center",gap:6},children:[s.jsx("span",{style:{fontSize:14,color:e.textTertiary,userSelect:"none",lineHeight:1},children:"≡"}),s.jsx("span",{style:{width:10,height:10,borderRadius:2,background:"#78909c",flexShrink:0}}),s.jsx("span",{style:{fontSize:11,fontWeight:600,color:e.textSecondary,flex:1,overflow:"hidden",textOverflow:"ellipsis",whiteSpace:"nowrap"},children:"Track Name"}),s.jsx("span",{style:{fontSize:13,color:e.textTertiary,lineHeight:1,padding:"0 2px"},children:"×"})]})}),s.jsx("div",{style:{flex:1,background:e.canvasBg}})]})}function nx(){const{theme:e}=Xe(),{genome:t,region:n,setGenome:r,navigateTo:o}=at(),{tracks:l,reorderTracks:i,addTrack:a,uploadTrack:u,commitTrack:c,discardTrack:h,addGenomeAnnotationTrack:d,restoreAnnotationTracks:m}=Jt(),T=C.useRef(null),[v,y]=C.useState(800),[x,f]=C.useState(!1),[p,g]=C.useState(!1),[w,S]=C.useState(!1),[j,b]=C.useState(!1),[E,O]=C.useState(!1),[z,P]=C.useState(!1),[H,R]=C.useState(140),[U,N]=C.useState(null),[Y,I]=C.useState(null),[L,$]=C.useState(!1),[D,A]=C.useState(null),[F,V]=C.useState(null),[M,k]=C.useState(null),Q=C.useRef(0);Sy(H),C.useEffect(()=>{const B=()=>fetch("/api/heartbeat").catch(()=>{});B();const q=setInterval(B,1e4);return()=>clearInterval(q)},[]);const ee=C.useRef(n==null?void 0:n.chrom);C.useEffect(()=>{n!=null&&n.chrom&&n.chrom!==ee.current&&(ee.current=n.chrom,m())},[n==null?void 0:n.chrom,m]);const ce=new Set([".gb",".gbk",".genbank",".fasta",".fa"]),he=new Set([".bam",".bw",".bigwig",".wig",".bedgraph",".bdg",".vcf",".bed",".gtf",".gff",".gff2",".gff3"]),pe=new Set([".bai"]);function ae(B){if(!B)return"";if(B.toLowerCase().endsWith(".vcf.gz"))return".vcf.gz";const q=B.lastIndexOf(".");return q>=0?B.slice(q).toLowerCase():""}const ie=C.useCallback(B=>{var q,X;B.preventDefault(),B.stopPropagation(),(X=(q=B.dataTransfer)==null?void 0:q.types)!=null&&X.includes("Files")&&(Q.current++,Q.current===1&&$(!0))},[]),ne=C.useCallback(B=>{var q,X;B.preventDefault(),B.stopPropagation(),(X=(q=B.dataTransfer)==null?void 0:q.types)!=null&&X.includes("Files")&&(Q.current--,Q.current<=0&&(Q.current=0,$(!1)))},[]),xe=C.useCallback(B=>{B.preventDefault(),B.stopPropagation()},[]);function Me(B){const q=B==null?void 0:B.compatibility;return q&&q.status!=="ok"&&q.status!=="no_genome"}const ve=C.useCallback(async B=>{var Ie,ut,Da,Ua,Wa;if(B.preventDefault(),B.stopPropagation(),Q.current=0,$(!1),!((ut=(Ie=B.dataTransfer)==null?void 0:Ie.types)!=null&&ut.includes("Files")))return;const q=Array.from(B.dataTransfer.files);if(!q.length)return;const X=[],Z=[],le=[],oe=[];for(const Re of q){const Be=ae(Re.name),yt=Re.name.toLowerCase();ce.has(Be)?X.push(Re):he.has(Be)||Be===".vcf.gz"?Z.push(Re):pe.has(Be)||yt.endsWith(".bam.bai")?le.push(Re):oe.push(Re)}const fe=Z.filter(Re=>Re.name.toLowerCase().endsWith(".bam")&&Re.size>50*1024*1024),we=le.filter(Re=>Re.size>10*1024*1024);if(fe.length||we.length){const Re=[...fe,...we].map(yt=>yt.name).join(", "),Be=[...fe,...we].reduce((yt,jo)=>yt+jo.size,0)/(1024*1024);A({error:`${Re} (${Be.toFixed(0)} MB) — large files load faster via the Path button. Click 📂 Path in the toolbar and paste the file path instead of uploading.`}),setTimeout(()=>A(null),1e4);return}if(oe.length&&!X.length&&!Z.length&&!le.length){A({error:`Unsupported file${oe.length>1?"s":""}: ${oe.map(Re=>Re.name).join(", ")}`}),setTimeout(()=>A(null),4e3);return}try{if(X.length>0&&!t){A({msg:`Loading genome: ${X[0].name}...`});const Be=(await yn.load(X[0])).data;if(Be.name&&(Be.name=Ft(Be.name)),r(Be),((Da=Be.chromosomes)==null?void 0:Da.length)>0){const yt=Be.chromosomes[0];o(yt.name,0,Math.min(yt.length,5e4))}Be.is_annotated&&d({id:"genome_annotations",name:`${Be.name} (annotations)`,track_type:"genome_annotations",file_format:"genbank",targetChromosomes:Be.annotated_chromosomes||null})}else X.length>0&&t&&V({files:X});if(Z.length>0){if(!t&&X.length===0){A({error:"Load a genome file first (.fasta, .gb, .genbank)"}),setTimeout(()=>A(null),4e3);return}A({msg:`Loading ${Z.length} track${Z.length>1?"s":""}...`});const Re=[],Be=[],yt=[];for(const jo of Z)try{const kn=await u(jo,void 0);Me(kn)?Be.push(kn):(c(kn),Re.push(kn))}catch(kn){yt.push(`${jo.name}: ${((Wa=(Ua=kn.response)==null?void 0:Ua.data)==null?void 0:Wa.detail)||kn.message}`)}if(yt.length){A({error:yt.join("; ")}),setTimeout(()=>A(null),5e3);return}Be.length>0&&k({tracks:Be})}oe.length?(A({error:`Skipped unsupported: ${oe.map(Re=>Re.name).join(", ")}`}),setTimeout(()=>A(null),4e3)):(A({msg:"Files loaded"}),setTimeout(()=>A(null),2e3))}catch(Re){A({error:Re.message||"Drop failed"}),setTimeout(()=>A(null),5e3)}},[t,r,o,a,d]),Fe=C.useCallback(async()=>{var q,X;if(!F)return;const B=F.files;V(null);try{const Z=[];for(const le of B){A({msg:`Adding chromosomes from ${le.name}...`});try{const fe=(await yn.addChromosomes(le)).data;fe.name&&(fe.name=Ft(fe.name)),r(fe),fe.is_annotated&&d({id:"genome_annotations",name:`${fe.name} (annotations)`,track_type:"genome_annotations",file_format:"genbank",targetChromosomes:fe.annotated_chromosomes||null})}catch(oe){Z.push(`${le.name}: ${((X=(q=oe.response)==null?void 0:q.data)==null?void 0:X.detail)||oe.message}`)}}Z.length?(A({error:Z.join("; ")}),setTimeout(()=>A(null),5e3)):(A({msg:`Added chromosomes from ${B.length} file${B.length>1?"s":""}`}),setTimeout(()=>A(null),3e3))}catch(Z){A({error:Z.message||"Failed to add chromosomes"}),setTimeout(()=>A(null),5e3)}},[F,r,d]),et=C.useCallback(async()=>{var q,X;if(!F)return;const B=F.files;V(null);try{A({msg:`Loading ${B.length} track${B.length>1?"s":""}...`});const Z=[];for(const le of B)try{await a(le,void 0)}catch(oe){Z.push(`${le.name}: ${((X=(q=oe.response)==null?void 0:q.data)==null?void 0:X.detail)||oe.message}`)}Z.length?(A({error:Z.join("; ")}),setTimeout(()=>A(null),5e3)):(A({msg:`Added ${B.length} track${B.length>1?"s":""}`}),setTimeout(()=>A(null),3e3))}catch(Z){A({error:Z.message||"Failed to load tracks"}),setTimeout(()=>A(null),5e3)}},[F,a]),me=C.useCallback(async()=>{if(M){for(const B of M.tracks)await h(B.id);k(null)}},[M,h]),gt=C.useCallback(()=>{if(M){for(const B of M.tracks)c(B);k(null),A({msg:`Added ${M.tracks.length} track${M.tracks.length>1?"s":""}`}),setTimeout(()=>A(null),3e3)}},[M,c]),G=C.useCallback(B=>{B.preventDefault();const q=B.clientX,X=H;function Z(oe){R(Math.max(60,Math.min(400,X+(oe.clientX-q))))}function le(){window.removeEventListener("mousemove",Z),window.removeEventListener("mouseup",le),document.body.style.cursor="",document.body.style.userSelect=""}document.body.style.cursor="ew-resize",document.body.style.userSelect="none",window.addEventListener("mousemove",Z),window.addEventListener("mouseup",le)},[H]);C.useEffect(()=>{if(!T.current)return;const B=new ResizeObserver(q=>{for(const X of q)y(X.contentRect.width)});return B.observe(T.current),()=>B.disconnect()},[]);const J=C.useCallback(B=>B.visible?!B.targetChromosomes||!(n!=null&&n.chrom)?!0:B.targetChromosomes.includes(n.chrom):!1,[n==null?void 0:n.chrom]),te={app:{display:"flex",flexDirection:"column",height:"100vh",background:e.appBg,color:e.textPrimary},header:{background:e.headerBg,borderBottom:`2px solid ${e.borderAccent}`,padding:"8px 16px",display:"flex",alignItems:"center",justifyContent:"space-between"},headerLeft:{display:"flex",alignItems:"center",gap:12},title:{fontSize:18,fontWeight:700,color:e.textPrimary,letterSpacing:1},subtitle:{fontSize:11,color:e.textTertiary},headerBtns:{display:"flex",gap:8},btn:{background:e.btnBg,border:`1px solid ${e.borderStrong}`,borderRadius:4,color:e.btnText,padding:"5px 14px",cursor:"pointer",fontSize:12,fontWeight:600,display:"flex",alignItems:"center",gap:6},trackArea:{flex:1,overflowY:"auto",overflowX:"hidden",display:"flex",flexDirection:"column"},emptyState:{display:"flex",flexDirection:"column",alignItems:"center",justifyContent:"center",flex:1,color:e.textMuted,gap:12},emptyTitle:{fontSize:22,fontWeight:300},emptyHint:{fontSize:13}};return s.jsxs("div",{style:te.app,onDragEnter:ie,onDragLeave:ne,onDragOver:xe,onDrop:ve,children:[s.jsxs("div",{style:te.header,children:[s.jsxs("div",{style:te.headerLeft,children:[s.jsx(zc,{size:34}),s.jsxs("div",{children:[s.jsx("div",{style:te.title,children:"BiNgo Genome Viewer"}),t&&s.jsxs("div",{style:te.subtitle,children:[t.name," · ",t.chromosomes.length," chr"]})]}),s.jsxs("button",{onClick:()=>O(!0),title:"About / References",style:{background:"none",border:`1px solid ${e.border}`,borderRadius:10,padding:"2px 8px",display:"flex",alignItems:"center",gap:4,cursor:"pointer",color:e.textSecondary,fontSize:11,fontWeight:600,lineHeight:1,flexShrink:0},onMouseEnter:B=>{B.currentTarget.style.color=e.textPrimary,B.currentTarget.style.borderColor=e.textSecondary},onMouseLeave:B=>{B.currentTarget.style.color=e.textSecondary,B.currentTarget.style.borderColor=e.border},children:[s.jsxs("svg",{width:"12",height:"12",viewBox:"0 0 16 16",fill:"currentColor",style:{flexShrink:0},children:[s.jsx("path",{d:"M8 15A7 7 0 1 1 8 1a7 7 0 0 1 0 14zm0 1A8 8 0 1 0 8 0a8 8 0 0 0 0 16z"}),s.jsx("circle",{cx:"8",cy:"4.5",r:"1.2"}),s.jsx("rect",{x:"7",y:"6.5",width:"2",height:"5.5",rx:"0.8"})]}),"Info"]}),s.jsxs("button",{onClick:()=>P(!0),title:"Guided Tour",style:{background:"none",border:`1px solid ${e.border}`,borderRadius:10,padding:"2px 8px",display:"flex",alignItems:"center",gap:4,cursor:"pointer",color:e.textSecondary,fontSize:11,fontWeight:600,lineHeight:1,flexShrink:0},onMouseEnter:B=>{B.currentTarget.style.color=e.textPrimary,B.currentTarget.style.borderColor=e.textSecondary},onMouseLeave:B=>{B.currentTarget.style.color=e.textSecondary,B.currentTarget.style.borderColor=e.border},children:[s.jsxs("svg",{width:"12",height:"12",viewBox:"0 0 16 16",fill:"currentColor",style:{flexShrink:0},children:[s.jsx("path",{d:"M8 15A7 7 0 1 1 8 1a7 7 0 0 1 0 14zm0 1A8 8 0 1 0 8 0a8 8 0 0 0 0 16z"}),s.jsx("path",{d:"M5.255 5.786a.237.237 0 0 0 .241.247h.825c.138 0 .248-.113.266-.25.09-.656.54-1.134 1.342-1.134.686 0 1.314.343 1.314 1.168 0 .635-.374.927-.965 1.371-.673.489-1.206 1.06-1.168 1.987l.003.217a.25.25 0 0 0 .25.246h.811a.25.25 0 0 0 .25-.25v-.105c0-.718.273-.927 1.01-1.486.609-.463 1.244-.977 1.244-2.056 0-1.511-1.276-2.241-2.673-2.241-1.267 0-2.655.59-2.75 2.286zM8 13.5a1 1 0 1 0 0-2 1 1 0 0 0 0 2z"})]}),"Help"]})]}),s.jsxs("div",{style:te.headerBtns,"data-tour":"header-btns",children:[s.jsxs("button",{style:te.btn,onClick:()=>b(!0),title:"Save or restore a session",children:[s.jsxs("svg",{width:"12",height:"12",viewBox:"0 0 12 12",fill:"none",stroke:"currentColor",strokeWidth:"1.3",strokeLinecap:"round",strokeLinejoin:"round",style:{flexShrink:0},children:[s.jsx("path",{d:"M2 2h8v8H2z"}),s.jsx("path",{d:"M4 2v4h4V2"}),s.jsx("path",{d:"M5 3h2"})]}),"Save Session"]}),s.jsxs("button",{style:te.btn,onClick:()=>g(!0),title:"Customize color theme",children:[s.jsxs("svg",{width:"12",height:"12",viewBox:"0 0 12 12",style:{flexShrink:0},children:[s.jsx("rect",{x:"0",y:"0",width:"5.5",height:"5.5",rx:"1",fill:"#66bb6a"}),s.jsx("rect",{x:"6.5",y:"0",width:"5.5",height:"5.5",rx:"1",fill:"#42a5f5"}),s.jsx("rect",{x:"0",y:"6.5",width:"5.5",height:"5.5",rx:"1",fill:"#ffa726"}),s.jsx("rect",{x:"6.5",y:"6.5",width:"5.5",height:"5.5",rx:"1",fill:"#ab47bc"})]}),"Theme"]}),s.jsxs("button",{"data-tour":"btn-export",style:{...te.btn,...n&&l.length>0?{}:{opacity:.35,cursor:"default"}},onClick:()=>{n&&l.length>0&&S(!0)},title:"Export current view as SVG or PNG",children:[s.jsx("svg",{width:"12",height:"12",viewBox:"0 0 12 12",fill:"none",stroke:"currentColor",strokeWidth:"1.5",strokeLinecap:"round",strokeLinejoin:"round",style:{flexShrink:0},children:s.jsx("path",{d:"M6 1v7M3 5.5L6 8.5 9 5.5M2 11h8"})}),"Export Image"]}),s.jsxs("button",{"data-tour":"btn-settings",style:{...te.btn,...l.length===0?{opacity:.35,cursor:"default"}:{}},onClick:()=>{l.length>0&&f(!0)},title:"Adjust height, scale, color, and bar width for tracks",children:["⚙"," Track Settings"]})]})]}),s.jsx(D0,{}),s.jsx(jy,{}),s.jsxs("div",{style:te.trackArea,ref:T,"data-tour":"track-area",children:[l.filter(J).length===0&&s.jsx(tx,{theme:e,labelWidth:H}),t?n?s.jsxs(s.Fragment,{children:[s.jsxs("div",{style:{display:"flex"},children:[s.jsx("div",{style:{width:H,minWidth:H,background:e.panelBg,borderRight:`1px solid ${e.border}`,position:"relative"},children:s.jsx("div",{onMouseDown:G,style:{position:"absolute",right:-3,top:0,bottom:0,width:6,cursor:"ew-resize",zIndex:10},onMouseEnter:B=>B.currentTarget.style.background="rgba(255,255,255,0.15)",onMouseLeave:B=>B.currentTarget.style.background="transparent"})}),s.jsx(Ey,{width:v-H})]}),l.filter(J).map(B=>s.jsx(Qy,{track:B,containerWidth:v,labelWidth:H,onLabelResizeStart:G,isDragging:U===B.id,isDropTarget:Y===B.id,onDragStart:()=>N(B.id),onDragOver:()=>I(B.id),onDrop:()=>{U&&U!==B.id&&i(U,B.id),N(null),I(null)},onDragEnd:()=>{N(null),I(null)}},B.id)),l.length===0&&s.jsx("div",{style:{padding:24,color:e.textMuted,fontSize:13},children:"Add tracks above — BAM, VCF, BigWig, BED, GTF, GFF, WIG..."})]}):s.jsx("div",{style:te.emptyState,children:s.jsx("div",{style:te.emptyHint,children:"Select a chromosome to begin"})}):s.jsxs("div",{style:te.emptyState,children:[s.jsx("div",{style:te.emptyTitle,children:"No genome loaded"}),s.jsx("div",{style:te.emptyHint,children:"Load a FASTA or GenBank file above to get started"})]})]}),x&&s.jsx(Q0,{onClose:()=>f(!1)}),p&&s.jsx(Z0,{onClose:()=>g(!1)}),w&&s.jsx(ay,{onClose:()=>S(!1)}),j&&s.jsx(by,{onClose:()=>b(!1),labelWidth:H,setLabelWidth:R}),z&&s.jsx(Ty,{onClose:()=>{P(!1),f(!1),g(!1)},theme:e,onAction:B=>{B==="open-settings"?(f(!0),g(!1)):B==="open-theme"?(g(!0),f(!1)):(f(!1),g(!1))}}),E&&s.jsx("div",{style:{position:"fixed",inset:0,background:"rgba(0,0,0,0.6)",display:"flex",alignItems:"center",justifyContent:"center",zIndex:9999},onClick:()=>O(!1),children:s.jsxs("div",{style:{background:e.panelBg,border:`1px solid ${e.border}`,borderRadius:8,padding:"28px 36px",maxWidth:520,maxHeight:"85vh",overflowY:"auto",color:e.textPrimary,lineHeight:1.7},onClick:B=>B.stopPropagation(),children:[s.jsxs("div",{style:{display:"flex",alignItems:"center",gap:12,marginBottom:16},children:[s.jsx(zc,{size:44}),s.jsx("div",{style:{fontSize:20,fontWeight:700},children:"BiNgo Genome Viewer"})]}),s.jsxs("div",{style:{fontSize:13,color:e.textSecondary,marginBottom:12},children:[s.jsx("strong",{style:{color:e.textPrimary},children:"Version:"})," ",Ac]}),s.jsxs("div",{style:{fontSize:13,color:e.textSecondary,marginBottom:12},children:[s.jsx("strong",{style:{color:e.textPrimary},children:"Publisher:"})," Billy M Ngo"]}),s.jsxs("div",{style:{fontSize:13,color:e.textSecondary,marginBottom:20},children:[s.jsx("strong",{style:{color:e.textPrimary},children:"Published:"})," April 2026"]}),s.jsxs("div",{style:{fontSize:12,color:e.textSecondary,background:e.canvasBg,border:`1px solid ${e.border}`,borderRadius:4,padding:"10px 14px",fontFamily:"monospace",lineHeight:1.6,marginBottom:20,userSelect:"all"},children:["Ngo, B.M. (2026). BiNgo Genome Viewer (v",Ac,") [Software]."]}),s.jsxs("details",{style:{marginBottom:20},children:[s.jsx("summary",{style:{cursor:"pointer",fontSize:13,fontWeight:600,color:e.textPrimary,marginBottom:8},children:"References & Acknowledgments"}),s.jsxs("div",{style:{fontSize:11,color:e.textSecondary,lineHeight:1.8,paddingTop:8},children:[s.jsx("div",{style:{fontWeight:600,color:e.textPrimary,marginBottom:4},children:"Software Dependencies"}),s.jsxs("div",{children:[s.jsx("strong",{children:"FastAPI"})," ","—"," Ram","í","rez, S. (2018). A modern web framework for building APIs with Python."]}),s.jsxs("div",{children:[s.jsx("strong",{children:"Uvicorn"})," ","—"," Encode OSS. ASGI server implementation for Python."]}),s.jsxs("div",{children:[s.jsx("strong",{children:"BioPython"})," ","—"," Cock, P.J.A. et al. (2009). ",s.jsx("em",{children:"Bioinformatics"}),", 25(11), 1422","–","1423."]}),s.jsxs("div",{children:[s.jsx("strong",{children:"pyfaidx"})," ","—"," Shirley, M.D. et al. (2015). ",s.jsx("em",{children:"PeerJ PrePrints"}),", 3:e1196."]}),s.jsxs("div",{children:[s.jsx("strong",{children:"bamnostic"})," ","—"," Sherman, M.A. & Mills, R.E. (2019). Pure Python BAM parser."]}),s.jsxs("div",{children:[s.jsx("strong",{children:"React"})," ","—"," Meta Platforms, Inc. JavaScript UI library."]}),s.jsxs("div",{children:[s.jsx("strong",{children:"Vite"})," ","—"," You, E. (2020). Next generation frontend tooling."]}),s.jsx("div",{style:{fontWeight:600,color:e.textPrimary,marginTop:12,marginBottom:4},children:"File Format Specifications"}),s.jsxs("div",{children:[s.jsx("strong",{children:"SAM/BAM"})," ","—"," Li, H. et al. (2009). ",s.jsx("em",{children:"Bioinformatics"}),", 25(16), 2078","–","2079."]}),s.jsxs("div",{children:[s.jsx("strong",{children:"VCF"})," ","—"," Danecek, P. et al. (2011). ",s.jsx("em",{children:"Bioinformatics"}),", 27(15), 2156","–","2158."]}),s.jsxs("div",{children:[s.jsx("strong",{children:"BigWig/WIG"})," ","—"," Kent, W.J. et al. (2010). ",s.jsx("em",{children:"Bioinformatics"}),", 26(17), 2204","–","2207."]}),s.jsxs("div",{children:[s.jsx("strong",{children:"BED"})," ","—"," UCSC Genome Browser, UC Santa Cruz."]}),s.jsxs("div",{children:[s.jsx("strong",{children:"GFF3"})," ","—"," Sequence Ontology Project."]}),s.jsxs("div",{children:[s.jsx("strong",{children:"GTF"})," ","—"," Ensembl genome database project."]}),s.jsxs("div",{children:[s.jsx("strong",{children:"GenBank"})," ","—"," Benson, D.A. et al. (2013). ",s.jsx("em",{children:"Nucleic Acids Res."}),", 41(D1), D36","–","D42."]}),s.jsx("div",{style:{fontWeight:600,color:e.textPrimary,marginTop:12,marginBottom:4},children:"Inspiration"}),s.jsxs("div",{children:[s.jsx("strong",{children:"IGV"})," ","—"," Robinson, J.T. et al. (2011). ",s.jsx("em",{children:"Nature Biotechnology"}),", 29(1), 24","–","26."]}),s.jsx("div",{style:{fontWeight:600,color:e.textPrimary,marginTop:12,marginBottom:4},children:"Acknowledgments"}),s.jsx("div",{children:"Early version testing and feedback:"}),s.jsx("div",{children:"Amanda Antoch, Isaac Poarch, Otto Chipashvili, Jake Colautti"})]})]}),s.jsx("div",{style:{textAlign:"right"},children:s.jsx("button",{onClick:()=>O(!1),style:{background:e.btnBg,border:`1px solid ${e.borderStrong}`,borderRadius:4,color:e.btnText,padding:"5px 18px",cursor:"pointer",fontSize:12,fontWeight:600},children:"Close"})})]})}),F&&(()=>{const B=F.files.length>1,q=F.files.map(X=>X.name).join(", ");return s.jsx("div",{style:{position:"fixed",inset:0,background:"rgba(0,0,0,0.45)",display:"flex",alignItems:"center",justifyContent:"center",zIndex:9999},children:s.jsxs("div",{style:{background:e.panelBg,border:`1px solid ${e.borderAccent}`,borderRadius:8,padding:"20px 24px",maxWidth:440,width:"90%",boxShadow:"0 8px 32px rgba(0,0,0,0.5)"},onClick:X=>X.stopPropagation(),children:[s.jsxs("div",{style:{fontSize:14,fontWeight:700,color:e.textPrimary,marginBottom:8},children:["Genome file",B?"s":""," detected"]}),s.jsxs("div",{style:{fontSize:12,color:e.textSecondary,lineHeight:1.6,marginBottom:16},children:[s.jsx("strong",{style:{color:e.textPrimary},children:q}),B?" appear to be genome files. A genome is already loaded.":" appears to be a genome file. A genome is already loaded.",s.jsx("br",{}),"How would you like to handle ",B?"them":"it","?"]}),s.jsxs("div",{style:{display:"flex",gap:8,justifyContent:"flex-end",flexWrap:"wrap"},children:[s.jsx("button",{onClick:()=>V(null),style:{background:e.btnBg,border:`1px solid ${e.borderStrong}`,borderRadius:4,color:e.btnText,padding:"5px 16px",cursor:"pointer",fontSize:12,fontWeight:600},children:"Skip"}),s.jsxs("button",{onClick:et,style:{background:e.btnBg,border:`1px solid ${e.borderStrong}`,borderRadius:4,color:e.btnText,padding:"5px 16px",cursor:"pointer",fontSize:12,fontWeight:600},children:["Add as Track",B?"s":""]}),s.jsxs("button",{onClick:Fe,style:{background:"#1976d2",border:"none",borderRadius:4,color:"#fff",padding:"5px 16px",cursor:"pointer",fontSize:12,fontWeight:600},children:["Add as Chromosome",B?"s":""]})]})]})})})(),M&&s.jsx("div",{style:{position:"fixed",inset:0,background:"rgba(0,0,0,0.45)",display:"flex",alignItems:"center",justifyContent:"center",zIndex:9999},children:s.jsxs("div",{style:{background:e.panelBg,border:`1px solid ${e.borderAccent}`,borderRadius:8,padding:"20px 24px",maxWidth:480,width:"90%",boxShadow:"0 8px 32px rgba(0,0,0,0.5)"},onClick:B=>B.stopPropagation(),children:[s.jsx("div",{style:{fontSize:14,fontWeight:700,color:e.textPrimary,marginBottom:8},children:"Track compatibility warning"}),s.jsxs("div",{style:{fontSize:12,color:e.textSecondary,lineHeight:1.6,marginBottom:16},children:[M.tracks.map(B=>{var q;return s.jsxs("div",{style:{marginBottom:6},children:[s.jsx("strong",{style:{color:e.textPrimary},children:B.name})," — ",((q=B.compatibility)==null?void 0:q.message)||"Possible mismatch with loaded genome"]},B.id)}),s.jsx("div",{style:{marginTop:8},children:M.tracks.length>1?"These tracks may not match the loaded genome.":"This track may not match the loaded genome."})]}),s.jsxs("div",{style:{display:"flex",gap:8,justifyContent:"flex-end",flexWrap:"wrap"},children:[s.jsx("button",{onClick:me,style:{background:e.btnBg,border:`1px solid ${e.borderStrong}`,borderRadius:4,color:e.btnText,padding:"5px 16px",cursor:"pointer",fontSize:12,fontWeight:600},children:"Skip"}),s.jsx("button",{onClick:gt,style:{background:"#1976d2",border:"none",borderRadius:4,color:"#fff",padding:"5px 16px",cursor:"pointer",fontSize:12,fontWeight:600},children:"Load Anyway"})]})]})}),L&&s.jsx("div",{style:{position:"fixed",inset:0,zIndex:9998,background:"rgba(0,0,0,0.45)",display:"flex",alignItems:"center",justifyContent:"center",pointerEvents:"none"},children:s.jsxs("div",{style:{border:`3px dashed ${e.textSecondary}`,borderRadius:16,padding:"40px 60px",textAlign:"center"},children:[s.jsx("div",{style:{fontSize:28,fontWeight:300,color:e.textPrimary,marginBottom:8},children:"Drop files here"}),s.jsx("div",{style:{fontSize:13,color:e.textSecondary},children:"Genome (.gb, .fasta) or track files (.bam, .bw, .wig, .vcf, .bed, .gff, .gtf)"})]})}),D&&s.jsx("div",{style:{position:"fixed",bottom:20,left:"50%",transform:"translateX(-50%)",zIndex:10001,padding:"8px 20px",borderRadius:6,background:D.error?"#c62828":e.panelBg,border:`1px solid ${D.error?"#e53935":e.borderAccent}`,color:D.error?"#fff":"#81c784",fontSize:12,fontWeight:600,boxShadow:"0 4px 16px rgba(0,0,0,0.5)"},children:D.error||D.msg}),t&&s.jsx(Zy,{labelWidth:H})]})}function rx(){return s.jsx(N0,{children:s.jsx(tg,{children:s.jsx(A0,{children:s.jsx(nx,{})})})})}Fi.createRoot(document.getElementById("root")).render(s.jsx(Us.StrictMode,{children:s.jsx(rx,{})}));
@@ -10,7 +10,7 @@
10
10
  body { font-family: Arial, Helvetica, sans-serif; background: #1a1a1a; color: #e0e0e0; height: 100vh; overflow: hidden; }
11
11
  #root { height: 100vh; display: flex; flex-direction: column; }
12
12
  </style>
13
- <script type="module" crossorigin src="/assets/index-LIiETdAH.js"></script>
13
+ <script type="module" crossorigin src="/assets/index-r8ddmuu9.js"></script>
14
14
  </head>
15
15
  <body>
16
16
  <div id="root"></div>
@@ -25,7 +25,7 @@ def _validate_region(start: int, end: int):
25
25
 
26
26
 
27
27
  @router.get("/{track_id}/coverage")
28
- def get_coverage(track_id: str, chrom: str, start: int, end: int, bins: int = Query(default=1000, le=5000)):
28
+ def get_coverage(track_id: str, chrom: str, start: int, end: int, bins: int = Query(default=1000, ge=1, le=10000)):
29
29
  _validate_region(start, end)
30
30
  reader = _get_reader(track_id)
31
31
  track_type = app_state.tracks[track_id]["track_type"]
@@ -24,7 +24,7 @@ from api.genome import router as genome_router
24
24
  from api.tracks import router as tracks_router
25
25
  from api.data import router as data_router
26
26
 
27
- app = FastAPI(title="BiNgo Genome Viewer API", version="2.3.2")
27
+ app = FastAPI(title="BiNgo Genome Viewer API", version="2.3.3")
28
28
 
29
29
  app.add_middleware(
30
30
  CORSMiddleware,
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
4
4
 
5
5
  [project]
6
6
  name = "BiNgoViewer"
7
- version = "2.3.2"
7
+ version = "2.3.3"
8
8
  description = "BiNgo Genome Viewer — a lightweight browser-based genomics viewer"
9
9
  readme = "README.md"
10
10
  license = {text = "Proprietary"}
File without changes
File without changes