are there currently limitations on or a correct approach to use applyMatrix4()
on geometry that’s part of a gltf model generated with the EXT_mesh_gpu_instancing
extension?
I’m currently importing a gltf file with the extension included for instanced parts, i’ve noticed that if i traverse the gltf.scene and try to applyMatrix4()
to all geometries of the model i get the following error…
the code i’m using is pretty straight forward and uses the typical traverse
conventions…
model.scale.set(3, 3, 3);
model.updateMatrix();
model.traverse(function (o) {
o.updateMatrix()
o.updateMatrixWorld()
if(o.isMesh){
o.geometry.applyMatrix4( o.matrixWorld );
}
else{
o.position.set(0,0,0)
o.rotation.set(0,0,0)
o.scale.set(1,1,1)
o.updateMatrix()
}
});
it would be good to know if this is a current limitation or i’ve discovered a bug, i have read that the geometry of instanced items from the EXT_mesh_gpu_instancing
extension are generated through the gltf.parser.json.nodes graph of the gltf (afaict) but i’m not sure how they are eventually rendered inside the gltf.scene graph and wether or not what i am trying to do is possible…
any guidance would be much appreciated.
EDIT: i forgot to mention this is using r148.
Loading a glTF file using this extension creates THREE.InstancedMesh objects. I’m not sure if there’s any reason THREE.InstancedMesh doesn’t/shouldn’t support .applyMatrix4, or if that’s just a bug, though. I think it’s probably worth filing a ticket on GitHub!
1 Like
Hey @donmccurdy, OK thanks for the response, I did think that also but don’t know enough about the extension and it’s translation into three, I’ll file a report tomorrow with a live example on how the error is triggered.
EDIT: I was thinking maybe inside the traverse function I may also need to include something such as
if(o.isInstancedMesh){
for(var i=0; i<o.count;i++){
o.setMatrixAt(i, o.matrixWorld)
}
This is untested but doesn’t seem like it would be a way to correctly access and apply a matrix4 to the instances for the relative Instanced Meshes… There also doesn’t seem to be an applyMatrix4At()
method for instancedMesh
so a little confused on how this would work
Nothing too special about EXT_mesh_gpu_instancing here, it is (or should be) just a normal THREE.InstancedMesh once the loading process is done.
1 Like
That’s an interesting situation.
What is the actual content of the position attribute of the geometry – are all values good? What are the data in the bounding spheres – are they good? Do you have morphing – are morphing data good too? Is the matrixWorld
good?
Yes everything looks good with the model, the file itself is a gltf exported from solid works as SLDASM (solid works assembly) the odd thing I’ve just noticed is that if I use
if(o.isInstancedMesh){
console.log(o)
}
nothing is actually logged in the console, the isInstancedMesh flag is not being detected which makes me think there’s not actually instances being drawn although they have to be because the model is complete and shows all parts. The original file is around 4.5MB, if I make a clone of each geometry and do what I’m trying to do it works but then the resulting exported gltf bloats to 50MB as geometries are absolute and not being instanced anymore… It’s an odd one
if you just want to fix that issue but avoid THREE.InstancedMesh, then running…
npm install --global @gltf-transform/cli
gltf-transform dedup input.glb output.glb
… should fix it.
1 Like
Good shout but the project in question needs to use a variable source of models that could come from any particular software export and need all model formatting preserved, the resulting 50MB file was actually what brought the current problem to my attention as its just extremely bulky, the file size essentially needs to be the same going out as it was coming in, I haven’t had time to post a report yet but will get on it ASAP