Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: code/branches/towerdefenseFS15/src/modules/towerdefense/TowerDefense.cc @ 10336

Last change on this file since 10336 was 10335, checked in by erbj, 10 years ago

tower don't shoot at the centerpoint anymore(because we shifted it by 2000,hack) and the tower and model are two different things now

  • Property svn:eol-style set to native
File size: 14.6 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 *  Author:
23 *
24 *   Co-authors:
25 *      ...
26 *
27 *NACHRICHT:
28 *
29 * Hier empfehle ich euch die gesamte Spielogik unter zu bringen. Viele Funktionen werden automatisch
30 * bei gewissen Ereignissen aufgerufen bzw. lösen Ereignisse aus
31 *
32 *Z.B:
33 * start() //wird aufgerufen, bevor das Spiel losgeht
34 * end() //wenn man diese Funktion aufruft wird
35 * pawnKilled() // wird aufgerufen, wenn ein Pawn stirbt (z.B: wenn )
36 * playerScored() // kann man aufrufen um dem Spieler Punkte zu vergeben.
37 *
38 *
39 *
40 *TIPP: Eclipse hilft euch schnell auf bereits vorhanden Funktionen zuzugreifen:
41 * einfach "this->" eingeben und kurz warten. Dann tauch eine Liste mit Vorschlägen auf. Wenn ihr jetzt weiter
42 * tippt, werden die Vorschläge entsprechend gefiltert.
43 *
44 *
45 *TIPP: schaut euch mal Tetris::createStone() an. Dort wird ein TetrisStone-Objekt (ControllableEntity) erzeugt,
46 * ihm ein Template zugewiesen (welches vorher im Level definiert wurde und dem CenterPoint übergeben wurde)
47 * Ähnlich könnt ihr vorgehen, um einen Turm zu erzeugen. (Zusätzlich braucht ein Turm noch einen Controller)
48 * z.B: WaypointPatrolController. Wenn kein Team zugewiesen wurde bekämpft ein WaypointPatrolController alles,
49 * was in seiner Reichweite liegt.
50 *
51 *
52 *HUD:
53 * Ein Gametype kann ein HUD (Head up Display haben.) Z.B: hat Pong eine Anzeige welcher Spieler wieviele Punkte hat.
54 * Generell kann man a) Grafiken oder b) Zeichen in einer HUD anzeigen.
55 * Fuer den ersten Schritt reicht reiner Text.
56 *
57 * a)
58 * PongScore.cc uebernehmen und eigene Klasse draus machen.
59 * Wenn ihr bloss anzeigen wollt wieviele Punkte der Spieler bereits erspielt hat (Punkte = Kapital fuer neue Tuerme) dann orientiert ihr euch an
60 * TetrisScore.cc (im pCuts branch): http://www.orxonox.net/browser/code/branches/pCuts/src/modules/tetris/TetrisScore.cc
61 * Ich habe TetrisScore lediglich dazu gebraucht, um eine Variable auf dem HUD auszugeben. Ein Objekt fuer statischen Text gibt es bereits.
62 *
63 * b)
64 * Im naesten Schritt erstellt man die Vorlage fuer das HUD-Objekt: siehe /data/overlays/pongHUD
65 * OverlayText ist eine Vorlage fuer statischen text zb: "Points Scored:". Aus mir nicht erklaerlichen Gruenden sollte man die OverlayText
66 * Objekte immer erst nach dem PongScore anlegen.
67 *
68 * c)  Im TowerDefense gamtype muss im Constructor noch das HUD-Template gesetzt werden.
69 *
70 * d) in CMakeLists.txt noch das Module includen das fuer die Overlays zustaendig ist. Siehe das gleiche File im Pong module.
71 *
72 *
73 *
74 */
75#include "TowerDefense.h"
76#include "TowerDefenseTower.h"
77#include "TowerDefenseCenterpoint.h"
78//#include "TDCoordinate.h"
79#include "worldentities/SpawnPoint.h"
80#include "worldentities/pawns/Pawn.h"
81#include "worldentities/pawns/SpaceShip.h"
82#include "controllers/WaypointController.h"
83#include "graphics/Model.h"
84#include "infos/PlayerInfo.h"
85#include "chat/ChatManager.h"
86#include "core/CoreIncludes.h"
87/* Part of a temporary hack to allow the player to add towers */
88#include "core/command/ConsoleCommand.h"
89
90namespace orxonox
91{
92    RegisterUnloadableClass(TowerDefense);
93
94    TowerDefense::TowerDefense(Context* context) : Deathmatch(context)
95    {
96        RegisterObject(TowerDefense);
97/*
98        for (int i=0; i < 16 ; i++){
99            for (int j = 0; j< 16 ; j++){
100                towermatrix[i][j] = NULL;
101            }
102        }*/
103
104        this->setHUDTemplate("TowerDefenseHUD");
105
106        //this->stats_ = new TowerDefensePlayerStats();
107
108        /* Temporary hack to allow the player to add towers and upgrade them */
109        this->dedicatedAddTower_ = createConsoleCommand( "addTower", createExecutor( createFunctor(&TowerDefense::addTower, this) ) );
110        this->dedicatedUpgradeTower_ = createConsoleCommand( "upgradeTower", createExecutor( createFunctor(&TowerDefense::upgradeTower, this) ) );
111    }
112
113    TowerDefense::~TowerDefense()
114    {
115        /* Part of a temporary hack to allow the player to add towers */
116        if (this->isInitialized())
117        {
118            if( this->dedicatedAddTower_ )
119                delete this->dedicatedAddTower_;
120        }
121    }
122
123    void TowerDefense::setCenterpoint(TowerDefenseCenterpoint *centerpoint)
124    {
125        orxout() << "Centerpoint now setting..." << endl;
126        this->center_ = centerpoint;
127        orxout() << "Centerpoint now set..." << endl;
128    }
129
130    void TowerDefense::start()
131    {
132
133        Deathmatch::start();
134
135// Waypoints: [1,3] [10,3] [10,11] [13,11] -> add the points to a matrix so the player cant place towers on the path
136        for (int i=0; i < 16 ; i++){
137            for (int j = 0; j< 16 ; j++){
138                towermatrix[i][j] = false;
139            }
140        }
141
142        //the path of the spacehips has to be blocked, so that no towers can be build there
143        for (int k=0; k<3; k++)
144            towermatrix[1][k]=true;
145        for (int l=1; l<11; l++)
146            towermatrix[l][3]=true;
147        for (int m=3; m<12; m++)
148            towermatrix[10][m]=true;
149        for (int n=10; n<14; n++)
150            towermatrix[n][11]=true;
151        for (int o=13; o<16; o++)
152            towermatrix[13][o]=true;
153
154        //set initial credits, lifes and WaveNumber
155        this->setCredit(1000);
156        this->setLifes(100);
157        this->setWaveNumber(0);
158        time=0.0;
159
160        //adds initial towers
161        /*
162        for (int i=0; i <7; i++){
163            addTower(i+3,4);
164        }
165        */
166    }
167
168    // Generates a TowerDefenseEnemy. Uses Template "enemytowerdefense". Sets position at first waypoint of path.
169    void TowerDefense::addTowerDefenseEnemy(std::vector<TDCoordinate*> path, int templatenr){
170
171
172        TowerDefenseEnemy* en1 = new TowerDefenseEnemy(this->center_->getContext());
173       
174        switch(templatenr)
175        {
176        case 1 :
177            en1->addTemplate("enemytowerdefense1");
178            en1->setScale(3);
179            en1->setHealth(en1->getHealth() + this->getWaveNumber()*4);
180            break;
181
182        case 2 :
183            en1->addTemplate("enemytowerdefense2");
184            en1->setScale(2);
185            en1->setHealth(en1->getHealth() + this->getWaveNumber()*4);
186            //  en1->setShieldHealth(en1->getShield() = this->getWaveNumber()*2))
187            break;
188
189        case 3 :
190            en1->addTemplate("enemytowerdefense3");
191            en1->setScale(1);
192            en1->setHealth(en1->getHealth() + this->getWaveNumber()*4);
193            break;
194        }
195
196        en1->setTeam(2);
197        en1->getController();
198        en1->setPosition(path.at(0)->get3dcoordinate());
199        TowerDefenseEnemyvector.push_back(en1);
200
201        for(unsigned int i = 0; i < path.size(); ++i)
202        {
203            en1->addWaypoint((path.at(i)));
204        }
205    }
206
207
208    void TowerDefense::end()
209    {
210
211        Deathmatch::end();
212        ChatManager::message("Match is over! Gameover!");
213
214    }
215
216    //not working yet
217    void TowerDefense::upgradeTower(int x,int y)
218    {/*
219        const int upgradeCost = 20;
220
221        if (!this->hasEnoughCreditForTower(upgradeCost))
222        {
223            orxout() << "not enough credit: " << (this->getCredit()) << " available, " << upgradeCost << " needed.";
224            return;
225        }
226
227        if (towermatrix [x][y] == NULL)
228        {
229            orxout() << "no tower on this position" << endl;
230            return;
231        }
232
233        else
234        {
235            (towermatrix [x][y])->upgradeTower();
236        }*/
237    }
238
239    /*adds Tower at Position (x,y) and reduces credit and adds the point to the towermatrix. template ("towerturret")
240    so towers have ability if the turrets
241
242    */
243    void TowerDefense::addTower(int x, int y)
244    {
245        const int towerCost = 20;
246
247        if (!this->hasEnoughCreditForTower(towerCost))
248        {
249            orxout() << "not enough credit: " << (this->getCredit()) << " available, " << towerCost << " needed.";
250            return;
251        }
252
253        if (towermatrix [x][y]==true)
254        {
255            orxout() << "not possible to put tower here!!" << endl;
256            return;
257        }
258
259/*
260        unsigned int width = this->center_->getWidth();
261        unsigned int height = this->center_->getHeight();
262*/
263
264        int tileScale = (int) this->center_->getTileScale();
265
266        if (x > 15 || y > 15 || x < 0 || y < 0)
267        {
268            //Hard coded: TODO: let this depend on the centerpoint's height, width and fieldsize (fieldsize doesn't exist yet)
269            orxout() << "Can not add Tower: x and y should be between 0 and 15" << endl;
270            return;
271        }
272
273        orxout() << "Will add tower at (" << (x-8) * tileScale << "," << (y-8) * tileScale << ")" << endl;
274
275       //Reduce credit
276        this->buyTower(towerCost);
277        towermatrix [x][y]=true;
278
279        //Create Model
280        Model* newtowermodel = new Model(this->center_->getContext());
281        newtowermodel->setMeshSource("Tower.mesh");
282        newtowermodel->setScale(45);
283        newtowermodel->setPosition(static_cast<float>((x-8) * tileScale), static_cast<float>((y-8) * tileScale), 50);
284
285
286
287        //Creates tower
288        TowerDefenseTower* towernew = new TowerDefenseTower(this->center_->getContext());
289        towernew->setPosition(static_cast<float>((x-8) * tileScale), static_cast<float>((y-8) * tileScale), 275);
290        towernew->setGame(this);
291        towernew->setTeam(1);
292    }
293
294    bool TowerDefense::hasEnoughCreditForTower(int towerCost)
295    {
296        return ((this->getCredit()) >= towerCost);
297    }
298
299
300    bool TowerDefense::hasEnoughCreditForUpgrade()
301    {
302        return true;
303    }
304
305 
306    void TowerDefense::tick(float dt)
307    {
308        SUPER(TowerDefense, tick, dt);
309        time +=dt;
310
311        TDCoordinate* coord1 = new TDCoordinate(1,1);
312        std::vector<TDCoordinate*> path;
313        path.push_back(coord1);
314        if(time>1 && TowerDefenseEnemyvector.size() < 30)
315        {
316            //adds different types of enemys depending on the WaveNumber
317            addTowerDefenseEnemy(path, this->getWaveNumber() % 3 +1 );
318            time = time-1;
319        }
320
321        Vector3* endpoint = new Vector3(500, 700, 150);
322        //if ships are at the end they get destroyed
323        for(unsigned int i =0; i < TowerDefenseEnemyvector.size(); ++i)
324        {
325            if(TowerDefenseEnemyvector.at(i) != NULL && TowerDefenseEnemyvector.at(i)->isAlive())
326            {
327                //destroys enemys at the end of teh path and reduces the life by 1. no credits gifted
328
329                Vector3 ship = TowerDefenseEnemyvector.at(i)->getRVWorldPosition();
330                float distance = ship.distance(*endpoint);
331
332                if(distance <50){
333                    TowerDefenseEnemyvector.at(i)->destroy();
334                    this->reduceLifes(1);
335                    this->buyTower(1);
336                    if (this->getLifes()==0)
337                    {
338                        this->end();
339                    }
340                }
341            }
342        }
343        //goes thorugh vector to see if an enemy is still alive. if not next wave is launched
344        int count= 0;
345        for(unsigned int i =0; i < TowerDefenseEnemyvector.size(); ++i)
346        {
347            if(TowerDefenseEnemyvector.at(i)!= NULL)
348            {
349                ++count;
350            }
351        }
352
353        if(count== 0)
354        {
355            time2 +=dt;
356            if(time2 > 10)
357            {
358                TowerDefenseEnemyvector.clear();
359                this->nextwave();
360                time=0;
361                time2=0;
362            }
363        }
364
365
366    }
367
368    // Function to test if we can add waypoints using code only. Doesn't work yet
369
370    // THE PROBLEM: WaypointController's getControllableEntity() returns null, so it won't track. How do we get the controlableEntity to NOT BE NULL???
371    /*
372    void TowerDefense::addWaypointsAndFirstEnemy()
373    {
374        SpaceShip *newShip = new SpaceShip(this->center_);
375        newShip->addTemplate("spaceshipassff");
376
377        WaypointController *newController = new WaypointController(newShip);
378        newController->setAccuracy(3);
379
380        Model *wayPoint1 = new Model(newController);
381        wayPoint1->setMeshSource("crate.mesh");
382        wayPoint1->setPosition(7,-7,5);
383        wayPoint1->setScale(0.2);
384
385        Model *wayPoint2 = new Model(newController);
386        wayPoint2->setMeshSource("crate.mesh");
387        wayPoint2->setPosition(7,7,5);
388        wayPoint2->setScale(0.2);
389
390        newController->addWaypoint(wayPoint1);
391        newController->addWaypoint(wayPoint2);
392
393        // The following line causes the game to crash
394
395        newShip->setController(newController);
396//        newController -> getPlayer() -> startControl(newShip);
397        newShip->setPosition(-7,-7,5);
398        newShip->setScale(0.1);
399        //newShip->addSpeed(1);
400
401
402
403//      this->center_->attach(newShip);
404    }
405    */
406    /*
407    void TowerDefense::playerEntered(PlayerInfo* player)
408    {
409        Deathmatch::playerEntered(player);
410
411        const std::string& message = player->getName() + " entered the game";
412        ChatManager::message(message);
413    }
414
415    bool TowerDefense::playerLeft(PlayerInfo* player)
416    {
417        bool valid_player = Deathmatch::playerLeft(player);
418
419        if (valid_player)
420        {
421            const std::string& message = player->getName() + " left the game";
422            ChatManager::message(message);
423        }
424
425        return valid_player;
426    }
427
428
429    void TowerDefense::pawnKilled(Pawn* victim, Pawn* killer)
430    {
431        if (victim && victim->getPlayer())
432        {
433            std::string message;
434            if (killer)
435            {
436                if (killer->getPlayer())
437                    message = victim->getPlayer()->getName() + " was killed by " + killer->getPlayer()->getName();
438                else
439                    message = victim->getPlayer()->getName() + " was killed";
440            }
441            else
442                message = victim->getPlayer()->getName() + " died";
443
444            ChatManager::message(message);
445        }
446
447        Deathmatch::pawnKilled(victim, killer);
448    }
449
450    void TowerDefense::playerScored(PlayerInfo* player, int score)
451    {
452        Gametype::playerScored(player, score);
453    }*/
454}
Note: See TracBrowser for help on using the repository browser.