About InstancedMesh

Actually, that’s not all, because I also imported the ammo.js physics engine, which requires the vertices of the mesh to create the convex hull of the ammunition. If I use InstancedMesh, it requires a geometry as the first parameter, but in my junk model, each mesh’s geometry has an offset and a scale. This would be very easy if I could remove the offset and scaling in Model->Mesh->Geometry.

Since I don’t know how to introduce ammo in “jsfiddle” I don’t have it in my example, sorry

Sorry to bother you again, I was wondering how you scale all the children of the garbage model in your example? I don’t see anything similar to scale.multiplyScalar. I read the InstancedMesh documentation on the official website, but I still don’t quite understand its principles (please forgive my ignorance and stupidity :sob:)

Hey no you’re all good. I’m sorry I was cranky. :slight_smile:
The positioning of the instances is done in index.js line 50…
I didn’t scale them down but you could do it there… by scaling “gp.scale.multiplyScalar(.5)” or whatever.
There is a lot of stuff going on in that glitch but the main instancing code is in index.js and InstanceGroup.js… try and read those and see if maybe some of it becomes more clear.

    let index = Math.floor(Math.random() * trashModels.length);
    let model = trashModels[index].scene.clone();

    let trashs = model.children;

    let mesh = trashs[10].children[0] as Mesh<BufferGeometry, MeshStandardMaterial>;
    let geometry = mesh.geometry.clone();
    let material = mesh.material.clone();

    mesh.updateMatrixWorld();
    let matrix = mesh.matrixWorld.clone();
    matrix.scale(new Vector3(0.1, 0.1, 0.1));
    geometry.computeBoundingBox();

    let count = 100;
    let instancedMesh = new InstancedMesh(geometry, material, count);
    instancedMesh.add(new AxesHelper(10));

    for (let i = 0; i < count; i++) {
      matrix.setPosition(0, 0, 0);
      instancedMesh.setMatrixAt(i, matrix);
    }

    render.scene.add(instancedMesh);

I successfully created the InstancedMesh by reading your code, but now I seem to have a new problem, which is that the center of mass of my geometry is actually offset from the origin. I want to eliminate it, but when I try to eliminate it by .translate the geometry, my geometry deforms and becomes very abstract. How should I remove this offset correctly?
Sorry for keeping asking you questions, I know it’s annoying, sorry again :sob:

    geometry.computeBoundingBox();
    const boundingBox = geometry.boundingBox;

    const centerX = (boundingBox.min.x + boundingBox.max.x) / 2;
    const centerY = (boundingBox.min.y + boundingBox.max.y) / 2;
    const centerZ = (boundingBox.min.z + boundingBox.max.z) / 2;

    const offset = new Vector3(-centerX, -centerY, -centerZ);

    geometry.translate(offset.x, offset.y, offset.z);

When I call the “translate” method it becomes like this

Right. This is why I shared the “InstanceGroup” class that I made. It handles having more complex scaling/positioning hierarchies but still lets you use Instancing.

Can I directly “translate” the “geometry” of the gltf sub-object “mesh”? Because I found that this is feasible, but if it is placed in a sub-object of gltf, it cannot be translated normally.

    let cube = new BoxGeometry(1, 1, 1);
    cube.translate(-0.5, -0.5, -0.5);

You can, but you should try to avoid doing operations on the vertex data itself, since each mutation of the vertices will result in a small amount of error that compounds over time. If you do it at init time, it should be ok… but usually it’s better to solve these things by adding a parent node and then scaling/moving the parent or the child from there. This doesn’t introduce errors and is more flexible and dynamic, at a small runtime cost, since the node hierarchy is recomputed from scratch every frame.

Like I said above, when I did “translation”, something went wrong.
translation Before:


translation After:

You’re using meshopt compressed meshes which have to re-scale the model as part of the compression scheme. To undo that scaling at runtime, meshopt inserts new parent nodes into the hierarchy.

That is why you will see new parent nodes inserted in your hierarchy after gltfpack / meshopt.

Before meshopt you may have

Scene->Mesh

and after meshopt you may have:

Scene->Object3D->Mesh…

so instead of manipulating Mesh you may want to be manipulating its parent Object3D instead to avoid having to scale vertices etc.

Additionally… if your meshes are meshopt compressed, they may be using lower bit depth numeric types to store the mesh, so if you scale a mesh down by half… your byte per channel vertices 0 to 255 are now only 0 to 128 which may make them distort the closer you get to 0.

Finally, I understand! What I need to operate is “Object3D” not “Mesh”. I need to update and get the world transform of a “Mesh” by adjusting the scale/position/rotation of the “Object3D”! You are simply a miracle doctor! You got my stupid brain working again. :smiling_face_with_three_hearts:

1 Like

Oh man… I know! It’s complicated! Not super easy to understand… I went through the same learning process when I encountered meshopt mesh compression i.e. (vertex format quantization).

1 Like

Awesome my friend! If you have the opportunity to come to China, I will definitely entertain you! :laughing:

2 Likes