Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: code/branches/Racingbot/src/modules/gametypes/SpaceRaceController.cc @ 9451

Last change on this file since 9451 was 9451, checked in by purgham, 11 years ago

working Version 19.11.2012 - Bots can allways be included

File size: 9.4 KB
Line 
1/*
2 *   ORXONOX - the hottest 3D action shooter ever to exist
3 *                    > www.orxonox.net <
4 *
5 *
6 *   License notice:
7 *
8 *   This program is free software; you can redistribute it and/or
9 *   modify it under the terms of the GNU General Public License
10 *   as published by the Free Software Foundation; either version 2
11 *   of the License, or (at your option) any later version.
12 *
13 *   This program is distributed in the hope that it will be useful,
14 *   but WITHOUT ANY WARRANTY; without even the implied warranty of
15 *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16 *   GNU General Public License for more details.
17 *
18 *   You should have received a copy of the GNU General Public License
19 *   along with this program; if not, write to the Free Software
20 *   Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
21 *
22 *  Created on: Oct 8, 2012
23 *      Author: purgham
24 */
25 /**
26  * Conventions:
27  * -first Checkpoint has index 0
28  *
29  */
30#include <gametypes/SpaceRaceController.h>
31#include "core/CoreIncludes.h"
32#include "core/XMLPort.h"
33#include "gametypes/SpaceRaceManager.h"
34
35
36
37
38namespace orxonox
39{
40    CreateFactory(SpaceRaceController);
41
42    /*
43     * Idea: Find static Point (checkpoints the spaceship has to reach)
44     */
45    SpaceRaceController::SpaceRaceController(BaseObject* creator) :
46        ArtificialController(creator)
47    {
48        RegisterObject(SpaceRaceController);
49        std::vector<RaceCheckPoint*> checkpoints;
50        for (ObjectList<SpaceRaceManager>::iterator it = ObjectList<SpaceRaceManager>::begin(); it!= ObjectList<SpaceRaceManager>::end(); ++it)
51        {
52            checkpoints = it->getAllCheckpoints();
53            nextRaceCheckpoint_=it->findCheckpoint(1);
54        }
55
56        OrxAssert(!checkpoints.empty(), "No Checkpoints in Level");
57        checkpoints_=checkpoints;
58        staticRacePoints_ = findStaticCheckpoints(checkpoints);
59        // initialisation of currentRaceCheckpoint_
60        currentRaceCheckpoint_ = NULL;
61        // find first Checkpoint
62        for (int i=0; true; i++){
63            if(checkpoints_[i]->getCheckpointIndex()==0){
64                nextRaceCheckpoint_=checkpoints_[i];
65                break;
66            }
67        }
68
69    }
70
71    int SpaceRaceController::distanceSpaceshipToCheckPoint(RaceCheckPoint* CheckPoint)
72    {
73        if (this->getControllableEntity() != NULL)
74        {
75            return (CheckPoint->getPosition()- this->getControllableEntity()->getPosition()).length();
76        }
77        return -1;
78    }
79
80    RaceCheckPoint* SpaceRaceController::nextPointFind(RaceCheckPoint* raceCheckpoint)
81    {
82        int distances[] ={   -1, -1, -1};
83        int temp_i = 0;
84        for (std::set<int>::iterator it =raceCheckpoint->getNextCheckpoints().begin(); it!= raceCheckpoint->getNextCheckpoints().end(); ++it)
85        {
86            distances[temp_i] = recCalculateDistance(raceCheckpoint, this->getControllableEntity()->getPosition());
87            temp_i++;
88        }
89        if (distances[0] > distances[1] && distances[1] != -1)
90        {
91            if (distances[2] < distances[1] && distances[2] != -1)
92            {
93                return checkpoints_[*raceCheckpoint->getNextCheckpoints().end()]; // return [2]
94            }
95            else
96            {
97                std::set<int>::iterator temp = raceCheckpoint->getNextCheckpoints().begin();
98                return checkpoints_[*(++temp)];
99            }
100        }
101        else
102        {
103            if (distances[2] < distances[0] && distances[2] != -1)
104            {
105                return checkpoints_[*raceCheckpoint->getNextCheckpoints().end()]; // return [2]
106            }
107            else
108            {
109                return checkpoints_[*raceCheckpoint->getNextCheckpoints().begin()]; // return [2]
110            }
111        }
112    }
113
114    RaceCheckPoint* SpaceRaceController::adjustNextPoint()
115    {
116        if (currentRaceCheckpoint_ == NULL) // no Adjust possible
117
118        {
119            return nextRaceCheckpoint_;
120        }
121        if ((currentRaceCheckpoint_->getNextCheckpoints()).size() == 1) // no Adjust possible
122
123        {
124            return nextRaceCheckpoint_;
125        }
126
127        //Adjust possible
128
129        return nextPointFind(currentRaceCheckpoint_);
130    }
131
132    int SpaceRaceController::recCalculateDistance(RaceCheckPoint* currentCheckPoint, Vector3 currentPosition)
133    {
134        orxout()<< "rec Aufruf" << endl;
135        // if ( staticCheckPoint was reached)
136        if (std::find(staticRacePoints_.begin(), staticRacePoints_.end(),currentCheckPoint) != staticRacePoints_.end())
137        {
138            return (currentCheckPoint->getPosition() - currentPosition).length();
139        }
140        else
141        {
142            int minimum = std::numeric_limits<int>::max();
143            int temp=0;
144            for (std::set<int>::iterator it = currentCheckPoint->getNextCheckpoints().begin(); it!= currentCheckPoint->getNextCheckpoints().end(); ++it)
145            { //temp++;
146                WorldEntity* ttt= dynamic_cast<WorldEntity*> (currentCheckPoint);
147                OrxAssert(!(ttt==NULL), "WorldEntity null");
148                OrxAssert(!(ttt->getNode()==NULL), "Node of WorldEntity is null");
149
150                //orxout()<< temp <<endl;
151                //if(temp==1){orxout()<<currentCheckPoint << " == null?  => "<<(currentCheckPoint==NULL)<<currentPosition<<endl;}
152                Vector3 t=(currentPosition- ttt->getPosition()); //TODO: Find Crash Reason. Why can't currentCheck access node.
153                int tt=static_cast<int>(t.length());
154                //OrxAssert(!currentCheckPoint.empty(), "currentCheckPoint == null");
155                //OrxAssert(!(it == currentCheckPoint->getNextCheckpoints().end()), "it is null");
156                minimum= std::min(minimum, tt+ recCalculateDistance(checkpoints_[(*it)], currentCheckPoint->getPosition()));
157                // minimum of distanz from 'currentPosition' to the next static Checkpoint
158            }//Error tritt manchmal auf
159            return minimum;
160        }
161    }
162
163    /*
164     * returns a vector of static Point (checkpoints the spaceship has to reach)
165     */
166    std::vector<RaceCheckPoint*> SpaceRaceController::findStaticCheckpoints(
167            std::vector<RaceCheckPoint*> allCheckpoints)
168    {
169        std::map<RaceCheckPoint*, int> * zaehler = new std::map<
170        RaceCheckPoint*, int>(); // counts how many times the checkpoit was reached (for simulation)
171        for (unsigned int i = 0; i < allCheckpoints.size(); i++)
172        {
173            zaehler->insert(std::pair<RaceCheckPoint*, int>(allCheckpoints[i],0));
174        }
175        int maxWays = rekSimulationCheckpointsReached(zaehler->begin()->first,&allCheckpoints, zaehler);
176
177        std::vector<RaceCheckPoint*> returnVec;
178        returnVec.clear();
179        for (std::map<RaceCheckPoint*, int>::iterator iter = zaehler->begin(); iter!= zaehler->end(); iter++)
180        {
181            if (iter->second == maxWays)
182            {
183                //returnVec.insert(allCheckpoints[1]);
184                returnVec.insert(returnVec.end(), iter->first);
185            }
186        }
187        delete zaehler;
188        return returnVec;
189    }
190
191    /*
192     *
193     * return how many ways go from the given checkpoint to the last one
194     */
195    int SpaceRaceController::rekSimulationCheckpointsReached(RaceCheckPoint* currentCheckpoint, std::vector<RaceCheckPoint*>* checkpoints, std::map<RaceCheckPoint*, int>* zaehler)
196    {
197        if (currentCheckpoint->isLast())
198        {// last point reached
199            (*zaehler)[currentCheckpoint] += 1;
200            return 1; // 1 Way form the last point to this one
201        }
202        else
203        {
204            int numberOfWays = 0; // counts number of ways from this Point to the last point
205            for (std::set<int>::iterator it =
206                    currentCheckpoint->getNextCheckpoints().begin(); it
207                    != currentCheckpoint->getNextCheckpoints().end(); ++it)
208            {
209                numberOfWays += rekSimulationCheckpointsReached((*checkpoints)[(*it)], checkpoints, zaehler);
210            }
211            (*zaehler)[currentCheckpoint] += numberOfWays;
212            return numberOfWays; // returns the number of ways from this point to the last one
213        }
214    }
215
216    SpaceRaceController::~SpaceRaceController()
217    {
218        // TODO Auto-generated destructor stub
219    }
220
221    void SpaceRaceController::XMLPort(Element& xmlelement, XMLPort::Mode mode)
222    {
223        SUPER(SpaceRaceController, XMLPort, xmlelement, mode);
224        XMLPortParam(ArtificialController, "accuracy", setAccuracy, getAccuracy, xmlelement, mode).defaultValues(
225                100.0f);
226        XMLPortObject(ArtificialController, WorldEntity, "waypoints", addWaypoint, getWaypoint, xmlelement, mode)
227        ;
228
229    }
230    void SpaceRaceController::tick(float dt)
231    {
232        if (this->getControllableEntity() ==  NULL || this->getControllableEntity()->getPlayer() == NULL ){orxout()<<this->getControllableEntity()<< " in tick"<<endl; return;}
233        if (nextRaceCheckpoint_->playerWasHere(this->getControllableEntity()->getPlayer()))
234        {//Checkpoint erreicht
235            currentRaceCheckpoint_=nextRaceCheckpoint_;
236            OrxAssert(nextRaceCheckpoint_, "next race checkpoint undefined");
237            nextRaceCheckpoint_ = nextPointFind(nextRaceCheckpoint_);
238        }
239        else if (std::abs(lastDistance - distanceSpaceshipToCheckPoint(nextRaceCheckpoint_)) < 500)
240        {
241            nextRaceCheckpoint_ = adjustNextPoint();
242        }
243        this->moveToPosition(nextRaceCheckpoint_->getPosition());
244    }
245
246}
Note: See TracBrowser for help on using the repository browser.