Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: code/branches/core7/src/modules/docking/Dock.cc @ 10633

Last change on this file since 10633 was 10478, checked in by landauf, 10 years ago

callStaticNetworkFunction() and callMemberNetworkFunction() are now template functions instead of macros.
simplified function call interface: always pass five MultiType-references. Check if MultiType.null() evaluates to true to see if the argument was defined.
moved references to NetworkFunctionManager to NetworkFunctionIncludes.cc.
this also fixed a linker error in MSVC by including NetworkFunctionIncludes.h in a build-unit inside the network library.

  • Property svn:eol-style set to native
File size: 10.5 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 *      Sven Stucki
24 *   Co-authors:
25 *      ...
26 *
27 */
28
29/**
30    @file Dock.cc
31    @brief Docking system main class
32*/
33
34#include "Dock.h"
35
36#include "core/CoreIncludes.h"
37#include "core/LuaState.h"
38#include "core/GUIManager.h"
39#include "core/command/ConsoleCommandIncludes.h"
40#include "network/NetworkFunctionIncludes.h"
41
42#include "infos/HumanPlayer.h"
43#include "interfaces/PlayerTrigger.h"
44#include "worldentities/pawns/Pawn.h"
45
46namespace orxonox
47{
48    RegisterClass(Dock);
49
50    SetConsoleCommand("Dock", "dock",    &Dock::cmdDock).addShortcut().setAsInputCommand();
51    SetConsoleCommand("Dock", "undock",  &Dock::cmdUndock).addShortcut().setAsInputCommand();
52
53    registerStaticNetworkFunction(Dock::showDockingDialog);
54
55    Dock::Dock(Context* context) : StaticEntity(context)
56    {
57        RegisterObject(Dock);
58    }
59
60    Dock::~Dock()
61    {
62    }
63
64    void Dock::XMLPort(Element& xmlelement, XMLPort::Mode mode)
65    {
66        SUPER(Dock, XMLPort, xmlelement, mode);
67
68        XMLPortObject(Dock, DockingEffect, "effects", addEffect, getEffect, xmlelement, mode);
69        XMLPortObject(Dock, DockingAnimation, "animations", addAnimation, getAnimation, xmlelement, mode);
70        XMLPortEventSink(Dock, BaseObject, "execute", execute, xmlelement, mode);
71        XMLPortEventSink(Dock, BaseObject, "undocking", undocking, xmlelement, mode);
72
73    }
74
75    void Dock::XMLEventPort(Element& xmlelement, XMLPort::Mode mode)
76    {
77        SUPER(Dock, XMLEventPort, xmlelement, mode);
78
79        XMLPortEventSink(Dock, BaseObject, "execute", execute, xmlelement, mode);
80
81        XMLPortEventSink(Dock, BaseObject, "undocking", undocking, xmlelement, mode);
82    }
83
84
85    bool Dock::undocking(bool bTriggered, BaseObject* trigger)
86    {
87
88        PlayerTrigger* pTrigger = orxonox_cast<PlayerTrigger*>(trigger);
89        PlayerInfo* player = NULL;
90
91        // Check whether it is a player trigger and extract pawn from it
92        if(pTrigger != NULL)
93        {
94            if(!pTrigger->isForPlayer()) {  // The PlayerTrigger is not exclusively for Pawns which means we cannot extract one.
95            orxout(verbose, context::docking) << "Docking:execute PlayerTrigger was not triggered by a player.." << endl;
96            return false;
97            }
98            player = pTrigger->getTriggeringPlayer();
99        }
100        else
101        {
102            orxout(verbose, context::docking) << "Docking::execute Not a player trigger, can't extract pawn from it.." << endl;
103            return false;
104        }
105        if(player == NULL)
106        {
107            orxout(verbose, context::docking) << "Docking::execute Can't retrieve PlayerInfo from Trigger. (" << trigger->getIdentifier()->getName() << ")" << endl;
108            return false;
109        }
110
111        if(bTriggered)
112        {
113            // Add player to this Docks candidates
114            candidates_.insert(player);
115
116            // Show docking dialog
117            this->showUndockingDialogHelper(player);
118        }
119        else
120        {
121            // Remove player from candidates list
122            candidates_.erase(player);
123        }
124
125        return true;
126    }
127
128
129
130    bool Dock::execute(bool bTriggered, BaseObject* trigger)
131    {
132        PlayerTrigger* pTrigger = orxonox_cast<PlayerTrigger*>(trigger);
133        PlayerInfo* player = NULL;
134
135        // Check whether it is a player trigger and extract pawn from it
136        if(pTrigger != NULL)
137        {
138            if(!pTrigger->isForPlayer()) {  // The PlayerTrigger is not exclusively for Pawns which means we cannot extract one.
139                orxout(verbose, context::docking) << "Docking:execute PlayerTrigger was not triggered by a player.." << endl;
140                return false;
141            }
142            player = pTrigger->getTriggeringPlayer();
143        }
144        else
145        {
146            orxout(verbose, context::docking) << "Docking::execute Not a player trigger, can't extract pawn from it.." << endl;
147            return false;
148        }
149        if(player == NULL)
150        {
151            orxout(verbose, context::docking) << "Docking::execute Can't retrieve PlayerInfo from Trigger. (" << trigger->getIdentifier()->getName() << ")" << endl;
152            return false;
153        }
154
155        if(bTriggered)
156        {
157            // Add player to this Docks candidates
158            candidates_.insert(player);
159
160            // Show docking dialog
161            this->showDockingDialogHelper(player);
162        }
163        else
164        {
165            // Remove player from candidates list
166            candidates_.erase(player);
167        }
168
169        return true;
170    }
171
172
173    void Dock::showUndockingDialogHelper(PlayerInfo* player)
174        {
175            assert(player);
176
177            if(!player->isHumanPlayer())
178                return;
179
180            if(GameMode::isMaster())
181            {
182                if(GameMode::showsGraphics())
183                    GUIManager::showGUI("UndockingDialog");
184            }
185            else
186                callStaticNetworkFunction(&Dock::showDockingDialog, player->getClientID());
187
188        }
189
190    void Dock::showDockingDialogHelper(PlayerInfo* player)
191    {
192        assert(player);
193       
194        if(!player->isHumanPlayer())
195            return;
196       
197        if(GameMode::isMaster())
198        {
199            if(GameMode::showsGraphics())
200                GUIManager::showGUI("DockingDialog");
201        }
202        else
203            callStaticNetworkFunction(&Dock::showDockingDialog, player->getClientID());
204
205    }
206
207    /*static*/ void Dock::showDockingDialog()
208    {
209        if(GameMode::showsGraphics())
210            GUIManager::showGUI("DockingDialog");
211    }
212
213    void Dock::cmdDock()
214    {
215        PlayerInfo* player = HumanController::getLocalControllerSingleton()->getPlayer();
216        for(ObjectList<Dock>::iterator it = ObjectList<Dock>::begin(); it != ObjectList<Dock>::end(); ++it)
217        {
218            if(it->dock(player))
219                break;
220        }
221    }
222
223    void Dock::cmdUndock()
224    {
225        PlayerInfo* player = HumanController::getLocalControllerSingleton()->getPlayer();
226        for(ObjectList<Dock>::iterator it = ObjectList<Dock>::begin(); it != ObjectList<Dock>::end(); ++it)
227        {
228            if(it->undock(player))
229                break;
230        }
231    }
232
233    bool Dock::dock(PlayerInfo* player)
234    {
235        // Check if player is a candidate
236        if(candidates_.find(player) == candidates_.end())
237        {
238            orxout(internal_warning, context::docking) << "Dock::dock Player is not a candidate!" << endl;
239            return false;
240        }
241
242        candidates_.erase(player);
243        docked_.insert(player);
244
245        if (animations_.empty())
246            return dockingAnimationFinished(player);
247
248        else
249            DockingAnimation::invokeAnimation(true, player, animations_);
250
251        return true;
252    }
253
254    bool Dock::dockingAnimationFinished(PlayerInfo* player)
255    {
256        if(docked_.find(player) == docked_.end())
257        {
258            orxout(internal_warning, context::docking) << "Dock::dockingAnimationFinished Player is not currently docked." << endl;
259            return false;
260        }
261
262        DockingEffect::invokeEffect(true, player, effects_);
263        return true;
264    }
265
266    bool Dock::undock(PlayerInfo* player)
267    {
268        // Check if player is docked to this Dock
269        if(docked_.find(player) == docked_.end())
270        {
271            orxout(internal_warning, context::docking) << "Dock::undock Player is not docked to this Dock." << endl;
272            return false;
273        }
274
275        docked_.erase(player);
276        candidates_.insert(player);
277
278        DockingEffect::invokeEffect(false, player, effects_);
279
280        if (animations_.empty())
281            return undockingAnimationFinished(player);
282        else
283            DockingAnimation::invokeAnimation(false, player, animations_);
284
285        return true;
286    }
287
288    bool Dock::undockingAnimationFinished(PlayerInfo* player) {
289        orxout(verbose, context::docking) << "Dock::undockingAnimationFinished executed" << endl;
290        return true;
291    }
292
293    unsigned int Dock::getNumberOfActiveDocks()
294    {
295        int i = 0;
296        PlayerInfo* player = HumanController::getLocalControllerSingleton()->getPlayer();
297        for(ObjectList<Dock>::iterator it = ObjectList<Dock>::begin(); it != ObjectList<Dock>::end(); ++it)
298        {
299            if(it->candidates_.find(player) != it->candidates_.end())
300                i++;
301        }
302        return i;
303    }
304
305    Dock* Dock::getActiveDockAtIndex(unsigned int index)
306    {
307        PlayerInfo* player = HumanController::getLocalControllerSingleton()->getPlayer();
308        for(ObjectList<Dock>::iterator it = ObjectList<Dock>::begin(); it != ObjectList<Dock>::end(); ++it)
309        {
310            if(it->candidates_.find(player) != it->candidates_.end())
311            {
312                if(index == 0)
313                    return *it;
314                index--;
315            }
316        }
317        return NULL;
318    }
319
320    bool Dock::addEffect(DockingEffect* effect)
321    {
322        assert(effect);
323        effects_.push_back(effect);
324        return true;
325    }
326
327    const DockingEffect* Dock::getEffect(unsigned int i) const
328    {
329        for (std::list<DockingEffect*>::const_iterator effect = this->effects_.begin(); effect != this->effects_.end(); ++effect)
330        {
331            if(i == 0)
332               return *effect;
333            i--;
334        }
335        return NULL;
336    }
337
338    bool Dock::addAnimation(DockingAnimation* animation)
339    {
340        assert(animation);
341        animation->setParent(this);
342        animations_.push_back(animation);
343        return true;
344    }
345
346    const DockingAnimation* Dock::getAnimation(unsigned int i) const
347    {
348        for (std::list<DockingAnimation*>::const_iterator animation = this->animations_.begin(); animation != this->animations_.end(); ++animation)
349        {
350            if(i == 0)
351               return *animation;
352            i--;
353        }
354        return NULL;
355    }
356}
Note: See TracBrowser for help on using the repository browser.