Node.js 4.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188
  1. import {NodeSocket} from "./NodeSocket";
  2. import {RoundedBox} from "../RoundedBox";
  3. import {Object2D} from "../../Object2D";
  4. /**
  5. * Node objects can be connected between them to create graphs.
  6. *
  7. * Each node contains inputs, outputs and a set of attributes containing their state. Inputs can be connected to outputs of other nodes, and vice-versa.
  8. *
  9. * This class implements node basic functionality, the logic to connect node and define inputs/outputs of the nodes.
  10. *
  11. * @class
  12. * @extends {RoundedBox}
  13. */
  14. function Node()
  15. {
  16. RoundedBox.call(this);
  17. this.draggable = true;
  18. /**
  19. * List of inputs of the node.
  20. *
  21. * @type {NodeSocket[]}
  22. */
  23. this.inputs = [];
  24. /**
  25. * List of outputs of the node.
  26. *
  27. * @type {NodeSocket[]}
  28. */
  29. this.outputs = [];
  30. }
  31. Node.prototype = Object.create(RoundedBox.prototype);
  32. Node.prototype.constructor = Node;
  33. Node.prototype.type = "Node";
  34. Object2D.register(Node, "Node");
  35. /**
  36. * This method should be used for the node to register their socket inputs/outputs.
  37. *
  38. * It is called automatically after the node is added to the node graph to create sockets.
  39. */
  40. Node.prototype.registerSockets = null;
  41. /**
  42. * Add input to this node, can be connected to other nodes to receive data.
  43. *
  44. * @param {string} type Data type of the node socket.
  45. * @param {string} name Name of the node socket.
  46. * @return {NodeSocket} Node socket created for this node.
  47. */
  48. Node.prototype.addInput = function(type, name)
  49. {
  50. var socket = new NodeSocket(this, NodeSocket.INPUT, type, name);
  51. this.inputs.push(socket);
  52. this.parent.add(socket);
  53. return socket;
  54. };
  55. /**
  56. * Add output socket to this node, can be connected to other nodes to send data.
  57. *
  58. * @param {string} type Data type of the node socket.
  59. * @param {string} name Name of the node socket.
  60. * @return {NodeSocket} Node socket created for this node.
  61. */
  62. Node.prototype.addOutput = function(type, name)
  63. {
  64. var socket = new NodeSocket(this, NodeSocket.OUTPUT, type, name);
  65. this.outputs.push(socket);
  66. this.parent.add(socket);
  67. return socket;
  68. };
  69. /**
  70. * Get a output socket by its name. If there are multiple sockets with the same name only the first one found is returned.
  71. *
  72. * @param {string} name Name of the node socket to get.
  73. * @return {NodeSocket} Node socket if it was found, null otherwise.
  74. */
  75. Node.prototype.getOutput = function(name)
  76. {
  77. for(var i = 0; i < this.outputs.length; i++)
  78. {
  79. if(this.outputs[i].name === name)
  80. {
  81. return this.outputs[i];
  82. }
  83. }
  84. return null;
  85. };
  86. /**
  87. * Get a input socket by its name. If there are multiple sockets with the same name only the first one found is returned.
  88. *
  89. * @param {string} name Name of the node socket to get.
  90. * @return {NodeSocket} Node socket if it was found, null otherwise.
  91. */
  92. Node.prototype.getInput = function(name)
  93. {
  94. for(var i = 0; i < this.inputs.length; i++)
  95. {
  96. if(this.inputs[i].name === name)
  97. {
  98. return this.inputs[i];
  99. }
  100. }
  101. return null;
  102. };
  103. Node.prototype.destroy = function()
  104. {
  105. RoundedBox.prototype.destroy.call(this);
  106. for(var i = 0; i < this.inputs.length; i++)
  107. {
  108. this.inputs[i].destroy();
  109. }
  110. for(var i = 0; i < this.outputs.length; i++)
  111. {
  112. this.outputs[i].destroy();
  113. }
  114. };
  115. Node.prototype.onUpdate = function()
  116. {
  117. var height = this.box.max.y - this.box.min.y;
  118. // Input hooks position
  119. var step = height / (this.inputs.length + 1);
  120. var start = this.box.min.y + step;
  121. for(var i = 0; i < this.inputs.length; i++)
  122. {
  123. this.inputs[i].position.set(this.position.x + this.box.min.x, this.position.y + (start + step * i));
  124. }
  125. // Output hooks position
  126. step = height / (this.outputs.length + 1);
  127. start = this.box.min.y + step;
  128. for(var i = 0; i < this.outputs.length; i++)
  129. {
  130. this.outputs[i].position.set(this.position.x + this.box.max.x, this.position.y + (start + step * i));
  131. }
  132. };
  133. Node.prototype.serialize = function(recursive)
  134. {
  135. var data = RoundedBox.prototype.serialize.call(this, recursive);
  136. data.inputs = [];
  137. for(var i = 0; i < this.inputs.length; i++)
  138. {
  139. data.inputs.push(this.inputs[i].uuid);
  140. }
  141. data.outputs = [];
  142. for(var i = 0; i < this.outputs.length; i++)
  143. {
  144. data.outputs.push(this.outputs[i].uuid);
  145. }
  146. return data;
  147. };
  148. Node.prototype.parse = function(data, root)
  149. {
  150. RoundedBox.prototype.parse.call(this, data, root);
  151. for(var i = 0; i < data.inputs.length; i++)
  152. {
  153. this.inputs.push(root.getChildByUUID(data.inputs[i]));
  154. }
  155. for(var i = 0; i < data.outputs.length; i++)
  156. {
  157. this.outputs.push(root.getChildByUUID(data.outputs[i]));
  158. }
  159. };
  160. export {Node};