SpriteSheetUVNode.js 1.7 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758
  1. import Node from '../core/Node.js';
  2. import FloatNode from '../inputs/FloatNode.js';
  3. import UVNode from '../accessors/UVNode.js';
  4. import MathNode from '../math/MathNode.js';
  5. import OperatorNode from '../math/OperatorNode.js';
  6. import SplitNode from '../utils/SplitNode.js';
  7. import JoinNode from '../utils/JoinNode.js';
  8. class SpriteSheetUVNode extends Node {
  9. constructor( countNode, uvNode = new UVNode(), frameNode = new FloatNode( 0 ).setConst( true ) ) {
  10. super( 'vec2' );
  11. this.countNode = countNode;
  12. this.uvNode = uvNode;
  13. this.frameNode = frameNode;
  14. }
  15. generate( builder ) {
  16. const count = this.countNode;
  17. const uv = this.uvNode;
  18. const frame = this.frameNode;
  19. const one = new FloatNode( 1 ).setConst( true );
  20. const width = new SplitNode( count, 'x' );
  21. const height = new SplitNode( count, 'y' );
  22. const total = new OperatorNode( '*', width, height );
  23. const roundFrame = new MathNode( MathNode.FLOOR, new MathNode( MathNode.MOD, frame, total ) );
  24. const frameNum = new OperatorNode( '+', roundFrame, one );
  25. const cell = new MathNode( MathNode.MOD, roundFrame, width );
  26. const row = new MathNode( MathNode.CEIL, new OperatorNode( '/', frameNum, width ) );
  27. const rowInv = new OperatorNode( '-', height, row );
  28. const scale = new OperatorNode( '/', one, count );
  29. const uvFrameOffset = new JoinNode( [
  30. new OperatorNode( '*', cell, new SplitNode( scale, 'x' ) ),
  31. new OperatorNode( '*', rowInv, new SplitNode( scale, 'y' ) )
  32. ] );
  33. const uvScale = new OperatorNode( '*', uv, scale );
  34. const uvFrame = new OperatorNode( '+', uvScale, uvFrameOffset );
  35. return uvFrame.build( builder, this.getNodeType( builder ) );
  36. }
  37. }
  38. export default SpriteSheetUVNode;