NL3D::CVegetableVBAllocator Class Reference

#include <vegetablevb_allocator.h>


Detailed Description

A VB allocator (landscape like). Big difference is that here, we do not really matter about reallocation because both software and hardware VB are present. Also, VertexProgram MUST be supported by driver here. NB: unlike Landscape VBAllocator, the VertexProgram is not managed by this class.
Author:
Lionel Berenguier

Nevrax France

Date:
2001

Definition at line 58 of file vegetablevb_allocator.h.

VB mgt .

void allocateVertexBufferAndFillVBHard (uint32 numVertices)
void deleteVertexBufferHard ()
 delete only the Vertexbuffer hard.

void setupVBFormat ()
uint8_AGPBufferPtr
bool _BufferLocked
NLMISC::CRefPtr< IDriver_Driver
uint _MaxVertexInBufferHard
 Maximum vertices in BufferHard allowed for this VBAllocator.

CVertexBuffer _VB
NLMISC::CRefPtr< IVertexBufferHard_VBHard
bool _VBHardOk

Public Types

enum  TVBType { VBTypeLighted = 0, VBTypeUnlit, VBTypeCount }

Public Member Functions

void clear ()
 CVegetableVBAllocator ()
 Constructor.

void init (TVBType vbType, uint maxVertexInBufferHard)
void updateDriver (IDriver *driver)
 ~CVegetableVBAllocator ()
Buffer access.
void activate ()
bool bufferLocked () const
void flushVertex (uint i)
 If VBHard ok, copy the vertex in AGP. Warning: buffer must be locked!

const CVertexBuffergetSoftwareVertexBuffer () const
void * getVertexPointer (uint i)
 get the software VB pointer to the ith index. valid only beetween 2 allocateVertex().

void lockBuffer ()
 if any, lock the AGP buffer.

void unlockBuffer ()
 if any, unlock the AGP buffer.

Allocation.
uint allocateVertex ()
void deleteVertex (uint vid)
 Delete free vertices in VB. (AGP or RAM).

bool exceedMaxVertexInBufferHard (uint numAddVerts) const
uint getNumUserVerticesAllocated () const

Private Attributes

uint _NumVerticesAllocated
TVBType _Type
std::vector< uint_VertexFreeMemory
std::vector< CVertexInfo_VertexInfos


Member Enumeration Documentation

enum NL3D::CVegetableVBAllocator::TVBType
 

Enumeration values:
VBTypeLighted 
VBTypeUnlit 
VBTypeCount 

Definition at line 62 of file vegetablevb_allocator.h.


Constructor & Destructor Documentation

NL3D::CVegetableVBAllocator::CVegetableVBAllocator  ) 
 

Constructor.

Definition at line 55 of file vegetablevb_allocator.cpp.

References _AGPBufferPtr, _MaxVertexInBufferHard, NL3D_VEGETABLE_VERTEX_FREE_MEMORY_RESERVE, and VBTypeUnlit.

00056 {
00057         _Type= VBTypeUnlit;
00058         _MaxVertexInBufferHard= 0;
00059 
00060         // Init free list
00061         _VertexFreeMemory.reserve(NL3D_VEGETABLE_VERTEX_FREE_MEMORY_RESERVE);
00062         _NumVerticesAllocated= 0;
00063 
00064         // Init vbhard
00065         _VBHardOk= false;
00066         _BufferLocked= false;
00067         _AGPBufferPtr= NULL;
00068 }

NL3D::CVegetableVBAllocator::~CVegetableVBAllocator  ) 
 

Definition at line 83 of file vegetablevb_allocator.cpp.

References clear().

00084 {
00085         clear();
00086 }


Member Function Documentation

void NL3D::CVegetableVBAllocator::activate  ) 
 

activate the VB or the VBHard in Driver setuped. nlassert if driver is NULL or if buffer is locked.

Definition at line 266 of file vegetablevb_allocator.cpp.

References nlassert.

Referenced by NL3D::CVegetableManager::render(), and NL3D::CVegetableBlendLayerModel::render().

00267 {
00268         nlassert(_Driver);
00269         nlassert(!_BufferLocked);
00270 
00271         // Activate VB.
00272         if(_VBHard)
00273                 _Driver->activeVertexBufferHard(_VBHard);
00274         else
00275                 _Driver->activeVertexBuffer(_VB);
00276 }

uint NL3D::CVegetableVBAllocator::allocateVertex  ) 
 

Allocate free vertices in VB. (RAM and AGP if possible). work with locked or unlocked buffer. if VBHard reallocation occurs, VB is unlocked, destroyed, reallocated, and refilled.

Definition at line 185 of file vegetablevb_allocator.cpp.

References _MaxVertexInBufferHard, allocateVertexBufferAndFillVBHard(), NL3D_VEGETABLE_VERTEX_ALLOCATE_SECURITY, NL3D_VEGETABLE_VERTEX_ALLOCATE_START, nlassert, and uint.

Referenced by NL3D::CVegetableManager::addInstance(), and NL3D::CVegetableManager::swapIgRdrPassHardMode().

00186 {
00187         // if no more free, allocate.
00188         if( _VertexFreeMemory.size()==0 )
00189         {
00190                 // enlarge capacity.
00191                 uint    newResize;
00192                 if(_NumVerticesAllocated==0)
00193                         newResize= NL3D_VEGETABLE_VERTEX_ALLOCATE_START;
00194                 else
00195                         newResize= NL3D_VEGETABLE_VERTEX_ALLOCATE_SECURITY;
00196                 // try to not overlap _MaxVertexInBufferHard limit, to avoid VBufferHard to be disabled.
00197                 if(_NumVerticesAllocated<_MaxVertexInBufferHard && _NumVerticesAllocated+newResize > _MaxVertexInBufferHard)
00198                 {
00199                         newResize= _MaxVertexInBufferHard - _NumVerticesAllocated;
00200                 }
00201                 _NumVerticesAllocated+= newResize;
00202                 // re-allocate VB.
00203                 allocateVertexBufferAndFillVBHard(_NumVerticesAllocated);
00204                 // resize infos on vertices.
00205                 _VertexInfos.resize(_NumVerticesAllocated);
00206 
00207                 // Fill list of free elements.
00208                 for(uint i=0;i<newResize;i++)
00209                 {
00210                         // create a new entry which points to this vertex.
00211                         // the list is made so allocation is in growing order.
00212                         _VertexFreeMemory.push_back( _NumVerticesAllocated - (i+1) );
00213 
00214                         // Mark as free the new vertices. (Debug).
00215                         _VertexInfos[_NumVerticesAllocated - (i+1)].Free= true;
00216                 }
00217         }
00218 
00219         // get a vertex (pop_back).
00220         uint    id= _VertexFreeMemory.back();
00221         // delete this vertex free entry.
00222         _VertexFreeMemory.pop_back();
00223 
00224         // check and Mark as not free the vertex. (Debug).
00225         nlassert(id<_NumVerticesAllocated);
00226         nlassert(_VertexInfos[id].Free);
00227         _VertexInfos[id].Free= false;
00228 
00229 
00230         return id;
00231 }

void NL3D::CVegetableVBAllocator::allocateVertexBufferAndFillVBHard uint32  numVertices  )  [private]
 

Definition at line 306 of file vegetablevb_allocator.cpp.

References _AGPBufferPtr, _MaxVertexInBufferHard, bufferLocked(), NL3D::CVertexBuffer::getUVRouting(), NL3D::CVertexBuffer::getValueTypePointer(), NL3D::CVertexBuffer::getVertexCoordPointer(), NL3D::CVertexBuffer::getVertexFormat(), NL3D::CVertexBuffer::getVertexSize(), lockBuffer(), nlassert, NL3D::CVertexBuffer::setNumVertices(), uint32, and unlockBuffer().

Referenced by allocateVertex(), and updateDriver().

00307 {
00308         // resize the Soft VB.
00309         _VB.setNumVertices(numVertices);
00310 
00311         // no allocation must be done if the Driver is not setuped, or if the driver has been deleted by refPtr.
00312         nlassert(_Driver);
00313 
00314         // must unlock VBhard before.
00315         bool    wasLocked= bufferLocked();
00316         unlockBuffer();
00317 
00318         // try to allocate a vbufferhard if possible.
00319         if( _VBHardOk )
00320         {
00321                 // delete possible old _VBHard.
00322                 if(_VBHard!=NULL)
00323                 {
00324                         // VertexBufferHard lifetime < Driver lifetime.
00325                         nlassert(_Driver!=NULL);
00326                         _Driver->deleteVertexBufferHard(_VBHard);
00327                 }
00328 
00329                 // try to create new one, in AGP Ram
00330                 // If too many vertices wanted, abort VBHard.
00331                 if(numVertices <= _MaxVertexInBufferHard)
00332                 {
00333                         _VBHard= _Driver->createVertexBufferHard(_VB.getVertexFormat(), _VB.getValueTypePointer(), numVertices, IDriver::VBHardAGP, _VB.getUVRouting());
00334                         // Set Name For lock Profiling.
00335                         if(_VBHard)
00336                                 _VBHard->setName("VegetableVB");
00337                 }
00338                 else
00339                         _VBHard= NULL;
00340 
00341                 // If KO, never try again.
00342                 if(_VBHard==NULL)
00343                         _VBHardOk= false;
00344                 else
00345                 {
00346                         // else, fill this AGP VBuffer Hard.
00347                         // lock before the AGP buffer
00348                         lockBuffer();
00349 
00350                         // copy all the vertices to AGP.
00351                         memcpy(_AGPBufferPtr, _VB.getVertexCoordPointer(0), _VB.getVertexSize() * numVertices);
00352 
00353                         // If was not locked before, unlock this VB
00354                         if(!wasLocked)
00355                                 unlockBuffer();
00356                 }
00357         }
00358 
00359         //nlinfo("VEGET: Alloc %d verts. %s", numVertices, _VBHardOk?"VBHard":"VBSoft");
00360 }

bool NL3D::CVegetableVBAllocator::bufferLocked  )  const [inline]
 

activate the VB or the VBHard in Driver setuped. nlassert if driver is NULL or if buffer is locked.

Definition at line 120 of file vegetablevb_allocator.h.

Referenced by allocateVertexBufferAndFillVBHard().

00120 {return _BufferLocked;}

void NL3D::CVegetableVBAllocator::clear  ) 
 

Definition at line 126 of file vegetablevb_allocator.cpp.

References NL3D::CVertexBuffer::deleteAllVertices(), and deleteVertexBufferHard().

Referenced by ~CVegetableVBAllocator().

00127 {
00128         // clear list.
00129         _VertexFreeMemory.clear();
00130         _NumVerticesAllocated= 0;
00131 
00132         // delete the VB.
00133         deleteVertexBufferHard();
00134         // really delete the VB soft too
00135         _VB.deleteAllVertices();
00136 
00137         // clear other states.
00138         _Driver= NULL;
00139         _VBHardOk= false;
00140 }

void NL3D::CVegetableVBAllocator::deleteVertex uint  vid  ) 
 

Delete free vertices in VB. (AGP or RAM).

Definition at line 234 of file vegetablevb_allocator.cpp.

References nlassert, and uint.

Referenced by NL3D::CVegetableManager::deleteIg(), and NL3D::CVegetableManager::swapIgRdrPassHardMode().

00235 {
00236         // check and Mark as free the vertex. (Debug).
00237         nlassert(vid<_NumVerticesAllocated);
00238         nlassert(!_VertexInfos[vid].Free);
00239         _VertexInfos[vid].Free= true;
00240 
00241         // Add this vertex to the free list.
00242         // create a new entry which points to this vertex.
00243         _VertexFreeMemory.push_back( vid );
00244 }

void NL3D::CVegetableVBAllocator::deleteVertexBufferHard  )  [private]
 

delete only the Vertexbuffer hard.

Definition at line 287 of file vegetablevb_allocator.cpp.

References nlassert, and unlockBuffer().

Referenced by clear(), and updateDriver().

00288 {
00289         // must unlock VBhard before.
00290         unlockBuffer();
00291 
00292         // test (refptr) if the object still exist in memory.
00293         if(_VBHard!=NULL)
00294         {
00295                 // A vbufferhard should still exist only if driver still exist.
00296                 nlassert(_Driver!=NULL);
00297 
00298                 // delete it from driver.
00299                 _Driver->deleteVertexBufferHard(_VBHard);
00300                 _VBHard= NULL;
00301         }
00302 
00303 }

bool NL3D::CVegetableVBAllocator::exceedMaxVertexInBufferHard uint  numAddVerts  )  const
 

if I add numAddVerts vertices, will it overide _MaxVertexInBufferHard ??

Definition at line 178 of file vegetablevb_allocator.cpp.

References _MaxVertexInBufferHard, getNumUserVerticesAllocated(), and uint.

Referenced by NL3D::CVegetableManager::addInstance().

00179 {
00180         return (getNumUserVerticesAllocated() + numAddVerts) > _MaxVertexInBufferHard;
00181 }

void NL3D::CVegetableVBAllocator::flushVertex uint  i  ) 
 

If VBHard ok, copy the vertex in AGP. Warning: buffer must be locked!

Definition at line 253 of file vegetablevb_allocator.cpp.

References _AGPBufferPtr, getVertexPointer(), NL3D::CVertexBuffer::getVertexSize(), nlassert, src, and uint.

Referenced by NL3D::CVegetableManager::addInstance(), NL3D::CVegetableManager::swapIgRdrPassHardMode(), and NL3D::CVegetableManager::updateInstanceLighting().

00254 {
00255         if(_VBHardOk)
00256         {
00257                 nlassert(_VBHard && _BufferLocked);
00258                 // copy the VB soft to the VBHard.
00259                 void    *src= getVertexPointer(i);
00260                 void    *dst= _AGPBufferPtr + i*_VB.getVertexSize();
00261                 memcpy(dst, src, _VB.getVertexSize());
00262         }
00263 }

uint NL3D::CVegetableVBAllocator::getNumUserVerticesAllocated  )  const
 

return number of vertices allocated with allocateVertex() (NB: do not return the actual number of vertices allocated in VBuffer, but the number of vertices asked to be allocated).

Definition at line 171 of file vegetablevb_allocator.cpp.

References uint.

Referenced by exceedMaxVertexInBufferHard(), and NL3D::CVegetableManager::render().

00172 {
00173         // get the number of vertices which are allocated by allocateVertex().
00174         return _NumVerticesAllocated - _VertexFreeMemory.size();
00175 }

const CVertexBuffer& NL3D::CVegetableVBAllocator::getSoftwareVertexBuffer  )  const [inline]
 

activate the VB or the VBHard in Driver setuped. nlassert if driver is NULL or if buffer is locked.

Definition at line 112 of file vegetablevb_allocator.h.

Referenced by NL3D::CVegetableManager::addInstance(), NL3D::CVegetableManager::swapIgRdrPassHardMode(), and NL3D::CVegetableManager::updateInstanceLighting().

00112 {return _VB;}

void * NL3D::CVegetableVBAllocator::getVertexPointer uint  i  ) 
 

get the software VB pointer to the ith index. valid only beetween 2 allocateVertex().

Definition at line 247 of file vegetablevb_allocator.cpp.

References NL3D::CVertexBuffer::getVertexCoordPointer(), and uint.

Referenced by NL3D::CVegetableManager::addInstance(), flushVertex(), NL3D::CVegetableManager::swapIgRdrPassHardMode(), and NL3D::CVegetableManager::updateInstanceLighting().

00248 {
00249         return _VB.getVertexCoordPointer(i);
00250 }

void NL3D::CVegetableVBAllocator::init TVBType  vbType,
uint  maxVertexInBufferHard
 

init the VB allocator, with the good type. must do it first. maxVertexInBufferHard is the maximum vertex allowed to reside in AGP mem. if More are allocated, then VBHard is disabled, and replaced with software VB (slower!), for ever.

Definition at line 72 of file vegetablevb_allocator.cpp.

References _MaxVertexInBufferHard, setupVBFormat(), type, and uint.

Referenced by NL3D::CVegetableManager::CVegetableManager().

00073 {
00074         _Type= type;
00075         _MaxVertexInBufferHard= maxVertexInBufferHard;
00076 
00077         // According to _Type, build VB format, and create VertexProgram
00078         setupVBFormat();
00079 }

void NL3D::CVegetableVBAllocator::lockBuffer  ) 
 

if any, lock the AGP buffer.

Definition at line 144 of file vegetablevb_allocator.cpp.

References _AGPBufferPtr, uint8, and unlockBuffer().

Referenced by allocateVertexBufferAndFillVBHard(), and NL3D::CVegetableManager::lockBuffers().

00145 {
00146         // force unlock
00147         unlockBuffer();
00148 
00149         if(_VBHard)
00150         {
00151                 _AGPBufferPtr= (uint8*)_VBHard->lock();
00152         }
00153 
00154         _BufferLocked= true;
00155 }

void NL3D::CVegetableVBAllocator::setupVBFormat  )  [private]
 

Definition at line 364 of file vegetablevb_allocator.cpp.

References NL3D::CVertexBuffer::addValueEx(), NL3D::CVertexBuffer::clearValueEx(), NL3D::CVertexBuffer::initEx(), NL3D_VEGETABLE_VPPOS_BENDINFO, NL3D_VEGETABLE_VPPOS_CENTER, NL3D_VEGETABLE_VPPOS_COLOR0, NL3D_VEGETABLE_VPPOS_COLOR1, NL3D_VEGETABLE_VPPOS_NORMAL, NL3D_VEGETABLE_VPPOS_POS, NL3D_VEGETABLE_VPPOS_TEX0, and VBTypeLighted.

Referenced by init().

00365 {
00366         // Build the Vertex Format.
00367         _VB.clearValueEx();
00368 
00369         // if lighted, need world space normal and AmbientColor for each vertex.
00370         if( _Type == VBTypeLighted )
00371         {
00372                 _VB.addValueEx(NL3D_VEGETABLE_VPPOS_POS,        CVertexBuffer::Float3);         // v[0]
00373                 _VB.addValueEx(NL3D_VEGETABLE_VPPOS_NORMAL, CVertexBuffer::Float3);             // v[2]
00374                 _VB.addValueEx(NL3D_VEGETABLE_VPPOS_BENDINFO,   CVertexBuffer::Float3);         // v[9]
00375         }
00376         // If unlit
00377         else
00378         {
00379                 // slightly different VertexProgram, v[0].w== BendWeight, and v[9].x== v[0].norm()
00380                 _VB.addValueEx(NL3D_VEGETABLE_VPPOS_POS,                CVertexBuffer::Float4);         // v[0]
00381                 // Unlit VP has BlendDistance in v[9].w
00382                 _VB.addValueEx(NL3D_VEGETABLE_VPPOS_BENDINFO,   CVertexBuffer::Float4);         // v[9]
00383         }
00384         _VB.addValueEx(NL3D_VEGETABLE_VPPOS_COLOR0,             CVertexBuffer::UChar4);         // v[3]
00385         _VB.addValueEx(NL3D_VEGETABLE_VPPOS_COLOR1,             CVertexBuffer::UChar4);         // v[4]
00386         _VB.addValueEx(NL3D_VEGETABLE_VPPOS_TEX0,               CVertexBuffer::Float2);         // v[8]
00387         _VB.addValueEx(NL3D_VEGETABLE_VPPOS_CENTER,             CVertexBuffer::Float3);         // v[10]
00388         _VB.initEx();
00389 
00390 }

void NL3D::CVegetableVBAllocator::unlockBuffer  ) 
 

if any, unlock the AGP buffer.

Definition at line 158 of file vegetablevb_allocator.cpp.

References _AGPBufferPtr.

Referenced by allocateVertexBufferAndFillVBHard(), deleteVertexBufferHard(), lockBuffer(), and NL3D::CVegetableManager::unlockBuffers().

00159 {
00160         if(_BufferLocked)
00161         {
00162                 if(_VBHard)
00163                         _VBHard->unlock();
00164                 _BufferLocked= false;
00165                 _AGPBufferPtr= NULL;
00166         }
00167 }

void NL3D::CVegetableVBAllocator::updateDriver IDriver driver  ) 
 

setup driver, and test for possible VBHard reallocation. if reallocation, refill the VBHard to do anytime you're not sure of change of the driver/vbHard state.

Parameters:
driver must not be NULL.

Definition at line 89 of file vegetablevb_allocator.cpp.

References _MaxVertexInBufferHard, allocateVertexBufferAndFillVBHard(), deleteVertexBufferHard(), and nlassert.

Referenced by NL3D::CVegetableManager::updateDriver().

00090 {
00091         // test change of driver.
00092         nlassert(driver && !_BufferLocked);
00093         // If change of driver
00094         if( _Driver==NULL || driver!=_Driver )
00095         {
00096                 // delete old VBHard.
00097                 deleteVertexBufferHard();
00098                 _Driver= driver;
00099                 _VBHardOk= (_MaxVertexInBufferHard>0) && (_Driver->supportVertexBufferHard());
00100                 /* Because so much lock/unlock are performed during a frame (refine/clip etc...).
00101                         we must disable VBHard for ATI Gl extension.
00102                         NB: CLandscape don't do this and fast copy the entire VB each frame.
00103                         This is not possible for vegetables because the VB describe all Vegetable around the camera, not only
00104                         what is in frustrum. Hence a fast copy each frame would copy far too much unseen vertices (4x).
00105                 */
00106                 if(_Driver->slowUnlockVertexBufferHard())
00107                         _VBHardOk= false;
00108 
00109                 // Driver must support VP.
00110                 nlassert(_Driver->isVertexProgramSupported());
00111 
00112                 // must reallocate the VertexBuffer.
00113                 if( _NumVerticesAllocated>0 )
00114                         allocateVertexBufferAndFillVBHard(_NumVerticesAllocated);
00115         }
00116         else
00117         {
00118                 // if VBHard possible, and if vbHardDeleted but space needed, reallocate.
00119                 if( _VBHardOk && _VBHard==NULL && _NumVerticesAllocated>0 )
00120                         allocateVertexBufferAndFillVBHard(_NumVerticesAllocated);
00121         }
00122 
00123 }


Field Documentation

uint8* NL3D::CVegetableVBAllocator::_AGPBufferPtr [private]
 

Definition at line 158 of file vegetablevb_allocator.h.

Referenced by allocateVertexBufferAndFillVBHard(), CVegetableVBAllocator(), flushVertex(), lockBuffer(), and unlockBuffer().

bool NL3D::CVegetableVBAllocator::_BufferLocked [private]
 

Definition at line 157 of file vegetablevb_allocator.h.

NLMISC::CRefPtr<IDriver> NL3D::CVegetableVBAllocator::_Driver [private]
 

Definition at line 153 of file vegetablevb_allocator.h.

uint NL3D::CVegetableVBAllocator::_MaxVertexInBufferHard [private]
 

Maximum vertices in BufferHard allowed for this VBAllocator.

Definition at line 160 of file vegetablevb_allocator.h.

Referenced by allocateVertex(), allocateVertexBufferAndFillVBHard(), CVegetableVBAllocator(), exceedMaxVertexInBufferHard(), init(), and updateDriver().

uint NL3D::CVegetableVBAllocator::_NumVerticesAllocated [private]
 

Definition at line 143 of file vegetablevb_allocator.h.

TVBType NL3D::CVegetableVBAllocator::_Type [private]
 

Definition at line 138 of file vegetablevb_allocator.h.

CVertexBuffer NL3D::CVegetableVBAllocator::_VB [private]
 

Definition at line 150 of file vegetablevb_allocator.h.

NLMISC::CRefPtr<IVertexBufferHard> NL3D::CVegetableVBAllocator::_VBHard [private]
 

Definition at line 156 of file vegetablevb_allocator.h.

bool NL3D::CVegetableVBAllocator::_VBHardOk [private]
 

Definition at line 155 of file vegetablevb_allocator.h.

std::vector<uint> NL3D::CVegetableVBAllocator::_VertexFreeMemory [private]
 

Definition at line 141 of file vegetablevb_allocator.h.

std::vector<CVertexInfo> NL3D::CVegetableVBAllocator::_VertexInfos [private]
 

Definition at line 142 of file vegetablevb_allocator.h.


The documentation for this class was generated from the following files:
Generated on Tue Mar 16 08:22:56 2004 for NeL by doxygen 1.3.6