CSC3095_Project_And_Dissertation_In_Computing / nclgl / Vector3.h
Vector3.h
Raw
#pragma once
/*
Class:Vector3
Implements:
Author:Rich Davison
Description:VERY simple Vector3 class. Students are encouraged to modify this as necessary!

-_-_-_-_-_-_-_,------,   
_-_-_-_-_-_-_-|   /\_/\   NYANYANYAN
-_-_-_-_-_-_-~|__( ^ .^) /
_-_-_-_-_-_-_-""  ""   

*/

static const float pi = 3.14159265358979323846f;
#include <cmath>
#include <iostream>

class Vector3 {
public:	
	Vector3(void) {
		ToZero();
	}

	Vector3(const float x, const float y, const float z) {
		this->x = x;
		this->y = y;
		this->z = z;
	}

	~Vector3(void) {}

	float x;
	float y;
	float z;

	void Normalise() {
		float length = Length();

		if (length != 0.0f) {
			length = 1.0f / length;
			x = x * length;
			y = y * length;
			z = z * length;
		}
	}

	void ToZero() {
		x = y = z = 0.0f;
	}

	float Length() const {
		return sqrt((x*x) + (y*y) + (z*z));
	}

	void Invert() {
		x = -x;
		y = -y;
		z = -z;
	}

	Vector3 Inverse() const {
		return Vector3(-x, -y, -z);
	}

	static float Dot(const Vector3 &a, const Vector3 &b) {
		return (a.x*b.x) + (a.y*b.y) + (a.z*b.z);
	}

	static Vector3 Cross(const Vector3 &a, const Vector3 &b) {
		return Vector3((a.y*b.z) - (a.z*b.y), (a.z*b.x) - (a.x*b.z), (a.x*b.y) - (a.y*b.x));
	}

	inline friend std::ostream& operator<<(std::ostream& o, const Vector3& v) {
		o << "Vector3(" << v.x << "," << v.y << "," << v.z << ")" << std::endl;
		return o;
	}

	inline Vector3  operator+(const Vector3  &a) const {
		return Vector3(x + a.x, y + a.y, z + a.z);
	}

	inline Vector3  operator-(const Vector3  &a) const {
		return Vector3(x - a.x, y - a.y, z - a.z);
	}

	inline Vector3  operator-() const {
		return Vector3(-x, -y, -z);
	}

	inline void operator+=(const Vector3  &a) {
		x += a.x;
		y += a.y;
		z += a.z;
	}

	inline void operator-=(const Vector3  &a) {
		x -= a.x;
		y -= a.y;
		z -= a.z;
	}

	inline Vector3  operator*(const float a) const {
		return Vector3(x * a, y * a, z * a);
	}

	inline Vector3  operator*(const Vector3  &a) const {
		return Vector3(x * a.x, y * a.y, z * a.z);
	}

	inline Vector3  operator/(const Vector3  &a) const {
		return Vector3(x / a.x, y / a.y, z / a.z);
	};

	inline Vector3  operator/(const float v) const {
		return Vector3(x / v, y / v, z / v);
	};

	inline bool	operator==(const Vector3 &A)const { return (A.x == x && A.y == y && A.z == z) ? true : false; };
	inline bool	operator!=(const Vector3 &A)const { return (A.x == x && A.y == y && A.z == z) ? false : true; };

	/**/
	Vector3 makeUnitVector3(const Vector3 &a) const {
		//Store the magnitude of this Vector3D
		float mag = magnitude(a);

		//If magnitude is 0 return default Vector3D
		if (mag == 0.0f) {
			return Vector3();
		}
		//If magnitude is one, return copy of current Vector3D 
		else if (mag == 1.0f) {
			return Vector3(*this);
		}

		//Calculate each component of unit vector
		float xU = x / mag;
		float yU = y / mag;
		float zU = z / mag;

		return Vector3(xU, yU, zU);
	}


	inline float Vector3::magnitude(const Vector3  &a) const {
		return sqrt((pow(x, 2) + pow(y, 2) + pow(z, 2)));
	}





 float Vector3::getAngle(Vector3 v1, Vector3 v2)
 	{
	 float angle=0;
 	//	angle = acos(Vector3::Dot(v1.unit(), v2.unit())); //calculate the angle in radians
 	angle = angle * 180 / pi; // transform the angle in degrees
 		return angle;
 	}




 float dist(const Vector3 &v1, const Vector3 &v2) {
	 float dX = v2.x - v1.x,
		 dY = v2.y - v1.y,
		 dZ = v2.z - v1.z;

	 return sqrtf( (dX*dX) + (dY*dY) + (dZ*dZ)  );
 }


	/*static float distance(Vector3 p1, Vector3 p2)
	{
		return sqrt(pow(p2.x - p1.x, 2) + pow(p2.y - p1.y, 2) + pow(p2.y - p1.y, 2));
	}*/


	Vector3 Vector3::multiply(Vector3 v1, float s)
	{
		Vector3 v2;
		//multiply each component with a scalar
		v2.x = v1.x*s;
		v2.y = v1.y*s;
		v2.z = v1.z*s;
		return v2;
	}






	/**/

	// Sets values of x and y for Vector2
	inline void Vector3::set(float x, float y, float z)
	{
		this->x = x;
		this->y = y;
		this->z = z;
	}

	inline void Vector3::addVector(Vector3 v)
	{
		x += v.x;
		y += v.y;
		z += v.z;
	}

	// Adds to a Vector2 by a constant number
	inline void Vector3::addScalar(float s)
	{
		x += s;
		y += s;
		z += s;
	}

	// Subtracts 2 vectors
	inline void Vector3::subVector(Vector3 v)
	{
		x -= v.x;
		y -= v.y;
		z -= v.z;
	}

	// Subtracts two vectors and returns the difference as a vector
	inline Vector3 Vector3::subTwoVector(Vector3 v, Vector3 v2)
	{
		Vector3 tmp;
		v.x -= v2.x;
		v.y -= v2.y;
		v.z -= v2.z;
		tmp.set(v.x, v.y, v.z);
		return tmp;
	}

	// Adds to a Vector2 by a constant number
	inline void Vector3::subScalar(float s)
	{
		x -= s;
		y -= s;
		z -= s;
	}

	// Multiplies 2 vectors
	inline void Vector3::mulVector(Vector3 v)
	{
		x *= v.x;
		y *= v.y;
		z *= v.z;
	}

	// Adds to a Vector2 by a constant number
	inline void Vector3::mulScalar(float s)
	{
		x *= s;
		y *= s;
		z *= s;
	}

	// Divides 2 vectors
	inline void Vector3::divVector(Vector3 v)
	{
		x /= v.x;
		y /= v.y;
		z /= v.z;
	}

	// Adds to a Vector2 by a constant number
	inline void Vector3::divScalar(float s)
	{
		x /= s;
		y /= s;
		z /= s;
	}

	inline void Vector3::limit(float max)
	{
		float size = magnitudeCalc();

		if (size > max) {
			set(x / size, y / size, z / size);
		}
	}

	// Calculates the distance between the first Vector2 and second Vector2
	inline float Vector3::distanceCalculated(Vector3 v) const
	{
		float dx = x - v.x;
		float dy = y - v.y;
		float dz = z - v.z;
		float dist = sqrt(dx*dx + dy*dy + dz*dz);
		return dist;
	}

/*	// Calculates the dot product of a vector
	float Vector3::dotProduct(Vector3 v) const
	{
		float dot = x * v.x + y * v.y + z * v.z;
		return dot;
	}*/

	// Calculates magnitude of referenced object
	inline float Vector3::magnitudeCalc() const
	{
		return sqrt(x*x + y*y + z*z);
	}





	/*void Vector3::setMagnitude(float x)
	{
		normalize();
		mulScalar(x);
	}*/

	// Calculate the angle between Vector2 1 and Vector2 2
	inline float Vector3::angleBetween(Vector3 v) const
	{
		if (x == 0 && y == 0 && z == 0) return 0.0f;
		if (v.x == 0 && v.y == 0 && z == 0) return 0.0f;

		float dot = x * v.x + y * v.y + z * v.z;
		float v1mag = sqrt(x * x + y * y + z * z);
		float v2mag = sqrt(v.x * v.x + v.y * v.y + v.z * v.z);
		float amt = dot / (v1mag * v2mag); //Based of definition of dot product
											//dot product / product of magnitudes gives amt
		if (amt <= -1) {
			return pi;
		}
		else if (amt >= 1) {
			return 0;
		}
		float tmp = acos(amt);
		return tmp;
	}

/*	// normalize divides x and y by magnitude if it has a magnitude.
	void Vector3::normalize()
	{
		float m = magnitude();

		if (m > 0) {
			set(x / m, y / m, z / m);
		}
		else {
			set(x, y, z);
		}
	}*/

/*	// Creates and returns a copy of the Vector2 used as a parameter
	Vector3 Vector3::copy(Vector3 v)
	{
		Vector3 copy(v.x, v.y, v.z);
		return copy;
	}*/

};