source: trunk/VUT/work/ogre_changes/OgreMain/src/OgreRenderSystem.cpp @ 316

Revision 316, 15.0 KB checked in by mattausch, 19 years ago (diff)

queries are realized as templates

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-2005 The OGRE Team
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-----------------------------------------------------------------------------
24*/
25#include "OgreStableHeaders.h"
26// RenderSystem implementation
27// Note that most of this class is abstract since
28//  we cannot know how to implement the behaviour without
29//  being aware of the 3D API. However there are a few
30//  simple functions which can have a base implementation
31
32#include "OgreRenderSystem.h"
33
34#include "OgreRoot.h"
35#include "OgreViewport.h"
36#include "OgreException.h"
37#include "OgreRenderTarget.h"
38#include "OgreRenderWindow.h"
39#include "OgreMeshManager.h"
40#include "OgreMaterial.h"
41#include "OgreTimer.h"
42
43namespace Ogre {
44
45    const PlaneList Renderable::msDummyPlaneList; // FIX ME: temporary
46
47    //-----------------------------------------------------------------------
48    RenderSystem::RenderSystem()
49    {
50        mActiveViewport = 0;
51                mActiveRenderTarget = NULL;
52        mTextureManager = 0;
53        mCapabilities = 0;
54        mVSync = true;
55                mWBuffer = false;
56
57
58        // This means CULL clockwise vertices, i.e. front of poly is counter-clockwise
59        // This makes it the same as OpenGL and other right-handed systems
60        mCullingMode = CULL_CLOCKWISE;
61        mInvertVertexWinding = false;
62
63        // instanciate RenderSystemCapabilities
64        mCapabilities = new RenderSystemCapabilities();
65    }
66
67    //-----------------------------------------------------------------------
68    RenderSystem::~RenderSystem()
69    {
70        shutdown();
71    }
72    //-----------------------------------------------------------------------
73    void RenderSystem::_initRenderTargets(void)
74    {
75
76        // Init stats
77        for(
78            RenderTargetMap::iterator it = mRenderTargets.begin();
79            it != mRenderTargets.end();
80            ++it )
81        {
82            it->second->resetStatistics();
83        }
84
85    }
86    //-----------------------------------------------------------------------
87    void RenderSystem::_updateAllRenderTargets(void)
88    {
89        // Update all in order of priority
90        // This ensures render-to-texture targets get updated before render windows
91                RenderTargetPriorityMap::iterator itarg, itargend;
92                itargend = mPrioritisedRenderTargets.end();
93                for( itarg = mPrioritisedRenderTargets.begin(); itarg != itargend; ++itarg )
94                {
95                        if( itarg->second->isActive() && itarg->second->isAutoUpdated())
96                                itarg->second->update();
97                }
98    }
99    //-----------------------------------------------------------------------
100    RenderWindow* RenderSystem::initialise(bool autoCreateWindow, const String& windowTitle)
101    {
102        // Have I been registered by call to Root::setRenderSystem?
103                /** Don't do this anymore, just allow via Root
104        RenderSystem* regPtr = Root::getSingleton().getRenderSystem();
105        if (!regPtr || regPtr != this)
106            // Register self - library user has come to me direct
107            Root::getSingleton().setRenderSystem(this);
108                */
109
110
111        // Subclasses should take it from here
112        // They should ALL call this superclass method from
113        //   their own initialise() implementations.
114
115        return 0;
116    }
117    //---------------------------------------------------------------------------------------------
118    void RenderSystem::destroyRenderWindow(const String& name)
119    {
120        destroyRenderTarget(name);
121    }
122    //---------------------------------------------------------------------------------------------
123    void RenderSystem::destroyRenderTexture(const String& name)
124    {
125        destroyRenderTarget(name);
126    }
127    //---------------------------------------------------------------------------------------------
128    void RenderSystem::destroyRenderTarget(const String& name)
129    {
130        RenderTarget* rt = detachRenderTarget(name);
131        delete rt;
132    }
133    //---------------------------------------------------------------------------------------------
134    void RenderSystem::attachRenderTarget( RenderTarget &target )
135    {
136                assert( target.getPriority() < OGRE_NUM_RENDERTARGET_GROUPS );
137
138        mRenderTargets.insert( RenderTargetMap::value_type( target.getName(), &target ) );
139        mPrioritisedRenderTargets.insert(
140            RenderTargetPriorityMap::value_type(target.getPriority(), &target ));
141    }
142
143    //---------------------------------------------------------------------------------------------
144    RenderTarget * RenderSystem::getRenderTarget( const String &name )
145    {
146        RenderTargetMap::iterator it = mRenderTargets.find( name );
147        RenderTarget *ret = NULL;
148
149        if( it != mRenderTargets.end() )
150        {
151            ret = it->second;
152        }
153
154        return ret;
155    }
156
157    //---------------------------------------------------------------------------------------------
158    RenderTarget * RenderSystem::detachRenderTarget( const String &name )
159    {
160        RenderTargetMap::iterator it = mRenderTargets.find( name );
161        RenderTarget *ret = NULL;
162
163        if( it != mRenderTargets.end() )
164        {
165            ret = it->second;
166                       
167                        /* Remove the render target from the priority groups. */
168            RenderTargetPriorityMap::iterator itarg, itargend;
169            itargend = mPrioritisedRenderTargets.end();
170                        for( itarg = mPrioritisedRenderTargets.begin(); itarg != itargend; ++itarg )
171            {
172                                if( itarg->second == ret ) {
173                                        mPrioritisedRenderTargets.erase( itarg );
174                                        break;
175                                }
176            }
177
178            mRenderTargets.erase( it );
179        }
180
181        return ret;
182    }
183    //-----------------------------------------------------------------------
184    Viewport* RenderSystem::_getViewport(void)
185    {
186        return mActiveViewport;
187    }
188    //-----------------------------------------------------------------------
189    void RenderSystem::_setTextureUnitSettings(size_t texUnit, TextureUnitState& tl)
190    {
191        // This method is only ever called to set a texture unit to valid details
192        // The method _disableTextureUnit is called to turn a unit off
193
194        // Texture name
195                if (tl.isBlank())
196                {
197                        _setTexture(texUnit, true, StringUtil::BLANK);
198                }
199                else
200                {
201                        _setTexture(texUnit, true, tl.getTextureName());
202                }
203
204        // Set texture coordinate set
205        _setTextureCoordSet(texUnit, tl.getTextureCoordSet());
206
207        // Set texture layer filtering
208        _setTextureUnitFiltering(texUnit,
209            tl.getTextureFiltering(FT_MIN),
210            tl.getTextureFiltering(FT_MAG),
211            tl.getTextureFiltering(FT_MIP));
212
213        // Set texture layer filtering
214        _setTextureLayerAnisotropy(texUnit, tl.getTextureAnisotropy());
215
216                // Set blend modes
217                // Note, colour before alpha is important
218        _setTextureBlendMode(texUnit, tl.getColourBlendMode());
219        _setTextureBlendMode(texUnit, tl.getAlphaBlendMode());
220
221        // Texture addressing mode
222        _setTextureAddressingMode(texUnit, tl.getTextureAddressingMode() );
223
224        // Set texture effects
225        TextureUnitState::EffectMap::iterator effi;
226        // Iterate over new effects
227        bool anyCalcs = false;
228        for (effi = tl.mEffects.begin(); effi != tl.mEffects.end(); ++effi)
229        {
230            switch (effi->second.type)
231            {
232            case TextureUnitState::ET_ENVIRONMENT_MAP:
233                if (effi->second.subtype == TextureUnitState::ENV_CURVED)
234                {
235                    _setTextureCoordCalculation(texUnit, TEXCALC_ENVIRONMENT_MAP);
236                    anyCalcs = true;
237                }
238                else if (effi->second.subtype == TextureUnitState::ENV_PLANAR)
239                {
240                    _setTextureCoordCalculation(texUnit, TEXCALC_ENVIRONMENT_MAP_PLANAR);
241                    anyCalcs = true;
242                }
243                else if (effi->second.subtype == TextureUnitState::ENV_REFLECTION)
244                {
245                    _setTextureCoordCalculation(texUnit, TEXCALC_ENVIRONMENT_MAP_REFLECTION);
246                    anyCalcs = true;
247                }
248                else if (effi->second.subtype == TextureUnitState::ENV_NORMAL)
249                {
250                    _setTextureCoordCalculation(texUnit, TEXCALC_ENVIRONMENT_MAP_NORMAL);
251                    anyCalcs = true;
252                }
253                break;
254            case TextureUnitState::ET_SCROLL:
255            case TextureUnitState::ET_ROTATE:
256            case TextureUnitState::ET_TRANSFORM:
257                break;
258            case TextureUnitState::ET_PROJECTIVE_TEXTURE:
259                _setTextureCoordCalculation(texUnit, TEXCALC_PROJECTIVE_TEXTURE,
260                    effi->second.frustum);
261                anyCalcs = true;
262                break;
263            }
264        }
265        // Ensure any previous texcoord calc settings are reset if there are now none
266        if (!anyCalcs)
267        {
268            _setTextureCoordCalculation(texUnit, TEXCALC_NONE);
269            _setTextureCoordSet(texUnit, tl.getTextureCoordSet());
270        }
271
272        // Change tetxure matrix
273        _setTextureMatrix(texUnit, tl.getTextureTransform());
274
275
276    }
277    //-----------------------------------------------------------------------
278    void RenderSystem::_disableTextureUnit(size_t texUnit)
279    {
280        _setTexture(texUnit, false, "");
281        _setTextureMatrix(texUnit, Matrix4::IDENTITY);
282    }
283    //---------------------------------------------------------------------
284    void RenderSystem::_disableTextureUnitsFrom(size_t texUnit)
285    {
286        for (size_t i = texUnit; i < mCapabilities->getNumTextureUnits(); ++i)
287        {
288            _disableTextureUnit(i);
289        }
290    }
291    //-----------------------------------------------------------------------
292    void RenderSystem::_setTextureUnitFiltering(size_t unit, FilterOptions minFilter,
293            FilterOptions magFilter, FilterOptions mipFilter)
294    {
295        _setTextureUnitFiltering(unit, FT_MIN, minFilter);
296        _setTextureUnitFiltering(unit, FT_MAG, magFilter);
297        _setTextureUnitFiltering(unit, FT_MIP, mipFilter);
298    }
299    //-----------------------------------------------------------------------
300    CullingMode RenderSystem::_getCullingMode(void) const
301    {
302        return mCullingMode;
303    }
304    //-----------------------------------------------------------------------
305    bool RenderSystem::getWaitForVerticalBlank(void) const
306    {
307        return mVSync;
308    }
309    //-----------------------------------------------------------------------
310    void RenderSystem::setWaitForVerticalBlank(bool enabled)
311    {
312        mVSync = enabled;
313    }
314    bool RenderSystem::getWBufferEnabled(void) const
315    {
316        return mWBuffer;
317    }
318    //-----------------------------------------------------------------------
319    void RenderSystem::setWBufferEnabled(bool enabled)
320    {
321        mWBuffer = enabled;
322    }
323    //-----------------------------------------------------------------------
324    void RenderSystem::shutdown(void)
325    {
326        // Remove all the render targets.
327                // (destroy primary target last since others may depend on it)
328                RenderTarget* primary = 0;
329                for (RenderTargetMap::iterator it = mRenderTargets.begin(); it != mRenderTargets.end(); ++it)
330                {
331                        if (!primary && it->second->isPrimary())
332                                primary = it->second;
333                        else
334                                delete it->second;
335                }
336                delete primary;
337                mRenderTargets.clear();
338
339                mPrioritisedRenderTargets.clear();
340    }
341    //-----------------------------------------------------------------------
342    void RenderSystem::_beginGeometryCount(void)
343    {
344        mFaceCount = mVertexCount = 0;
345
346    }
347    //-----------------------------------------------------------------------
348    unsigned int RenderSystem::_getFaceCount(void) const
349    {
350        return static_cast< unsigned int >( mFaceCount );
351    }
352    //-----------------------------------------------------------------------
353    unsigned int RenderSystem::_getVertexCount(void) const
354    {
355        return static_cast< unsigned int >( mVertexCount );
356    }
357    //-----------------------------------------------------------------------
358    void RenderSystem::_setWorldMatrices(const Matrix4* m, unsigned short count)
359    {
360        // Save these matrices for software blending later
361        for (unsigned short i = 0; i < count; ++i)
362        {
363            mWorldMatrices[i] = m[i];
364        }
365        // Set hardware matrix to nothing
366        _setWorldMatrix(Matrix4::IDENTITY);
367    }
368    //-----------------------------------------------------------------------
369    void RenderSystem::_render(const RenderOperation& op)
370    {
371        // Update stats
372        size_t val;
373
374        if (op.useIndexes)
375            val = op.indexData->indexCount;
376        else
377            val = op.vertexData->vertexCount;
378
379        switch(op.operationType)
380        {
381                case RenderOperation::OT_TRIANGLE_LIST:
382            mFaceCount += val / 3;
383            break;
384        case RenderOperation::OT_TRIANGLE_STRIP:
385        case RenderOperation::OT_TRIANGLE_FAN:
386            mFaceCount += val - 2;
387            break;
388            case RenderOperation::OT_POINT_LIST:
389            case RenderOperation::OT_LINE_LIST:
390            case RenderOperation::OT_LINE_STRIP:
391                break;
392            }
393
394        mVertexCount += op.vertexData->vertexCount;
395
396    }
397    //-----------------------------------------------------------------------
398    void RenderSystem::setInvertVertexWinding(bool invert)
399    {
400        mInvertVertexWinding = invert;
401    }
402    //-----------------------------------------------------------------------
403    void RenderSystem::setClipPlane (ushort index, const Plane &p)
404    {
405        setClipPlane (index, p.normal.x, p.normal.y, p.normal.z, p.d);
406    }
407    //-----------------------------------------------------------------------
408    void RenderSystem::_notifyCameraRemoved(const Camera* cam)
409    {
410        RenderTargetMap::iterator i, iend;
411        iend = mRenderTargets.end();
412        for (i = mRenderTargets.begin(); i != iend; ++i)
413        {
414            RenderTarget* target = i->second;
415            target->_notifyCameraRemoved(cam);
416        }
417    }
418}
419
Note: See TracBrowser for help on using the repository browser.