UNPKG

@animech-public/playcanvas

Version:
2 lines (1 loc) 3.62 kB
import{Quat as t}from"../../core/math/quat.js";import{Vec3 as e}from"../../core/math/vec3.js";import{Vec4 as a}from"../../core/math/vec4.js";import{GSplatData as s}from"./gsplat-data.js";const n=.28209479177387814;class r{constructor(t,e,a,s,n,r){const c=(t,e)=>{const a=(1<<e)-1;return(t&a)/a},o=(t,e)=>{t.x=c(e>>>21,11),t.y=c(e>>>11,10),t.z=c(e,11)},h=(t,e,a)=>t===e?t:t*(1-a)+e*a,{chunkData:i,chunkSize:l,vertexData:u,shData:m,shBands:_}=t,f=[3,8,15][_-1];this.read=t=>{const x=Math.floor(t/256)*l;var p,y;if(e&&(o(e,u[4*t+0]),e.x=h(i[x+0],i[x+3],e.x),e.y=h(i[x+1],i[x+4],e.y),e.z=h(i[x+2],i[x+5],e.z)),a&&((t,e)=>{const a=1/(.5*Math.sqrt(2)),s=(c(e>>>20,10)-.5)*a,n=(c(e>>>10,10)-.5)*a,r=(c(e,10)-.5)*a,o=Math.sqrt(1-(s*s+n*n+r*r));switch(e>>>30){case 0:t.set(s,n,r,o);break;case 1:t.set(o,n,r,s);break;case 2:t.set(n,o,r,s);break;case 3:t.set(n,r,o,s)}})(a,u[4*t+1]),s&&(o(s,u[4*t+2]),s.x=h(i[x+6],i[x+9],s.x),s.y=h(i[x+7],i[x+10],s.y),s.z=h(i[x+8],i[x+11],s.z)),n&&(p=n,y=u[4*t+3],p.x=c(y>>>24,8),p.y=c(y>>>16,8),p.z=c(y>>>8,8),p.w=c(y,8),l>12&&(n.x=h(i[x+12],i[x+15],n.x),n.y=h(i[x+13],i[x+16],n.y),n.z=h(i[x+14],i[x+17],n.z))),r&&_>0)for(let e=0;e<3;++e)for(let a=0;a<15;++a)r[15*e+a]=a<f?m[(3*t+e)*f+a]*(8/255)-4:0}}}class c{constructor(){this.numSplats=void 0,this.chunkData=void 0,this.vertexData=void 0,this.shData=void 0}createIter(t,e,a,s,n){return new r(this,t,e,a,s,n)}calcAabb(t){const{chunkData:e,numChunks:a,chunkSize:s}=this;let n=Math.exp(Math.max(e[9],e[10],e[11])),r=e[0]-n,c=e[1]-n,o=e[2]-n,h=e[3]+n,i=e[4]+n,l=e[5]+n;for(let t=1;t<a;++t){const a=t*s;n=Math.exp(Math.max(e[a+9],e[a+10],e[a+11])),r=Math.min(r,e[a+0]-n),c=Math.min(c,e[a+1]-n),o=Math.min(o,e[a+2]-n),h=Math.max(h,e[a+3]+n),i=Math.max(i,e[a+4]+n),l=Math.max(l,e[a+5]+n)}return t.center.set(.5*(r+h),.5*(c+i),.5*(o+l)),t.halfExtents.set(.5*(h-r),.5*(i-c),.5*(l-o)),!0}getCenters(t){const{vertexData:e,chunkData:a,numChunks:s,chunkSize:n}=this;let r,c,o,h,i,l;for(let u=0;u<s;++u){const s=u*n;r=a[s+0],c=a[s+1],o=a[s+2],h=a[s+3],i=a[s+4],l=a[s+5];const m=Math.min(this.numSplats,256*(u+1));for(let a=256*u;a<m;++a){const s=e[4*a],n=(s>>>21)/2047,u=(s>>>11&1023)/1023,m=(2047&s)/2047;t[3*a+0]=(1-n)*r+n*h,t[3*a+1]=(1-u)*c+u*i,t[3*a+2]=(1-m)*o+m*l}}}calcFocalPoint(t){const{chunkData:e,numChunks:a,chunkSize:s}=this;t.x=0,t.y=0,t.z=0;for(let n=0;n<a;++n){const a=n*s;t.x+=e[a+0]+e[a+3],t.y+=e[a+1]+e[a+4],t.z+=e[a+2]+e[a+5]}t.mulScalar(.5/a)}get isCompressed(){return!0}get numChunks(){return Math.ceil(this.numSplats/256)}get chunkSize(){return this.chunkData.length/this.numChunks}get shBands(){var t,e;return null!=(t={3:1,8:2,15:3}[(null==(e=this.shData)?void 0:e.length)/this.numSplats/3])?t:0}decompress(){const r=["x","y","z","f_dc_0","f_dc_1","f_dc_2","opacity","rot_0","rot_1","rot_2","rot_3","scale_0","scale_1","scale_2"],{shBands:c}=this;if(c>0){const t=[];for(let e=0;e<45;++e)t.push(`f_rest_${e}`);r.splice(r.indexOf("f_dc_0")+1,0,...t)}const o={};r.forEach((t=>{o[t]=new Float32Array(this.numSplats)}));const h=new e,i=new t,l=new e,u=new a,m=c>0?new Float32Array(45):null,_=this.createIter(h,i,l,u,m);for(let t=0;t<this.numSplats;++t)if(_.read(t),o.x[t]=h.x,o.y[t]=h.y,o.z[t]=h.z,o.rot_1[t]=i.x,o.rot_2[t]=i.y,o.rot_3[t]=i.z,o.rot_0[t]=i.w,o.scale_0[t]=l.x,o.scale_1[t]=l.y,o.scale_2[t]=l.z,o.f_dc_0[t]=(u.x-.5)/n,o.f_dc_1[t]=(u.y-.5)/n,o.f_dc_2[t]=(u.z-.5)/n,o.opacity[t]=u.w<=0?-40:u.w>=1?40:-Math.log(1/u.w-1),m)for(let e=0;e<45;++e)o[`f_rest_${e}`][t]=m[e];return new s([{name:"vertex",count:this.numSplats,properties:r.map((t=>({name:t,type:"float",byteSize:4,storage:o[t]})))}])}}export{c as GSplatCompressedData};