# Visualization Library

A lightweight C++ OpenGL middleware for 2D/3D graphics

[Home] [Tutorials] [All Classes] [Grouped Classes]

- Main Page
- Related Pages
- Namespaces
- Classes
- Files

- File List
- File Members

# D:/VL/BuildSystem/VL_DISTRO/Visualization_Library_SDK/src/vlGraphics/DrawRangeElements.hpp

Go to the documentation of this file.

    00001 /**************************************************************************************/
    00002 /*                                                                                    */
    00003 /*  Visualization Library                                                             */
    00004 /*  http://www.visualizationlibrary.org                                               */
    00005 /*                                                                                    */
    00006 /*  Copyright (c) 2005-2010, Michele Bosi                                             */
    00007 /*  All rights reserved.                                                              */
    00008 /*                                                                                    */
    00009 /*  Redistribution and use in source and binary forms, with or without modification,  */
    00010 /*  are permitted provided that the following conditions are met:                     */
    00011 /*                                                                                    */
    00012 /*  - Redistributions of source code must retain the above copyright notice, this     */
    00013 /*  list of conditions and the following disclaimer.                                  */
    00014 /*                                                                                    */
    00015 /*  - Redistributions in binary form must reproduce the above copyright notice, this  */
    00016 /*  list of conditions and the following disclaimer in the documentation and/or       */
    00017 /*  other materials provided with the distribution.                                   */
    00018 /*                                                                                    */
    00019 /*  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND   */
    00020 /*  ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED     */
    00021 /*  WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE            */
    00022 /*  DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR  */
    00023 /*  ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES    */
    00024 /*  (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;      */
    00025 /*  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON    */
    00026 /*  ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT           */
    00027 /*  (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS     */
    00028 /*  SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.                      */
    00029 /*                                                                                    */
    00030 /**************************************************************************************/
    00031
    00032 #ifndef DrawRangeElements_INCLUDE_ONCE
    00033 #define DrawRangeElements_INCLUDE_ONCE
    00034
    00035 #include <vlGraphics/DrawCall.hpp>
    00036 #include <vlGraphics/TriangleIterator.hpp>
    00037 #include <vlGraphics/Array.hpp>
    00038 #include <vlCore/Log.hpp>
    00039 #include <vlCore/Say.hpp>
    00040 #include <algorithm>
    00041
    00042 namespace vl
    00043 {
    00044
    00045   //------------------------------------------------------------------------------
    00046   // DrawRangeElementsBase
    00047   //------------------------------------------------------------------------------
    00053   class DrawRangeElementsBase: public DrawCall
    00054   {
    00055     VL_INSTRUMENT_ABSTRACT_CLASS(vl::DrawRangeElementsBase, DrawCall)
    00056
    00057   public:
    00059     void setRangeStart(int rstart) { mRangeStart = rstart; }
    00060
    00062     int rangeStart() const { return mRangeStart; }
    00063
    00065     void setRangeEnd(int rend) { mRangeEnd = rend; }
    00066
    00068     int rangeEnd() const { return mRangeEnd; }
    00069
    00071     virtual bool primitiveRestartEnabled() const { return mPrimitiveRestartEnabled; }
    00072
    00074     void setPrimitiveRestartEnabled(bool enabled) { mPrimitiveRestartEnabled = enabled; }
    00075
    00080     void setBaseVertex(int base_vertex) { mBaseVertex = base_vertex; }
    00081
    00084     int  baseVertex() const { return mBaseVertex; }
    00085
    00086   protected:
    00087     int mRangeStart;
    00088     int mRangeEnd;
    00089     GLuint mBaseVertex;
    00090     bool mPrimitiveRestartEnabled;
    00091   };
    00092   //------------------------------------------------------------------------------
    00093   // DrawRangeElements
    00094   //------------------------------------------------------------------------------
    00119   template <class arr_type>
    00120   class DrawRangeElements: public DrawRangeElementsBase
    00121   {
    00122     VL_INSTRUMENT_CLASS(vl::DrawRangeElements<arr_type>, DrawRangeElementsBase)
    00123
    00124   public:
    00125     typedef typename arr_type::scalar_type index_type;
    00127     static const index_type primitive_restart_index = index_type(~0);
    00128     virtual unsigned int primitiveRestartIndex() { return (unsigned int)primitive_restart_index; }
    00129
    00130   private:
    00131     template<typename T>
    00132     class Triangle
    00133     {
    00134     public:
    00135       T ABC[3];
    00136       bool operator<(const Triangle<index_type>& b) const
    00137       {
    00138         if (ABC[0] != b.ABC[0])
    00139           return ABC[0] < b.ABC[0];
    00140         else
    00141         if (ABC[1] != b.ABC[1])
    00142           return ABC[1] < b.ABC[1];
    00143         else
    00144           return ABC[2] < b.ABC[2];
    00145       }
    00146       void rotate()
    00147       {
    00148         if (ABC[0] > ABC[1])
    00149           { T tmp = ABC[0]; ABC[0] = ABC[1]; ABC[1] = ABC[2]; ABC[2] = tmp; }
    00150         if (ABC[0] > ABC[1])
    00151           { T tmp = ABC[0]; ABC[0] = ABC[1]; ABC[1] = ABC[2]; ABC[2] = tmp; }
    00152       }
    00153     };
    00154
    00155   public:
    00156     DrawRangeElements(EPrimitiveType primitive = PT_TRIANGLES, int r_start=0, int r_end=primitive_restart_index)
    00157     {
    00158       VL_DEBUG_SET_OBJECT_NAME()
    00159       mType                    = primitive;
    00160       mRangeStart              = r_start;
    00161       mRangeEnd                = r_end;
    00162       mIndexBuffer             = new arr_type;
    00163       mPrimitiveRestartEnabled = false;
    00164       mBaseVertex              = 0;
    00165       mCount                   = -1; // till the end of the indexBuffer()
    00166       mOffset                  = 0; // from the beginning of the indexBuffer()
    00167     }
    00168
    00169     DrawRangeElements& operator=(const DrawRangeElements& other)
    00170     {
    00171       super::operator=(other);
    00172       *indexBuffer()               = *other.indexBuffer();
    00173       mRangeStart              = other.mRangeStart;
    00174       mRangeEnd                = other.mRangeEnd;
    00175       mPrimitiveRestartEnabled = other.mPrimitiveRestartEnabled;
    00176       mBaseVertex              = other.mBaseVertex;
    00177       mCount                   = other.mCount;
    00178       mOffset                  = other.mOffset;
    00179       return *this;
    00180     }
    00181
    00182     virtual ref<DrawCall> clone() const
    00183     {
    00184       ref<DrawRangeElements> de = new DrawRangeElements;
    00185       *de = *this;
    00186       return de;
    00187     }
    00188
    00190     void setCount(i32 count) { mCount = count; }
    00191
    00193     i32 count() const { return mCount; }
    00194
    00196     void setOffset(u32 offset) { mOffset = offset; }
    00197
    00199     u32 offset() const { return mOffset; }
    00200
    00202     void setIndexBuffer(arr_type* index_buffer) { mIndexBuffer = index_buffer; }
    00203
    00205     arr_type* indexBuffer() { return mIndexBuffer.get(); }
    00206
    00208     const arr_type* indexBuffer() const { return mIndexBuffer.get(); }
    00209
    00210     virtual void updateDirtyBufferObject(EBufferObjectUpdateMode mode)
    00211     {
    00212       if (indexBuffer()->isBufferObjectDirty() || (mode & BUF_ForceUpdate))
    00213         indexBuffer()->updateBufferObject(mode);
    00214     }
    00215
    00216     virtual void deleteBufferObject()
    00217     {
    00218       indexBuffer()->bufferObject()->deleteBufferObject();
    00219     }
    00220
    00221     virtual void render(bool use_bo) const
    00222     {
    00223       VL_CHECK_OGL()
    00224       VL_CHECK(!use_bo || (use_bo && Has_BufferObject))
    00225       use_bo &= Has_BufferObject; // && indexBuffer()->bufferObject()->handle() && indexBuffer()->sizeBufferObject();
    00226       if ( !use_bo && !indexBuffer()->size() )
    00227         return;
    00228
    00229       // apply patch parameters if any and if using PT_PATCHES
    00230       applyPatchParameters();
    00231
    00232       // primitive restart enable
    00233       if(primitiveRestartEnabled())
    00234       {
    00235         VL_CHECK(Has_Primitive_Restart);
    00236         glEnable(GL_PRIMITIVE_RESTART); VL_CHECK_OGL();
    00237         glPrimitiveRestartIndex(primitive_restart_index); VL_CHECK_OGL();
    00238       }
    00239
    00240       // compute base pointer
    00241
    00242       const GLvoid* ptr = indexBuffer()->bufferObject()->ptr();
    00243       if (use_bo && indexBuffer()->bufferObject()->handle())
    00244       {
    00245         VL_glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, indexBuffer()->bufferObject()->handle()); VL_CHECK_OGL()
    00246         ptr = 0;
    00247       }
    00248       else
    00249       {
    00250         VL_glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0); VL_CHECK_OGL()
    00251       }
    00252
    00253       // compute final pointer and count
    00254
    00255       const char*ptr_end = NULL;
    00256       if(mCount < 0)
    00257       {
    00258         // compute the end of the index buffer
    00259         ptr_end = (char*)ptr + sizeof(index_type)*(use_bo ? indexBuffer()->sizeBufferObject() : indexBuffer()->size());
    00260
    00261         // offset in the index buffer
    00262         ptr = (char*)ptr + mOffset;
    00263       }
    00264       else
    00265       {
    00266         // offset in the index buffer
    00267         ptr = (char*)ptr + mOffset;
    00268
    00269         // compute the end of the indices
    00270         ptr_end = (char*)ptr + sizeof(index_type)*mCount;
    00271       }
    00272
    00273       // compute the remaining indices
    00274       const GLsizei count = (GLsizei)((index_type*)ptr_end - (index_type*)ptr);
    00275
    00276       if (mBaseVertex == 0)
    00277       {
    00278         glDrawRangeElements( primitiveType(), mRangeStart, mRangeEnd, count, arr_type::gl_type, ptr ); VL_CHECK_OGL()
    00279       }
    00280       else
    00281       {
    00282         VL_CHECK(Has_Base_Vertex)
    00283         VL_glDrawRangeElementsBaseVertex( primitiveType(), mRangeStart, mRangeEnd, count, arr_type::gl_type, ptr, mBaseVertex ); VL_CHECK_OGL()
    00284       }
    00285
    00286       // primitive restart disable
    00287
    00288       if(primitiveRestartEnabled())
    00289       {
    00290         glDisable(GL_PRIMITIVE_RESTART); VL_CHECK_OGL()
    00291       }
    00292     }
    00293
    00294     TriangleIterator triangleIterator() const
    00295     {
    00296       ref< TriangleIteratorIndexed<arr_type> > it =
    00297         new TriangleIteratorIndexed<arr_type>( mIndexBuffer.get(), primitiveType(),
    00298             baseVertex(), primitiveRestartEnabled(), primitive_restart_index );
    00299       it->initialize();
    00300       return TriangleIterator(it.get());
    00301     }
    00302
    00303     IndexIterator indexIterator() const
    00304     {
    00305       ref< IndexIteratorElements<arr_type> > iie = new IndexIteratorElements<arr_type>;
    00306       iie->initialize( mIndexBuffer.get(), NULL, NULL, mBaseVertex, mPrimitiveRestartEnabled, primitive_restart_index );
    00307       IndexIterator iit;
    00308       iit.initialize( iie.get() );
    00309       return iit;
    00310     }
    00311
    00312     void computeRange()
    00313     {
    00314       mRangeStart = primitive_restart_index;
    00315       mRangeEnd   = 0;
    00316
    00317       for(IndexIterator it=indexIterator(); it.hasNext(); it.next())
    00318       {
    00319         if (it.index() < mRangeStart)
    00320           mRangeStart = it.index();
    00321         if (it.index() > mRangeEnd)
    00322           mRangeEnd   = it.index();
    00323       }
    00324
    00325       if (mRangeEnd < mRangeStart)
    00326       {
    00327         mRangeStart = 0;
    00328         mRangeEnd   = primitive_restart_index;
    00329       }
    00330     }
    00331
    00332   protected:
    00333     ref< arr_type > mIndexBuffer;
    00334     i32 mCount;
    00335     u32 mOffset;
    00336   };
    00337   //------------------------------------------------------------------------------
    00338   // typedefs
    00339   //------------------------------------------------------------------------------
    00341   class DrawRangeElementsUInt: public DrawRangeElements<ArrayUInt1>
    00342   {
    00343     VL_INSTRUMENT_CLASS(vl::DrawRangeElementsUInt, DrawRangeElements<ArrayUInt1>)
    00344
    00345   public:
    00346     DrawRangeElementsUInt(EPrimitiveType primitive = PT_TRIANGLES, int r_start=0, int r_end=GLuint(~0))
    00347     :DrawRangeElements<ArrayUInt1>(primitive, r_start, r_end)
    00348     {
    00349       VL_DEBUG_SET_OBJECT_NAME();
    00350     }
    00351   };
    00352   //------------------------------------------------------------------------------
    00354   class DrawRangeElementsUShort: public DrawRangeElements<ArrayUShort1>
    00355   {
    00356     VL_INSTRUMENT_CLASS(vl::DrawRangeElementsUShort, DrawRangeElements<ArrayUShort1>)
    00357
    00358   public:
    00359     DrawRangeElementsUShort(EPrimitiveType primitive = PT_TRIANGLES, int r_start=0, int r_end=GLushort(~0))
    00360     :DrawRangeElements<ArrayUShort1>(primitive, r_start, r_end)
    00361     {
    00362       VL_DEBUG_SET_OBJECT_NAME();
    00363     }
    00364   };
    00365   //------------------------------------------------------------------------------
    00367   class DrawRangeElementsUByte: public DrawRangeElements<ArrayUByte1>
    00368   {
    00369     VL_INSTRUMENT_CLASS(vl::DrawRangeElementsUByte, DrawRangeElements<ArrayUByte1>)
    00370
    00371   public:
    00372     DrawRangeElementsUByte(EPrimitiveType primitive = PT_TRIANGLES, int r_start=0, int r_end=GLubyte(~0))
    00373     :DrawRangeElements<ArrayUByte1>(primitive, r_start, r_end)
    00374     {
    00375       VL_DEBUG_SET_OBJECT_NAME();
    00376     }
    00377   };
    00378   //------------------------------------------------------------------------------
    00379 }
    00380
    00381 #endif

Visualization Library v2011.09.1162 Reference Documentation
Copyright 2005-2011 Michele Bosi. All rights reserved.
Updated on Thu Jan 26 2012 00:43:37.
Permission is granted to use this page to write and publish articles regarding Visualization Library.