- Timestamp:
- 06/12/13 09:38:06 (12 years ago)
- Location:
- trunk
- Files:
-
- 3 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/nv/gfx/cached_buffer.hh
r118 r119 16 16 namespace nv 17 17 { 18 18 19 template< typename T > class cached_buffer; 19 20 … … 30 31 m_cache->reset(); 31 32 } 32 void commit() 33 { 34 m_cache->commit( this ); 33 bool commit( bool force_changed = false ) 34 { 35 bool resized = force_changed || ( m_cached_size != m_data.size() ); 36 bool result = m_cache->commit( m_data, m_locked, resized, m_offset ); 35 37 m_cached_size = m_data.size(); 36 38 m_locked = false; 37 } 39 return result; 40 } 41 42 template < typename V > 43 bool commit_offset( bool force_changed, V value ) 44 { 45 bool locked = m_locked; 46 bool result = commit( force_changed ); 47 if ( locked || result ) 48 { 49 m_cache->add_offset<T>( m_data.size(), m_offset, static_cast<T>(value) ); 50 } 51 return result; 52 } 53 54 bool is_locked() const 55 { 56 return m_locked; 57 } 58 59 size_t get_offset() const 60 { 61 return m_offset; 62 } 63 38 64 vector& lock() 39 65 { … … 49 75 m_cache->reset(); 50 76 } 51 private: 52 friend class cached_buffer<T>; 53 77 public: 54 78 vector m_data; 55 79 cache* m_cache; … … 63 87 { 64 88 public: 65 typedef buffer_slice<T> slice;66 89 typedef std::vector<T> vector; 67 90 typedef T value_type; 68 static const int value_type_size = sizeof(T);69 70 cached_buffer( device* dev, buffer_hint hint, int initial_size, bool is_vertex = true )91 static const size_t value_type_size = sizeof(T); 92 93 cached_buffer( device* dev, buffer_hint hint, size_t initial_size, bool is_vertex = true ) 71 94 : m_device( dev ) 72 95 , m_buffer( nullptr ) … … 81 104 } 82 105 83 void commit( slice* bslice ) 84 { 106 bool commit( const vector& bv, bool updated, bool resized, size_t& offset ) 107 { 108 if ( !m_full_update && resized ) 109 { 110 m_data.erase( m_data.begin() + offset, m_data.end() ); 111 m_min = glm::min<int>( m_min, offset ); 112 m_full_update = true; 113 } 85 114 if ( m_full_update ) 86 115 { 87 const vector& bv = bslice->data(); 88 bslice->m_offset = m_data.size(); 116 offset = m_data.size(); 89 117 m_data.insert( m_data.end(), bv.cbegin(), bv.cend() ); 90 118 } 91 else if ( bslice->m_locked ) 92 { 93 const vector& bv = bslice->data(); 94 if ( bslice->m_cached_size != bv.size() ) 95 { 96 m_data.erase( m_data.begin() + bslice->m_offset, m_data.end() ); 97 m_full_update = true; 98 m_data.insert( m_data.end(), bv.cbegin(), bv.cend() ); 99 m_min = glm::min<int>( m_min, bslice->m_offset ); 100 } 101 else 102 { 103 std::copy( bv.cbegin(), bv.cend(), m_data.begin() + bslice->m_offset ); 104 m_min = glm::min<int>( m_min, bslice->m_offset ); 105 m_max = glm::max<int>( m_max, bslice->m_offset + bv.size() ); 106 } 119 else if ( updated ) 120 { 121 std::copy( bv.cbegin(), bv.cend(), m_data.begin() + offset ); 122 m_min = glm::min<size_t>( m_min, offset ); 123 m_max = glm::max<size_t>( m_max, offset + bv.size() ); 124 } 125 return m_full_update; 126 } 127 128 template < typename V > 129 void add_offset( size_t size, size_t offset, V value ) 130 { 131 if ( size == 0 ) return; 132 T* ptr = m_data.data() + offset; 133 T* pend = ptr + size; 134 for ( ; ptr != pend; ptr++ ) 135 { 136 *ptr += value; 107 137 } 108 138 } … … 128 158 create_buffer( bsize ); 129 159 m_full_update = true; 160 m_min = 0; 130 161 result = true; 131 162 } 132 m_buffer->bind(); 133 if ( m_full_update ) 134 { 135 if ( m_min > 0 ) 136 { 137 int offset = m_min * value_type_size; 138 int size = m_data.size() * value_type_size - offset; 139 m_buffer->update( m_data.data() + m_min, offset, size ); 140 } 141 else 142 { 143 m_buffer->update( m_data.data(), 0, m_data.size() * value_type_size ); 144 } 145 } 146 else if ( m_max > 0 ) 147 { 163 if ( m_full_update ) m_max = m_data.size(); 164 if ( m_max > 0 ) 165 { 166 m_buffer->bind(); 148 167 int offset = m_min * value_type_size; 149 168 int size = (m_max-m_min) * value_type_size; 150 169 m_buffer->update( m_data.data() + m_min, offset, size ); 151 }152 m_buffer->unbind();170 m_buffer->unbind(); 171 } 153 172 m_full_update = false; 154 173 m_min = get_max_size(); … … 193 212 vector m_data; 194 213 195 intm_min;196 intm_max;214 size_t m_min; 215 size_t m_max; 197 216 }; 198 217 218 template< typename T, typename I = uint16 > class indexed_cached_buffer; 219 220 template< typename T, typename I = uint16 > 221 class indexed_buffer_slice 222 { 223 public: 224 typedef indexed_cached_buffer<T,I> cache; 225 typedef buffer_slice<T> vertex_slice; 226 typedef buffer_slice<I> index_slice; 227 typedef typename vertex_slice::vector vertex_vector; 228 typedef typename index_slice::vector index_vector; 229 230 indexed_buffer_slice( cache* c ) 231 : m_vertex_slice( &c->get_vertex_cache() ) 232 , m_index_slice( &c->get_index_cache() ) 233 , m_cache( c ) 234 { 235 } 236 237 void commit() 238 { 239 bool changed = m_vertex_slice.commit(); 240 m_index_slice.commit_offset( changed, m_vertex_slice.get_offset() ); 241 } 242 vertex_vector& lock_vertices() 243 { 244 return m_vertex_slice.lock(); 245 } 246 index_vector& lock_indices() 247 { 248 return m_index_slice.lock(); 249 } 250 const vertex_vector& vertex_data() 251 { 252 return m_vertex_slice.data(); 253 } 254 const index_vector& index_data() 255 { 256 return m_index_slice.data(); 257 } 258 259 private: 260 vertex_slice m_vertex_slice; 261 index_slice m_index_slice; 262 cache* m_cache; 263 }; 264 265 template< typename T, typename I > 266 class indexed_cached_buffer 267 { 268 public: 269 typedef cached_buffer<T> cached_vertex_buffer; 270 typedef cached_buffer<I> cached_index_buffer; 271 static const int value_type_size = sizeof(T); 272 273 indexed_cached_buffer( device* dev, buffer_hint hint, int initial_size, int initial_index_size ) 274 : m_vertex_buffer( dev, hint, initial_size, true ) 275 , m_index_buffer( dev, hint, initial_index_size, false ) 276 { 277 278 } 279 280 void reset() 281 { 282 m_vertex_buffer.reset(); 283 m_index_buffer.reset(); 284 } 285 286 bool commit() 287 { 288 bool vresult = m_vertex_buffer.commit(); 289 bool iresult = m_index_buffer.commit(); 290 return vresult || iresult; 291 } 292 293 int get_max_vertex_size() const { return m_vertex_buffer.get_max_size(); } 294 int get_max_index_size() const { return m_index_buffer.get_max_size(); } 295 int get_vertex_size() const { return m_vertex_buffer.get_size(); } 296 int get_index_size() const { return m_index_buffer.get_size(); } 297 vertex_buffer* get_vertex_buffer() { return static_cast<vertex_buffer*>( m_vertex_buffer.get_buffer() ); } 298 index_buffer* get_index_buffer() { return static_cast<index_buffer*>( m_index_buffer.get_buffer() ); } 299 cached_vertex_buffer& get_vertex_cache() { return m_vertex_buffer; } 300 cached_index_buffer& get_index_cache() { return m_index_buffer; } 301 302 private: 303 cached_vertex_buffer m_vertex_buffer; 304 cached_index_buffer m_index_buffer; 305 }; 306 307 199 308 } // namespace nv 200 309 -
trunk/nv/interface/vertex_buffer.hh
r116 r119 93 93 { 94 94 public: 95 vertex_array() : m_map(), m_index( nullptr ), m_index_owner( false ), m_index_type( INT) {}95 vertex_array() : m_map(), m_index( nullptr ), m_index_owner( false ), m_index_type(USHORT) {} 96 96 void add_vertex_buffer( int location, vertex_buffer* buffer, datatype datatype, int components, int offset = 0, int stride = 0, bool owner = true ) 97 97 { … … 109 109 void set_index_buffer( index_buffer* buffer, datatype datatype, bool owner ) 110 110 { 111 if (m_index && m_index_owner) delete m_index; 111 112 m_index = buffer; 112 113 m_index_owner = owner; 113 114 m_index_type = datatype; 115 } 116 void set_index_buffer( index_buffer* buffer ) 117 { 118 if (m_index && m_index_owner) delete m_index; 119 m_index = buffer; 114 120 } 115 121 bool has_index_buffer() const { return m_index != nullptr; } -
trunk/tests/cachebuf_test/nv_cachebuf_test.cc
r118 r119 19 19 #include <nv/gfx/cached_buffer.hh> 20 20 21 #define INDEXED_TEST 22 21 23 struct vertex 22 24 { … … 28 30 }; 29 31 32 #ifndef INDEXED_TEST 30 33 struct quad 31 34 { … … 63 66 64 67 }; 68 #endif 69 70 #ifdef INDEXED_TEST 71 typedef nv::indexed_cached_buffer<vertex> gcache; 72 typedef nv::indexed_buffer_slice<vertex> gslice; 73 #else 74 typedef nv::cached_buffer<quad> gcache; 75 typedef nv::buffer_slice<quad> gslice; 76 #endif 65 77 66 78 struct app_window 67 79 { 68 app_window( nv::cached_buffer<quad>* cache, const glm::ivec2& a, const glm::ivec2& b, const glm::vec4& color )69 : m_slice( cache ), m_ a( a ), m_b( b ), m_c( color )80 app_window( gcache* cache, const glm::ivec2& a, const glm::ivec2& b, const glm::vec4& color ) 81 : m_slice( cache ), m_simple( false ), m_a( a ), m_b( b ), m_c( color ) 70 82 { 71 83 create_complex(); … … 76 88 m_c = color; 77 89 glm::vec4 dcolor( color.x * 0.5, color.y * 0.5, color.z * 0.5, 1.0 ); 90 #ifdef INDEXED_TEST 91 std::vector<vertex>& v = m_slice.lock_vertices(); 92 size_t size = v.size(); 93 size_t dcount = 8; 94 size_t dmin = 8; 95 size_t count = size; 96 #else 78 97 std::vector<quad>& v = m_slice.lock(); 98 size_t size = v.size(); 99 size_t dcount = (size - 1) * 6; 100 size_t dmin = 1; 101 size_t count = size * 6; 102 #endif 79 103 vertex* vtx = (vertex*)v.data(); 80 if ( v.size() > 1)81 { 82 for (size_t i = 0; i < (v.size() - 1) * 6; ++i )104 if ( size > dmin ) 105 { 106 for (size_t i = 0; i < dcount; ++i ) 83 107 vtx[i].color = dcolor; 84 for (size_t i = (v.size() - 1) * 6; i < (v.size()) * 6; ++i )108 for (size_t i = dcount; i < count; ++i ) 85 109 vtx[i].color = color; 86 110 } 87 111 else 88 112 { 89 for (size_t i = 0; i < 6; ++i )113 for (size_t i = 0; i < count; ++i ) 90 114 vtx[i].color = color; 91 115 } … … 94 118 void simplify_toggle() 95 119 { 96 if ( m_slice.data().size() > 1)120 if ( !m_simple ) 97 121 { 98 122 NV_LOG( nv::LOG_INFO, "Simplifing" ); … … 108 132 void create_simple() 109 133 { 134 #ifdef INDEXED_TEST 135 std::vector<vertex>& v = m_slice.lock_vertices(); 136 std::vector<nv::uint16>& i = m_slice.lock_indices(); 137 v.clear(); 138 i.clear(); 139 v.emplace_back( m_a, m_c ); 140 v.emplace_back( nv::ivec2( m_a.x, m_b.y ), m_c ); 141 v.emplace_back( m_b, m_c ); 142 v.emplace_back( nv::ivec2( m_b.x, m_a.y ), m_c ); 143 nv::uint16 tmp[] = { 0, 1, 2, 2, 3, 0 }; 144 i.insert( i.end(), tmp, std::end( tmp ) ); 145 #else 110 146 std::vector<quad>& v = m_slice.lock(); 111 147 v.clear(); 112 148 v.emplace_back( m_a, m_b, m_c ); 149 #endif 150 m_simple = true; 113 151 } 114 152 … … 116 154 { 117 155 glm::vec4 dcolor( m_c.x * 0.5, m_c.y * 0.5, m_c.z * 0.5, 1.0 ); 118 std::vector<quad>& v = m_slice.lock();119 v.clear();120 156 nv::ivec2 a2( m_a.x, m_b.y ); 121 157 nv::ivec2 b2( m_b.x, m_a.y ); 122 158 nv::ivec2 t1( 10, 10 ); 123 159 nv::ivec2 t2( -10, 10 ); 160 #ifdef INDEXED_TEST 161 std::vector<vertex>& v = m_slice.lock_vertices(); 162 std::vector<nv::uint16>& i = m_slice.lock_indices(); 163 v.clear(); 164 i.clear(); 165 v.emplace_back( m_a- t1, dcolor ); // 0 166 v.emplace_back( a2 + t2, dcolor ); // 1 167 v.emplace_back( m_b+ t1, dcolor ); // 2 168 v.emplace_back( b2 - t2, dcolor ); // 3 169 170 v.emplace_back( m_a, dcolor ); // 4 171 v.emplace_back( a2, dcolor ); // 5 172 v.emplace_back( m_b, dcolor ); // 6 173 v.emplace_back( b2, dcolor ); // 7 174 nv::uint16 tmp[] = { 175 0, 4, 7, 7, 3, 0, 176 0, 1, 5, 5, 4, 0, 177 1, 2, 6, 6, 5, 1, 178 2, 3, 7, 7, 6, 2, 179 }; 180 i.insert( i.end(), tmp, std::end( tmp ) ); 181 182 v.emplace_back( m_a, m_c ); // 8 183 v.emplace_back( a2, m_c ); // 9 184 v.emplace_back( m_b, m_c ); // 10 185 v.emplace_back( b2, m_c ); // 11 186 nv::uint16 tmp2[] = { 8, 9, 10, 10, 11, 8 }; 187 i.insert( i.end(), tmp2, std::end( tmp2 ) ); 188 189 #else 190 std::vector<quad>& v = m_slice.lock(); 191 v.clear(); 124 192 v.emplace_back( m_a - t1, m_a, b2, b2 - t2, dcolor ); 125 193 v.emplace_back( m_a - t1, a2 + t2, a2, m_a, dcolor ); … … 127 195 v.emplace_back( m_b + t1, b2 - t2, b2, m_b, dcolor ); 128 196 v.emplace_back( m_a, m_b, m_c ); 197 #endif 198 m_simple = false; 129 199 } 130 200 … … 134 204 } 135 205 136 nv::buffer_slice<quad> m_slice; 206 gslice m_slice; 207 bool m_simple; 137 208 nv::ivec2 m_a; 138 209 nv::ivec2 m_b; … … 157 228 nv::render_state m_render_state; 158 229 159 nv::cached_buffer<quad>* m_quad_cache;230 gcache* m_quad_cache; 160 231 std::vector<app_window> m_windows; 161 232 … … 185 256 { 186 257 { 187 m_program = m_device->create_program( nv::slurp( "cachebuf.vert" ), nv::slurp( "cachebuf.frag" ) ); 188 m_va = m_device->create_vertex_array(); 189 190 m_quad_cache = new nv::cached_buffer<quad>( m_device, nv::DYNAMIC_DRAW, 20, true ); 191 m_coord_loc = m_program->get_attribute("coord")->get_location(); 192 m_color_loc = m_program->get_attribute("color")->get_location(); 193 194 m_va->add_vertex_buffer( m_coord_loc, (nv::vertex_buffer*)m_quad_cache->get_buffer(), nv::INT, 2, 0, sizeof( vertex ), false ); 195 m_va->add_vertex_buffer( m_color_loc, (nv::vertex_buffer*)m_quad_cache->get_buffer(), nv::FLOAT, 4, offset_of( &vertex::color ), sizeof( vertex ), false ); 258 m_program = m_device->create_program( nv::slurp( "cachebuf.vert" ), nv::slurp( "cachebuf.frag" ) ); 259 m_coord_loc = m_program->get_attribute("coord")->get_location(); 260 m_color_loc = m_program->get_attribute("color")->get_location(); 261 m_va = m_device->create_vertex_array(); 262 263 #ifdef INDEXED_TEST 264 m_quad_cache = new gcache( m_device, nv::DYNAMIC_DRAW, 200, 200 ); 265 m_va->set_index_buffer( m_quad_cache->get_index_buffer(), nv::USHORT, false ); 266 nv::vertex_buffer* buffer = m_quad_cache->get_vertex_buffer(); 267 #else 268 m_quad_cache = new gcache( m_device, nv::DYNAMIC_DRAW, 20, true ); 269 nv::vertex_buffer* buffer = (nv::vertex_buffer*)m_quad_cache->get_buffer(); 270 #endif 271 272 m_va->add_vertex_buffer( m_coord_loc, buffer, nv::INT, 2, 0, sizeof( vertex ), false ); 273 m_va->add_vertex_buffer( m_color_loc, buffer, nv::FLOAT, 4, offset_of( &vertex::color ), sizeof( vertex ), false ); 196 274 } 197 275 return true; … … 213 291 if (m_quad_cache->commit() ) 214 292 { 215 m_va->update_vertex_buffer( m_coord_loc, (nv::vertex_buffer*)m_quad_cache->get_buffer(), false ); 216 m_va->update_vertex_buffer( m_color_loc, (nv::vertex_buffer*)m_quad_cache->get_buffer(), false ); 293 #ifdef INDEXED_TEST 294 m_va->set_index_buffer( m_quad_cache->get_index_buffer() ); 295 nv::vertex_buffer* buffer = m_quad_cache->get_vertex_buffer(); 296 #else 297 nv::vertex_buffer* buffer = (nv::vertex_buffer*)m_quad_cache->get_buffer(); 298 #endif 299 m_va->update_vertex_buffer( m_coord_loc, buffer, false ); 300 m_va->update_vertex_buffer( m_color_loc, buffer, false ); 217 301 } 218 302 … … 220 304 m_program->bind(); 221 305 // m_program->set_uniform( "tex", 0 ); 222 m_window->get_context()->draw( nv::TRIANGLES, m_render_state, m_program, m_va, m_quad_cache->get_size() * 6 ); 306 #ifdef INDEXED_TEST 307 size_t draw_size = m_quad_cache->get_index_size(); 308 #else 309 size_t draw_size = m_quad_cache->get_size() * 6; 310 #endif 311 m_window->get_context()->draw( nv::TRIANGLES, m_render_state, m_program, m_va, draw_size ); 223 312 m_window->swap_buffers(); 224 313
Note: See TracChangeset
for help on using the changeset viewer.