A cool starry night scene. Made for Christmas (actually new year) 2016.

Vector.js 6.5KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219
  1. "use strict";
  2. /******************************************************
  3. ************** Simple ES6 Vector Class **************
  4. ******************************************************
  5. * Author: Starbeamrainbowlabs
  6. * Twitter: @SBRLabs
  7. * Email: feedback at starbeamrainbowlabs dot com
  8. *
  9. * From https://gist.github.com/sbrl/69a8fa588865cacef9c0
  10. ******************************************************
  11. * Originally written for my 2D Graphics ACW at Hull
  12. * University.
  13. ******************************************************
  14. * Changelog
  15. ******************************************************
  16. * 19th December 2015:
  17. * Added this changelog.
  18. * 28th December 2015:
  19. * Rewrite tests with klud.js + Node.js
  20. * 30th January 2016:
  21. * Tweak angleFrom function to make it work properly.
  22. * 31st January 2016:
  23. * Add the moveTowards function.
  24. * Add the minComponent getter.
  25. * Add the maxComponent getter.
  26. * Add the equalTo function.
  27. * Tests still need to be written for all of the above.
  28. * 19th September 2016:
  29. * Added Vector support to the multiply method.
  30. */
  31. class Vector {
  32. // Constructor
  33. constructor(inX, inY) {
  34. if (typeof inX != "number") throw new Error("Invalid x value.");
  35. if (typeof inY != "number") throw new Error("Invalid y value.");
  36. // Store the (x, y) coordinates
  37. this.x = inX;
  38. this.y = inY;
  39. }
  40. /**
  41. * Add another vector to this vector.
  42. * @param {Vector} v The vector to add.
  43. * @return {Vector} The current vector. useful for daisy-chaining calls.
  44. */
  45. add(v) {
  46. this.x += v.x;
  47. this.y += v.y;
  48. return this;
  49. }
  50. /**
  51. * Take another vector from this vector.
  52. * @param {Vector} v The vector to subtrace from this one.
  53. * @return {Vector} The current vector. useful for daisy-chaining calls.
  54. */
  55. subtract(v) {
  56. this.x -= v.x;
  57. this.y -= v.y;
  58. return this;
  59. }
  60. /**
  61. * Divide the current vector by a given value.
  62. * @param {number} value The value to divide by.
  63. * @return {Vector} The current vector. Useful for daisy-chaining calls.
  64. */
  65. divide(value) {
  66. if (typeof value != "number") throw new Error("Can't divide by non-number value.");
  67. this.x /= value;
  68. this.y /= value;
  69. return this;
  70. }
  71. /**
  72. * Multiply the current vector by a given value.
  73. * @param {(number|Vector)} value The number (or Vector) to multiply the current vector by.
  74. * @return {Vector} The current vector. useful for daisy-chaining calls.
  75. */
  76. multiply(value) {
  77. if (value instanceof Vector) {
  78. this.x *= value.x;
  79. this.y *= value.y;
  80. } else if (typeof value == "number") {
  81. this.x *= value;
  82. this.y *= value;
  83. } else throw new Error("Can't multiply by non-number value.");
  84. return this;
  85. }
  86. /**
  87. * Move the vector towards the given vector by the given amount.
  88. * @param {Vector} v The vector to move towards.
  89. * @param {number} amount The distance to move towards the given vector.
  90. */
  91. moveTowards(v, amount) {
  92. // From http://stackoverflow.com/a/2625107/1460422
  93. var dir = new Vector(
  94. v.x - this.x,
  95. v.y - this.y).limitTo(amount);
  96. this.x += dir.x;
  97. this.y += dir.y;
  98. return this;
  99. }
  100. /**
  101. * Limit the length of the current vector to value without changing the
  102. * direction in which the vector is pointing.
  103. * @param {number} value The number to limit the current vector's length to.
  104. * @return {Vector} The current vector. useful for daisy-chaining calls.
  105. */
  106. limitTo(value) {
  107. if (typeof value != "number") throw new Error("Can't limit to non-number value.");
  108. this.divide(this.length);
  109. this.multiply(value);
  110. return this;
  111. }
  112. /**
  113. * Return the dot product of the current vector and another vector.
  114. * @param {Vector} v The other vector we should calculate the dot product with.
  115. * @return {Vector} The current vector. useful for daisy-chaining calls.
  116. */
  117. dotProduct(v) {
  118. return (this.x * v.x) + (this.y * v.y);
  119. }
  120. /**
  121. * Calculate the angle, in radians, from north to another vector.
  122. * @param {Vector} v The other vector to which to calculate the angle.
  123. * @return {Vector} The current vector. useful for daisy-chaining calls.
  124. */
  125. angleFrom(v) {
  126. // From http://stackoverflow.com/a/16340752/1460422
  127. var angle = Math.atan2(v.y - this.y, v.x - this.x) - (Math.PI / 2);
  128. angle += Math.PI / 2;
  129. if (angle < 0) angle += Math.PI * 2;
  130. return angle;
  131. }
  132. /**
  133. * Clones the current vector.
  134. * @return {Vector} A clone of the current vector. Very useful for passing around copies of a vector if you don't want the original to be altered.
  135. */
  136. clone() {
  137. return new Vector(this.x, this.y);
  138. }
  139. /*
  140. * Returns a representation of the current vector as a string.
  141. * @returns {string} A representation of the current vector as a string.
  142. */
  143. toString() {
  144. return` ($ {
  145. this.x
  146. }, $ {
  147. this.y
  148. })`;
  149. }
  150. /**
  151. * Whether the vector is equal to another vector.
  152. * @param {Vector} v The vector to compare to.
  153. * @return {boolean} Whether the current vector is equal to the given vector.
  154. */
  155. equalTo(v) {
  156. if (this.x == v.x && this.y == v.y) return true;
  157. else return false;
  158. }
  159. /**
  160. * Get the unit vector of the current vector - that is a vector poiting in the same direction with a length of 1. Note that this does *not* alter the original vector.
  161. * @return {Vector} The current vector's unit form.
  162. */
  163. get unitVector() {
  164. var length = this.length;
  165. return new Vector(
  166. this.x / length,
  167. this.y / length);
  168. }
  169. /**
  170. * Get the length of the current vector.
  171. * @return {number} The length of the current vector.
  172. */
  173. get length() {
  174. return Math.sqrt((this.x * this.x) + (this.y * this.y));
  175. }
  176. /**
  177. * Get the value of the minimum component of the vector.
  178. * @return {number} The minimum component of the vector.
  179. */
  180. get minComponent() {
  181. return Math.min(this.x, this.y);
  182. }
  183. /**
  184. * Get the value of the maximum component of the vector.
  185. * @return {number} The maximum component of the vector.
  186. */
  187. get maxComponent() {
  188. return Math.min(this.x, this.y);
  189. }
  190. }
  191. // Make Vector.js Node.js friendly
  192. export default Vector;