/*
All material copyright Esri, All Rights Reserved, unless otherwise specified.
See https://js.arcgis.com/5.0/esri/copyright.txt for details.
*/
import"../../core/has.js";import"../../core/Logger.js";import{acosClamped as t}from"../../core/mathUtils.js";import{getEpsilon as e}from"../../core/libs/gl-matrix-2/math/common.js";import{fromRotation as r}from"../../core/libs/gl-matrix-2/math/mat4.js";import{d as s,E as i,s as n,e as o,j as c,b as a,i as h,f as u,p as m,B as l,l as d,c as g,D as f,n as p,h as M}from"../../chunks/vec32.js";import{fromValues as j,fromArray as y,clone as _,create as x}from"../../core/libs/gl-matrix-2/factories/vec3f64.js";import{fromValues as b}from"../../core/libs/gl-matrix-2/factories/vec4f64.js";import{isVec3 as v}from"../../core/libs/gl-matrix-2/types/vec3.js";import{isVec4 as S}from"../../core/libs/gl-matrix-2/types/vec4.js";import{fromPoints as P,closestPoint as A}from"./ray.js";import{cartesianToSpherical as R}from"./sphereUtils.js";import{angle as q}from"./vector.js";import{sv3d as F,sm4d as O}from"./vectorStacks.js";class w{constructor(t=0,e=0,r=0,s=0){this.radius=s,"number"==typeof t?this._center=j(t,e,r):v(t)||S(t)?(this._center=y(t),this.radius=4===t.length?t[3]:e):(this._center=_(t.center),this.radius=t.radius)}get isValid(){return this.radius>=0}invalidate(){this.radius=-1}get center(){return this._center}set center(t){s(this.center,t)}exactEquals(t){return i(this._center,t.center)&&this.radius===t.radius}copyFrom(t){return t!==this&&(s(this._center,t.center),this.radius=t.radius),this}clone(){return new w(this.center,this.radius)}toVec4(){return b(this.center[0],this.center[1],this.center[2],this.radius)}contains(t){return n(this.center,t)<=this.radius**2}intersectRay(t,e){if(null==t)return!1;if(!this._intersect(t,V))return!1;let{t0:r,t1:s}=V;if((r<0||s<r&&s>0)&&(r=s),r<0)return!1;if(e){const{origin:s,direction:i}=t;e[0]=s[0]+i[0]*r,e[1]=s[1]+i[1]*r,e[2]=s[2]+i[2]*r}return!0}intersectLine(t,r){const s=P(t,r);if(!this._intersect(s,V))return[];const{origin:i,direction:n}=s,{t0:o,t1:c}=V,a=t=>{const e=x();return g(e,i,n,t),this.projectPoint(e,e)};return Math.abs(o-c)<e()?[a(o)]:[a(o),a(c)]}_intersect(t,e){const{origin:r,direction:s}=t,i=k;i[0]=r[0]-this.center[0],i[1]=r[1]-this.center[1],i[2]=r[2]-this.center[2];const n=s[0]*s[0]+s[1]*s[1]+s[2]*s[2];if(0===n)return!1;const o=2*(s[0]*i[0]+s[1]*i[1]+s[2]*i[2]),c=o*o-4*n*(i[0]*i[0]+i[1]*i[1]+i[2]*i[2]-this.radius**2);if(c<0)return!1;const a=Math.sqrt(c);return e.t0=(-o-a)/(2*n),e.t1=(-o+a)/(2*n),!0}projectPoint(t,e){const r=o(F.get(),t,this.center),s=c(F.get(),r,this.radius/a(r));return h(e,s,this.center)}closestPointOnSilhouette(t,e){const s=F.get(),i=O.get();u(s,t.origin,t.direction),u(e,s,t.origin),c(e,e,1/a(e)*this.radius);const n=this._angleToSilhouette(t.origin),o=q(t.origin,e);return r(i,o+n,s),m(e,e,i),e}frustumCoverage(t,e,r){const s=this.radius,i=s*s,n=t+.5*Math.PI,o=e*e+i-2*Math.cos(n)*e*s,c=Math.sqrt(o),a=o-i;if(a<=0)return.5;const h=Math.sqrt(a),u=Math.acos(h/c)-Math.asin(s/(c/Math.sin(n)));return Math.min(1,(u+.5*r)/r)}_angleToSilhouette(e){const r=o(F.get(),e,this.center),s=a(r),i=this.radius,n=i+Math.abs(i-s);return t(i/n)}union(t){const e=l(this._center,t.center),r=this.radius,s=t.radius;return e+s<r?this:e+r<s?(this.copyFrom(t),this):(d(this._center,this._center,t.center,(e+s-r)/(2*e)),this.radius=(e+r+s)/2,this)}toJSON(){return{center:this.center,radius:this.radius}}}const E={create:t=>new w(t),copy:(t,e)=>e.copyFrom(t),setExtent:(t,e,r)=>r.copyFrom(t),getExtent:(t,e)=>e,elevate:(t,e,r)=>(r.copyFrom(t),r.radius+=e,r),axisAt(t,e,r,s){const i=o(C,e,t.center);switch(r){case 0:{const t=R(i,C)[2];return M(s,-Math.sin(t),Math.cos(t),0)}case 1:{const t=R(i,C),e=t[1],r=t[2],n=Math.sin(e);return M(s,-n*Math.cos(r),-n*Math.sin(r),Math.cos(e))}case 2:return p(s,i);default:return}},altitudeAt(t,e){const r=o(L,e,t.center);return a(r)-t.radius},setAltitudeAt(t,e,r,s){const i=E.altitudeAt(t,e),n=E.axisAt(t,e,2,L),o=c(L,n,r-i);return h(s,e,o)},intersectRay:(t,e,r)=>t.intersectRay(e,r),closestPoint:(t,e,r)=>t.intersectRay(e,r)?r:(A(e,t.center,r),t.projectPoint(r,r)),intersectRayClosestSilhouette(t,e,r){if(t.intersectRay(e,r))return r;const s=t.closestPointOnSilhouette(e,F.get());return h(r,e.origin,c(F.get(),e.direction,l(e.origin,s)/a(e.direction))),r},closestPointOnSilhouette:(t,e,r)=>t.closestPointOnSilhouette(e,r),distanceToSilhouette(t,e){const r=o(F.get(),e,t.center),s=f(r),i=t.radius**2;return Math.sqrt(Math.abs(s-i))}},T=new w,V={t0:0,t1:0},k=x(),C=x(),L=x();export{T as NullSphere,w as Sphere,E as sphereCSO};
