memoscan
← all memos

Memo 0x3b9f9a24…ad2627 on Ethereum

xlbmd0aDpsfSl9aS5zb3J0KCgoZSx0KT0+ZS5kaXN0YW5jZS10LmRpc3RhbmNlKSksZi5wdXNoKHtwb2ludDp0LHNlZ21lbnRzQnlEaXN0YW5jZTppfSl9bGV0IHg9Zi5yZWR1Y2UoKChlLHQpPT5sKGUsdC5zZWdtZW50c0J5RGlzdGFuY2VbMF0uZGlzdGFuY2UpKSwwKTtmb3IobGV0IHQ9MDt0PGYubGVuZ3RoO3QrKyl7bGV0e3BvaW50OnMsc2VnbWVudHNCeURpc3RhbmNlOnJ9PWZbdF0sbz1yWzBdLGw9clsxXTtpZih2LmJvb2woKHk9TyhvLmRpc3RhbmNlLDAseCpwLC4xLC41KSkqeSp5KjEwMCkpY29udGludWU7bGV0IGg9by5zZWdtZW50Lm1hcCgoZT0+bmV3IEQoLi4uZSkpKSxhPWwuc2VnbWVudC5tYXAoKGU9Pm5ldyBEKC4uLmUpKSksYz1oWzBdLmxlcnAoaFsxXSwuNSkuYW5nbGVUbyhhWzBdLmxlcnAoYVsxXSwuNSkpLGQ9aFswXS5hbmdsZVRvKGhbMV0pLGc9TyhvLmRpc3RhbmNlLDAseCwwLC4yKSxtPUMoZCxjLGcpO20rPWFlKHMucG9pbnQueCxzLnBvaW50LnksMWUzLDEwLC0uMSwuMSkqTyhvLmRpc3RhbmNlLDAseCwxLDQpO2xldCB3PXYubnVtKHUvMTAsdS81KS8yLGI9ZSh3LzIpLE09dy9iLFA9W3MucG9pbnQudG9BcnJheSgpXTtmb3IobGV0IGU9MDtlPGI7ZSsrKXtsZXQgdD1uKG0pKk0qZSxyPWkobSkqTSplLG89cy5wb2ludC54K3QsbD1zLnBvaW50LnkrcjtQLnB1c2goW28sbF0pO2xldCBoPXMucG9pbnQueC10LGE9cy5wb2ludC55LXI7UC51bnNoaWZ0KFtoLGFdKX1QLmxlbmd0aD4yJiYoeWllbGQgUCl9dmFyIHl9KHIpO2JyZWFrO2Nhc2UiYm5ub2lzZSI6Zz1mdW5jdGlvbiooZSl7aWYoImJubm9pc2UiIT09ZS52ZWN0b3JGaWVsZFR5cGUpcmV0dXJuO2NvbnN0e2JvdW5kczp0LGJvdW5kaW5nR2VvbWV0cnk6aX09ZTtsZXQgbj17d2FycFN0cmVuZ3RoOmUudmVjdG9yRmllbGROb2lzZVByb3BzLndhcnBTdHJlbmd0aCxtaW5EaXN0OjIwKmUubWluRGlzdGFuY2UsbWF4RGlzdDoyMCplLm1pbkRpc3RhbmNlfSxzPVtdO2ZvcihsZXQgZSBvZiBQZSh7Ym91bmRzOnQsYm91bmRpbmdHZW9tZXRyeTppLGJsdWVOb2lzZVByb3BzOm59KSllLmNvbXBsZXRlJiYocz1lLnBvaW50cyk7Y29uc3R7d2FycFN0cmVuZ3RoOnIscm90YXRpb25BbmdsZUFkZGl0aW9uOm8sd29iYmxlT2Zmc2V0Omx9PWUudmVjdG9yRmllbGROb2lzZVByb3BzO2xldCBoPWJlKHIsbyxsLDApO2NvbnN0IGE9aGUoey4uLmUsdmVjdG9yRmllbGQ6aCxzZWVkUG9pbnRzOnMubWFwKChlPT5lLnBvaW50LnRvQXJyYXkoKSkpLHJhbmRvbTp2fSk7Zm9yKGxldCBlIG9mIGEpeWllbGQgZX0ocik7YnJlYWs7Y2FzZSJvdXRsaW5lIjpnPWZ1bmN0aW9uKihlKXtsZXQgdD13ZShlLDApO3lpZWxkIHR9KHIpO2JyZWFrO2RlZmF1bHQ6dGhyb3cgRXJyb3IoIkludmFsaWQgZmllbGQgdHlwZSIpfWZvcihsZXQgZSBvZiBnKXtpZighZXx8ZS5sZW5ndGg8Miljb250aW51ZTtpZigib3V0bGluZSI9PT10KXtwb3N0TWVzc2FnZSh7cmVzdWx0OltlXSxkb25lOiExLGVycm9yOm51bGwsd29ya2VySWQ6ZH0pO2JyZWFrfWxldCBpPW1lKGUpO2lmKHIucG9zdFByb2Nlc3NpbmdBcmdzKXtpPXZlKGkscik7bGV0IGU9ZihpKTtpZighZS5sZW5ndGgpY29udGludWU7ZT1lLm1hcCgoZT0+TWUoZSxyKSkpLmZpbHRlcigoZT0+ZS5sZW5ndGg+PTIpKSx1LnB1c2goLi4uZSkscCgpfWVsc2UgdS5wdXNoKGkpLHAoKX1pZigib3V0bGluZSIhPT10JiZyLmFkZE91dGxpbmUmJiFyLmluc2V0RnJvbUdlb21ldHJ5JiZyLmJvdW5kaW5nR2VvbWV0cnkpe2xldCBlPXdlKHIpO3UucHVzaChlKX1wKCEwKX1jYXRjaChlKXtwb3N0TWVzc2FnZSh7cmVzdWx0Om51bGwsZXJyb3I6ZS5tZXNzYWdlLHdvcmtlcklkOmR9KX19fSgpOwovLyMgc291cmNlTWFwcGluZ1VSTD1zdHJlYW1saW5lcy53b3JrZXIuanMubWFwCgo=");const Li=navigator.hardwareConcurrency||4,Si=[],Xi={},Ci={},Vi=[],wi={};for(let e=0;e<Li;e++){const t=new vi;Si.push(t),wi[e]=!0,Ci[e]=[],t.onmessage=function(e){const{result:t,done:n,error:i,workerId:l}=e.data;if(t?.length>0&&Ci[l].push(...t),n||i){const e=Xi[l];if(i?e.reject(i):e.resolve(Ci[l]),delete Xi[l],wi[l]=!0,Ci[l]=[],Vi.length>0){const e=Vi.shift();e.data.workerId=l,Ki(l,e)}}}}function Ki(e,t){const n=Si[e];wi[e]=!1,Xi[e]=t,n.postMessage(t.data)}async function Ri(e){return new Promise(((t,n)=>{const i={data:e,resolve:t,reject:n};Vi.push(i),function(){for(let e=0;e<Si.length&&0!==Vi.length;e++)if(wi[e]){const t=Vi.shift();t.data.workerId=e,Ki(e,t)}}()}))}let ki=[],Ti=(e,{isInDominantPoly:t,normal:n,isOverlay:i=!1,isInCurveOrObject:l=!1})=>{const a=[{condition:i,key:Ge.overlay},{condition:!0,key:Ge.override},{condition:t,key:Ge.dominant},{condition:!t,key:Ge.nonDominant},{condition:n>Ke.default,key:Ge.normalHigh},{condition:n<Ke.default,key:Ge.normalLow},{condition:l,key:Ge.inCurveOrObject},{condition:!l,key:Ge.notInCurveOrObject}].filter((({key:t})=>e.spatialOverride?.[t]));for(const{condition:t,key:n}of a)if(t&&e.spatialOverride[n])return ge(e,e.spatialOverride[n]);return e},Mi=(e,t)=>e?.layerOverride?.[t]?ge(e,e.layerOverride[t]):e,zi=({random:e,type:t="noise",direction:n=e.num(0,360),objAABB:i,addOutline:l=!1,boundingGeometry:a,insetFromGeometry:s,insetFromGeometryDistance:c={min:2,max:4},lineWeight:d,scribble:u=!1,scribbleStrength:h=0,maxLength:m=1e10,minDistance:p=r(.2,.75*d),minLength:g=2*p,wobbleAmplitude:b=e.easedNum($n,.5,2),wobbleFreq:f=e.easedNum($n,10*d,20*d),streamLineProps:x})=>{const Z={stepSize:o(p/2,1),maxLength:m,minLength:g,insetFromGeometry:s,addOutline:l,insetFromGeometryDistance:c,minDistance:p,bounds:{topLeft:[i.minX,i.minY],bottomRight:[i.maxX,i.maxY]},postProcessingArgs:{directional:!0,scribbleStrength:u?h:0,wobbleFreq:f,wobbleAmplitude:d*b}};switch(t){case"noise":case"bnnoise":return{...Z,vectorFieldType:t,boundingGeometry:a,vectorFieldNoiseProps:{...x,wobbleDetail:e.num(1,2)}};case"outline":return{...Z,vectorFieldType:t,boundingGeometry:a};case"directional":return{...Z,vectorFieldType:t,boundingGeometry:a,vectorFieldDirectionalProps:{direction:n}};case"wobbles":return{...Z,vectorFieldType:"wobbles",boundingGeometry:a,blueNoiseProps:{warpStrength:1e3,minDist:1*p,maxDist:1.5*p},wobbleProps:{tension:{min:.5,max:3},maxPointUse:1,maxDivergence:4,maxLinePoints:30}};case"bluenoise":return{...Z,vectorFieldType:t,boundingGeometry:a,vectorFieldNoiseProps:{...x,wobbleDetail:1},blueNoiseProps:{warpStrength:100,minDist:p+d,maxDist:4*(p+d)}};case"edgefill":return{...Z,vectorFieldType:t,boundingGeometry:a,blueNoiseProps:{warpStrength:100,minDist:2*(p+d),maxDist:2.2*(p+d)}}}},Yi=(e,t,n=[],i)=>{if(n.length){let e=n[0],t=i.int(0,e.verts.length-1),l=(t+1)%e.verts.length;return new zt(...e.verts[t]).angleTo(new zt(...e.verts[l]))}let l=Zl.getLinesIntersectingFace(e,!1),a=e.center,s=new Set([...t].map((e=>e.meta.lineCategory))),o=[be.horizontal,be.vertical,be.perspective,be.objects].filter((e=>!s.has(e))),r=l.filter((e=>!t.has(e.constructionLine)&&o.some((t=>t==e.constructionLine.meta.lineCategory))));if(r.length){let e=r.reduce(((e,t)=>fn(a.toArray(),e.constructionLine.line)<fn(a.toArray(),t.constructionLine.line)?e:t),r[0]);t.add(e.constructionLine);let n=e.constructionLine.line.map((e=>new zt(...e)));return n[0].angleTo(n[n.length-1])}},Pi=(e,t)=>{let{fade:n,scale:i}=e;return{fade:{in:{enabled:t.bool(n.in.enabledChance),length:t.num(n.in.min,n.in.max)},out:{enabled:t.bool(n.out.enabledChance),length:t.num(n.out.min,n.out.max)}},scale:{in:{enabled:t.bool(i.in.enabledChance),length:t.num(i.in.min,i.in.max)},out:{enabled:t.bool(i.out.enabledChance),length:t.num(i.out.min,i.out.max)}}}};async function Ii(e,t){let{colorOverride:n}=e?.detailObjectProps||{};const i=new A(e?.detailObjectProps?.noiseSeedOverride||t),l=new nn;l.expands(e.polygon),l.expandByValue(10);const a=e.faceRef?.center||l.center,s=e?.detailObjectProps?.inDominantShapes||[],o=e?.detailObjectProps?.inObject||[],d=s.length>0,u=!!e?.isInCurve,h=!!e?.detailObjectProps?.inObject?.length,m=e?.detailObjectProps?.isFineDetail,p=Rt(e.lightingIntensity||Ke.default,Ke.clamp),{skipFill:g,skipDetails:b}=e.detailObjectProps||{};let f=Ti(Pe,{isInDominantPoly:m||d,normal:p,isOverlay:e.category==sn.overlay,isInCurveOrObject:h||u}),x=Ti(Ye,{isInDominantPoly:m||d,normal:p,isOverlay:e.category==sn.overlay,isInCurveOrObject:h||u});const Z=!g&&i.bool(f.fillChance),y=!b&&i.bool(x.fillChance),G=i.bool(f.insetChance),W=i.bool(x.insetChance),v=Z?i.weightedChoice(...f.layerCountChances):0,L=u?0:y?i.weightedChoice(...x.layerCountChances):0;let S=new Set,X=new Set,C=new Set,V=[],w=[],K=!1;function R(t,i,c){const h=[];for(let g=0;g<c;g++){const c=Mi("fill"===i?f:x,g);let b,Z=t.num(c.lineWeight.min,c.lineWeight.max),y=t.num(c.linePressure.min,c.linePressure.max);b=r(.4,Z*t.num(c.minDistanceMult.min,c.minDistanceMult.max)),m&&"detail"===i&&(Z*=.75,b*=.25);const v="fill"===i?ki.filter((e=>!S.has(e))):ki.filter((e=>!X.has(e)));let L,R=t.choice(v);v.length||("fill"===i?S.clear():X.clear(),R=t.choice(ki)),"fill"===i?S.add(R):X.add(R),d&&("fill"===i&&G||"detail"===i&&W)&&(L=u?e.isInCurve.line:s[0].face.vertexlist.map((e=>e.toArray())));let k=c.colorMap[g]||c.colorMap[0],T=t.weightedChoice(...k),M=hi(t,T,a,p,c.colorPalette,"fill"==i?V:w),z=null;if(t.bool(c.fadeAtLineSegmentChance)){let n,i,a=t.int(0,l.vertexList.length-1),s=[l.vertexList[a],l.vertexList[(a+1)%l.vertexList.length]],o=s[0].lerp(s[1],t.num(.01,.99));for(let t=0;t<e.polygon.length;t++){let n=[e.polygon[t],e.polygon[(t+1)%e.polygon.length]],l=xn(o.toArray(),n[0].toArray(),n[1].toArray());(!i||l<i.dist)&&(i={seg:n,dist:l})}n=i.seg;const{fadeAtLineSegmentDistanceMult:r,fadeAtLineSegmentStrengthMult:d}=c;let u=l.center.distanceTo(n[0].lerp(n[1],.5));z={segment:n,distance:2*u*t.num(r.min,r.max),strength:t.num(d.min,d.max)}}let Y=t.weightedChoice(...c.styleChances),P=0;"directional"===Y&&(P=Yi(e.faceRef,C,o,t));let I,H,F="fill"==i&&u&&(K||0==g&&t.bool(Ue.renderLightChance));K=F,"fill"===i?(n?M=n:F&&(M=hi(t,ye.lightestOrDarkestBasedOnBg,a,p,c.colorPalette,V)),V.push(M)):"detail"==i&&w.push(M);const N=t.bool(c.ignoreLightingChance);I=!(u&&Ue.ignoreLighting||N),H=!!(u&&Ue.ignoreLighting||N),h.push({paintLineObj:{colorLayerType:T,lineBrightness:I?Tt(p,Ke.min,Ke.max,wt(Ke.default,Ke.min,Ke.influencesBrightnessMult),wt(Ke.default,Ke.max,Ke.influencesBrightnessMult)):Ke.default,type:i,lines:[],closedPolyOrLine:!1,noiseOffset:[t.num(-1,1),t.num(-1,1)],canBulge:!0,isShading:!0,canWarp:!0,fadeAtLineSegment:z,lineTapering:Pi("bluenoise"==Y&&"detail"==i?{fade:{in:{enabledChance:0,min:1,max:1},out:{enabledChance:0,min:4,max:6}},scale:{in:{enabledChance:100,min:.5,max:.8},out:{enabledChance:100,min:.5,max:.8}}}:c.lineTapering,t),disableSaturationShift:H,linePressure:y*Tt(p,Ke.max,Ke.min,Tt(Ke.influencesPressureMult,1,0,.5,1),1),edgeSharpness:t.num(c.edgeSharpness.min,c.edgeSharpness.max),accumulationStrength:t.num(c.accumulationStrength.min,c.accumulationStrength.max),materialHardness:t.num(c.materialHardness.min,c.materialHardness.max),lineWeight:.8*Z,lineColor:M},workerData:{streamlineWorkerProps:zi({type:Y,direction:P,addOutline:"edgefill"==Y,scribble:d?!u&&t.bool(c.scribbleChance):t.bool(c.scribbleChance),scribbleStrength:t.num(c.scribbleStrength.min,c.scribbleStrength.max),random:t,insetFromGeometry:L,insetFromGeometryDistance:{min:c.insetDistance.min,max:c.insetDistance.max},objAABB:l,boundingGeometry:e.polygon.map((e=>e.toArray())),lineWeight:Z,minDistance:"bluenoise"==Y&&"detail"==i?.4*b:r(.4,"fill"==i?b*Kt(p,Ke.max,Ke.min,Kt(Ke.influencesMinDistanceMult,1,0,1,1),Kt(Ke.influencesMinDistanceMult,0,1,1,.5)):b),maxLength:c.maxLength?t.num(c.maxLength.min,c.maxLength.max):1e10,wobbleAmplitude:t.easedNum($n,c.wobbleAmplitude.min,c.wobbleAmplitude.max),wobbleFreq:t.easedNum($n,c.wobbleFreq.min,c.wobbleFreq.max),streamLineProps:{...R,wobbleDetail:t.int(1,2)}}),noiseSeed:un,randomSeed:E(t)}})}return h}const k=[...R(i,"fill",v),...R(i,"detail",L)],T=k.map((e=>Ri(e.workerData))),M=await Promise.all(T);e.allowExtraDetails=!1,k.filter((e=>"detail"==e.paintLineObj.type)).length>=2&&k.filter((e=>"detail"==e.paintLineObj.type)).every((e=>"directional"==e.workerData.streamlineWorkerProps.vectorFieldType))&&(e.allowExtraDetails=!0);for(let t=0;t<M.length;t++){const n=[],i=M[t],l=k[t].paintLineObj;"detail"==l.type&&"bluenoise"==k[t].workerData.streamlineWorkerProps.vectorFieldType&&(l.lineWeight*=1.5);for(let e of i){const t=e;t.length&&n.push(t)}n.length<1||(l.lines=n,e.detailObject=e.detailObject||[],e.detailObject.push(l))}if(e?.detailObject?.length){let t=[];for(let n=e.detailObject.length-1;n>0;n--){let i=e.detailObject[n-1],l=e.detailObject[n];l.colorLayerType===ye.previous&&i?.lines?.length&&l?.lines?.length&&(i.lines=[...i.lines,...l.lines],t.push(l))}t.length>0&&(e.detailObject=e.detailObject.filter((e=>!t.includes(e))))}e.allowExtraDetails&&e?.detailObject?.length&&!m&&i.bool(d?80:40)&&async function(e,t){let n=[...Wl,...an].filter((e=>e.category==sn.overlay));for(let t of n){let n=new nn;if(n.expands(t.polygon),e.faceRef.aabb.intersects(n))return}let i=e.detailObject.filter((e=>"detail"==e.type));const l=new nn;l.expands(e.polygon),l.expandByValue(10);const a=e.faceRef?.center||l.center;let s=new Ln([],[]);s.insertPolygon(e.polygon.map((e=>e.toArray())),!0);for(let e=0;e<i.length;e++){let t=i[e];for(let e of t.lines)s.insertPolygon(e,!1),await new Promise((e=>setTimeout(e,0)))}s.cleanupTrailingEdges();let o=s.internalFaces(),r=c(mn(a.x,a.y,100,5,40,100)),d=mn(a.x,a.y,600,0,100)>60;if(o.length>2)for(let n of o.filter((e=>e.area>100)))if(n.hedges.every((e=>e.face&&e.twin.face&&e.face!==e.twin.face))&&t.bool(r)){let i=t.num(.35,.45),l=n.vertexlist.map((e=>e.addPolar(e.angleTo(n.center),e.distanceTo(n.center)*i))),a={category:sn.detail,faceRef:n,polygon:l,detailObject:[],detailObjectProps:{isFineDetail:!0,skipDetails:!d,skipFill:!!d,inObject:e.detailObjectProps?.inObject,inDominantShapes:e.detailObjectProps?.inDominantShapes,noiseSeedOverride:E(t)}};Wl.push(a)}}(e,i),e.readyForRender=!0}let Hi,Fi,Ni=new Set;function Ui(e){let t,n=0;for(;!t&&n++<200;){let n=J.choice(e.internalFaces()),i=J.choice(n.vertexlist);Ni.has(i)||(t=i)}return t}class Di{dcel;maxAngle;pathVerts=[];AABB=new nn;constructor(e,t=.3){this.dcel=e,this.maxAngle=t}*findDominantPaths(e=!1){let t=new Set(this.dcel.hedges.filter((e=>e.face&&e.face.area>0&&e.twin.face&&e.twin.face.area>0&&e.origin!==e.twin.origin&&e.face!==e.twin.face)));for(;t.size>0;){let n=t.values().next().value;t.delete(n),t.delete(n.twin);let i=[n.twin.origin],l=[n.origin],a=new Set;a.add(n.origin),a.add(n.twin.origin);let o=0;for(let r of[n,n.twin]){let c=r.twin.origin,d=r===n?i:l,u=r.origin,h=u.angleTo(c);for(;;){const n=c.hedgelist.filter((t=>(!e||t.twin.face&&t.twin.face.area>0)&&t.face&&t.face.area>0&&!a.has(t.twin.origin)&&s(c.angleTo(t.twin.origin)-h)<this.maxAngle)).sort(((e,t)=>s(c.angleTo(e.twin.origin)-h)-s(c.angleTo(t.twin.origin)-h)));if(!n.length)break;let i=n[0];o+=s(c.angleTo(i.twin.origin)-h),t.delete(i),t.delete(i.twin),u=c,c=i.twin.origin,d.push(c),a.add(c),h=u.angleTo(c)}}l.reverse();let r=l.concat(i),c=r.reduce(((e,t,n)=>0===n?0:e+t.distanceTo(r[n-1])),0);yield{vertices:r,length:c,curviness:o/r.length}}}walk(e,t,n=!0){let i=e;if(!i)return;let l=0,a=0;this.AABB.expand(i);let s=new Set;for(s.add(i),Ni.add(i);l<=t&&a++<400;){const e=i.hedgelist.filter((e=>!s.has(e.twin.origin)&&!Ni.has(e.twin.origin)));if(e.sort(((e,t)=>{let n=e.twin.origin,i=t.twin.origin,l=this.AABB.center.distanceTo(n);return this.AABB.center.distanceTo(i)-l})),0===e.length)break;let a=e[0].twin.origin;if(l+=i.distanceTo(a),n&&l>t){let e=(o=i,r=a,c=1-(l-t)/i.distanceTo(a),new zt(wt(o.x,r.x,c),wt(o.y,r.y,c)));s.add(e),this.AABB.expand(e);break}s.add(a),Ni.add(a),this.AABB.expand(a),i=a}var o,r,c;this.pathVerts.push(...Array.from(s))}}class Oi{heap;maxSize;valueFunction;epsilon=b;constructor(e,t){this.valueFunction=t,this.heap=[],this.maxSize=e}size(){return this.heap.length}push(e){this.heap.push(e),this.siftUp(this.heap.length-1),this.heap.length>this.maxSize&&this.heap.pop()}clear(){this.heap=[]}peek(){return this.heap[0]}remove(e){const t=this.heap.findIndex((t=>t===e));-1!==t&&(this.heap[t]=this.heap[this.heap.length-1],this.heap.pop(),t<this.heap.length&&this.siftDown(t))}replaceTop(e){this.heap[0]=e,this.siftDown(0)}toArray(){return[...this.heap]}siftUp(e){for(;e>0;){const t=Math.floor((e-1)/2),n=this.valueFunction(this.heap[e])-this.valueFunction(this.heap[t]);if(n<this.epsilon&&n>-this.epsilon)break;if(n<=0)break;[this.heap[e],this.heap[t]]=[this.heap[t],this.heap[e]],e=t}}siftDown(e){const t=this.heap.length;for(;;){let n=e;const i=2*e+1,l=2*e+2,a=this.valueFunction(this.heap[n]);if(i<t&&this.valueFunction(this.heap[i])-a>this.epsilon&&(n=i),l<t){const e=this.valueFunction(this.heap[n]);this.valueFunction(this.heap[l])-e>this.epsilon&&(n=l)}if(n===e)break;[this.heap[e],this.heap[n]]=[this.heap[n],this.heap[e]],e=n}}}class Bi{position;rotation;dimensions;numSides;cameraPos;fov;aspect;near;far;lights;cullBackfaces;localVertices=[];worldVertices=[];screenVertices=[];constructor(e,t,n,i,l,a=90,s=Y/P,o=.1,r=1e4,c=[],d=!1){this.position=e,this.rotation=t,this.dimensions=n,this.numSides=i,this.cameraPos=l,this.fov=a,this.aspect=s,this.near=o,this.far=r,this.lights=c,this.cullBackfaces=d,this._buildLocalGeometry()}_buildLocalGeometry(){const{width:e,height:t,depth:n}=this.dimensions,i=e/2,l=t/2,a=n/2,s=2*Math.PI/this.numSides,o=this.numSides%2==0?-Math.PI/this.numSides:-Math.PI/2;if(0===n)for(let e=0;e<this.numSides;e++){const t=o+s*e,n=Math.cos(t)*i,a=Math.sin(t)*l;this.localVertices.push({x:n,y:a,z:0})}else for(let e=0;e<this.numSides;e++){const t=o+s*e,n=Math.cos(t),r=Math.sin(t);this.localVertices.push({x:n*i,y:r*l,z:+a}),this.localVertices.push({x:n*i,y:r*l,z:-a})}}getFaces2D(){const e=function(e,t,n,i,l,a){const s=Ji(e*Math.PI/180),o=ji(t*Math.PI/180),r=Ai(n*Math.PI/180),c=Ei(i,l,a),d=_i(r,_i(o,s));return _i(c,d)}(this.rotation.x,this.rotation.y,this.rotation.z,this.position.x,this.position.y,this.position.z),t=Ei(-this.cameraPos.x,-this.cameraPos.y,-this.cameraPos.z),n=_i(function(e,t,n,i){const l=1/Math.tan(e*Math.PI/180/2),a=1/(n-i);return[[l/t,0,0,0],[0,l,0,0],[0,0,(n+i)*a,n*i*a*2],[0,0,-1,0]]}(this.fov,this.aspect,this.near,this.far),_i(t,e));this.worldVertices=[],this.screenVertices=[];for(const t of this.localVertices){const i=qi(e,[t.x,t.y,t.z,1]);this.worldVertices.push({x:i[0],y:i[1],z:i[2]});const l=qi(n,[t.x,t.y,t.z,1]);0!==l[3]&&(l[0]/=l[3],l[1]/=l[3],l[2]/=l[3]);const a=(.5*l[0]+.5)*Y,s=(1-(.5*l[1]+.5))*P;this.screenVertices.push([a,s])}const i=this._buildFaces(),l=this.cameraPos.x,a=this.cameraPos.y,s=this.cameraPos.z,o=[];for(let e of i){const t=e.indices.map((e=>this.worldVertices[e])),n=e.indices.map((e=>this.screenVertices[e])),i=$i(t),r=el(t),c=tl(i,r,this.lights);if(this.cullBackfaces){const e={x:r.x-l,y:r.y-a,z:r.z-s};i[0]*e.x+i[1]*e.y+i[2]*e.z<0&&o.push({vertices:n,normal:i,lighting:c})}else o.push({vertices:n,normal:i,lighting:c})}return o}_buildFaces(){const e=[],t=this.numSides;if(0!==this.dimensions.depth){const n=[];for(let e=0;e<t;e++)n.push(2*e);e.push({indices:n});const i=[];for(let e=t-1;e>=0;e--)i.push(2*e+1);e.push({indices:i});for(let n=0;n<t;n++){const i=(n+1)%t,l=[2*n,2*n+1,2*i+1,2*i];e.push({indices:l})}}else e.push({indices:Array.from({length:t},((e,t)=>t))});return e}}class Qi{vertices;rotation;perspective;zShift;transformOrigin;projectedVertices;vertices3D;constructor(e,t,n=800,i=-50,l={x:Y/2,y:P/2}){this.vertices=e,this.rotation=t,this.perspective=n,this.zShift=i,this.transformOrigin=l}getLineSegments(){let e=new nn;for(let t of this.vertices)e.expands(t.map((e=>new zt(...e))));const{x:t,y:n,z:i}={...e.center,z:this.zShift},{x:l,y:a,z:s}=this.rotation,o=this.perspective,r=e.center,c=this.vertices.map((e=>e.map((e=>new zt(...e).subtract(r)))));this.vertices3D=[];for(let e=0;e<c.length;e++){this.vertices3D.push([]);for(const t of c[e])this.vertices3D[e].push({x:t.x,y:t.y,z:0})}const d=function(e,t,n,i,l,a){const s=t*Math.PI/180,o=n*Math.PI/180,r=Ji(e*Math.PI/180),c=ji(s);let d=_i(Ai(o),_i(c,r));return _i(Ei(i,l,a),d)}(l,a,s,t,n,i),u=this.vertices3D.map((e=>e.map((e=>{const t=[e.x,e.y,e.z,1],n=qi(d,t);return{x:n[0],y:n[1],z:n[2]}}))));return this.projectedVertices=u.map((e=>e.map((e=>function(e,t,n={x:Y/2,y:P/2}){const{x:i,y:l,z:a}=e,s=i-n.x,o=(l-n.y)*t/(t+a);return t+a<=0?null:[s*t/(t+a)+n.x,o+n.y]}(e,o,this.transformOrigin))).filter((e=>null!==e)))).map((e=>e.filter((e=>e[0]>=-100&&e[0]<=Y+100&&e[1]>=-100&&e[1]<=P+100)))).filter((e=>e.length>0)),this.projectedVertices}}function Ji(e){const t=Math.cos(e),n=Math.sin(e);return[[1,0,0,0],[0,t,-n,0],[0,n,t,0],[0,0,0,1]]}function ji(e){const t=Math.cos(e),n=Math.sin(e);return[[t,0,n,0],[0,1,0,0],[-n,0,t,0],[0,0,0,1]]}function Ai(e){const t=Math.cos(e),n=Math.sin(e);return[[t,-n,0,0],[n,t,0,0],[0,0,1,0],[0,0,0,1]]}function Ei(e,t,n=0){return[[1,0,0,e],[0,1,0,t],[0,0,1,n],[0,0,0,1]]}function _i(e,t){const n=Array.from(Array(e.length),(()=>Array(t[0].length).fill(0)));for(let i=0;i<e.length;i++)for(let l=0;l<t[0].length;l++)for(let a=0;a<e[0].length;a++)n[i][l]+=e[i][a]*t[a][l];return n}function qi(e,t){const n=[];for(let i=0;i<e.length;i++){let l=0;for(let n=0;n<t.length;n++)l+=e[i][n]*t[n];n.push(l)}return n}function $i(e){const t=e[0],n=e[1],i=e[2],l=[n.x-t.x,n.y-t.y,n.z-t.z],a=[i.x-t.x,i.y-t.y,i.z-t.z],s=[l[1]*a[2]-l[2]*a[1],l[2]*a[0]-l[0]*a[2],l[0]*a[1]-l[1]*a[0]],o=Math.sqrt(s[0]**2+s[1]**2+s[2]**2);return s.map((e=>e/o))}function el(e){const t=e.reduce(((e,t)=>(e.x+=t.x,e.y+=t.y,e.z+=t.z,e)),{x:0,y:0,z:0}),n=e.length;return{x:t.x/n,y:t.y/n,z:t.z/n}}function tl(e,t,n){let i=0;for(const l of n){const n={x:l.position.x-t.x,y:l.position.y-t.y,z:l.position.z-t.z},a=Math.sqrt(n.x*n.x+n.y*n.y+n.z*n.z);if(0===a)continue;const s=n.x/a,o=n.y/a,r=n.z/a;i+=(e[0]*s+e[1]*o+e[2]*r)*l.brightness}return i}let nl=!1,il=0,ll=0;T();let al=T();const sl=()=>{if(!Vl[il])return void rl();const e=Vl[il][0](),t=Vl[il][1]||!1;let n,i=!1;const l=()=>{n=e.next(),$l?i=!1:(i=!0,n?.done||function(e){nl||(Hi=K.getParameter(K.MAX_CLIENT_WAIT_TIMEOUT_WEBGL),Fi=K.SYNC_FLUSH_COMMANDS_BIT,nl=!0);const t=K.fenceSync(K.SYNC_GPU_COMMANDS_COMPLETE,0);!function n(){const i=K.clientWaitSync(t,Fi,Hi);i===K.ALREADY_SIGNALED||i===K.CONDITION_SATISFIED||$l?(clearTimeout(void 0),K.deleteSync(t),e()):setTimeout(n,0)}()}(l))},a=()=>{const s=T();if(t)!i&&!$l&&l();else for(;T()-s<1e3/30&&!$l&&!n?.done;)n=e.next();ll++,n?.done?(ol("Step took"),Xt?.copyBufferToScreen(),i=!1,n=null,il++,sl()):(v(n.value||{showUpdate:!1}),setTimeout(a,0))};a()};function ol(e="",t=!1){T(),al=T()}const rl=()=>{document.complete=!0,An(mi([...oi][0],[...oi],oi.size)),ol("Total render time",!0),function(){for(let e=0;e<Si.length;e++){const t=Si[e];t&&t.terminate()}}()};function cl(e,t,n=4){const i=t/2,l=[];for(let t=0;t<e.length-1;t++){const[n,i]=e[t],[a,s]=e[t+1],o=a-n,r=s-i,c=Math.hypot(o,r);if(0===c){l.push([0,0]);continue}const d=-r/c,u=o/c;l.push([d,u])}const a=[],s=[];for(let t=0;t<e.length;t++){const[o,r]=e[t];if(0===t){const[e,t]=l[0],n=e*i,c=t*i;a.push([o+n,r+c]),s.push([o-n,r-c])}else if(t===e.length-1){const[e,t]=l[l.length-1],n=e*i,c=t*i;a.push([o+n,r+c]),s.push([o-n,r-c])}else{const[e,c]=l[t-1],[d,u]=l[t],h=Math.sqrt((e*d+c*u+1)/2);if(0===h){const t=e*i,n=c*i;a.push([o+t,r+n]),s.push([o-t,r-n]);continue}const m=i/h;if(m>n*i){const[t,n]=[e*i,c*i],[l,h]=[d*i,u*i];a.push([o+t,r+n]),a.push([o+l,r+h]),s.push([o-t,r-n]),s.push([o-l,r-h])}else{const[t,n]=[e+d,c+u],l=Math.hypot(t,n);if(0===l){const t=e*i,n=c*i;a.push([o+t,r+n]),s.push([o-t,r-n])}else{const[e,i]=[t/l,n/l],c=e*m,d=i*m;a.push([o+c,r+d]),s.push([o-c,r-d])}}}}return[...a.reverse(),...s]}class dl{root=null;epsilon=b;count=0;wasRemoved=!1;insert(e){this.root=this.insertRec(this.root,e,0),this.count++}compareCoord