javascript 3d three.js

javascript - Three JS: encuentra todos los puntos donde una malla se cruza con un plano



3d three.js (1)

He creado una escena three.js que incluye un plano que se cruza con una malla. Lo que me gustaría hacer es obtener una serie de puntos para todas las ubicaciones donde un borde de la malla cruza el plano. He buscado soluciones y parece que no puedo encontrar nada.

Aquí hay una imagen de lo que tengo actualmente:

Y aquí he resaltado las coordenadas que estoy tratando de reunir:

Si alguien puede señalarme en la dirección correcta, sería muy apreciado.

Gracias,

S


Esta no es la solución definitiva. Este es solo un punto desde el que puede comenzar.

UPD: Here hay una extensión de esta respuesta, cómo formar contornos a partir de puntos dados.

Además, se refiere a esta pregunta SO con asombrosas respuestas de WestLangley y Lee Stemkoski sobre el método THREE.Object3D() de THREE.Object3D() .

Imaginemos que desea encontrar puntos de intersección de una geometría habitual (por ejemplo, THREE.DodecahedronGeometry() ).

La idea:

  1. THREE.Plane() tiene el .intersectLine ( line, optionalTarget )

  2. Una malla contiene caras ( THREE.Face3() )

  3. Cada cara tiene propiedades a a, b, c , donde se almacenan los índices de vértices.

  4. Cuando conocemos índices de vértices, podemos obtenerlos de la matriz de vertices

  5. Cuando conocemos las coordenadas de los vértices de una cara, podemos construir tres objetos THREE.Line3()

  6. Cuando tenemos tres líneas, podemos verificar si nuestro avión las intersecta.

  7. Si tenemos un punto de intersección, podemos almacenarlo en una matriz.

  8. Repita los pasos 3 a 7 para cada cara de la malla.

Alguna explicación con código:

Tenemos plane que es THREE.PlaneGeometry() y obj que es THREE.DodecahedronGeometry()

Entonces, THREE.Plane() un THREE.Plane() :

var planePointA = new THREE.Vector3(), planePointB = new THREE.Vector3(), planePointC = new THREE.Vector3(); var mathPlane = new THREE.Plane(); plane.localToWorld(planePointA.copy(plane.geometry.vertices[plane.geometry.faces[0].a])); plane.localToWorld(planePointB.copy(plane.geometry.vertices[plane.geometry.faces[0].b])); plane.localToWorld(planePointC.copy(plane.geometry.vertices[plane.geometry.faces[0].c])); mathPlane.setFromCoplanarPoints(planePointA, planePointB, planePointC);

Aquí, tres vértices de cualquier cara del plane son coplanares, por lo que podemos crear mathPlane partir de ellos, utilizando el método .setFromCoplanarPoints() .

Luego recorreremos las caras de nuestro obj :

var a = new THREE.Vector3(), b = new THREE.Vector3(), c = new THREE.Vector3(); obj.geometry.faces.forEach(function(face) { obj.localToWorld(a.copy(obj.geometry.vertices[face.a])); obj.localToWorld(b.copy(obj.geometry.vertices[face.b])); obj.localToWorld(c.copy(obj.geometry.vertices[face.c])); lineAB = new THREE.Line3(a, b); lineBC = new THREE.Line3(b, c); lineCA = new THREE.Line3(c, a); setPointOfIntersection(lineAB, mathPlane); setPointOfIntersection(lineBC, mathPlane); setPointOfIntersection(lineCA, mathPlane); });

dónde

var pointsOfIntersection = new THREE.Geometry(); ... var pointOfIntersection = new THREE.Vector3();

y

function setPointOfIntersection(line, plane) { pointOfIntersection = plane.intersectLine(line); if (pointOfIntersection) { pointsOfIntersection.vertices.push(pointOfIntersection.clone()); }; }

Al final haremos visibles nuestros puntos:

var pointsMaterial = new THREE.PointsMaterial({ size: .5, color: "yellow" }); var points = new THREE.Points(pointsOfIntersection, pointsMaterial); scene.add(points);

Ejemplo de jsfiddle . Presione el botón para obtener los puntos de intersección entre el plano y el dodecaedro.