/*
 *  psychlops_g_fundamental.cpp
 *  Psychlops Standard Library (Universal)
 *
 *  Last Modified 2005/10/05 by Kenchi HOSOKAWA
 *  (C) 2005 Kenchi HOSOKAWA, Kazushi MARUYA, Takao SATO
 */

#include <Math.h>

#include "../math/psychlops_math.h"
#include "psychlops_g_fundamental.h"
#include "psychlops_g_module.h"


namespace Psychlops {




/*	Point::Point() : x(0.0), y(0.0), z(0.0) {}

	Point::Point(const double ix, const double iy, const double iz) : x(ix), y(iy), z(iz) {}
	Point& Point::set(const double ix, const double iy, const double iz) {
		setbypix(ix,iy,iz);
		return *this;
	}
	Point& Point::shift(const double h, const double v, const double d) {
		setbypix(x+h,y+v,z+d);
		return *this;
	}
*/
	Point& Point::centering() {
		*this = Drawable::prime->getCenter();
		return *this;
	}
	Point& Point::centering(const Figure &fig) {
		*this = fig.getDatum();
		return *this;
	}
/*	Point& Point::centering(const double h, const double v, const double d) {
		setbypix(h, v, d);
		return *this;
	}

	Point& Point::setX(const double val) { x = val; return *this; }
	Point& Point::setY(const double val) { y = val; return *this; }

	double Point::getX() const { return x; }
	double Point::getY() const { return y; }
	double Point::getZ() const { return z; }

	Point Point::dup() {
		return *this;
	}

	Point Point::operator+(const Point& rhs) {
		return Point(x+rhs.x, y+rhs.y, z+rhs.z);
	}
	Point Point::operator-(const Point& rhs) {
		return Point(x-rhs.x, y-rhs.y, z-rhs.z);
	}
*/

	double Point::length() const {
		return sqrt((x*x)+(y*y)+(z*z));
	}

}	/*	<- namespace Psycholops 	*/










namespace Psychlops {


	Length::Length() : px_(0.0) {}
	Length::Length(const int val) : px_((double)val) {}
	Length::Length(const double val) : px_(val) {}
	Length::Length(const Length &val) : px_(val.px_) {}

	Length::operator double() const {
		return px_;
	}
	Length & Length::operator =(const double val) {
		px_ = val;
		return *this;
	}


	LENGTH_ARCDEG arcdeg;
	LENGTH_PIXEL pixel;
	Length operator *(double pixels, LENGTH_PIXEL &unit) {
		return Length(pixels);
	}



	ANGLE_DEGREE degree;
	Angle operator *(double degrees, ANGLE_DEGREE &unit) {
		return Angle(degrees, degree);
	}
	ANGLE_RADIAN radian;
	Angle operator *(double radians, ANGLE_RADIAN &unit) {
		return Angle(radians, radian);
	}

	Angle::Angle(double decadegree, int dummy) : decadegree_(decadegree) {
	}
	Angle::Angle() {
	}
	Angle::Angle(const int degrees) {
		set_as_degree((double)degrees);
	}
	Angle::Angle(const double degrees) {
		set_as_degree(degrees);
	}
	Angle::Angle(const double degrees, ANGLE_DEGREE &unit) {
		set_as_degree(degrees);
	}
	Angle::Angle(const double radians, ANGLE_RADIAN &unit) {
		set_as_radian(radians);
	}
	Angle::Angle(const Angle &init) : decadegree_(init.decadegree_) {
	}
	Angle::operator double() const {
		return decadegree_/SCALE_TO_DEGREE;
	}
	Angle Angle::operator =(const double rhs) {
		set_as_degree(rhs);
		return *this;
	}
	Angle Angle::operator +(Angle rhs) const {
		return Angle(decadegree_+rhs.decadegree_, 0);
	}
	Angle Angle::operator -(Angle rhs) const {
		return Angle(decadegree_-rhs.decadegree_, 0);
	}
	Angle & Angle::operator +=(Angle rhs) {
		decadegree_ += rhs.decadegree_;
		return *this;
	}
	Angle & Angle::operator -=(Angle rhs) {
		decadegree_ -= rhs.decadegree_;
		return *this;
	}
	double Angle::clip() const {
		return Math::mod(decadegree_, PERIOD)/SCALE_TO_DEGREE;
	}
	double Angle::at_degree() const {
		return decadegree_/SCALE_TO_DEGREE;
	}
	double Angle::at_radian() const {
		return PI * decadegree_ / HALF_PERIOD;
	}
	double Angle::sin() const {
		return ::sin(this->at_radian());
	}
	double Angle::cos() const {
		return ::cos(this->at_radian());
	}
	double Angle::tan() const {
		return ::tan(this->at_radian());
	}
	void Angle::set_as_degree(double degrees) {
		decadegree_ = degrees * SCALE_TO_DEGREE;
	}
	void Angle::set_as_decadegree(double decadegree) {
		decadegree_ = decadegree;
	}
	void Angle::set_as_radian(double radians) {
		decadegree_ = HALF_PERIOD * radians / PI;
	}

	const double Angle::HALF_PERIOD = PERIOD/2;
	const double Angle::SCALE_TO_DEGREE = PERIOD/360;

	const double Angle::PERIOD = 3600;



}	/*	<- namespace Psycholops 	*/


