Last active
September 7, 2017 01:47
-
-
Save sujinleeme/468a5ddb4429ea964d66aa5744bf2e28 to your computer and use it in GitHub Desktop.
JavaScript 2D Vector Class
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
class Vector { | |
constructor(v, w) { | |
this.v = v | |
this.w = w | |
this.decimalPlaces = 2 | |
this.sign = { | |
add : '+', | |
subtract: '-', | |
multiply: '*', | |
division:'/' | |
} | |
} | |
exec(sign) { | |
this.convertSinCos() | |
return this.v.map((e, i) => this.round(eval(e + sign + '('+this.w[i]+')'))) | |
} | |
//add vectors | |
add() { | |
return this.exec(this.sign.add) | |
} | |
//subtract vectors | |
sub() { | |
return this.exec(this.sign.subtract) | |
} | |
//scale the vector with multiplication | |
mult() { | |
return this.exec(this.sign.multiply) | |
} | |
// scale the vector with division | |
div() { | |
return this.exec(this.sign.division) | |
} | |
// base logic to get the magnitude of a vector | |
baseMagitude(x, y) { | |
return Math.sqrt(Math.pow(x, 2)+Math.pow(y, 2)) | |
} | |
// calculate the magnitude of a vector with components | |
magnitude(){ | |
const comp = this.components() | |
return this.round(this.baseMagitude(comp[0], comp[1])) | |
} | |
// normalize the vector to a unit length of 1 | |
normalize() { | |
const x = this.v[0] | |
const y = this.v[1] | |
const magnitude = this.baseMagitude(x, y) | |
const base = 1/magnitude | |
return [base*x, base*y] | |
} | |
// Find the components of vector | |
components() { | |
return this.sub().map(e => {return e *-1}) | |
} | |
// limit the magnitude of a vector() | |
limit() { | |
} | |
// the 2D heading of a vector expressed as an angle | |
heading2D() { | |
} | |
//Find the direction angle of unitvector | |
// eg u = 4i + (-2j) | |
directionAngle(){ | |
const quadrant = this.getQuadrant() | |
const rad = Math.atan(this.v[1]/this.v[0]) | |
let deg = rad * 180 / Math.PI | |
switch (quadrant) { | |
case 1: | |
deg = deg | |
case 2: | |
deg += 180 | |
case 3: | |
deg += 180 | |
case 4 : | |
deg += 360 | |
} | |
return this.round(deg) | |
} | |
// the Euclidean distance between two vectors (considered as points) | |
dist() { | |
} | |
// find the angle between two vectors | |
angleBetween() { | |
const x = this.v[0] | |
const y = this.v[1] | |
} | |
// the dot product of two vectors === Scalar product | |
dot() { | |
return this.mult().reduce((acc, val) => { return acc+val }) | |
} | |
// the cross product of two vectors (only relevant in three dimensions) | |
cross(){ | |
} | |
convertSinCos() { | |
const vectors = [this.v, this.w] | |
for (let vector of vectors) { | |
const isDeg = typeof(vector[1])=== 'string' && vector[1].includes("deg") | |
if (isDeg) { | |
const magnitude = vector[0] | |
const dirAngle = vector[1].match(/\d+/g) * (Math.PI / 180); | |
vector[0] = magnitude * Math.cos(dirAngle) | |
vector[1] = magnitude * Math.sin(dirAngle) | |
} | |
} | |
this.v = vectors[0] | |
this.w = vectors[1] | |
return this | |
} | |
round(number) { | |
const precision = this.decimalPlaces | |
let pair = (number + 'e').split('e') | |
let value = Math.round(pair[0] + 'e' + (+pair[1] + precision)) | |
pair = (value + 'e').split('e') | |
return +(pair[0] + 'e' + (+pair[1] - precision)) | |
} | |
getQuadrant() { | |
const x = this.v[0] | |
const y = this.v[1] | |
if (x>=0) { | |
return y >= 0 ? 1 : 4 | |
} else { | |
return y >= 0? 2: 3 | |
} | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment