Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: code/branches/hudHS14/src/modules/overlays/hud/HUDNavigation.cc @ 10121

Last change on this file since 10121 was 10110, checked in by aejonas, 10 years ago

new way to display the healthbar on the screen (in a similar way like the existing ship marker)

  • Property svn:eol-style set to native
File size: 26.6 KB
RevLine 
[1505]1/*
2 *   ORXONOX - the hottest 3D action shooter ever to exist
3 *                    > www.orxonox.net <
[1454]4 *
[1505]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 *
[1454]22 *   Author:
23 *      Felix Schulthess
24 *   Co-authors:
[1590]25 *      Reto Grieder
[7801]26 *      Oliver Scheuss
[9016]27 *      Matthias Spalinger
[1454]28 *
29 */
[1393]30
[1601]31#include "HUDNavigation.h"
[1410]32
[6417]33#include <OgreCamera.h>
[7163]34#include <OgreFontManager.h>
[1393]35#include <OgreOverlayManager.h>
[1614]36#include <OgreTextAreaOverlayElement.h>
37#include <OgrePanelOverlayElement.h>
[1410]38
[9526]39#include <typeinfo>
40
[1614]41#include "util/Math.h"
[1616]42#include "util/Convert.h"
[9526]43#include "core/command/ConsoleCommand.h"
[1616]44#include "core/CoreIncludes.h"
45#include "core/XMLPort.h"
[6417]46#include "CameraManager.h"
[5929]47#include "Scene.h"
[5735]48#include "Radar.h"
[6417]49#include "graphics/Camera.h"
50#include "controllers/HumanController.h"
51#include "worldentities/pawns/Pawn.h"
[7163]52#include "worldentities/WorldEntity.h"
[9667]53#include "core/config/ConfigValueIncludes.h"
[7163]54#include "tools/TextureGenerator.h"
55// #include <boost/bind/bind_template.hpp>
[1393]56
[7163]57
[1393]58namespace orxonox
59{
[9526]60
61    SetConsoleCommand("HUDNavigation","selectClosest", &HUDNavigation::selectClosestTarget).addShortcut().keybindMode(KeybindMode::OnPress);
62    SetConsoleCommand("HUDNavigation","selectNext", &HUDNavigation::selectNextTarget).addShortcut().keybindMode(KeybindMode::OnPress);
63
64    static bool compareDistance(std::pair<RadarViewable*, unsigned int> a,
65            std::pair<RadarViewable*, unsigned int> b)
[9348]66    {
67        return a.second < b.second;
68    }
[9667]69    RegisterClass ( HUDNavigation );
[2087]70
[9526]71    HUDNavigation* HUDNavigation::localHUD_s = 0;
72
[9667]73    HUDNavigation::HUDNavigation(Context* context) :
74        OrxonoxOverlay(context)
[9348]75    {
[9939]76        RegisterObject(HUDNavigation);
77        this->setConfigValues();
[2087]78
[9348]79        // Set default values
80        this->setFont("Monofur");
81        this->setTextSize(0.05f);
[9526]82        this->setNavMarkerSize(0.03f);
83        this->setAimMarkerSize(0.02f);
84
[9348]85        this->setDetectionLimit(10000.0f);
[9526]86        this->currentMunitionSpeed_ = 2500.0f;
87
88        this->closestTarget_ = true;
89        this->nextTarget_ = false;
90        HUDNavigation::localHUD_s = this;
[9348]91    }
[2087]92
[9348]93    HUDNavigation::~HUDNavigation()
94    {
95        if (this->isInitialized())
96        {
97            for (std::map<RadarViewable*, ObjectInfo>::iterator it = this->activeObjectList_.begin(); it != this->activeObjectList_.end();)
[9526]98            removeObject((it++)->first);
[9348]99        }
100        this->sortedObjectList_.clear();
101    }
[2087]102
[9348]103    void HUDNavigation::setConfigValues()
104    {
105        SetConfigValue(markerLimit_, 3);
106        SetConfigValue(showDistance_, false);
107    }
[2087]108
[9348]109    void HUDNavigation::XMLPort(Element& xmlelement, XMLPort::Mode mode)
[7163]110    {
[9348]111        SUPER(HUDNavigation, XMLPort, xmlelement, mode);
[2087]112
[9526]113        XMLPortParam(HUDNavigation, "font", setFont, getFont, xmlelement, mode);
114        XMLPortParam(HUDNavigation, "textSize", setTextSize, getTextSize, xmlelement, mode);
115        XMLPortParam(HUDNavigation, "navMarkerSize", setNavMarkerSize, getNavMarkerSize, xmlelement, mode);
[9348]116        XMLPortParam(HUDNavigation, "detectionLimit", setDetectionLimit, getDetectionLimit, xmlelement, mode);
[9526]117        XMLPortParam(HUDNavigation, "aimMarkerSize", setAimMarkerSize, getAimMarkerSize, xmlelement, mode);
[1393]118    }
119
[9348]120    void HUDNavigation::setFont(const std::string& font)
121    {
122        const Ogre::ResourcePtr& fontPtr = Ogre::FontManager::getSingleton().getByName(font);
123        if (fontPtr.isNull())
124        {
125            orxout(internal_warning) << "HUDNavigation: Font '" << font << "' not found" << endl;
126            return;
127        }
128        this->fontName_ = font;
129        for (std::map<RadarViewable*, ObjectInfo>::iterator it = this->activeObjectList_.begin(); it != this->activeObjectList_.end(); ++it)
130        {
131            if (it->second.text_ != NULL)
[9526]132            it->second.text_->setFontName(this->fontName_);
[9348]133        }
134    }
[1564]135
[9348]136    const std::string& HUDNavigation::getFont() const
[1590]137    {
[9348]138        return this->fontName_;
[1590]139    }
[9348]140
141    void HUDNavigation::setTextSize(float size)
[1590]142    {
[9348]143        if (size <= 0.0f)
144        {
145            orxout(internal_warning) << "HUDNavigation: Negative font size not allowed" << endl;
146            return;
147        }
148        this->textSize_ = size;
149        for (std::map<RadarViewable*, ObjectInfo>::iterator it = this->activeObjectList_.begin(); it!=this->activeObjectList_.end(); ++it)
150        {
151            if (it->second.text_)
[9526]152            it->second.text_->setCharHeight(size);
[9348]153        }
[1590]154    }
155
[9348]156    float HUDNavigation::getTextSize() const
[1590]157    {
[9348]158        return this->textSize_;
[1590]159    }
[9348]160
161    float HUDNavigation::getArrowSizeX(int dist) const
[7163]162    {
[9348]163        if (dist < 600)
[9526]164        dist = 600;
[9348]165        return this->getActualSize().x * 900 * this->navMarkerSize_ / dist;
[7163]166    }
[1590]167
[9348]168    float HUDNavigation::getArrowSizeY(int dist) const
[1590]169    {
[9348]170        if (dist < 600)
[9526]171        dist = 600;
[9348]172        return this->getActualSize().y * 900 * this->navMarkerSize_ / dist;
[1590]173    }
174
[9348]175    void HUDNavigation::tick(float dt)
[1590]176    {
[9348]177        SUPER(HUDNavigation, tick, dt);
[1400]178
[9348]179        Camera* cam = CameraManager::getInstance().getActiveCamera();
180        if (cam == NULL)
[9526]181        return;
[9348]182        const Matrix4& camTransform = cam->getOgreCamera()->getProjectionMatrix() * cam->getOgreCamera()->getViewMatrix();
[1399]183
[9348]184        for (std::list<std::pair<RadarViewable*, unsigned int> >::iterator listIt = this->sortedObjectList_.begin(); listIt != this->sortedObjectList_.end(); ++listIt)
[9526]185        listIt->second = (int)((listIt->first->getRVWorldPosition() - HumanController::getLocalControllerSingleton()->getControllableEntity()->getWorldPosition()).length() + 0.5f);
[1564]186
[9348]187        this->sortedObjectList_.sort(compareDistance);
[9016]188
[9348]189        unsigned int markerCount = 0;
190        bool closeEnough = false; // only display objects that are close enough to be relevant for the player
[1399]191
[9526]192        // if the selected object doesn't exist any more or is now out of range select the closest object
193        std::map<RadarViewable*, ObjectInfo>::iterator selectedActiveObject = this->activeObjectList_.find(this->selectedTarget_);
194        if(selectedActiveObject == this->activeObjectList_.end())
195        {
196            this->closestTarget_ = true;
197        }
198        else if(this->detectionLimit_ < (this->selectedTarget_->getRVWorldPosition() - HumanController::getLocalControllerSingleton()->getControllableEntity()->getWorldPosition()).length() + 0.5f)
199        {
200            this->closestTarget_ = true;
201            selectedActiveObject->second.selected_ = false;
202        }
203
204        bool nextHasToBeSelected = false;
205
[9348]206        for (std::list<std::pair<RadarViewable*, unsigned int> >::iterator listIt = this->sortedObjectList_.begin(); listIt != this->sortedObjectList_.end(); ++markerCount, ++listIt)
207        {
208            std::map<RadarViewable*, ObjectInfo>::iterator it = this->activeObjectList_.find(listIt->first);
209            closeEnough = listIt->second < this->detectionLimit_;
210            // display radarviewables on HUD if the marker limit and max-distance is not exceeded
[9526]211            if (markerCount < this->markerLimit_ && (closeEnough || this->detectionLimit_ < 0))
[1580]212            {
[9348]213                // Get Distance to HumanController and save it in the TextAreaOverlayElement.
214                int dist = listIt->second;
215                float textLength = 0.0f;
[1590]216
[9348]217                if (this->showDistance_)
[1580]218                {
[9348]219                    //display distance next to cursor
220                    it->second.text_->setCaption(multi_cast<std::string>(dist));
221                    textLength = multi_cast<std::string>(dist).size() * it->second.text_->getCharHeight() * 0.3f;
[1399]222                }
[9348]223                else
224                {
225                    //display name next to cursor
226                    it->second.text_->setCaption(it->first->getRadarName());
227                    textLength = it->first->getRadarName().size() * it->second.text_->getCharHeight() * 0.3f;
228                }
[7163]229
[9526]230                // select the object that aim-assistant indicates
231                if(this->closestTarget_)
232                // select the closest object
233                {
234                    if(listIt == this->sortedObjectList_.begin())
235                    {
236                        it->second.selected_ = true;
237                        this->selectedTarget_ = it->first;
238                    }
239                    else if(it->second.selected_)
240                    {
241                        it->second.selected_ = false;
242                    }
243
244                }
245                else if(this->nextTarget_)
246                // select the next object in sortedObjectList
247                {
248                    if(nextHasToBeSelected){
249                        it->second.selected_ = true;
250                        this->selectedTarget_ = it->first;
251                        nextHasToBeSelected = false;
252                    }
253                    else if(it->second.selected_)
254                    {
255                        nextHasToBeSelected = true;
256                        it->second.selected_ = false;
257
258                        // check if there's a next object
259                        listIt++;
260                        if(listIt != this->sortedObjectList_.end())
261                        {
262                            // and if the marker limit and max-distance are not exceeded for it
263                            if (markerCount + 1 >= this->markerLimit_ ||
264                                    (listIt->second > this->detectionLimit_ && detectionLimit_ >= 0))
265                            {
266                                // otherwise select the closest object
267                                this->activeObjectList_.find(this->sortedObjectList_.begin()->first)->second.selected_ = true;
268                                this->selectedTarget_ = it->first;
269                                nextHasToBeSelected = false;
270                            }
271                        }
272                        listIt--;
273                    }
274                }
275
276
[9348]277                // Transform to screen coordinates
278                Vector3 pos = camTransform * it->first->getRVWorldPosition();
[9016]279
[9348]280                bool outOfView = true;
281                if (pos.z > 1.0)
282                {
283                    // z > 1.0 means that the object is behind the camera
284                    outOfView = true;
285                    // we have to switch all coordinates (if you don't know why,
286                    // try linear algebra lectures, because I can't explain..)
287                    pos.x = -pos.x;
288                    pos.y = -pos.y;
289                }
290                else
291                    outOfView = pos.x < -1.0 || pos.x > 1.0 || pos.y < -1.0 || pos.y > 1.0;
[9016]292
[9348]293                if (outOfView)
[7163]294                {
[9348]295                    // Object is not in view
296
297                    // Change material only if outOfView changed
298                    if (!it->second.wasOutOfView_)
[7163]299                    {
[10110]300                        it->second.health_->hide();
301                        it->second.panel_->setMaterialName(TextureGenerator::getMaterialName("arrows.png", it->first->getRadarObjectColour()));
[9348]302                        it->second.wasOutOfView_ = true;
[9526]303                        it->second.target_->hide();
[7163]304                    }
[9348]305
306                    //float xDistScale = this->getActualSize().x * 1000.0f * this->navMarkerSize_ / dist;
307                    //float yDistScale = this->getActualSize().y * 1000.0f * this->navMarkerSize_ / dist;
308
309                    // Adjust Arrowsize according to distance
310                    it->second.panel_->setDimensions(getArrowSizeX(dist), getArrowSizeY(dist));
311
312                    // Switch between top, bottom, left and right position of the arrow at the screen border
313                    if (pos.x < pos.y)
314                    {
315                        if (pos.y > -pos.x)
316                        {
317                            // Top
318                            float position = pos.x / pos.y + 1.0f;
319                            it->second.panel_->setPosition((position - it->second.panel_->getWidth()) * 0.5f, 0.0f);
320                            it->second.panel_->setUV(0.5f, 0.0f, 1.0f, 0.5f);
321                            it->second.text_->setLeft((position - textLength) * 0.5f);
322                            it->second.text_->setTop(it->second.panel_->getHeight());
323                        }
324                        else
325                        {
326                            // Left
327                            float position = pos.y / pos.x + 1.0f;
328                            it->second.panel_->setPosition(0.0f, (position - it->second.panel_->getWidth()) * 0.5f);
329                            it->second.panel_->setUV(0.0f, 0.0f, 0.5f, 0.5f);
330                            it->second.text_->setLeft(it->second.panel_->getWidth() + 0.01f);
331                            it->second.text_->setTop((position - it->second.text_->getCharHeight()) * 0.5f);
332                        }
333                    }
[7163]334                    else
335                    {
[9348]336                        if (pos.y < -pos.x)
337                        {
338                            // Bottom
339                            float position = -pos.x / pos.y + 1.0f;
340                            it->second.panel_->setPosition((position - it->second.panel_->getWidth()) * 0.5f, 1.0f - it->second.panel_->getHeight());
341                            it->second.panel_->setUV(0.0f, 0.5f, 0.5f, 1.0f );
342                            it->second.text_->setLeft((position - textLength) * 0.5f);
343                            it->second.text_->setTop(1.0f - it->second.panel_->getHeight() - it->second.text_->getCharHeight());
344                        }
345                        else
346                        {
347                            // Right
348                            float position = -pos.y / pos.x + 1.0f;
349                            it->second.panel_->setPosition(1.0f - it->second.panel_->getWidth(), (position - it->second.panel_->getHeight()) * 0.5f);
350                            it->second.panel_->setUV(0.5f, 0.5f, 1.0f, 1.0f);
351                            it->second.text_->setLeft(1.0f - it->second.panel_->getWidth() - textLength - 0.01f);
352                            it->second.text_->setTop((position - it->second.text_->getCharHeight()) * 0.5f);
353                        }
[7163]354                    }
355                }
[1580]356                else
357                {
[9348]358                    // Object is in view
[7163]359
[9348]360                    // Change material only if outOfView changed
361                    if (it->second.wasOutOfView_)
[7163]362                    {
[9348]363                        //it->second.panel_->setMaterialName("Orxonox/NavTDC");
364                        it->second.panel_->setMaterialName(TextureGenerator::getMaterialName("tdc.png", it->first->getRadarObjectColour()));
365                        it->second.panel_->setDimensions(this->navMarkerSize_ * this->getActualSize().x, this->navMarkerSize_ * this->getActualSize().y);
[9526]366                        it->second.target_->setDimensions(this->aimMarkerSize_ * this->getActualSize().x, this->aimMarkerSize_ * this->getActualSize().y);
[10110]367
368                        //manipulation bzw versuch !!! Jonas
369                        it->second.health_->setMaterialName(TextureGenerator::getMaterialName("bar2b.png", it->first->getRadarObjectColour()));
370
[9348]371                        it->second.wasOutOfView_ = false;
[7163]372                    }
[9348]373
[10110]374                    // Position health (versuch !!!!)
375                    it->second.health_->setLeft((pos.x + 1.0f - it->second.panel_->getWidth()) * 0.5f);
376                    it->second.health_->setTop((-pos.y + 1.0f - it->second.panel_->getHeight()) * 0.5f);
377
378
[9348]379                    // Position marker
380                    it->second.panel_->setUV(0.0f, 0.0f, 1.0f, 1.0f);
381                    it->second.panel_->setLeft((pos.x + 1.0f - it->second.panel_->getWidth()) * 0.5f);
382                    it->second.panel_->setTop((-pos.y + 1.0f - it->second.panel_->getHeight()) * 0.5f);
383
384                    // Position text
385                    it->second.text_->setLeft((pos.x + 1.0f + it->second.panel_->getWidth()) * 0.5f);
386                    it->second.text_->setTop((-pos.y + 1.0f + it->second.panel_->getHeight()) * 0.5f);
[9526]387
388                    // Make sure the overlays are shown
[10110]389
390                    it->second.health_->show();
[9526]391                    it->second.panel_->show();
392                    it->second.text_->show();
393
394                    // Target marker
395                    const Pawn* pawn = dynamic_cast<const Pawn*>(it->first->getWorldEntity());
396                    /* Pawn* humanPawn = HumanController::getLocalControllerEntityAsPawn();*/
397                    if(!it->second.selected_
398                            || it->first->getRVVelocity().squaredLength() == 0
399                            || pawn == NULL
400                            /* TODO : improve getTeam in such a way that it works
401                             * || humanPawn == NULL
402                             * || pawn->getTeam() == humanPawn->getTeam()*/)
403                    {
404                        // don't show marker for not selected enemies nor if the selected doesn't move
405                        it->second.target_->hide();
406                    }
407                    else // object is selected and moves
408                    {
409                        // get the aim position
410                        Vector3* targetPos = this->toAimPosition(it->first);
411                        // Transform to screen coordinates
412                        Vector3 screenPos = camTransform * (*targetPos);
413                        // Check if the target marker is in view too
414                        if(screenPos.z > 1 || screenPos.x < -1.0 || screenPos.x > 1.0
415                                || screenPos.y < -1.0 || screenPos.y > 1.0)
416                        {
417                            it->second.target_->hide();
418                        }
419                        else
420                        {
421                            it->second.target_->setLeft((screenPos.x + 1.0f - it->second.target_->getWidth()) * 0.5f);
422                            it->second.target_->setTop((-screenPos.y + 1.0f - it->second.target_->getHeight()) * 0.5f);
423                            it->second.target_->show();
424                        }
425                        delete targetPos;
426                    }
427
[1411]428                }
429            }
[9348]430            else // do not display on HUD
[9526]431
[1580]432            {
[10110]433                it->second.health_->hide()
[9348]434                it->second.panel_->hide();
435                it->second.text_->hide();
[9526]436                it->second.target_->hide();
[9348]437            }
438        }
[9526]439
440        this->closestTarget_ = false;
441        this->nextTarget_ = false;
[9348]442    }
[7163]443
[9348]444    /** Overridden method of OrxonoxOverlay.
[9526]445     @details
446     Usually the entire overlay scales with scale().
447     Here we obviously have to adjust this.
448     */
[9348]449    void HUDNavigation::sizeChanged()
450    {
451        // Use size to compensate for aspect ratio if enabled.
452        float xScale = this->getActualSize().x;
453        float yScale = this->getActualSize().y;
[7163]454
[9348]455        for (std::map<RadarViewable*, ObjectInfo>::iterator it = this->activeObjectList_.begin(); it != this->activeObjectList_.end(); ++it)
[1580]456        {
[10110]457                if (it->second.health_ != NULL)
458                    it->second.health_->setDimensions(this->healthMarkerSize_ * xScale, this->healthMarkerSize_ * yScale);
[9348]459            if (it->second.panel_ != NULL)
460                it->second.panel_->setDimensions(this->navMarkerSize_ * xScale, this->navMarkerSize_ * yScale);
461            if (it->second.text_ != NULL)
462                it->second.text_->setCharHeight(it->second.text_->getCharHeight() * yScale);
[9526]463            if (it->second.target_ != NULL)
464                it->second.target_->setDimensions(this->aimMarkerSize_ * xScale, this->aimMarkerSize_ * yScale);
[7163]465        }
466    }
[1566]467
[9348]468    void HUDNavigation::addObject(RadarViewable* object)
[7163]469    {
[9348]470        if (showObject(object) == false)
[9526]471        return;
[7163]472
[9348]473        if (this->activeObjectList_.size() >= this->markerLimit_)
[9526]474        if (object == NULL)
475        return;
[7163]476
[9348]477        // Object hasn't been added yet (we know that)
478        assert(this->activeObjectList_.find(object) == this->activeObjectList_.end());
[7163]479
[9348]480        // Scales used for dimensions and text size
481        float xScale = this->getActualSize().x;
482        float yScale = this->getActualSize().y;
[7163]483
[9348]484        // Create everything needed to display the object on the radar and add it to the map
[10110]485        // Create health
486                Ogre::PanelOverlayElement* health = static_cast<Ogre::PanelOverlayElement*>( Ogre::OverlayManager::getSingleton()
487                        .createOverlayElement("Panel", "HUDNavigation_healthMarker_" + getUniqueNumberString()));
488                //panel->setMaterialName("Orxonox/NavTDC");
489                health->setMaterialName(TextureGenerator::getMaterialName("bar2b.png", object->getRadarObjectColour()));
490                health->setDimensions(this->healthMarkerSize_ * xScale, this->healthMarkerSize_ * yScale);
491                //panel->setColour(object->getRadarObjectColour());
[7163]492
[10110]493
[9348]494        // Create arrow/marker
495        Ogre::PanelOverlayElement* panel = static_cast<Ogre::PanelOverlayElement*>( Ogre::OverlayManager::getSingleton()
[9526]496                .createOverlayElement("Panel", "HUDNavigation_navMarker_" + getUniqueNumberString()));
[9348]497        //panel->setMaterialName("Orxonox/NavTDC");
498        panel->setMaterialName(TextureGenerator::getMaterialName("tdc.png", object->getRadarObjectColour()));
499        panel->setDimensions(this->navMarkerSize_ * xScale, this->navMarkerSize_ * yScale);
500        //panel->setColour(object->getRadarObjectColour());
[7163]501
[9526]502        // Create target marker
503        Ogre::PanelOverlayElement* target = static_cast<Ogre::PanelOverlayElement*>(Ogre::OverlayManager::getSingleton()
504                    .createOverlayElement("Panel", "HUDNavigation_targetMarker_" + getUniqueNumberString()));
505        target->setMaterialName(TextureGenerator::getMaterialName("target.png", object->getRadarObjectColour()));
506        target->setDimensions(this->aimMarkerSize_ * xScale, this->aimMarkerSize_ * yScale);
507
508        // Create text
[9348]509        Ogre::TextAreaOverlayElement* text = static_cast<Ogre::TextAreaOverlayElement*>( Ogre::OverlayManager::getSingleton()
[9526]510                .createOverlayElement("TextArea", "HUDNavigation_navText_" + getUniqueNumberString()));
[9348]511        text->setFontName(this->fontName_);
512        text->setCharHeight(text->getCharHeight() * yScale);
513        text->setColour(object->getRadarObjectColour());
[7163]514
[10110]515        health->hide();
[9348]516        panel->hide();
[9526]517        target->hide();
[9348]518        text->hide();
[7163]519
[9526]520        ObjectInfo tempStruct =
[10110]521        {   health, panel, target, text, false, false, false, false};
[9348]522        this->activeObjectList_[object] = tempStruct;
[7163]523
[10110]524        this->background_->addChild(health);
[9348]525        this->background_->addChild(panel);
[9526]526        this->background_->addChild(target);
[9348]527        this->background_->addChild(text);
[7163]528
[9348]529        this->sortedObjectList_.push_front(std::make_pair(object, (unsigned int)0));
530    }
[7163]531
[9348]532    void HUDNavigation::removeObject(RadarViewable* viewable)
[1580]533    {
[9348]534        std::map<RadarViewable*, ObjectInfo>::iterator it = this->activeObjectList_.find(viewable);
[7163]535
[9348]536        if (this->activeObjectList_.find(viewable) != this->activeObjectList_.end())
537        {
538            // Detach overlays
[10110]539                this->background_->removeChild(it->second.health_->getName());
[9348]540            this->background_->removeChild(it->second.panel_->getName());
[9526]541            this->background_->removeChild(it->second.target_->getName());
[9348]542            this->background_->removeChild(it->second.text_->getName());
543            // Properly destroy the overlay elements (do not use delete!)
[10110]544            Ogre::OverlayManager::getSingleton().destroyOverlayElement(it->second.health_);
[9348]545            Ogre::OverlayManager::getSingleton().destroyOverlayElement(it->second.panel_);
[9526]546            Ogre::OverlayManager::getSingleton().destroyOverlayElement(it->second.target_);
[9348]547            Ogre::OverlayManager::getSingleton().destroyOverlayElement(it->second.text_);
548            // Remove from the list
549            this->activeObjectList_.erase(viewable);
550        }
[7163]551
[9348]552        for (std::list<std::pair<RadarViewable*, unsigned int> >::iterator listIt = this->sortedObjectList_.begin(); listIt != this->sortedObjectList_.end(); ++listIt)
553        {
554            if ((listIt->first) == viewable)
555            {
556                this->sortedObjectList_.erase(listIt);
557                break;
558            }
559        }
[1410]560    }
[1590]561
[9348]562    void HUDNavigation::objectChanged(RadarViewable* viewable)
[1590]563    {
[9348]564        // TODO: niceification neccessary ;)
565        removeObject(viewable);
566        addObject(viewable);
567    }
[7163]568
[9348]569    bool HUDNavigation::showObject(RadarViewable* rv)
570    {
571        if (rv == orxonox_cast<RadarViewable*>(this->getOwner()))
[9526]572        return false;
[9348]573        assert(rv->getWorldEntity());
574        if (rv->getWorldEntity()->isVisible() == false || rv->getRadarVisibility() == false)
[9526]575        return false;
[9348]576        return true;
[1590]577    }
[7163]578
[9348]579    void HUDNavigation::changedOwner()
[7163]580    {
[9348]581        const std::set<RadarViewable*>& respawnObjects = this->getOwner()->getScene()->getRadar()->getRadarObjects();
582        for (std::set<RadarViewable*>::const_iterator it = respawnObjects.begin(); it != respawnObjects.end(); ++it)
583        {
584            if (!(*it)->isHumanShip_)
[9526]585            this->addObject(*it);
[9348]586        }
[7163]587    }
[9526]588
589    Vector3* HUDNavigation::toAimPosition(RadarViewable* target) const
590    {
591        Vector3 wePosition = HumanController::getLocalControllerSingleton()->getControllableEntity()->getWorldPosition();
592        Vector3 targetPosition = target->getRVWorldPosition();
593        Vector3 targetSpeed = target->getRVVelocity();
594        Vector3 relativePosition = targetPosition - wePosition; //Vector from attacker to target
595
596        float p_half = relativePosition.dotProduct(targetSpeed)/(targetSpeed.squaredLength() - this->currentMunitionSpeed_ * this->currentMunitionSpeed_);
597        float time1 = -p_half + sqrt(p_half * p_half - relativePosition.squaredLength()/(targetSpeed.squaredLength() - this->currentMunitionSpeed_ * this->currentMunitionSpeed_));
598
599        Vector3* result = new Vector3(targetPosition + targetSpeed * time1);
600        return result;
601    }
602
603    void HUDNavigation::selectClosestTarget()
604    {
605        if(HUDNavigation::localHUD_s)
606        {
607            HUDNavigation::localHUD_s->closestTarget_ = true;
608        }
609    }
610
611    void HUDNavigation::selectNextTarget()
612    {
613        if(HUDNavigation::localHUD_s)
614        {
615            HUDNavigation::localHUD_s->nextTarget_ = true;
616        }
617    }
[7163]618}
Note: See TracBrowser for help on using the repository browser.