skinning top-level property

dynamic skinning
getter/setter pair

Implementation

var skinning = shaderNode((inputs, builder) {
  var position = inputs.position;
  var normal = inputs.normal;
  var index = inputs.index;
  var weight = inputs.weight;
  var bindMatrix = inputs.bindMatrix;
  var bindMatrixInverse = inputs.bindMatrixInverse;
  var boneMatrices = inputs.boneMatrices;

  var boneMatX = element(boneMatrices, index.x);
  var boneMatY = element(boneMatrices, index.y);
  var boneMatZ = element(boneMatrices, index.z);
  var boneMatW = element(boneMatrices, index.w);

  // POSITION

  var skinVertex = mul(bindMatrix, position);

  var skinned = add(mul(mul(boneMatX, skinVertex), weight.x), mul(mul(boneMatY, skinVertex), weight.y),
      mul(mul(boneMatZ, skinVertex), weight.z), mul(mul(boneMatW, skinVertex), weight.w));

  var skinPosition = mul(bindMatrixInverse, skinned).xyz;

  // NORMAL

  var skinMatrix =
      add(mul(weight.x, boneMatX), mul(weight.y, boneMatY), mul(weight.z, boneMatZ), mul(weight.w, boneMatW));

  skinMatrix = mul(mul(bindMatrixInverse, skinMatrix), bindMatrix);

  var skinNormal = transformDirection(skinMatrix, normal).xyz;

  // ASSIGNS

  assign(position, skinPosition).build(builder);
  assign(normal, skinNormal).build(builder);
});