Vector2D Unit::AvoidUnitCollision() { if (DetectUnitCollision()){ std::cout << "\n" << " found"; RenderableObject* closesestUnit = objects[0]; for(std::vector<RenderableObject*>::iterator it = objects.begin(); it != objects.end(); ++it) { RenderableObject* currentObject = *it; Vector2D length = GetPosition() - currentObject->GetPosition(); // std::cout << "\n current : " << length.Length(); // std::cout << "\n current test : " << (GetPosition() - closesestUnit->GetPosition()).Length(); if ((GetPosition() - closesestUnit->GetPosition()).Length() == 0){ closesestUnit = currentObject; } if (length.Length() <= (GetPosition() - closesestUnit->GetPosition()).Length() && length.Length() > 0){ closesestUnit = currentObject; } } Vector2D colPosition = closesestUnit->GetPosition(); Vector2D currentToPosition = (GetPosition() + velocity) - colPosition; return currentToPosition.Normalized(); } else{ return Vector2D(0,0); } }
void UnitCaC::UnitMove() { if (destination->x == x && destination->y == y){ delete destination; destination = NULL; } if (destination != NULL){ Node destinationNode = Tools::GetNodeFromAxis(static_cast <int> (floor(destination->x)),floor(destination->y)); //std::cout << "out of bound X :"<< (int) destinationNode.GetX() << "out of bound Y :"<< (int) destinationNode.GetX() <<"\n" ; if (!Tools::CheckInBound(destinationNode)){ if (destinationNode.GetX()<0){ destinationNode.SetX(0); } if (destinationNode.GetY()<0){ destinationNode.SetY(0); } if (destinationNode.GetX()>33){ destinationNode.SetX(33); } if (destinationNode.GetY()>33){ destinationNode.SetY(33); } delete destination; destination = new Vector2D(destinationNode.GetWorldX(),destinationNode.GetWorldY()); } if ( !Tools::Passable(destinationNode,pathingMap)){ destinationNode = Tools::FindClosestPassable(Tools::GetNodeFromAxis(x,y),destinationNode,pathingMap); //std::cout << "position x : \n"; delete destination; destination = new Vector2D(destinationNode.GetWorldX(),destinationNode.GetWorldY()); } if (path.empty()){ Tools::Astar(Tools::GetNodeFromAxis(x,y),destinationNode,pathingMap, path); } else{ //std::cout << "position x : " << x << "position y : " << y << "\n"; Vector2D targetPosition; int index = 0; index = path.size()-1; speed = 1.5; pathForce = 1; Node currentNode = path[index]; //std::cout << "node x : " << currentNode.GetWorldX() << "node y : " << currentNode.GetWorldY() << "\n"; if (path.size() == 1){ targetPosition = Vector2D(destination->x,destination->y); } else{ targetPosition = Vector2D(currentNode.GetWorldX(),currentNode.GetWorldY()); } //std::cout << "seek x : " << Seek(targetPosition).x << "seek y : " << Seek(targetPosition).y << "\n"; Vector2D steering = velocity + Seek(targetPosition).Normalized() + AvoidUnitCollision(); facing = steering.Normalized(); velocity = steering; velocity.Truncate(speed); //std::cout << "steering x : " << steering.x << "steering y : " << steering.y << "\n"; Move(steering); if( Seek(targetPosition).Length()<= (32/2) && path.size() !=1){ path.erase(path.begin()+index); }else if (Seek(targetPosition).Length() <= 0 && path.size() == 1){ delete destination; destination = NULL; //std::cout << Seek(targetPosition).Length()<< "\n"; path.erase(path.begin()+index); } if (destinationNode.GetX() != path[0].GetX() || destinationNode.GetY()!= path[0].GetY()){ //std::cout << "clear" << "\n"; path.clear(); } //std::cout << Seek(targetPosition).Length()<< "\n"; } } else{ path.clear(); } }
void Unit::SetFacing(Vector2D face) { facing = face.Normalized(); }
int HitOutline::Raycast(Point2D p, Vector2D v, Scalar maxTime, Hit* hitArr, int hitArrSize, Scalar sense) { //local data: Bart Hit localHitArr[100]; int localHitArrSize=100; int hitCount = 0; // TODO: Currently very slow, brute force! int lineVertexCount = m_Lines.size(); int quadVertexCount = m_Quads.size(); Scalar epsilon = 1e-6; Point2D p1 = p; Point2D p2 = p+v; Point2D orig(0,0); Scalar vDv = v.Dot(v); Vector2D n = v.Orthogonal(); // Line-line intersections. if( lineVertexCount > 0 ) { Point2D* lines = &m_Lines[0]; for( int i=0; i<lineVertexCount && hitCount<localHitArrSize; i += 2 ) { Point2D q1 = lines[i+0]; Point2D q2 = lines[i+1]; Vector2D ortho = (q2-q1).Orthogonal(); if( (dot(ortho, v) * sense < 0) || sense==0) { Scalar time1; Scalar time2; if( IntersectLines(p1, p2, q1, q2, time1, time2) ) { if( time1 >= 0 && time1 < maxTime && time2 >= 0 && time2 <= 1 ) { Hit hit; hit.Time = time1; hit.Point = p + time1 * v; hit.Normal = ortho.Normalized(); localHitArr[hitCount++] = hit; } } } } } // Line-quadratic intersections. if( quadVertexCount > 0 ) { Point2D* quads = &m_Quads[0]; for( int i=0; i<quadVertexCount && hitCount<localHitArrSize; i += 3 ) { Vector2D q0 = quads[i+0] - p; Vector2D q1 = quads[i+1] - p; Vector2D q2 = quads[i+2] - p; // Hit only possible if: // (1) not all points are on same side of ray, // // (2) and some points are in front of ray (currently not checked, handled by abc formula) Scalar dot_n_q0 = dot(n,q0); Scalar dot_n_q1 = dot(n,q1); Scalar dot_n_q2 = dot(n,q2); if( dot_n_q0 <= 0 && dot_n_q1 <= 0 && dot_n_q2 <= 0 ) continue; if( dot_n_q0 >= 0 && dot_n_q1 >= 0 && dot_n_q2 >= 0 ) continue; Scalar ts[2]; Scalar a = 2*dot_n_q1-dot_n_q0-dot_n_q2; Scalar b = 2*dot_n_q0-2*dot_n_q1; Scalar c = -dot_n_q0; int n = solveQuadratic(a,b,c,ts); for( int j=0; j<n && hitCount < localHitArrSize; ++j ) { Scalar t = ts[j]; if( t >= 0 && t <= 1 ) { Vector2D diff = (2*(q2-q1)+2*(q0-q1))*t+2*(q1-q0); Vector2D ortho = diff.Orthogonal(); if( (dot(ortho, v) * sense < 0) || sense==0) { Vector2D h = lerp( lerp(q0,q1,t), lerp(q1,q2,t), t); Scalar time = h.Dot(v) / vDv; //time >= -maxTime if( time >= 0 && time < maxTime ) { Hit hit; hit.Point = p+h; hit.Time = time; hit.Normal = ortho.Normalized(); localHitArr[hitCount++] = hit; } } } } } } std::sort(localHitArr, localHitArr+hitCount, sortHitOnTime); //Bart for( int i=0; i<hitCount && i < hitArrSize; ++i ) { hitArr[i]=localHitArr[i]; } return hitCount; }