// Ray.cpp: implementation of the Ray class.
//
//////////////////////////////////////////////////////////////////////

#include "Ray.h"

//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////

Ray::Ray()
{
	origin = Point(0,0); 
	direction.SetX(1.0f);
	direction.SetY(0.0); 
	angle = 0;
}

Ray::~Ray()
{

}


Ray::Ray(const Point& orig, Angle ang)
{
	origin = orig;
	direction = PolarVector(1.0, ang);
	angle = ang;
}
#define  Sqr(x)     ((x)*(x))
/* intersects a ray and a cricle */
/* return the number of solutions */
/* psol1 1 is not as far along the ray as psol2 */
int Ray::CircleIntersect(const Circle& kruh, Point& psol1, Point& psol2) const
{
	Point center = kruh.GetCenter();
	float radius = kruh.GetRadius();
	float a,b,c,disc;
	float t1, t2;

	a = Sqr(direction.GetX()) + Sqr(direction.GetY());
	b = 2.0f * ((origin.GetX()-center.GetX()) * direction.GetX() + (origin.GetY()-center.GetY()) * direction.GetY());
	c = Sqr(origin.GetX()-center.GetX()) + Sqr(origin.GetY()-center.GetY()) - Sqr(radius);

	disc = Sqr(b) - 4 * a * c;
	if (disc < 0) {
		return 0; // No solutions
	}
  
	disc = (float) sqrt(disc);
	t1 = (-b + disc) / (2.0f * a);
	t2 = (-b - disc) / (2.0f * a);
  
	if (t1 > t2) {
		float temp = t1;
		t1 = t2;
		t2 = temp;
	}
 
	if (t1 > 0.0) {
		if (t2 > 0.0) {
			psol1 = origin + direction * t1;
			psol2 = origin + direction * t2;
			return 2; // Two solutions
		}
		else{
			return 0;
		}
	}
	else if (t2 > 0.0) {
		psol1 = origin + direction * t2;
		psol2 = psol1;
		return 1;
	}
	else
		return 0;
	return 0;
}

