Transforming copied vertex Data mutates the original mesh

Hi, i am trying to find out why transforming copied vertexdata like this mutates the original mesh Object, even if [ExtractFromMesh] and matrix is forced to do a copy of the Mesh.

const transformVerticesData = (array:FloatArray | null, matrix: Matrix) => {
  for(let i = 0; i<array.length/3; i++){
    const v = new Vector3(array[i*3], array[i*3+1], array[i*3+2]).clone();
    const mv = Vector3.TransformCoordinates(v, matrix).clone();
    array[i*3] = mv.x;
    array[i*3+1] = mv.y;
    array[i*3+2] = mv.z;
  return array;
const inputVertexdata = VertexData.ExtractFromMesh(input as Mesh, true);
const matrix = input.computeWorldMatrix().clone();
const positions = transformVerticesData(inputVertexdata.positions, matrix);

Here in the last line lies the problem - i somehow change the vertexdata from input.

thank you so much in advance!

I did a bit of digging and this is what I found:

  • In this old changeset we can find a comment indicating a slice is performed on the vertex buffer in order to copy it
  • In a later change the call is replaced, but the comment left in place
  • On the latest head this part of the code is still the same
  • The relevant code does not appear to slice (or otherwise copy) the buffer by default
  • This would mean that your call to VertexData.ExtractFromMesh doesn’t actually create a copy

Please not that I’ve never seen this code before, so I could be completely wrong. If my understanding is correct, this would be a bug and the comment in question simply an outdated leftover.

A possible fix might then be to pass the forceCopy flag to the internal call to getVerticesData(), unless that has unintended side effects elsewhere?

If the Babylon gurus agree with the above, I’ll be happy to submit a PR with the fix. I’ve been meaning to learn the workflow for contributing to the core engine anyway, so this would be as good a chance as any :smiley:

You should try VertexData.ExtractFromMesh(input as Mesh, true, true); to force a copy of the source data.

OR do not erase the data in your transformVerticesData function, but create a new array of the right size and place the result in the new array instead of replacing in the existing one.

Finally most of your .clone() won t help as they are anyway on new objects so unshared :slight_smile:

1 Like

Hello @pcace just checking in if there’s any more help you’d like