Changed std::map to boost::unordered_map for storing memory chunks and groups information.
This commit is contained in:
parent
00847a8aed
commit
a73216fc95
|
@ -26,8 +26,6 @@
|
|||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
*/
|
||||
|
||||
#include <cmath>
|
||||
|
||||
#include <gal/opengl/opengl_gal.h>
|
||||
#include <gal/opengl/vbo_container.h>
|
||||
#include <gal/definitions.h>
|
||||
|
@ -39,6 +37,7 @@
|
|||
#endif /* __WXDEBUG__ */
|
||||
|
||||
#include <limits>
|
||||
#include <boost/foreach.hpp>
|
||||
|
||||
#ifndef CALLBACK
|
||||
#define CALLBACK
|
||||
|
@ -82,7 +81,6 @@ OPENGL_GAL::OPENGL_GAL( wxWindow* aParent, wxEvtHandler* aMouseListener,
|
|||
groupCounter = 0;
|
||||
transform = glm::mat4( 1.0f ); // Identity matrix
|
||||
|
||||
|
||||
SetSize( parentSize );
|
||||
|
||||
screenSize.x = parentSize.x;
|
||||
|
@ -1606,10 +1604,9 @@ void OPENGL_GAL::EndGroup()
|
|||
|
||||
void OPENGL_GAL::ClearCache()
|
||||
{
|
||||
std::map<unsigned int, VBO_ITEM*>::iterator it, end;
|
||||
for( it = groups.begin(), end = groups.end(); it != end; it++ )
|
||||
BOOST_FOREACH( GroupsMap::value_type it, groups )
|
||||
{
|
||||
delete it->second;
|
||||
delete it.second;
|
||||
}
|
||||
|
||||
groups.clear();
|
||||
|
|
|
@ -30,6 +30,7 @@
|
|||
#include <gal/opengl/vbo_container.h>
|
||||
#include <cstring>
|
||||
#include <cstdlib>
|
||||
#include <boost/foreach.hpp>
|
||||
#include <wx/log.h>
|
||||
#ifdef __WXDEBUG__
|
||||
#include <profile.h>
|
||||
|
@ -38,7 +39,8 @@
|
|||
using namespace KiGfx;
|
||||
|
||||
VBO_CONTAINER::VBO_CONTAINER( int aSize ) :
|
||||
m_freeSpace( aSize ), m_currentSize( aSize ), itemStarted( false ), m_transform( NULL )
|
||||
m_freeSpace( aSize ), m_currentSize( aSize ), itemStarted( false ), m_transform( NULL ),
|
||||
m_failed( false )
|
||||
{
|
||||
// By default no shader is used
|
||||
m_shader[0] = 0;
|
||||
|
@ -82,6 +84,7 @@ void VBO_CONTAINER::EndItem()
|
|||
m_freeSpace += ( itemChunkSize - itemSize );
|
||||
}
|
||||
|
||||
item = NULL;
|
||||
itemStarted = false;
|
||||
}
|
||||
|
||||
|
@ -91,6 +94,9 @@ void VBO_CONTAINER::Add( VBO_ITEM* aVboItem, const VBO_VERTEX* aVertex, unsigned
|
|||
unsigned int offset;
|
||||
VBO_VERTEX* vertexPtr;
|
||||
|
||||
if( m_failed )
|
||||
return;
|
||||
|
||||
if( itemStarted ) // There is an item being created with an unknown size..
|
||||
{
|
||||
unsigned int itemChunkOffset;
|
||||
|
@ -98,27 +104,34 @@ void VBO_CONTAINER::Add( VBO_ITEM* aVboItem, const VBO_VERTEX* aVertex, unsigned
|
|||
// ..and unfortunately does not fit into currently reserved chunk
|
||||
if( itemSize + aSize > itemChunkSize )
|
||||
{
|
||||
// Find the previous chunk for the item, save it, so it can be removed later
|
||||
// Find the previous chunk for the item and change mark it as NULL
|
||||
// so it will not be removed during a possible defragmentation
|
||||
ReservedChunkMap::iterator it = m_reservedChunks.find( item );
|
||||
m_reservedChunks.insert( ReservedChunk( static_cast<VBO_ITEM*>( NULL ), it->second ) );
|
||||
m_reservedChunks.erase( it );
|
||||
|
||||
// Reserve bigger memory fo r the current item
|
||||
int newSize = ( 2 * itemSize ) + aSize;
|
||||
itemChunkOffset = allocate( aVboItem, newSize );
|
||||
aVboItem->SetOffset( itemChunkOffset );
|
||||
|
||||
// Check if there was no error
|
||||
if( itemChunkOffset > m_currentSize )
|
||||
{
|
||||
m_failed = true;
|
||||
return;
|
||||
}
|
||||
|
||||
// Save previous chunk's offset for copying data
|
||||
it = m_reservedChunks.find( static_cast<VBO_ITEM*>( NULL ) );
|
||||
// Check if the chunk was not reallocated after defragmentation
|
||||
int oldItemChunkOffset = getChunkOffset( *it );
|
||||
// Free the space previously used by the chunk
|
||||
freeChunk( it );
|
||||
|
||||
// Copy all the old data
|
||||
memcpy( &m_vertices[itemChunkOffset], &m_vertices[oldItemChunkOffset],
|
||||
itemSize * VBO_ITEM::VertByteSize );
|
||||
|
||||
// Return memory used by the previous chunk
|
||||
freeChunk( it );
|
||||
|
||||
itemChunkSize = newSize;
|
||||
}
|
||||
else
|
||||
|
@ -310,6 +323,7 @@ bool VBO_CONTAINER::defragment( VBO_VERTEX* aTarget )
|
|||
memcpy( &aTarget[newOffset], &m_vertices[itemOffset], itemSize * VBO_ITEM::VertByteSize );
|
||||
|
||||
// Update new offset
|
||||
if( vboItem )
|
||||
vboItem->SetOffset( newOffset );
|
||||
setChunkOffset( *it, newOffset );
|
||||
|
||||
|
@ -349,28 +363,34 @@ void VBO_CONTAINER::resizeChunk( VBO_ITEM* aVboItem, int aNewSize )
|
|||
|
||||
bool VBO_CONTAINER::resizeContainer( unsigned int aNewSize )
|
||||
{
|
||||
unsigned int copySize;
|
||||
VBO_VERTEX* newContainer;
|
||||
|
||||
if( aNewSize < m_currentSize )
|
||||
{
|
||||
// Sanity check, no shrinking if we cannot fit all the data
|
||||
if( ( m_currentSize - m_freeSpace ) > aNewSize )
|
||||
return false;
|
||||
|
||||
defragment();
|
||||
copySize = ( m_currentSize - m_freeSpace );
|
||||
}
|
||||
else
|
||||
{
|
||||
copySize = m_currentSize;
|
||||
}
|
||||
|
||||
VBO_VERTEX* newContainer = static_cast<VBO_VERTEX*>( realloc( m_vertices, aNewSize * sizeof( VBO_VERTEX ) ) );
|
||||
newContainer = static_cast<VBO_VERTEX*>( malloc( aNewSize * sizeof( VBO_VERTEX ) ) );
|
||||
if( newContainer == NULL )
|
||||
{
|
||||
wxLogError( wxT( "Run out of memory" ) );
|
||||
return false;
|
||||
}
|
||||
|
||||
// Defragment directly to the new, smaller container
|
||||
defragment( newContainer );
|
||||
}
|
||||
else
|
||||
{
|
||||
newContainer = static_cast<VBO_VERTEX*>( realloc( m_vertices, aNewSize * sizeof( VBO_VERTEX ) ) );
|
||||
if( newContainer == NULL )
|
||||
{
|
||||
wxLogError( wxT( "Run out of memory" ) );
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
m_vertices = newContainer;
|
||||
|
||||
// Update variables
|
||||
|
|
|
@ -49,6 +49,7 @@
|
|||
#include <iterator>
|
||||
#include <vector>
|
||||
#include <algorithm>
|
||||
#include <boost/unordered_map.hpp>
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <iostream>
|
||||
|
@ -355,7 +356,8 @@ private:
|
|||
GLuint displayListSemiCircle; ///< Semi circle display list
|
||||
|
||||
// Vertex buffer objects related fields
|
||||
std::map<unsigned int, VBO_ITEM*> groups; ///< Stores informations about VBO objects (groups)
|
||||
typedef boost::unordered_map<unsigned int, VBO_ITEM*> GroupsMap;
|
||||
GroupsMap groups; ///< Stores informations about VBO objects (groups)
|
||||
unsigned int groupCounter; ///< Counter used for generating keys for groups
|
||||
VBO_ITEM* currentGroup; ///< Currently used VBO_ITEM (for grouping)
|
||||
VBO_CONTAINER* vboContainer; ///< Container for storing VBO_ITEMs
|
||||
|
@ -559,7 +561,7 @@ private:
|
|||
if( isGrouping )
|
||||
{
|
||||
// New vertex coordinates for VBO
|
||||
VBO_VERTEX vertex = { aX, aY, aZ };
|
||||
const VBO_VERTEX vertex = { aX, aY, aZ };
|
||||
currentGroup->PushVertex( &vertex );
|
||||
}
|
||||
else
|
||||
|
|
|
@ -35,6 +35,7 @@
|
|||
#include <gal/opengl/vbo_item.h>
|
||||
#include <gal/color4d.h>
|
||||
#include <map>
|
||||
#include <boost/unordered_map.hpp>
|
||||
#include <wx/log.h>
|
||||
|
||||
namespace KiGfx
|
||||
|
@ -52,9 +53,9 @@ public:
|
|||
typedef std::pair<const unsigned int, unsigned int> Chunk;
|
||||
typedef std::multimap<const unsigned int, unsigned int> FreeChunkMap;
|
||||
|
||||
///< Maps size of reserved memory chunks to their owners (VBO_ITEMs)
|
||||
///< Maps VBO_ITEMs to reserved memory chunks offsets & sizes
|
||||
typedef std::pair<VBO_ITEM* const, Chunk> ReservedChunk;
|
||||
typedef std::multimap<VBO_ITEM* const, Chunk> ReservedChunkMap;
|
||||
typedef boost::unordered_map<VBO_ITEM* const, Chunk> ReservedChunkMap;
|
||||
|
||||
/**
|
||||
* Function StartItem()
|
||||
|
@ -115,7 +116,7 @@ public:
|
|||
/**
|
||||
* Function GetVertices()
|
||||
* Returns vertices stored at the specific offset.
|
||||
* @aOffest is the specific offset.
|
||||
* @aOffset is the specific offset.
|
||||
*/
|
||||
inline VBO_VERTEX* GetVertices( unsigned int aOffset ) const
|
||||
{
|
||||
|
@ -326,6 +327,9 @@ private:
|
|||
///< Current transform matrix applied for every new vertex pushed.
|
||||
const glm::mat4* m_transform;
|
||||
|
||||
///< Failure flag
|
||||
bool m_failed;
|
||||
|
||||
/**
|
||||
* Function getPowerOf2()
|
||||
* Returns the nearest power of 2, bigger than aNumber.
|
||||
|
|
Loading…
Reference in New Issue