Skip to content

Instantly share code, notes, and snippets.

@grignaak
Last active December 13, 2015 18:58
Show Gist options
  • Save grignaak/4959075 to your computer and use it in GitHub Desktop.
Save grignaak/4959075 to your computer and use it in GitHub Desktop.
Some JS Vector stuff
/*jshint curly:false */
/*global define:true */
define(function() {
"use strict";
function Vector2D(x,y) {
Object.defineProperties(this, {
x: { value: x, enumerable: true },
y: { value: y, enumerable: true },
_length: { writable: true }
});
}
function dot(a, b) {
return (a.x * b.x) + (a.y * b.y);
}
Vector2D.dot = dot;
var zero = Vector2D.zero = new Vector2D(0,0);
// Create a vector from the polar coordinates (r, theta).
Vector2D.fromPolar = function (radius, angle) {
return new Vector2D(radius * Math.cos(angle), radius * Math.sin(angle));
};
Vector2D.prototype = {
negate: function () {
return new Vector2D(-this.x, -this.y);
},
add: function (other) {
return new Vector2D(this.x + other.x, this.y + other.y);
},
sub: function (other) {
return new Vector2D(this.x - other.x, this.y - other.y);
},
length: function () {
var length = this._length;
if (length !== undefined) return length;
this._length = length = Math.sqrt(this.lengthSquared);
return length;
},
scale: function (factor) {
return new Vector2D(this.x * factor, this.y * factor);
},
distanceSquared: function (other) {
var dx = this.x - other.x, dy = this.y - other.y;
return dx*dx + dy*dy;
},
normalize: function () {
var length = this.length(),
x = this.x, y = this.y;
if (length <= 0) return zero;
return new Vector2D(x / length, y / length);
},
toLength: function (scale) {
var length = this.length();
if (length <= 0 || scale === 0)
return zero;
var factor = scale / length,
x = this.x, y = this.y;
return new Vector2D(x * factor, y * factor);
},
truncatedLength: function(max) {
var lengthSquared = this.lengthSquared;
return (lengthSquared <= max * max) ? this : this.normalizedScale(max);
},
perpindicular: function () {
return new Vector2D(-this.y, this.x);
},
rotate: function (theta) {
var x = this.x, y = this.y,
c = Math.cos(theta), s = Math.sin(theta);
return new Vector2D(
(x * c) - (y * s),
(x * s) + (y * c));
},
projectOnto: function (dest) {
var factor = dot(this, dest) / dest.lengthSquared;
return dest.scale(factor);
},
perpindicularOnto: function (dest) {
return this.projectOnto(dest.perpindicular());
}
};
Object.defineProperty(Vector2D.prototype, 'lengthSquared', {
get: function () {
var x = this.x, y = this.y;
return x*x + y*y;
}
});
return Vector2D;
});
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment