Panda3D
|
00001 // Filename: renderState.I 00002 // Created by: drose (21Feb02) 00003 // 00004 //////////////////////////////////////////////////////////////////// 00005 // 00006 // PANDA 3D SOFTWARE 00007 // Copyright (c) Carnegie Mellon University. All rights reserved. 00008 // 00009 // All use of this software is subject to the terms of the revised BSD 00010 // license. You should have received a copy of this license along 00011 // with this source code in a file named "LICENSE." 00012 // 00013 //////////////////////////////////////////////////////////////////// 00014 00015 00016 //////////////////////////////////////////////////////////////////// 00017 // Function: RenderState::is_empty 00018 // Access: Published 00019 // Description: Returns true if the state is empty, false otherwise. 00020 //////////////////////////////////////////////////////////////////// 00021 INLINE bool RenderState:: 00022 is_empty() const { 00023 return _filled_slots.is_zero(); 00024 } 00025 00026 //////////////////////////////////////////////////////////////////// 00027 // Function: RenderState::has_cull_callback 00028 // Access: Published 00029 // Description: Returns true if any of the RenderAttribs in this 00030 // state request a cull_callback(), false if none of 00031 // them do. 00032 //////////////////////////////////////////////////////////////////// 00033 INLINE bool RenderState:: 00034 has_cull_callback() const { 00035 if ((_flags & F_checked_cull_callback) == 0) { 00036 // We pretend this function is const, even though it transparently 00037 // modifies the internal shader cache. 00038 ((RenderState *)this)->determine_cull_callback(); 00039 } 00040 return (_flags & F_has_cull_callback) != 0; 00041 } 00042 00043 //////////////////////////////////////////////////////////////////// 00044 // Function: RenderState::remove_attrib 00045 // Access: Published 00046 // Description: Returns a new RenderState object that represents the 00047 // same as the source state, with the indicated 00048 // RenderAttrib removed. 00049 //////////////////////////////////////////////////////////////////// 00050 INLINE CPT(RenderState) RenderState:: 00051 remove_attrib(TypeHandle type) const { 00052 RenderAttribRegistry *reg = RenderAttribRegistry::quick_get_global_ptr(); 00053 int slot = reg->get_slot(type); 00054 return remove_attrib(slot); 00055 } 00056 00057 //////////////////////////////////////////////////////////////////// 00058 // Function: RenderState::has_attrib 00059 // Access: Published 00060 // Description: Returns true if an attrib of the indicated type is 00061 // present, false otherwise. 00062 //////////////////////////////////////////////////////////////////// 00063 INLINE bool RenderState:: 00064 has_attrib(TypeHandle type) const { 00065 return get_attrib(type) != (RenderAttrib *)NULL; 00066 } 00067 00068 //////////////////////////////////////////////////////////////////// 00069 // Function: RenderState::has_attrib 00070 // Access: Published 00071 // Description: Returns true if an attrib of the indicated type is 00072 // present, false otherwise. 00073 //////////////////////////////////////////////////////////////////// 00074 INLINE bool RenderState:: 00075 has_attrib(int slot) const { 00076 return get_attrib(slot) != (RenderAttrib *)NULL; 00077 } 00078 00079 //////////////////////////////////////////////////////////////////// 00080 // Function: RenderState::get_attrib 00081 // Access: Published 00082 // Description: Looks for a RenderAttrib of the indicated type in the 00083 // state, and returns it if it is found, or NULL if it 00084 // is not. 00085 //////////////////////////////////////////////////////////////////// 00086 INLINE const RenderAttrib *RenderState:: 00087 get_attrib(TypeHandle type) const { 00088 RenderAttribRegistry *reg = RenderAttribRegistry::get_global_ptr(); 00089 int slot = reg->get_slot(type); 00090 return _attributes[slot]._attrib; 00091 } 00092 00093 //////////////////////////////////////////////////////////////////// 00094 // Function: RenderState::get_attrib 00095 // Access: Published 00096 // Description: Returns the RenderAttrib with the indicated slot 00097 // index, or NULL if there is no such RenderAttrib in 00098 // the state. 00099 //////////////////////////////////////////////////////////////////// 00100 INLINE const RenderAttrib *RenderState:: 00101 get_attrib(int slot) const { 00102 return _attributes[slot]._attrib; 00103 } 00104 00105 //////////////////////////////////////////////////////////////////// 00106 // Function: RenderState::get_attrib_def 00107 // Access: Published 00108 // Description: Returns the RenderAttrib with the indicated slot 00109 // index, or the default attrib for that slot if there 00110 // is no such RenderAttrib in the state. 00111 //////////////////////////////////////////////////////////////////// 00112 INLINE const RenderAttrib *RenderState:: 00113 get_attrib_def(int slot) const { 00114 if (_attributes[slot]._attrib != (RenderAttrib *)NULL) { 00115 return _attributes[slot]._attrib; 00116 } 00117 return make_full_default()->get_attrib(slot); 00118 } 00119 00120 //////////////////////////////////////////////////////////////////// 00121 // Function: RenderState::get_override 00122 // Access: Published 00123 // Description: Looks for a RenderAttrib of the indicated type in the 00124 // state, and returns its override value if it is found, 00125 // or 0 if it is not. 00126 //////////////////////////////////////////////////////////////////// 00127 INLINE int RenderState:: 00128 get_override(TypeHandle type) const { 00129 RenderAttribRegistry *reg = RenderAttribRegistry::get_global_ptr(); 00130 int slot = reg->get_slot(type); 00131 return _attributes[slot]._override; 00132 } 00133 00134 //////////////////////////////////////////////////////////////////// 00135 // Function: RenderState::get_override 00136 // Access: Published 00137 // Description: Looks for a RenderAttrib of the indicated type in the 00138 // state, and returns its override value if it is found, 00139 // or 0 if it is not. 00140 //////////////////////////////////////////////////////////////////// 00141 INLINE int RenderState:: 00142 get_override(int slot) const { 00143 return _attributes[slot]._override; 00144 } 00145 00146 //////////////////////////////////////////////////////////////////// 00147 // Function: RenderState::get_unique 00148 // Access: Published 00149 // Description: Returns the pointer to the unique RenderState in 00150 // the cache that is equivalent to this one. This may 00151 // be the same pointer as this object, or it may be a 00152 // different pointer; but it will be an equivalent 00153 // object, and it will be a shared pointer. This may be 00154 // called from time to time to improve cache benefits. 00155 //////////////////////////////////////////////////////////////////// 00156 INLINE CPT(RenderState) RenderState:: 00157 get_unique() const { 00158 return return_unique((RenderState *)this); 00159 } 00160 00161 //////////////////////////////////////////////////////////////////// 00162 // Function: RenderState::cache_ref 00163 // Access: Published 00164 // Description: Overrides this method to update PStats appropriately. 00165 //////////////////////////////////////////////////////////////////// 00166 INLINE void RenderState:: 00167 cache_ref() const { 00168 #ifdef DO_PSTATS 00169 int old_referenced_bits = get_referenced_bits(); 00170 NodeCachedReferenceCount::cache_ref(); 00171 consider_update_pstats(old_referenced_bits); 00172 #else // DO_PSTATS 00173 NodeCachedReferenceCount::cache_ref(); 00174 #endif // DO_PSTATS 00175 } 00176 00177 //////////////////////////////////////////////////////////////////// 00178 // Function: RenderState::cache_unref 00179 // Access: Published 00180 // Description: Overrides this method to update PStats appropriately. 00181 //////////////////////////////////////////////////////////////////// 00182 INLINE bool RenderState:: 00183 cache_unref() const { 00184 #ifdef DO_PSTATS 00185 int old_referenced_bits = get_referenced_bits(); 00186 bool result = do_cache_unref(); 00187 consider_update_pstats(old_referenced_bits); 00188 return result; 00189 #else // DO_PSTATS 00190 return do_cache_unref(); 00191 #endif // DO_PSTATS 00192 } 00193 00194 //////////////////////////////////////////////////////////////////// 00195 // Function: RenderState::node_ref 00196 // Access: Published 00197 // Description: Overrides this method to update PStats appropriately. 00198 //////////////////////////////////////////////////////////////////// 00199 INLINE void RenderState:: 00200 node_ref() const { 00201 #ifdef DO_PSTATS 00202 int old_referenced_bits = get_referenced_bits(); 00203 NodeCachedReferenceCount::node_ref(); 00204 consider_update_pstats(old_referenced_bits); 00205 #else // DO_PSTATS 00206 NodeCachedReferenceCount::node_ref(); 00207 #endif // DO_PSTATS 00208 } 00209 00210 //////////////////////////////////////////////////////////////////// 00211 // Function: RenderState::node_unref 00212 // Access: Published 00213 // Description: Overrides this method to update PStats appropriately. 00214 //////////////////////////////////////////////////////////////////// 00215 INLINE bool RenderState:: 00216 node_unref() const { 00217 #ifdef DO_PSTATS 00218 int old_referenced_bits = get_referenced_bits(); 00219 bool result = do_node_unref(); 00220 consider_update_pstats(old_referenced_bits); 00221 return result; 00222 #else // DO_PSTATS 00223 return do_node_unref(); 00224 #endif // DO_PSTATS 00225 } 00226 00227 //////////////////////////////////////////////////////////////////// 00228 // Function: RenderState::get_composition_cache_num_entries 00229 // Access: Published 00230 // Description: Returns the number of entries in the composition 00231 // cache for this RenderState. This is the number of 00232 // other RenderStates whose composition with this one 00233 // has been cached. This number is not useful for any 00234 // practical reason other than performance analysis. 00235 //////////////////////////////////////////////////////////////////// 00236 INLINE int RenderState:: 00237 get_composition_cache_num_entries() const { 00238 LightReMutexHolder holder(*_states_lock); 00239 return _composition_cache.get_num_entries(); 00240 } 00241 00242 //////////////////////////////////////////////////////////////////// 00243 // Function: RenderState::get_invert_composition_cache_num_entries 00244 // Access: Published 00245 // Description: Returns the number of entries in the 00246 // invert_composition cache for this RenderState. 00247 // This is similar to the composition cache, but it 00248 // records cache entries for the invert_compose() 00249 // operation. See get_composition_cache_num_entries(). 00250 //////////////////////////////////////////////////////////////////// 00251 INLINE int RenderState:: 00252 get_invert_composition_cache_num_entries() const { 00253 LightReMutexHolder holder(*_states_lock); 00254 return _invert_composition_cache.get_num_entries(); 00255 } 00256 00257 //////////////////////////////////////////////////////////////////// 00258 // Function: RenderState::get_composition_cache_size 00259 // Access: Published 00260 // Description: Returns the number of slots in the composition 00261 // cache for this RenderState. You may use this as 00262 // an upper bound when walking through all of the 00263 // composition cache results via 00264 // get_composition_cache_source() or result(). 00265 // 00266 // This has no practical value other than for examining 00267 // the cache for performance analysis. 00268 //////////////////////////////////////////////////////////////////// 00269 INLINE int RenderState:: 00270 get_composition_cache_size() const { 00271 LightReMutexHolder holder(*_states_lock); 00272 return _composition_cache.get_size(); 00273 } 00274 00275 //////////////////////////////////////////////////////////////////// 00276 // Function: RenderState::get_composition_cache_source 00277 // Access: Published 00278 // Description: Returns the source RenderState of the nth element 00279 // in the composition cache. Returns NULL if there 00280 // doesn't happen to be an entry in the nth element. 00281 // See get_composition_cache_result(). 00282 // 00283 // This has no practical value other than for examining 00284 // the cache for performance analysis. 00285 //////////////////////////////////////////////////////////////////// 00286 INLINE const RenderState *RenderState:: 00287 get_composition_cache_source(int n) const { 00288 LightReMutexHolder holder(*_states_lock); 00289 if (!_composition_cache.has_element(n)) { 00290 return NULL; 00291 } 00292 return _composition_cache.get_key(n); 00293 } 00294 00295 //////////////////////////////////////////////////////////////////// 00296 // Function: RenderState::get_composition_cache_result 00297 // Access: Published 00298 // Description: Returns the result RenderState of the nth element 00299 // in the composition cache. Returns NULL if there 00300 // doesn't happen to be an entry in the nth element. 00301 // 00302 // In general, 00303 // a->compose(a->get_composition_cache_source(n)) == 00304 // a->get_composition_cache_result(n). 00305 // 00306 // This has no practical value other than for examining 00307 // the cache for performance analysis. 00308 //////////////////////////////////////////////////////////////////// 00309 INLINE const RenderState *RenderState:: 00310 get_composition_cache_result(int n) const { 00311 LightReMutexHolder holder(*_states_lock); 00312 if (!_composition_cache.has_element(n)) { 00313 return NULL; 00314 } 00315 return _composition_cache.get_data(n)._result; 00316 } 00317 00318 //////////////////////////////////////////////////////////////////// 00319 // Function: RenderState::get_invert_composition_cache_size 00320 // Access: Published 00321 // Description: Returns the number of slots in the composition 00322 // cache for this RenderState. You may use this as 00323 // an upper bound when walking through all of the 00324 // composition cache results via 00325 // get_invert_composition_cache_source() or result(). 00326 // 00327 // This has no practical value other than for examining 00328 // the cache for performance analysis. 00329 //////////////////////////////////////////////////////////////////// 00330 INLINE int RenderState:: 00331 get_invert_composition_cache_size() const { 00332 LightReMutexHolder holder(*_states_lock); 00333 return _invert_composition_cache.get_size(); 00334 } 00335 00336 //////////////////////////////////////////////////////////////////// 00337 // Function: RenderState::get_invert_composition_cache_source 00338 // Access: Published 00339 // Description: Returns the source RenderState of the nth element 00340 // in the invert composition cache. Returns NULL if 00341 // there doesn't happen to be an entry in the nth 00342 // element. See get_invert_composition_cache_result(). 00343 // 00344 // This has no practical value other than for examining 00345 // the cache for performance analysis. 00346 //////////////////////////////////////////////////////////////////// 00347 INLINE const RenderState *RenderState:: 00348 get_invert_composition_cache_source(int n) const { 00349 LightReMutexHolder holder(*_states_lock); 00350 if (!_invert_composition_cache.has_element(n)) { 00351 return NULL; 00352 } 00353 return _invert_composition_cache.get_key(n); 00354 } 00355 00356 //////////////////////////////////////////////////////////////////// 00357 // Function: RenderState::get_invert_composition_cache_result 00358 // Access: Published 00359 // Description: Returns the result RenderState of the nth element 00360 // in the invert composition cache. Returns NULL if 00361 // there doesn't happen to be an entry in the nth 00362 // element. 00363 // 00364 // In general, 00365 // a->invert_compose(a->get_invert_composition_cache_source(n)) 00366 // == a->get_invert_composition_cache_result(n). 00367 // 00368 // This has no practical value other than for examining 00369 // the cache for performance analysis. 00370 //////////////////////////////////////////////////////////////////// 00371 INLINE const RenderState *RenderState:: 00372 get_invert_composition_cache_result(int n) const { 00373 LightReMutexHolder holder(*_states_lock); 00374 if (!_invert_composition_cache.has_element(n)) { 00375 return NULL; 00376 } 00377 return _invert_composition_cache.get_data(n)._result; 00378 } 00379 00380 //////////////////////////////////////////////////////////////////// 00381 // Function: RenderState::get_draw_order 00382 // Access: Published 00383 // Description: Returns the draw order indicated by the 00384 // CullBinAttrib, if any, associated by this state (or 0 00385 // if there is no CullBinAttrib). See get_bin_index(). 00386 //////////////////////////////////////////////////////////////////// 00387 INLINE int RenderState:: 00388 get_draw_order() const { 00389 if ((_flags & F_checked_bin_index) == 0) { 00390 // We pretend this function is const, even though it transparently 00391 // modifies the internal draw_order cache. 00392 ((RenderState *)this)->determine_bin_index(); 00393 } 00394 return _draw_order; 00395 } 00396 00397 //////////////////////////////////////////////////////////////////// 00398 // Function: RenderState::get_bin_index 00399 // Access: Published 00400 // Description: Returns the bin index indicated by the CullBinAttrib, 00401 // if any, associated by this state (or the default bin 00402 // index if there is no CullBinAttrib). This function 00403 // is provided as an optimization for determining this 00404 // at render time. 00405 //////////////////////////////////////////////////////////////////// 00406 INLINE int RenderState:: 00407 get_bin_index() const { 00408 if ((_flags & F_checked_bin_index) == 0) { 00409 // We pretend this function is const, even though it transparently 00410 // modifies the internal bin_index cache. 00411 ((RenderState *)this)->determine_bin_index(); 00412 } 00413 return _bin_index; 00414 } 00415 00416 //////////////////////////////////////////////////////////////////// 00417 // Function: RenderState::set_destructing 00418 // Access: Private 00419 // Description: This function should only be called from the 00420 // destructor; it indicates that this RenderState 00421 // object is beginning destruction. It is only used as 00422 // a sanity check, and is only meaningful when NDEBUG is 00423 // not defined. 00424 //////////////////////////////////////////////////////////////////// 00425 INLINE void RenderState:: 00426 set_destructing() { 00427 #ifndef NDEBUG 00428 _flags |= F_is_destructing; 00429 #endif 00430 } 00431 00432 //////////////////////////////////////////////////////////////////// 00433 // Function: RenderState::is_destructing 00434 // Access: Private 00435 // Description: Returns true if the RenderState object is 00436 // currently within its destructor 00437 // (i.e. set_destructing() has been called). This is 00438 // only used as a sanity check, and is only meaningful 00439 // when NDEBUG is not defined. 00440 //////////////////////////////////////////////////////////////////// 00441 INLINE bool RenderState:: 00442 is_destructing() const { 00443 #ifndef NDEBUG 00444 return (_flags & F_is_destructing) != 0; 00445 #else 00446 return false; 00447 #endif 00448 } 00449 00450 //////////////////////////////////////////////////////////////////// 00451 // Function: RenderState::consider_update_pstats 00452 // Access: Private 00453 // Description: Calls update_pstats() if the state of the referenced 00454 // bits has changed from the indicated value. 00455 //////////////////////////////////////////////////////////////////// 00456 INLINE void RenderState:: 00457 consider_update_pstats(int old_referenced_bits) const { 00458 #ifdef DO_PSTATS 00459 int new_referenced_bits = get_referenced_bits(); 00460 if (old_referenced_bits != new_referenced_bits) { 00461 update_pstats(old_referenced_bits, new_referenced_bits); 00462 } 00463 #endif // DO_PSTATS 00464 } 00465 00466 //////////////////////////////////////////////////////////////////// 00467 // Function: RenderState::Composition::Constructor 00468 // Access: Public 00469 // Description: 00470 //////////////////////////////////////////////////////////////////// 00471 INLINE RenderState::Composition:: 00472 Composition() { 00473 } 00474 00475 //////////////////////////////////////////////////////////////////// 00476 // Function: RenderState::Composition::Copy Constructor 00477 // Access: Public 00478 // Description: 00479 //////////////////////////////////////////////////////////////////// 00480 INLINE RenderState::Composition:: 00481 Composition(const RenderState::Composition ©) : 00482 _result(copy._result) 00483 { 00484 } 00485 00486 //////////////////////////////////////////////////////////////////// 00487 // Function: RenderState::Attribute::Constructor 00488 // Access: Public 00489 // Description: 00490 //////////////////////////////////////////////////////////////////// 00491 INLINE RenderState::Attribute:: 00492 Attribute(const RenderAttrib *attrib, int override) : 00493 _attrib(attrib), 00494 _override(override) 00495 { 00496 } 00497 00498 //////////////////////////////////////////////////////////////////// 00499 // Function: RenderState::Attribute::Constructor 00500 // Access: Public 00501 // Description: 00502 //////////////////////////////////////////////////////////////////// 00503 INLINE RenderState::Attribute:: 00504 Attribute(int override) : 00505 _override(override) 00506 { 00507 } 00508 00509 //////////////////////////////////////////////////////////////////// 00510 // Function: RenderState::Attribute::Copy Constructor 00511 // Access: Public 00512 // Description: 00513 //////////////////////////////////////////////////////////////////// 00514 INLINE RenderState::Attribute:: 00515 Attribute(const Attribute ©) : 00516 _attrib(copy._attrib), 00517 _override(copy._override) 00518 { 00519 } 00520 00521 //////////////////////////////////////////////////////////////////// 00522 // Function: RenderState::Attribute::Copy Assignment Operator 00523 // Access: Public 00524 // Description: 00525 //////////////////////////////////////////////////////////////////// 00526 INLINE void RenderState::Attribute:: 00527 operator = (const Attribute ©) { 00528 _attrib = copy._attrib; 00529 _override = copy._override; 00530 } 00531 00532 //////////////////////////////////////////////////////////////////// 00533 // Function: RenderState::Attribute::compare_to 00534 // Access: Public 00535 // Description: Provides an indication of whether a particular 00536 // attribute is equivalent to another one, for purposes 00537 // of generating unique RenderStates. This should 00538 // compare all properties of the Attribute. 00539 //////////////////////////////////////////////////////////////////// 00540 INLINE int RenderState::Attribute:: 00541 compare_to(const Attribute &other) const { 00542 if (_attrib != other._attrib) { 00543 return _attrib < other._attrib ? -1 : 1; 00544 } 00545 return _override - other._override; 00546 } 00547 00548 //////////////////////////////////////////////////////////////////// 00549 // Function: RenderState::Attribute::set 00550 // Access: Public 00551 // Description: 00552 //////////////////////////////////////////////////////////////////// 00553 INLINE void RenderState::Attribute:: 00554 set(const RenderAttrib *attrib, int override) { 00555 _attrib = attrib; 00556 _override = override; 00557 } 00558 00559 //////////////////////////////////////////////////////////////////// 00560 // Function: RenderState::flush_level 00561 // Access: Public, Static 00562 // Description: Flushes the PStatCollectors used during traversal. 00563 //////////////////////////////////////////////////////////////////// 00564 INLINE void RenderState:: 00565 flush_level() { 00566 _node_counter.flush_level(); 00567 _cache_counter.flush_level(); 00568 } 00569 00570 //////////////////////////////////////////////////////////////////// 00571 // Function: RenderState::do_node_unref 00572 // Access: Private 00573 // Description: Reimplements NodeReferenceCount::node_unref(). We do 00574 // this because we have a non-virtual unref() method. 00575 //////////////////////////////////////////////////////////////////// 00576 INLINE bool RenderState:: 00577 do_node_unref() const { 00578 node_unref_only(); 00579 return unref(); 00580 } 00581 00582 //////////////////////////////////////////////////////////////////// 00583 // Function: RenderState::do_cache_unref 00584 // Access: Private 00585 // Description: Reimplements 00586 // CachedTypedWritableReferenceCount::cache_unref(). We 00587 // do this because we have a non-virtual unref() method. 00588 //////////////////////////////////////////////////////////////////// 00589 INLINE bool RenderState:: 00590 do_cache_unref() const { 00591 cache_unref_only(); 00592 return unref(); 00593 } 00594 00595 //////////////////////////////////////////////////////////////////// 00596 // Function: RenderState::CompositionCycleDescEntry::Constructor 00597 // Access: Public 00598 // Description: 00599 //////////////////////////////////////////////////////////////////// 00600 INLINE RenderState::CompositionCycleDescEntry:: 00601 CompositionCycleDescEntry(const RenderState *obj, 00602 const RenderState *result, 00603 bool inverted) : 00604 _obj(obj), 00605 _result(result), 00606 _inverted(inverted) 00607 { 00608 } 00609