Manthrax CSG with Custom Geometry Objects

Hi everyone!

––––
tl;dr: how can I calculate the faceVertexUvs attribute of a custom Geometry object (a tetrahedron
) to allow it to be used in CSG operations? Additionally, the custom geometry’s vertices will be changed throughout the run of the program (still always a tetrahedron), so I think the faceVertexUVs attribute will need to be updated as well. How can I do this, if possible?
––––

I’m doing a project with this CSG library by @manthrax: https://github.com/manthrax/THREE-CSGMesh. Many others on the forum have used it and it seems to work pretty well for everyone.

While I was able to make it work with primitive geometries from Three (TetrahedronGeometry, BoxGeometry, etc.), I’m running into some problems when trying to do it with custom geometries. I am using the exact same code to run the CSG operations (adapted from the library docs), except instead of using premade geometries objects I am using:

        /*a basic tetrahedron*/
        this.baseGeometry = new Geometry();
        this.baseGeometry.vertices = [
            this.A, this.B, this.C, this.D
        ];
        this.baseGeometry.faces.push(
            new Face3(0,3,1), new Face3(0,1,2), 
            new Face3(1,3,2), new Face3(2,3,0)
        );

and a BoxGeometry. These are then wrapped in mesh objects to be rendered and for the CSG to work.

When the box mesh is subtracted from the custom tetrahedron mesh, I get an error which basically says it cannot be performed because the faceVertexUvs attribute of the custom geometry is undefined. I am hoping that calculating this when creating the geometry will solve the problem. However, the geometry’s vertices will be changed throughout the run of the program, which I think means that the faceVertexUvs will need to be recalculated as well. What is the best way to go about doing this?
I am completely new to uv mapping so any help with this is much appreciated!

Thanks so much,
Vishal

You need to manually calculate your facevertexuvs. I didnt know what your tetrahedron vertices were so I used my own, which means the faces were also different. In my pic below, the tetrahedron is the blue triangle shape in the background used in the csg operations.

let geometry = new THREE.Geometry();
geometry.vertices.push(new THREE.Vector3(1, 1, 1), new THREE.Vector3(-1, -1, 1), new THREE.Vector3(-1, 1, -1), new THREE.Vector3(1, -1, -1));
geometry.faces.push(new THREE.Face3(2, 1, 0), new THREE.Face3(0, 3, 2), new THREE.Face3(1, 3, 0), new THREE.Face3(2, 3, 1));
geometry.computeBoundingBox();
const max = geometry.boundingBox.max;
const min = geometry.boundingBox.min;
const offset = new THREE.Vector2(0 - min.x, 0 - min.y);
const range = new THREE.Vector2(max.x - min.x, max.y - min.y);
for (let i = 0; i < geometry.faces.length; i++) {
    const v1 = geometry.vertices[geometry.faces[i].a];
    const v2 = geometry.vertices[geometry.faces[i].b];
    const v3 = geometry.vertices[geometry.faces[i].c];
    geometry.faceVertexUvs[0].push([
        new THREE.Vector2((v1.x + offset.x) / range.x, (v1.y + offset.y) / range.y),
        new THREE.Vector2((v2.x + offset.x) / range.x, (v2.y + offset.y) / range.y),
        new THREE.Vector2((v3.x + offset.x) / range.x, (v3.y + offset.y) / range.y)
    ]);
}
geometry.computeFlatVertexNormals();

1 Like

Thank you, this works perfectly.
I was getting some strange behavior at first (the same as what I saw when using @manthrax’s box unwrap function, so I think that would’ve worked too), but it ended up being an issue with the faces of the geometry.
If you get the chance, could you explain this algorithm a little more?

Thanks again.