Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: code/trunk/src/orxonox/graphics/Model.cc @ 10022

Last change on this file since 10022 was 9675, checked in by landauf, 11 years ago

merged branch 'libs' back to trunk. orxonox now compiles and runs with ogre 1.8 and it compiles (but doesn't run) with cegui 0.8

  • Property svn:eol-style set to native
File size: 7.5 KB
RevLine 
[2072]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 *      Fabian 'x3n' Landau
24 *   Co-authors:
25 *      ...
26 *
27 */
28
[3196]29#include "Model.h"
[2072]30
[2662]31#include <OgreEntity.h>
[9675]32#include <OgreProgressiveMesh.h>
[3196]33
34#include "core/CoreIncludes.h"
[9667]35#include "core/config/ConfigValueIncludes.h"
[2896]36#include "core/GameMode.h"
[2072]37#include "core/XMLPort.h"
[5735]38#include "Scene.h"
[7163]39#include "graphics/MeshLodInformation.h"
40#include "Level.h"
[2072]41
42namespace orxonox
43{
[9667]44    RegisterClass(Model);
[2072]45
[9667]46    Model::Model(Context* context) :
47        StaticEntity(context), bCastShadows_(true), lodLevel_(5), bLodEnabled_(true), numLodLevels_(10), lodReductionRate_(.15f)
[2072]48    {
49        RegisterObject(Model);
50
[7166]51        this->setConfigValues();
[2072]52        this->registerVariables();
53    }
54
55    Model::~Model()
56    {
57        if (this->isInitialized() && this->mesh_.getEntity())
[2662]58            this->detachOgreObject(this->mesh_.getEntity());
[2072]59    }
60
[7166]61    void Model::setConfigValues()
62    {
[8079]63        SetConfigValueExternal(bGlobalEnableLod_, "GraphicsSettings", "enableMeshLoD", true)
[7166]64            .description("Enable level of detail for models");
65    }
66
[2072]67    void Model::XMLPort(Element& xmlelement, XMLPort::Mode mode)
68    {
69        SUPER(Model, XMLPort, xmlelement, mode);
70
[7163]71        XMLPortParam(Model, "lodLevel", setLodLevel, getLodLevel, xmlelement, mode);
72
[2072]73        XMLPortParam(Model, "mesh", setMeshSource, getMeshSource, xmlelement, mode);
74        XMLPortParam(Model, "shadow", setCastShadows, getCastShadows, xmlelement, mode).defaultValues(true);
75    }
76
77    void Model::registerVariables()
78    {
[3280]79        registerVariable(this->meshSrc_,    VariableDirection::ToClient, new NetworkCallback<Model>(this, &Model::changedMesh));
80        registerVariable(this->bCastShadows_, VariableDirection::ToClient, new NetworkCallback<Model>(this, &Model::changedShadows));
[2072]81    }
82
[7163]83    float Model::getBiggestScale(Vector3 scale3d)
84    {
85        float scaleFactor = scale3d.x;
86        if(scale3d.y>scaleFactor)
87            scaleFactor = scale3d.y;
88        if(scale3d.z>scaleFactor)
89            scaleFactor = scale3d.z;
90        return scaleFactor;
91    }
92
[2072]93    void Model::changedMesh()
94    {
[2896]95        if (GameMode::showsGraphics())
[2662]96        {
97            if (this->mesh_.getEntity())
98                this->detachOgreObject(this->mesh_.getEntity());
[2072]99
[2662]100            this->mesh_.setMeshSource(this->getScene()->getSceneManager(), this->meshSrc_);
[2072]101
[2662]102            if (this->mesh_.getEntity())
103            {
104                this->attachOgreObject(this->mesh_.getEntity());
105                this->mesh_.getEntity()->setCastShadows(this->bCastShadows_);
106                this->mesh_.setVisible(this->isVisible());
[7163]107
[7166]108                if (this->bGlobalEnableLod_)
109                    this->enableLod();
110            }
111        }
112    }
[7163]113
[7166]114    void Model::changedShadows()
115    {
116        this->mesh_.setCastShadows(this->bCastShadows_);
117    }
[7163]118
[7166]119    void Model::changedVisibility()
120    {
121        SUPER(Model, changedVisibility);
[7163]122
[7166]123        this->mesh_.setVisible(this->isVisible());
124    }
[7163]125
[7166]126    void Model::enableLod()
127    {
128        //LOD
129        if( this->mesh_.getEntity()->getMesh()->getNumLodLevels()==1 )
130        {
131            Level* level = this->getLevel();
[7163]132
[7166]133            assert( level != 0 );
[7163]134
[7166]135            MeshLodInformation* lodInfo = level->getLodInfo(this->meshSrc_);
136            if( lodInfo )
137            {
138                setLodLevel(lodInfo->getLodLevel());
139                this->bLodEnabled_ = lodInfo->getEnabled();
140                this->numLodLevels_ = lodInfo->getNumLevels();
141                this->lodReductionRate_ = lodInfo->getReductionRate();
142            }
143            if( this->numLodLevels_>10 )
144            {
[8858]145                orxout(internal_warning, context::lod) << "More than 10 LoD levels requested. Creating only 10." << endl;
[7166]146                this->numLodLevels_ = 10;
147            }
148            if( this->bLodEnabled_ )
149            {
150                float volume = this->mesh_.getEntity()->getBoundingBox().volume();
151/*
152                float scaleFactor = 1;
153
154                BaseObject* creatorPtr = this;
155
156                while(creatorPtr!=NULL&&orxonox_cast<WorldEntity*>(creatorPtr))
157                {
158                    scaleFactor *= getBiggestScale(((WorldEntity*) creatorPtr)->getScale3D());
159                    creatorPtr = creatorPtr->getCreator();
160                }
[8858]161                orxout() << "name: " << this->meshSrc_ << "scaleFactor: " << scaleFactor << ", volume: " << volume << endl;
[7166]162*/
[8858]163                orxout(verbose, context::lod) << "Setting lodLevel for " << this->meshSrc_<< " with lodLevel_: " << this->lodLevel_ <<" and volume: "<< volume << ":" << endl;
[7166]164
[9675]165#if OGRE_VERSION >= 0x010800
166                Ogre::ProgressiveMesh::LodValueList distList;
167#elif OGRE_VERSION >= 0x010700
[7166]168                Ogre::Mesh::LodValueList distList;
[7163]169#else
[7166]170                Ogre::Mesh::LodDistanceList distList;
[7163]171#endif
172
[7166]173                if( lodLevel_>0 )
174                {
175//                    float factor = scaleFactor*5/lodLevel_;
176                    float factor = pow(volume, 2.0f / 3.0f) * 15.0f / lodLevel_;
[7163]177
[8858]178                    orxout(verbose, context::lod) << "LodLevel set with factor: " << factor << endl;
[7163]179
[7166]180                    distList.push_back(70.0f*factor);
181                    distList.push_back(140.0f*factor);
182                    distList.push_back(170.0f*factor);
183                    distList.push_back(200.0f*factor);
184                    distList.push_back(230.0f*factor);
185                    distList.push_back(250.0f*factor);
186                    distList.push_back(270.0f*factor);
187                    distList.push_back(290.0f*factor);
188                    distList.push_back(310.0f*factor);
189                    distList.push_back(330.0f*factor);
190                    while(distList.size()>this->numLodLevels_)
191                        distList.pop_back();
[7163]192
193
[7166]194                    //Generiert LOD-Levels
[9675]195#if OGRE_VERSION >= 0x010800
196                    Ogre::ProgressiveMesh::generateLodLevels(this->mesh_.getEntity()->getMesh().get(), distList, Ogre::ProgressiveMesh::VRQ_PROPORTIONAL,
197                        this->lodReductionRate_);
198#else
[7166]199                    this->mesh_.getEntity()->getMesh()->generateLodLevels(distList, Ogre::ProgressiveMesh::VRQ_PROPORTIONAL, this->lodReductionRate_);
[9675]200#endif
[7166]201                }
202                else
203                {
204                    std::string what;
205                    if(lodLevel_>5)
206                        what = ">5";
207                    else
208                        what = "<0";
[7163]209
[8858]210                    orxout(verbose, context::lod) << "LodLevel not set because lodLevel(" << lodLevel_ << ") was " << what << "." << endl;
[7163]211                }
[2662]212            }
[7166]213            else
[8858]214                orxout(verbose, context::lod) << "LodLevel for " << this->meshSrc_ << " not set because is disabled." << endl;
[2072]215        }
216    }
217}
Note: See TracBrowser for help on using the repository browser.