Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: downloads/OgreMain/src/OgreMovableObject.cpp @ 1

Last change on this file since 1 was 1, checked in by landauf, 17 years ago
File size: 12.8 KB
Line 
1/*
2-----------------------------------------------------------------------------
3This source file is part of OGRE
4    (Object-oriented Graphics Rendering Engine)
5For the latest info, see http://www.ogre3d.org/
6
7Copyright (c) 2000-2006 Torus Knot Software Ltd
8Also see acknowledgements in Readme.html
9
10This program is free software; you can redistribute it and/or modify it under
11the terms of the GNU Lesser General Public License as published by the Free Software
12Foundation; either version 2 of the License, or (at your option) any later
13version.
14
15This program is distributed in the hope that it will be useful, but WITHOUT
16ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
17FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details.
18
19You should have received a copy of the GNU Lesser General Public License along with
20this program; if not, write to the Free Software Foundation, Inc., 59 Temple
21Place - Suite 330, Boston, MA 02111-1307, USA, or go to
22http://www.gnu.org/copyleft/lesser.txt.
23
24You may alternatively use this source under the terms of a specific version of
25the OGRE Unrestricted License provided you have obtained such a license from
26Torus Knot Software Ltd.
27-----------------------------------------------------------------------------
28*/
29#include "OgreStableHeaders.h"
30
31#include "OgreMovableObject.h"
32#include "OgreSceneNode.h"
33#include "OgreTagPoint.h"
34#include "OgreLight.h"
35#include "OgreEntity.h"
36#include "OgreRoot.h"
37#include "OgreSceneManager.h"
38#include "OgreCamera.h"
39
40namespace Ogre {
41        //-----------------------------------------------------------------------
42        //-----------------------------------------------------------------------
43        uint32 MovableObject::msDefaultQueryFlags = 0xFFFFFFFF;
44        uint32 MovableObject::msDefaultVisibilityFlags = 0xFFFFFFFF;
45    //-----------------------------------------------------------------------
46    MovableObject::MovableObject()
47        : mCreator(0)
48        , mManager(0)
49        , mParentNode(0)
50        , mParentIsTagPoint(false)
51        , mVisible(true)
52        , mUpperDistance(0)
53        , mSquaredUpperDistance(0)
54        , mBeyondFarDistance(false)
55        , mRenderQueueID(RENDER_QUEUE_MAIN)
56        , mRenderQueueIDSet(false)
57        , mQueryFlags(msDefaultQueryFlags)
58        , mVisibilityFlags(msDefaultVisibilityFlags)
59        , mCastShadows(true)
60        , mRenderingDisabled(false)
61        , mListener(0)
62        , mLightListUpdated(0)
63    {
64    }
65    //-----------------------------------------------------------------------
66    MovableObject::MovableObject(const String& name)
67        : mName(name)
68        , mCreator(0)
69        , mManager(0)
70        , mParentNode(0)
71        , mParentIsTagPoint(false)
72        , mVisible(true)
73        , mUpperDistance(0)
74        , mSquaredUpperDistance(0)
75        , mBeyondFarDistance(false)
76        , mRenderQueueID(RENDER_QUEUE_MAIN)
77        , mRenderQueueIDSet(false)
78        , mQueryFlags(msDefaultQueryFlags)
79        , mVisibilityFlags(msDefaultVisibilityFlags)
80        , mCastShadows(true)
81        , mRenderingDisabled(false)
82        , mListener(0)
83        , mLightListUpdated(0)
84    {
85    }
86    //-----------------------------------------------------------------------
87    MovableObject::~MovableObject()
88    {
89        // Call listener (note, only called if there's something to do)
90        if (mListener)
91        {
92            mListener->objectDestroyed(this);
93        }
94
95        if (mParentNode)
96        {
97            // detach from parent
98            if (mParentIsTagPoint)
99            {
100                // May be we are a lod entity which not in the parent entity child object list,
101                // call this method could safely ignore this case.
102                static_cast<TagPoint*>(mParentNode)->getParentEntity()->detachObjectFromBone(this);
103            }
104            else
105            {
106                // May be we are a lod entity which not in the parent node child object list,
107                // call this method could safely ignore this case.
108                static_cast<SceneNode*>(mParentNode)->detachObject(this);
109            }
110        }
111    }
112    //-----------------------------------------------------------------------
113    void MovableObject::_notifyAttached(Node* parent, bool isTagPoint)
114    {
115        assert(!mParentNode || !parent);
116
117        bool different = (parent != mParentNode);
118
119        mParentNode = parent;
120        mParentIsTagPoint = isTagPoint;
121
122        // Mark light list being dirty, simply decrease
123        // counter by one for minimise overhead
124        --mLightListUpdated;
125
126        // Call listener (note, only called if there's something to do)
127        if (mListener && different)
128        {
129            if (mParentNode)
130                mListener->objectAttached(this);
131            else
132                mListener->objectDetached(this);
133        }
134    }
135    //-----------------------------------------------------------------------
136    Node* MovableObject::getParentNode(void) const
137    {
138        return mParentNode;
139    }
140    //-----------------------------------------------------------------------
141    SceneNode* MovableObject::getParentSceneNode(void) const
142    {
143        if (mParentIsTagPoint)
144        {
145            TagPoint* tp = static_cast<TagPoint*>(mParentNode);
146            return tp->getParentEntity()->getParentSceneNode();
147        }
148        else
149        {
150            return static_cast<SceneNode*>(mParentNode);
151        }
152    }
153    //-----------------------------------------------------------------------
154    bool MovableObject::isAttached(void) const
155    {
156        return (mParentNode != 0);
157
158    }
159    //-----------------------------------------------------------------------
160        bool MovableObject::isInScene(void) const
161        {
162                if (mParentNode != 0)
163                {
164                        if (mParentIsTagPoint)
165                        {
166                                TagPoint* tp = static_cast<TagPoint*>(mParentNode);
167                                return tp->getParentEntity()->isInScene();
168                        }
169                        else
170                        {
171                                SceneNode* sn = static_cast<SceneNode*>(mParentNode);
172                                return sn->isInSceneGraph();
173                        }
174                }
175                else
176                {
177                        return false;
178                }
179        }
180    //-----------------------------------------------------------------------
181    void MovableObject::_notifyMoved(void)
182    {
183        // Mark light list being dirty, simply decrease
184        // counter by one for minimise overhead
185        --mLightListUpdated;
186
187        // Notify listener if exists
188        if (mListener)
189        {
190            mListener->objectMoved(this);
191        }
192    }
193    //-----------------------------------------------------------------------
194    void MovableObject::setVisible(bool visible)
195    {
196        mVisible = visible;
197    }
198    //-----------------------------------------------------------------------
199    bool MovableObject::getVisible(void) const
200    {
201        return mVisible;
202    }
203    //-----------------------------------------------------------------------
204    bool MovableObject::isVisible(void) const
205    {
206        if (!mVisible || mBeyondFarDistance || mRenderingDisabled)
207            return false;
208
209        SceneManager* sm = Root::getSingleton()._getCurrentSceneManager();
210        if (sm && !(mVisibilityFlags & sm->_getCombinedVisibilityMask()))
211            return false;
212
213        return true;
214    }
215        //-----------------------------------------------------------------------
216        void MovableObject::_notifyCurrentCamera(Camera* cam)
217        {
218                if (mParentNode)
219                {
220                        if (cam->getUseRenderingDistance() && mUpperDistance > 0)
221                        {
222                                Real rad = getBoundingRadius();
223                                Real squaredDepth = mParentNode->getSquaredViewDepth(cam);
224                                // Max distance to still render
225                                Real maxDist = mUpperDistance + rad;
226                                if (squaredDepth > Math::Sqr(maxDist))
227                                {
228                                        mBeyondFarDistance = true;
229                                }
230                                else
231                                {
232                                        mBeyondFarDistance = false;
233                                }
234                        }
235                        else
236                        {
237                                mBeyondFarDistance = false;
238                        }
239                }
240
241        mRenderingDisabled = mListener && !mListener->objectRendering(this, cam);
242        }
243    //-----------------------------------------------------------------------
244    void MovableObject::setRenderQueueGroup(uint8 queueID)
245    {
246                assert(queueID <= RENDER_QUEUE_MAX && "Render queue out of range!");
247        mRenderQueueID = queueID;
248        mRenderQueueIDSet = true;
249    }
250    //-----------------------------------------------------------------------
251    uint8 MovableObject::getRenderQueueGroup(void) const
252    {
253        return mRenderQueueID;
254    }
255    //-----------------------------------------------------------------------
256        const Matrix4& MovableObject::_getParentNodeFullTransform(void) const
257        {
258               
259                if(mParentNode)
260                {
261                        // object attached to a sceneNode
262                        return mParentNode->_getFullTransform();
263                }
264        // fallback
265        return Matrix4::IDENTITY;
266        }
267    //-----------------------------------------------------------------------
268    const AxisAlignedBox& MovableObject::getWorldBoundingBox(bool derive) const
269    {
270        if (derive)
271        {
272            mWorldAABB = this->getBoundingBox();
273            mWorldAABB.transformAffine(_getParentNodeFullTransform());
274        }
275
276        return mWorldAABB;
277
278    }
279    //-----------------------------------------------------------------------
280        const Sphere& MovableObject::getWorldBoundingSphere(bool derive) const
281        {
282                if (derive)
283                {
284                        mWorldBoundingSphere.setRadius(getBoundingRadius());
285                        mWorldBoundingSphere.setCenter(mParentNode->_getDerivedPosition());
286                }
287                return mWorldBoundingSphere;
288        }
289    //-----------------------------------------------------------------------
290    const LightList& MovableObject::queryLights(void) const
291    {
292        // Try listener first
293        if (mListener)
294        {
295            const LightList* lightList =
296                mListener->objectQueryLights(this);
297            if (lightList)
298            {
299                return *lightList;
300            }
301        }
302
303        // Query from parent entity if exists
304        if (mParentIsTagPoint)
305        {
306            TagPoint* tp = static_cast<TagPoint*>(mParentNode);
307            return tp->getParentEntity()->queryLights();
308        }
309
310        if (mParentNode)
311        {
312            SceneNode* sn = static_cast<SceneNode*>(mParentNode);
313
314            // Make sure we only update this only if need.
315            ulong frame = sn->getCreator()->_getLightsDirtyCounter();
316            if (mLightListUpdated != frame)
317            {
318                mLightListUpdated = frame;
319
320                sn->findLights(mLightList, this->getBoundingRadius());
321            }
322        }
323        else
324        {
325            mLightList.clear();
326        }
327
328        return mLightList;
329    }
330    //-----------------------------------------------------------------------
331    ShadowCaster::ShadowRenderableListIterator MovableObject::getShadowVolumeRenderableIterator(
332        ShadowTechnique shadowTechnique, const Light* light, 
333        HardwareIndexBufferSharedPtr* indexBuffer, 
334        bool extrudeVertices, Real extrusionDist, unsigned long flags )
335    {
336        static ShadowRenderableList dummyList;
337        return ShadowRenderableListIterator(dummyList.begin(), dummyList.end());
338    }
339    //-----------------------------------------------------------------------
340    const AxisAlignedBox& MovableObject::getLightCapBounds(void) const
341    {
342        // Same as original bounds
343        return getWorldBoundingBox();
344    }
345    //-----------------------------------------------------------------------
346    const AxisAlignedBox& MovableObject::getDarkCapBounds(const Light& light, Real extrusionDist) const
347    {
348        // Extrude own light cap bounds
349        mWorldDarkCapBounds = getLightCapBounds();
350        this->extrudeBounds(mWorldDarkCapBounds, light.getAs4DVector(), 
351            extrusionDist);
352        return mWorldDarkCapBounds;
353
354    }
355    //-----------------------------------------------------------------------
356    Real MovableObject::getPointExtrusionDistance(const Light* l) const
357    {
358        if (mParentNode)
359        {
360            return getExtrusionDistance(mParentNode->_getDerivedPosition(), l);
361        }
362        else
363        {
364            return 0;
365        }
366    }
367        //-----------------------------------------------------------------------
368        uint32 MovableObject::getTypeFlags(void) const
369        {
370                if (mCreator)
371                {
372                        return mCreator->getTypeFlags();
373                }
374                else
375                {
376                        return 0xFFFFFFFF;
377                }
378        }
379        //-----------------------------------------------------------------------
380        //-----------------------------------------------------------------------
381        MovableObject* MovableObjectFactory::createInstance(
382                const String& name, SceneManager* manager, 
383                const NameValuePairList* params)
384        {
385                MovableObject* m = createInstanceImpl(name, params);
386                m->_notifyCreator(this);
387                m->_notifyManager(manager);
388                return m;
389        }
390
391
392}
393
Note: See TracBrowser for help on using the repository browser.