{"version":3,"file":"ConvexHull.cjs","sources":["../../src/math/ConvexHull.js"],"sourcesContent":["import { Line3, Plane, Triangle, Vector3 } from 'three'\n\n/**\n * Ported from: https://github.com/maurizzzio/quickhull3d/ by Mauricio Poppe (https://github.com/maurizzzio)\n */\n\nconst Visible = 0\nconst Deleted = 1\n\nconst _v1 = /* @__PURE__ */ new Vector3()\nconst _line3 = /* @__PURE__ */ new Line3()\nconst _plane = /* @__PURE__ */ new Plane()\nconst _closestPoint = /* @__PURE__ */ new Vector3()\nconst _triangle = /* @__PURE__ */ new Triangle()\n\nclass ConvexHull {\n constructor() {\n this.tolerance = -1\n\n this.faces = [] // the generated faces of the convex hull\n this.newFaces = [] // this array holds the faces that are generated within a single iteration\n\n // the vertex lists work as follows:\n //\n // let 'a' and 'b' be 'Face' instances\n // let 'v' be points wrapped as instance of 'Vertex'\n //\n // [v, v, ..., v, v, v, ...]\n // ^ ^\n // | |\n // a.outside b.outside\n //\n this.assigned = new VertexList()\n this.unassigned = new VertexList()\n\n this.vertices = [] // vertices of the hull (internal representation of given geometry data)\n }\n\n setFromPoints(points) {\n // The algorithm needs at least four points.\n\n if (points.length >= 4) {\n this.makeEmpty()\n\n for (let i = 0, l = points.length; i < l; i++) {\n this.vertices.push(new VertexNode(points[i]))\n }\n\n this.compute()\n }\n\n return this\n }\n\n setFromObject(object) {\n const points = []\n\n object.updateMatrixWorld(true)\n\n object.traverse(function (node) {\n const geometry = node.geometry\n\n if (geometry !== undefined) {\n const attribute = geometry.attributes.position\n\n if (attribute !== undefined) {\n for (let i = 0, l = attribute.count; i < l; i++) {\n const point = new Vector3()\n\n point.fromBufferAttribute(attribute, i).applyMatrix4(node.matrixWorld)\n\n points.push(point)\n }\n }\n }\n })\n\n return this.setFromPoints(points)\n }\n\n containsPoint(point) {\n const faces = this.faces\n\n for (let i = 0, l = faces.length; i < l; i++) {\n const face = faces[i]\n\n // compute signed distance and check on what half space the point lies\n\n if (face.distanceToPoint(point) > this.tolerance) return false\n }\n\n return true\n }\n\n intersectRay(ray, target) {\n // based on \"Fast Ray-Convex Polyhedron Intersection\" by Eric Haines, GRAPHICS GEMS II\n\n const faces = this.faces\n\n let tNear = -Infinity\n let tFar = Infinity\n\n for (let i = 0, l = faces.length; i < l; i++) {\n const face = faces[i]\n\n // interpret faces as planes for the further computation\n\n const vN = face.distanceToPoint(ray.origin)\n const vD = face.normal.dot(ray.direction)\n\n // if the origin is on the positive side of a plane (so the plane can \"see\" the origin) and\n // the ray is turned away or parallel to the plane, there is no intersection\n\n if (vN > 0 && vD >= 0) return null\n\n // compute the distance from the ray’s origin to the intersection with the plane\n\n const t = vD !== 0 ? -vN / vD : 0\n\n // only proceed if the distance is positive. a negative distance means the intersection point\n // lies \"behind\" the origin\n\n if (t <= 0) continue\n\n // now categorized plane as front-facing or back-facing\n\n if (vD > 0) {\n // plane faces away from the ray, so this plane is a back-face\n\n tFar = Math.min(t, tFar)\n } else {\n // front-face\n\n tNear = Math.max(t, tNear)\n }\n\n if (tNear > tFar) {\n // if tNear ever is greater than tFar, the ray must miss the convex hull\n\n return null\n }\n }\n\n // evaluate intersection point\n\n // always try tNear first since its the closer intersection point\n\n if (tNear !== -Infinity) {\n ray.at(tNear, target)\n } else {\n ray.at(tFar, target)\n }\n\n return target\n }\n\n intersectsRay(ray) {\n return this.intersectRay(ray, _v1) !== null\n }\n\n makeEmpty() {\n this.faces = []\n this.vertices = []\n\n return this\n }\n\n // Adds a vertex to the 'assigned' list of vertices and assigns it to the given face\n\n addVertexToFace(vertex, face) {\n vertex.face = face\n\n if (face.outside === null) {\n this.assigned.append(vertex)\n } else {\n this.assigned.insertBefore(face.outside, vertex)\n }\n\n face.outside = vertex\n\n return this\n }\n\n // Removes a vertex from the 'assigned' list of vertices and from the given face\n\n removeVertexFromFace(vertex, face) {\n if (vertex === face.outside) {\n // fix face.outside link\n\n if (vertex.next !== null && vertex.next.face === face) {\n // face has at least 2 outside vertices, move the 'outside' reference\n\n face.outside = vertex.next\n } else {\n // vertex was the only outside vertex that face had\n\n face.outside = null\n }\n }\n\n this.assigned.remove(vertex)\n\n return this\n }\n\n // Removes all the visible vertices that a given face is able to see which are stored in the 'assigned' vertex list\n\n removeAllVerticesFromFace(face) {\n if (face.outside !== null) {\n // reference to the first and last vertex of this face\n\n const start = face.outside\n let end = face.outside\n\n while (end.next !== null && end.next.face === face) {\n end = end.next\n }\n\n this.assigned.removeSubList(start, end)\n\n // fix references\n\n start.prev = end.next = null\n face.outside = null\n\n return start\n }\n }\n\n // Removes all the visible vertices that 'face' is able to see\n\n deleteFaceVertices(face, absorbingFace) {\n const faceVertices = this.removeAllVerticesFromFace(face)\n\n if (faceVertices !== undefined) {\n if (absorbingFace === undefined) {\n // mark the vertices to be reassigned to some other face\n\n this.unassigned.appendChain(faceVertices)\n } else {\n // if there's an absorbing face try to assign as many vertices as possible to it\n\n let vertex = faceVertices\n\n do {\n // we need to buffer the subsequent vertex at this point because the 'vertex.next' reference\n // will be changed by upcoming method calls\n\n const nextVertex = vertex.next\n\n const distance = absorbingFace.distanceToPoint(vertex.point)\n\n // check if 'vertex' is able to see 'absorbingFace'\n\n if (distance > this.tolerance) {\n this.addVertexToFace(vertex, absorbingFace)\n } else {\n this.unassigned.append(vertex)\n }\n\n // now assign next vertex\n\n vertex = nextVertex\n } while (vertex !== null)\n }\n }\n\n return this\n }\n\n // Reassigns as many vertices as possible from the unassigned list to the new faces\n\n resolveUnassignedPoints(newFaces) {\n if (this.unassigned.isEmpty() === false) {\n let vertex = this.unassigned.first()\n\n do {\n // buffer 'next' reference, see .deleteFaceVertices()\n\n const nextVertex = vertex.next\n\n let maxDistance = this.tolerance\n\n let maxFace = null\n\n for (let i = 0; i < newFaces.length; i++) {\n const face = newFaces[i]\n\n if (face.mark === Visible) {\n const distance = face.distanceToPoint(vertex.point)\n\n if (distance > maxDistance) {\n maxDistance = distance\n maxFace = face\n }\n\n if (maxDistance > 1000 * this.tolerance) break\n }\n }\n\n // 'maxFace' can be null e.g. if there are identical vertices\n\n if (maxFace !== null) {\n this.addVertexToFace(vertex, maxFace)\n }\n\n vertex = nextVertex\n } while (vertex !== null)\n }\n\n return this\n }\n\n // Computes the extremes of a simplex which will be the initial hull\n\n computeExtremes() {\n const min = new Vector3()\n const max = new Vector3()\n\n const minVertices = []\n const maxVertices = []\n\n // initially assume that the first vertex is the min/max\n\n for (let i = 0; i < 3; i++) {\n minVertices[i] = maxVertices[i] = this.vertices[0]\n }\n\n min.copy(this.vertices[0].point)\n max.copy(this.vertices[0].point)\n\n // compute the min/max vertex on all six directions\n\n for (let i = 0, l = this.vertices.length; i < l; i++) {\n const vertex = this.vertices[i]\n const point = vertex.point\n\n // update the min coordinates\n\n for (let j = 0; j < 3; j++) {\n if (point.getComponent(j) < min.getComponent(j)) {\n min.setComponent(j, point.getComponent(j))\n minVertices[j] = vertex\n }\n }\n\n // update the max coordinates\n\n for (let j = 0; j < 3; j++) {\n if (point.getComponent(j) > max.getComponent(j)) {\n max.setComponent(j, point.getComponent(j))\n maxVertices[j] = vertex\n }\n }\n }\n\n // use min/max vectors to compute an optimal epsilon\n\n this.tolerance =\n 3 *\n Number.EPSILON *\n (Math.max(Math.abs(min.x), Math.abs(max.x)) +\n Math.max(Math.abs(min.y), Math.abs(max.y)) +\n Math.max(Math.abs(min.z), Math.abs(max.z)))\n\n return { min: minVertices, max: maxVertices }\n }\n\n // Computes the initial simplex assigning to its faces all the points\n // that are candidates to form part of the hull\n\n computeInitialHull() {\n const vertices = this.vertices\n const extremes = this.computeExtremes()\n const min = extremes.min\n const max = extremes.max\n\n // 1. Find the two vertices 'v0' and 'v1' with the greatest 1d separation\n // (max.x - min.x)\n // (max.y - min.y)\n // (max.z - min.z)\n\n let maxDistance = 0\n let index = 0\n\n for (let i = 0; i < 3; i++) {\n const distance = max[i].point.getComponent(i) - min[i].point.getComponent(i)\n\n if (distance > maxDistance) {\n maxDistance = distance\n index = i\n }\n }\n\n const v0 = min[index]\n const v1 = max[index]\n let v2\n let v3\n\n // 2. The next vertex 'v2' is the one farthest to the line formed by 'v0' and 'v1'\n\n maxDistance = 0\n _line3.set(v0.point, v1.point)\n\n for (let i = 0, l = this.vertices.length; i < l; i++) {\n const vertex = vertices[i]\n\n if (vertex !== v0 && vertex !== v1) {\n _line3.closestPointToPoint(vertex.point, true, _closestPoint)\n\n const distance = _closestPoint.distanceToSquared(vertex.point)\n\n if (distance > maxDistance) {\n maxDistance = distance\n v2 = vertex\n }\n }\n }\n\n // 3. The next vertex 'v3' is the one farthest to the plane 'v0', 'v1', 'v2'\n\n maxDistance = -1\n _plane.setFromCoplanarPoints(v0.point, v1.point, v2.point)\n\n for (let i = 0, l = this.vertices.length; i < l; i++) {\n const vertex = vertices[i]\n\n if (vertex !== v0 && vertex !== v1 && vertex !== v2) {\n const distance = Math.abs(_plane.distanceToPoint(vertex.point))\n\n if (distance > maxDistance) {\n maxDistance = distance\n v3 = vertex\n }\n }\n }\n\n const faces = []\n\n if (_plane.distanceToPoint(v3.point) < 0) {\n // the face is not able to see the point so 'plane.normal' is pointing outside the tetrahedron\n\n faces.push(Face.create(v0, v1, v2), Face.create(v3, v1, v0), Face.create(v3, v2, v1), Face.create(v3, v0, v2))\n\n // set the twin edge\n\n for (let i = 0; i < 3; i++) {\n const j = (i + 1) % 3\n\n // join face[ i ] i > 0, with the first face\n\n faces[i + 1].getEdge(2).setTwin(faces[0].getEdge(j))\n\n // join face[ i ] with face[ i + 1 ], 1 <= i <= 3\n\n faces[i + 1].getEdge(1).setTwin(faces[j + 1].getEdge(0))\n }\n } else {\n // the face is able to see the point so 'plane.normal' is pointing inside the tetrahedron\n\n faces.push(Face.create(v0, v2, v1), Face.create(v3, v0, v1), Face.create(v3, v1, v2), Face.create(v3, v2, v0))\n\n // set the twin edge\n\n for (let i = 0; i < 3; i++) {\n const j = (i + 1) % 3\n\n // join face[ i ] i > 0, with the first face\n\n faces[i + 1].getEdge(2).setTwin(faces[0].getEdge((3 - i) % 3))\n\n // join face[ i ] with face[ i + 1 ]\n\n faces[i + 1].getEdge(0).setTwin(faces[j + 1].getEdge(1))\n }\n }\n\n // the initial hull is the tetrahedron\n\n for (let i = 0; i < 4; i++) {\n this.faces.push(faces[i])\n }\n\n // initial assignment of vertices to the faces of the tetrahedron\n\n for (let i = 0, l = vertices.length; i < l; i++) {\n const vertex = vertices[i]\n\n if (vertex !== v0 && vertex !== v1 && vertex !== v2 && vertex !== v3) {\n maxDistance = this.tolerance\n let maxFace = null\n\n for (let j = 0; j < 4; j++) {\n const distance = this.faces[j].distanceToPoint(vertex.point)\n\n if (distance > maxDistance) {\n maxDistance = distance\n maxFace = this.faces[j]\n }\n }\n\n if (maxFace !== null) {\n this.addVertexToFace(vertex, maxFace)\n }\n }\n }\n\n return this\n }\n\n // Removes inactive faces\n\n reindexFaces() {\n const activeFaces = []\n\n for (let i = 0; i < this.faces.length; i++) {\n const face = this.faces[i]\n\n if (face.mark === Visible) {\n activeFaces.push(face)\n }\n }\n\n this.faces = activeFaces\n\n return this\n }\n\n // Finds the next vertex to create faces with the current hull\n\n nextVertexToAdd() {\n // if the 'assigned' list of vertices is empty, no vertices are left. return with 'undefined'\n\n if (this.assigned.isEmpty() === false) {\n let eyeVertex,\n maxDistance = 0\n\n // grap the first available face and start with the first visible vertex of that face\n\n const eyeFace = this.assigned.first().face\n let vertex = eyeFace.outside\n\n // now calculate the farthest vertex that face can see\n\n do {\n const distance = eyeFace.distanceToPoint(vertex.point)\n\n if (distance > maxDistance) {\n maxDistance = distance\n eyeVertex = vertex\n }\n\n vertex = vertex.next\n } while (vertex !== null && vertex.face === eyeFace)\n\n return eyeVertex\n }\n }\n\n // Computes a chain of half edges in CCW order called the 'horizon'.\n // For an edge to be part of the horizon it must join a face that can see\n // 'eyePoint' and a face that cannot see 'eyePoint'.\n\n computeHorizon(eyePoint, crossEdge, face, horizon) {\n // moves face's vertices to the 'unassigned' vertex list\n\n this.deleteFaceVertices(face)\n\n face.mark = Deleted\n\n let edge\n\n if (crossEdge === null) {\n edge = crossEdge = face.getEdge(0)\n } else {\n // start from the next edge since 'crossEdge' was already analyzed\n // (actually 'crossEdge.twin' was the edge who called this method recursively)\n\n edge = crossEdge.next\n }\n\n do {\n const twinEdge = edge.twin\n const oppositeFace = twinEdge.face\n\n if (oppositeFace.mark === Visible) {\n if (oppositeFace.distanceToPoint(eyePoint) > this.tolerance) {\n // the opposite face can see the vertex, so proceed with next edge\n\n this.computeHorizon(eyePoint, twinEdge, oppositeFace, horizon)\n } else {\n // the opposite face can't see the vertex, so this edge is part of the horizon\n\n horizon.push(edge)\n }\n }\n\n edge = edge.next\n } while (edge !== crossEdge)\n\n return this\n }\n\n // Creates a face with the vertices 'eyeVertex.point', 'horizonEdge.tail' and 'horizonEdge.head' in CCW order\n\n addAdjoiningFace(eyeVertex, horizonEdge) {\n // all the half edges are created in ccw order thus the face is always pointing outside the hull\n\n const face = Face.create(eyeVertex, horizonEdge.tail(), horizonEdge.head())\n\n this.faces.push(face)\n\n // join face.getEdge( - 1 ) with the horizon's opposite edge face.getEdge( - 1 ) = face.getEdge( 2 )\n\n face.getEdge(-1).setTwin(horizonEdge.twin)\n\n return face.getEdge(0) // the half edge whose vertex is the eyeVertex\n }\n\n // Adds 'horizon.length' faces to the hull, each face will be linked with the\n // horizon opposite face and the face on the left/right\n\n addNewFaces(eyeVertex, horizon) {\n this.newFaces = []\n\n let firstSideEdge = null\n let previousSideEdge = null\n\n for (let i = 0; i < horizon.length; i++) {\n const horizonEdge = horizon[i]\n\n // returns the right side edge\n\n const sideEdge = this.addAdjoiningFace(eyeVertex, horizonEdge)\n\n if (firstSideEdge === null) {\n firstSideEdge = sideEdge\n } else {\n // joins face.getEdge( 1 ) with previousFace.getEdge( 0 )\n\n sideEdge.next.setTwin(previousSideEdge)\n }\n\n this.newFaces.push(sideEdge.face)\n previousSideEdge = sideEdge\n }\n\n // perform final join of new faces\n\n firstSideEdge.next.setTwin(previousSideEdge)\n\n return this\n }\n\n // Adds a vertex to the hull\n\n addVertexToHull(eyeVertex) {\n const horizon = []\n\n this.unassigned.clear()\n\n // remove 'eyeVertex' from 'eyeVertex.face' so that it can't be added to the 'unassigned' vertex list\n\n this.removeVertexFromFace(eyeVertex, eyeVertex.face)\n\n this.computeHorizon(eyeVertex.point, null, eyeVertex.face, horizon)\n\n this.addNewFaces(eyeVertex, horizon)\n\n // reassign 'unassigned' vertices to the new faces\n\n this.resolveUnassignedPoints(this.newFaces)\n\n return this\n }\n\n cleanup() {\n this.assigned.clear()\n this.unassigned.clear()\n this.newFaces = []\n\n return this\n }\n\n compute() {\n let vertex\n\n this.computeInitialHull()\n\n // add all available vertices gradually to the hull\n\n while ((vertex = this.nextVertexToAdd()) !== undefined) {\n this.addVertexToHull(vertex)\n }\n\n this.reindexFaces()\n\n this.cleanup()\n\n return this\n }\n}\n\n//\n\nconst Face = /* @__PURE__ */ (() => {\n class Face {\n constructor() {\n this.normal = new Vector3()\n this.midpoint = new Vector3()\n this.area = 0\n\n this.constant = 0 // signed distance from face to the origin\n this.outside = null // reference to a vertex in a vertex list this face can see\n this.mark = Visible\n this.edge = null\n }\n\n static create(a, b, c) {\n const face = new Face()\n\n const e0 = new HalfEdge(a, face)\n const e1 = new HalfEdge(b, face)\n const e2 = new HalfEdge(c, face)\n\n // join edges\n\n e0.next = e2.prev = e1\n e1.next = e0.prev = e2\n e2.next = e1.prev = e0\n\n // main half edge reference\n\n face.edge = e0\n\n return face.compute()\n }\n\n getEdge(i) {\n let edge = this.edge\n\n while (i > 0) {\n edge = edge.next\n i--\n }\n\n while (i < 0) {\n edge = edge.prev\n i++\n }\n\n return edge\n }\n\n compute() {\n const a = this.edge.tail()\n const b = this.edge.head()\n const c = this.edge.next.head()\n\n _triangle.set(a.point, b.point, c.point)\n\n _triangle.getNormal(this.normal)\n _triangle.getMidpoint(this.midpoint)\n this.area = _triangle.getArea()\n\n this.constant = this.normal.dot(this.midpoint)\n\n return this\n }\n\n distanceToPoint(point) {\n return this.normal.dot(point) - this.constant\n }\n }\n\n return Face\n})()\n\n// Entity for a Doubly-Connected Edge List (DCEL).\n\nclass HalfEdge {\n constructor(vertex, face) {\n this.vertex = vertex\n this.prev = null\n this.next = null\n this.twin = null\n this.face = face\n }\n\n head() {\n return this.vertex\n }\n\n tail() {\n return this.prev ? this.prev.vertex : null\n }\n\n length() {\n const head = this.head()\n const tail = this.tail()\n\n if (tail !== null) {\n return tail.point.distanceTo(head.point)\n }\n\n return -1\n }\n\n lengthSquared() {\n const head = this.head()\n const tail = this.tail()\n\n if (tail !== null) {\n return tail.point.distanceToSquared(head.point)\n }\n\n return -1\n }\n\n setTwin(edge) {\n this.twin = edge\n edge.twin = this\n\n return this\n }\n}\n\n// A vertex as a double linked list node.\n\nclass VertexNode {\n constructor(point) {\n this.point = point\n this.prev = null\n this.next = null\n this.face = null // the face that is able to see this vertex\n }\n}\n\n// A double linked list that contains vertex nodes.\n\nclass VertexList {\n constructor() {\n this.head = null\n this.tail = null\n }\n\n first() {\n return this.head\n }\n\n last() {\n return this.tail\n }\n\n clear() {\n this.head = this.tail = null\n\n return this\n }\n\n // Inserts a vertex before the target vertex\n\n insertBefore(target, vertex) {\n vertex.prev = target.prev\n vertex.next = target\n\n if (vertex.prev === null) {\n this.head = vertex\n } else {\n vertex.prev.next = vertex\n }\n\n target.prev = vertex\n\n return this\n }\n\n // Inserts a vertex after the target vertex\n\n insertAfter(target, vertex) {\n vertex.prev = target\n vertex.next = target.next\n\n if (vertex.next === null) {\n this.tail = vertex\n } else {\n vertex.next.prev = vertex\n }\n\n target.next = vertex\n\n return this\n }\n\n // Appends a vertex to the end of the linked list\n\n append(vertex) {\n if (this.head === null) {\n this.head = vertex\n } else {\n this.tail.next = vertex\n }\n\n vertex.prev = this.tail\n vertex.next = null // the tail has no subsequent vertex\n\n this.tail = vertex\n\n return this\n }\n\n // Appends a chain of vertices where 'vertex' is the head.\n\n appendChain(vertex) {\n if (this.head === null) {\n this.head = vertex\n } else {\n this.tail.next = vertex\n }\n\n vertex.prev = this.tail\n\n // ensure that the 'tail' reference points to the last vertex of the chain\n\n while (vertex.next !== null) {\n vertex = vertex.next\n }\n\n this.tail = vertex\n\n return this\n }\n\n // Removes a vertex from the linked list\n\n remove(vertex) {\n if (vertex.prev === null) {\n this.head = vertex.next\n } else {\n vertex.prev.next = vertex.next\n }\n\n if (vertex.next === null) {\n this.tail = vertex.prev\n } else {\n vertex.next.prev = vertex.prev\n }\n\n return this\n }\n\n // Removes a list of vertices whose 'head' is 'a' and whose 'tail' is b\n\n removeSubList(a, b) {\n if (a.prev === null) {\n this.head = b.next\n } else {\n a.prev.next = b.next\n }\n\n if (b.next === null) {\n this.tail = a.prev\n } else {\n b.next.prev = a.prev\n }\n\n return this\n }\n\n isEmpty() {\n return this.head === null\n }\n}\n\nexport { ConvexHull, Face, HalfEdge, VertexNode, VertexList }\n"],"names":["Vector3","Line3","Plane","Triangle","Face"],"mappings":"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"}