00001 // Filename: pandaNode.I 00002 // Created by: drose (20Feb02) 00003 // 00004 //////////////////////////////////////////////////////////////////// 00005 // 00006 // PANDA 3D SOFTWARE 00007 // Copyright (c) 2001, Disney Enterprises, Inc. All rights reserved 00008 // 00009 // All use of this software is subject to the terms of the Panda 3d 00010 // Software license. You should have received a copy of this license 00011 // along with this source code; you will also find a current copy of 00012 // the license at http://www.panda3d.org/license.txt . 00013 // 00014 // To contact the maintainers of this program write to 00015 // panda3d@yahoogroups.com . 00016 // 00017 //////////////////////////////////////////////////////////////////// 00018 00019 00020 //////////////////////////////////////////////////////////////////// 00021 // Function: PandaNode::DownConnection::Constructor 00022 // Access: Public 00023 // Description: 00024 //////////////////////////////////////////////////////////////////// 00025 INLINE PandaNode::DownConnection:: 00026 DownConnection(PandaNode *child, int sort) : 00027 _child(child), 00028 _sort(sort) 00029 { 00030 } 00031 00032 //////////////////////////////////////////////////////////////////// 00033 // Function: PandaNode::DownConnection::operator < 00034 // Access: Public 00035 // Description: Provides a partial ordering on the children of a node 00036 // so that they are ranked first in sort order, and then 00037 // (by virtue of the ordered_vector) in the order they 00038 // were added. 00039 //////////////////////////////////////////////////////////////////// 00040 INLINE bool PandaNode::DownConnection:: 00041 operator < (const DownConnection &other) const { 00042 return _sort < other._sort; 00043 } 00044 00045 //////////////////////////////////////////////////////////////////// 00046 // Function: PandaNode::DownConnection::get_child 00047 // Access: Public 00048 // Description: 00049 //////////////////////////////////////////////////////////////////// 00050 INLINE PandaNode *PandaNode::DownConnection:: 00051 get_child() const { 00052 return _child; 00053 } 00054 00055 //////////////////////////////////////////////////////////////////// 00056 // Function: PandaNode::DownConnection::set_child 00057 // Access: Public 00058 // Description: This is only called by PandaNode::replace_child(). 00059 //////////////////////////////////////////////////////////////////// 00060 INLINE void PandaNode::DownConnection:: 00061 set_child(PandaNode *child) { 00062 _child = child; 00063 } 00064 00065 //////////////////////////////////////////////////////////////////// 00066 // Function: PandaNode::DownConnection::get_sort 00067 // Access: Public 00068 // Description: 00069 //////////////////////////////////////////////////////////////////// 00070 INLINE int PandaNode::DownConnection:: 00071 get_sort() const { 00072 return _sort; 00073 } 00074 00075 //////////////////////////////////////////////////////////////////// 00076 // Function: PandaNode::UpConnection::Constructor 00077 // Access: Public 00078 // Description: 00079 //////////////////////////////////////////////////////////////////// 00080 INLINE PandaNode::UpConnection:: 00081 UpConnection(PandaNode *parent) : 00082 _parent(parent) 00083 { 00084 } 00085 00086 //////////////////////////////////////////////////////////////////// 00087 // Function: PandaNode::UpConnection::operator < 00088 // Access: Public 00089 // Description: Sorts the up connections of a node by pointer. This 00090 // is different from the down connections of a node, 00091 // which are sorted by the specified _sort number. This 00092 // makes it easy to locate a particular parent of a node 00093 // by pointer, or to test for a parent-child 00094 // relationship given two node pointers. 00095 //////////////////////////////////////////////////////////////////// 00096 INLINE bool PandaNode::UpConnection:: 00097 operator < (const UpConnection &other) const { 00098 return _parent < other._parent; 00099 } 00100 00101 //////////////////////////////////////////////////////////////////// 00102 // Function: PandaNode::UpConnection::get_parent 00103 // Access: Public 00104 // Description: 00105 //////////////////////////////////////////////////////////////////// 00106 INLINE PandaNode *PandaNode::UpConnection:: 00107 get_parent() const { 00108 return _parent; 00109 } 00110 00111 //////////////////////////////////////////////////////////////////// 00112 // Function: PandaNode::CData::Constructor 00113 // Access: Public 00114 // Description: 00115 //////////////////////////////////////////////////////////////////// 00116 INLINE PandaNode::CData:: 00117 CData() { 00118 _state = RenderState::make_empty(); 00119 _effects = RenderEffects::make_empty(); 00120 _transform = TransformState::make_identity(); 00121 _draw_mask = DrawMask::all_on(); 00122 _net_collide_mask = CollideMask::all_off(); 00123 _fixed_internal_bound = false; 00124 } 00125 00126 //////////////////////////////////////////////////////////////////// 00127 // Function: PandaNode::CData::Copy Constructor 00128 // Access: Public 00129 // Description: 00130 //////////////////////////////////////////////////////////////////// 00131 INLINE PandaNode::CData:: 00132 CData(const PandaNode::CData ©) : 00133 _down(copy._down), 00134 _stashed(copy._stashed), 00135 _up(copy._up), 00136 _paths(copy._paths), 00137 _state(copy._state), 00138 _effects(copy._effects), 00139 _transform(copy._transform), 00140 _draw_mask(copy._draw_mask), 00141 _fixed_internal_bound(copy._fixed_internal_bound) 00142 { 00143 _net_collide_mask = CollideMask::all_off(); 00144 } 00145 00146 //////////////////////////////////////////////////////////////////// 00147 // Function: PandaNode::Children::Constructor 00148 // Access: Public 00149 // Description: 00150 //////////////////////////////////////////////////////////////////// 00151 INLINE PandaNode::Children:: 00152 Children(const PandaNode::CDReader &cdata) : 00153 _cdata(cdata) 00154 { 00155 } 00156 00157 //////////////////////////////////////////////////////////////////// 00158 // Function: PandaNode::Children::Copy Constructor 00159 // Access: Public 00160 // Description: 00161 //////////////////////////////////////////////////////////////////// 00162 INLINE PandaNode::Children:: 00163 Children(const PandaNode::Children ©) : 00164 _cdata(copy._cdata) 00165 { 00166 } 00167 00168 //////////////////////////////////////////////////////////////////// 00169 // Function: PandaNode::Children::Copy Assignment Operator 00170 // Access: Public 00171 // Description: 00172 //////////////////////////////////////////////////////////////////// 00173 INLINE void PandaNode::Children:: 00174 operator = (const PandaNode::Children ©) { 00175 _cdata = copy._cdata; 00176 } 00177 00178 //////////////////////////////////////////////////////////////////// 00179 // Function: PandaNode::Children::get_num_children 00180 // Access: Public 00181 // Description: Returns the number of children of the node. 00182 //////////////////////////////////////////////////////////////////// 00183 INLINE int PandaNode::Children:: 00184 get_num_children() const { 00185 return _cdata->_down.size(); 00186 } 00187 00188 //////////////////////////////////////////////////////////////////// 00189 // Function: PandaNode::Children::get_child 00190 // Access: Public 00191 // Description: Returns the nth child of the node. 00192 //////////////////////////////////////////////////////////////////// 00193 INLINE PandaNode *PandaNode::Children:: 00194 get_child(int n) const { 00195 nassertr(n >= 0 && n < (int)_cdata->_down.size(), NULL); 00196 return _cdata->_down[n].get_child(); 00197 } 00198 00199 //////////////////////////////////////////////////////////////////// 00200 // Function: PandaNode::ChildrenCopy::Copy Constructor 00201 // Access: Public 00202 // Description: 00203 //////////////////////////////////////////////////////////////////// 00204 INLINE PandaNode::ChildrenCopy:: 00205 ChildrenCopy(const PandaNode::ChildrenCopy ©) : 00206 _list(copy._list) 00207 { 00208 } 00209 00210 //////////////////////////////////////////////////////////////////// 00211 // Function: PandaNode::ChildrenCopy::Copy Assignment Operator 00212 // Access: Public 00213 // Description: 00214 //////////////////////////////////////////////////////////////////// 00215 INLINE void PandaNode::ChildrenCopy:: 00216 operator = (const PandaNode::ChildrenCopy ©) { 00217 _list = copy._list; 00218 } 00219 00220 //////////////////////////////////////////////////////////////////// 00221 // Function: PandaNode::ChildrenCopy::get_num_children 00222 // Access: Public 00223 // Description: Returns the number of children of the node. 00224 //////////////////////////////////////////////////////////////////// 00225 INLINE int PandaNode::ChildrenCopy:: 00226 get_num_children() const { 00227 return _list.size(); 00228 } 00229 00230 //////////////////////////////////////////////////////////////////// 00231 // Function: PandaNode::ChildrenCopy::get_child 00232 // Access: Public 00233 // Description: Returns the nth child of the node. 00234 //////////////////////////////////////////////////////////////////// 00235 INLINE PandaNode *PandaNode::ChildrenCopy:: 00236 get_child(int n) const { 00237 nassertr(n >= 0 && n < (int)_list.size(), NULL); 00238 return _list[n]; 00239 } 00240 00241 //////////////////////////////////////////////////////////////////// 00242 // Function: PandaNode::get_num_parents 00243 // Access: Published 00244 // Description: Returns the number of parent nodes this node has. If 00245 // this number is greater than 1, the node has been 00246 // multiply instanced. The order of the parent nodes is 00247 // not meaningful and is not related to the order in 00248 // which the node was instanced to them. 00249 //////////////////////////////////////////////////////////////////// 00250 INLINE int PandaNode:: 00251 get_num_parents() const { 00252 CDReader cdata(_cycler); 00253 return cdata->_up.size(); 00254 } 00255 00256 //////////////////////////////////////////////////////////////////// 00257 // Function: PandaNode::get_parent 00258 // Access: Published 00259 // Description: Returns the nth parent node of this node. See 00260 // get_num_parents(). 00261 //////////////////////////////////////////////////////////////////// 00262 INLINE PandaNode *PandaNode:: 00263 get_parent(int n) const { 00264 CDReader cdata(_cycler); 00265 nassertr(n >= 0 && n < (int)cdata->_up.size(), NULL); 00266 return cdata->_up[n].get_parent(); 00267 } 00268 00269 //////////////////////////////////////////////////////////////////// 00270 // Function: PandaNode::find_parent 00271 // Access: Published 00272 // Description: Returns the index of the indicated parent node, if it 00273 // is a parent, or -1 if it is not. 00274 //////////////////////////////////////////////////////////////////// 00275 INLINE int PandaNode:: 00276 find_parent(PandaNode *node) const { 00277 CDReader cdata(_cycler); 00278 Up::const_iterator ui = cdata->_up.find(UpConnection(node)); 00279 if (ui == cdata->_up.end()) { 00280 return -1; 00281 } 00282 return ui - cdata->_up.begin(); 00283 } 00284 00285 //////////////////////////////////////////////////////////////////// 00286 // Function: PandaNode::get_num_children 00287 // Access: Published 00288 // Description: Returns the number of child nodes this node has. The 00289 // order of the child nodes *is* meaningful and is based 00290 // on the sort number that was passed to add_child(), 00291 // and also on the order in which the nodes were added. 00292 //////////////////////////////////////////////////////////////////// 00293 INLINE int PandaNode:: 00294 get_num_children() const { 00295 CDReader cdata(_cycler); 00296 return cdata->_down.size(); 00297 } 00298 00299 //////////////////////////////////////////////////////////////////// 00300 // Function: PandaNode::get_child 00301 // Access: Published 00302 // Description: Returns the nth child node of this node. See 00303 // get_num_children(). 00304 //////////////////////////////////////////////////////////////////// 00305 INLINE PandaNode *PandaNode:: 00306 get_child(int n) const { 00307 CDReader cdata(_cycler); 00308 nassertr(n >= 0 && n < (int)cdata->_down.size(), NULL); 00309 return cdata->_down[n].get_child(); 00310 } 00311 00312 //////////////////////////////////////////////////////////////////// 00313 // Function: PandaNode::get_child_sort 00314 // Access: Published 00315 // Description: Returns the sort index of the nth child node of this 00316 // node (that is, the number that was passed to 00317 // add_child()). See get_num_children(). 00318 //////////////////////////////////////////////////////////////////// 00319 INLINE int PandaNode:: 00320 get_child_sort(int n) const { 00321 CDReader cdata(_cycler); 00322 nassertr(n >= 0 && n < (int)cdata->_down.size(), -1); 00323 return cdata->_down[n].get_sort(); 00324 } 00325 00326 //////////////////////////////////////////////////////////////////// 00327 // Function: PandaNode::stash_child 00328 // Access: Published 00329 // Description: Stashes the indicated child node. This removes the 00330 // child from the list of active children and puts it on 00331 // a special list of stashed children. This child node 00332 // no longer contributes to the bounding volume of the 00333 // PandaNode, and is not visited in normal traversals. 00334 // It is invisible and uncollidable. The child may 00335 // later be restored by calling unstash_child(). 00336 // 00337 // This function returns true if the child node was 00338 // successfully stashed, or false if it was not a child 00339 // of the node in the first place (e.g. it was 00340 // previously stashed). 00341 //////////////////////////////////////////////////////////////////// 00342 INLINE bool PandaNode:: 00343 stash_child(PandaNode *child_node) { 00344 int child_index = find_child(child_node); 00345 if (child_index < 0) { 00346 return false; 00347 } 00348 stash_child(child_index); 00349 return true; 00350 } 00351 00352 //////////////////////////////////////////////////////////////////// 00353 // Function: PandaNode::unstash_child 00354 // Access: Published 00355 // Description: Returns the indicated stashed node to normal child 00356 // status. This removes the child from the list of 00357 // stashed children and puts it on the normal list of 00358 // active children. This child node once again 00359 // contributes to the bounding volume of the PandaNode, 00360 // and will be visited in normal traversals. It is 00361 // visible and collidable. 00362 // 00363 // This function returns true if the child node was 00364 // successfully stashed, or false if it was not a child 00365 // of the node in the first place (e.g. it was 00366 // previously stashed). 00367 //////////////////////////////////////////////////////////////////// 00368 INLINE bool PandaNode:: 00369 unstash_child(PandaNode *child_node) { 00370 int stashed_index = find_stashed(child_node); 00371 if (stashed_index < 0) { 00372 return false; 00373 } 00374 unstash_child(stashed_index); 00375 return true; 00376 } 00377 00378 //////////////////////////////////////////////////////////////////// 00379 // Function: PandaNode::get_num_stashed 00380 // Access: Published 00381 // Description: Returns the number of stashed nodes this node has. 00382 // These are former children of the node that have been 00383 // moved to the special stashed list via stash_child(). 00384 //////////////////////////////////////////////////////////////////// 00385 INLINE int PandaNode:: 00386 get_num_stashed() const { 00387 CDReader cdata(_cycler); 00388 return cdata->_stashed.size(); 00389 } 00390 00391 //////////////////////////////////////////////////////////////////// 00392 // Function: PandaNode::get_stashed 00393 // Access: Published 00394 // Description: Returns the nth stashed node of this node. See 00395 // get_num_stashed(). 00396 //////////////////////////////////////////////////////////////////// 00397 INLINE PandaNode *PandaNode:: 00398 get_stashed(int n) const { 00399 CDReader cdata(_cycler); 00400 nassertr(n >= 0 && n < (int)cdata->_stashed.size(), NULL); 00401 return cdata->_stashed[n].get_child(); 00402 } 00403 00404 //////////////////////////////////////////////////////////////////// 00405 // Function: PandaNode::get_stashed_sort 00406 // Access: Published 00407 // Description: Returns the sort index of the nth stashed node of this 00408 // node (that is, the number that was passed to 00409 // add_child()). See get_num_stashed(). 00410 //////////////////////////////////////////////////////////////////// 00411 INLINE int PandaNode:: 00412 get_stashed_sort(int n) const { 00413 CDReader cdata(_cycler); 00414 nassertr(n >= 0 && n < (int)cdata->_stashed.size(), -1); 00415 return cdata->_stashed[n].get_sort(); 00416 } 00417 00418 00419 //////////////////////////////////////////////////////////////////// 00420 // Function: PandaNode::set_attrib 00421 // Access: Published 00422 // Description: Adds the indicated render attribute to the scene 00423 // graph on this node. This attribute will now apply to 00424 // this node and everything below. If there was already 00425 // an attribute of the same type, it is replaced. 00426 //////////////////////////////////////////////////////////////////// 00427 INLINE void PandaNode:: 00428 set_attrib(const RenderAttrib *attrib, int override) { 00429 CDWriter cdata(_cycler); 00430 cdata->_state = cdata->_state->add_attrib(attrib, override); 00431 } 00432 00433 //////////////////////////////////////////////////////////////////// 00434 // Function: PandaNode::get_attrib 00435 // Access: Published 00436 // Description: Returns the render attribute of the indicated type, 00437 // if it is defined on the node, or NULL if it is not. 00438 // This checks only what is set on this particular node 00439 // level, and has nothing to do with what render 00440 // attributes may be inherited from parent nodes. 00441 //////////////////////////////////////////////////////////////////// 00442 INLINE const RenderAttrib *PandaNode:: 00443 get_attrib(TypeHandle type) const { 00444 CDReader cdata(_cycler); 00445 int index = cdata->_state->find_attrib(type); 00446 if (index >= 0) { 00447 return cdata->_state->get_attrib(index); 00448 } 00449 return NULL; 00450 } 00451 00452 //////////////////////////////////////////////////////////////////// 00453 // Function: PandaNode::has_attrib 00454 // Access: Published 00455 // Description: Returns true if there is a render attribute of the 00456 // indicated type defined on this node, or false if 00457 // there is not. 00458 //////////////////////////////////////////////////////////////////// 00459 INLINE bool PandaNode:: 00460 has_attrib(TypeHandle type) const { 00461 CDReader cdata(_cycler); 00462 int index = cdata->_state->find_attrib(type); 00463 return (index >= 0); 00464 } 00465 00466 //////////////////////////////////////////////////////////////////// 00467 // Function: PandaNode::clear_attrib 00468 // Access: Published 00469 // Description: Removes the render attribute of the given type from 00470 // this node. This node, and the subgraph below, will 00471 // now inherit the indicated render attribute from the 00472 // nodes above this one. 00473 //////////////////////////////////////////////////////////////////// 00474 INLINE void PandaNode:: 00475 clear_attrib(TypeHandle type) { 00476 CDWriter cdata(_cycler); 00477 cdata->_state = cdata->_state->remove_attrib(type); 00478 } 00479 00480 //////////////////////////////////////////////////////////////////// 00481 // Function: PandaNode::set_effect 00482 // Access: Published 00483 // Description: Adds the indicated render effect to the scene 00484 // graph on this node. If there was already an effect 00485 // of the same type, it is replaced. 00486 //////////////////////////////////////////////////////////////////// 00487 INLINE void PandaNode:: 00488 set_effect(const RenderEffect *effect) { 00489 CDWriter cdata(_cycler); 00490 cdata->_effects = cdata->_effects->add_effect(effect); 00491 } 00492 00493 //////////////////////////////////////////////////////////////////// 00494 // Function: PandaNode::get_effect 00495 // Access: Published 00496 // Description: Returns the render effect of the indicated type, 00497 // if it is defined on the node, or NULL if it is not. 00498 //////////////////////////////////////////////////////////////////// 00499 INLINE const RenderEffect *PandaNode:: 00500 get_effect(TypeHandle type) const { 00501 CDReader cdata(_cycler); 00502 int index = cdata->_effects->find_effect(type); 00503 if (index >= 0) { 00504 return cdata->_effects->get_effect(index); 00505 } 00506 return NULL; 00507 } 00508 00509 //////////////////////////////////////////////////////////////////// 00510 // Function: PandaNode::has_effect 00511 // Access: Published 00512 // Description: Returns true if there is a render effect of the 00513 // indicated type defined on this node, or false if 00514 // there is not. 00515 //////////////////////////////////////////////////////////////////// 00516 INLINE bool PandaNode:: 00517 has_effect(TypeHandle type) const { 00518 CDReader cdata(_cycler); 00519 int index = cdata->_effects->find_effect(type); 00520 return (index >= 0); 00521 } 00522 00523 //////////////////////////////////////////////////////////////////// 00524 // Function: PandaNode::clear_effect 00525 // Access: Published 00526 // Description: Removes the render effect of the given type from 00527 // this node. 00528 //////////////////////////////////////////////////////////////////// 00529 INLINE void PandaNode:: 00530 clear_effect(TypeHandle type) { 00531 CDWriter cdata(_cycler); 00532 cdata->_effects = cdata->_effects->remove_effect(type); 00533 } 00534 00535 //////////////////////////////////////////////////////////////////// 00536 // Function: PandaNode::set_state 00537 // Access: Published 00538 // Description: Sets the complete RenderState that will be applied to 00539 // all nodes at this level and below. (The actual state 00540 // that will be applied to lower nodes is based on the 00541 // composition of RenderStates from above this node as 00542 // well). This completely replaces whatever has been 00543 // set on this node via repeated calls to set_attrib(). 00544 //////////////////////////////////////////////////////////////////// 00545 INLINE void PandaNode:: 00546 set_state(const RenderState *state) { 00547 CDWriter cdata(_cycler); 00548 cdata->_state = state; 00549 } 00550 00551 //////////////////////////////////////////////////////////////////// 00552 // Function: PandaNode::get_state 00553 // Access: Published 00554 // Description: Returns the complete RenderState that will be applied 00555 // to all nodes at this level and below, as set on this 00556 // node. This returns only the RenderState set on this 00557 // particular node, and has nothing to do with state 00558 // that might be inherited from above. 00559 //////////////////////////////////////////////////////////////////// 00560 INLINE const RenderState *PandaNode:: 00561 get_state() const { 00562 CDReader cdata(_cycler); 00563 return cdata->_state; 00564 } 00565 00566 //////////////////////////////////////////////////////////////////// 00567 // Function: PandaNode::clear_state 00568 // Access: Published 00569 // Description: Resets this node to leave the render state alone. 00570 // Nodes at this level and below will once again inherit 00571 // their render state unchanged from the nodes above 00572 // this level. 00573 //////////////////////////////////////////////////////////////////// 00574 INLINE void PandaNode:: 00575 clear_state() { 00576 CDWriter cdata(_cycler); 00577 cdata->_state = RenderState::make_empty(); 00578 } 00579 00580 //////////////////////////////////////////////////////////////////// 00581 // Function: PandaNode::set_effects 00582 // Access: Published 00583 // Description: Sets the complete RenderEffects that will be applied 00584 // this node. This completely replaces whatever has 00585 // been set on this node via repeated calls to 00586 // set_attrib(). 00587 //////////////////////////////////////////////////////////////////// 00588 INLINE void PandaNode:: 00589 set_effects(const RenderEffects *effects) { 00590 CDWriter cdata(_cycler); 00591 cdata->_effects = effects; 00592 } 00593 00594 //////////////////////////////////////////////////////////////////// 00595 // Function: PandaNode::get_effects 00596 // Access: Published 00597 // Description: Returns the complete RenderEffects that will be 00598 // applied to this node. 00599 //////////////////////////////////////////////////////////////////// 00600 INLINE const RenderEffects *PandaNode:: 00601 get_effects() const { 00602 CDReader cdata(_cycler); 00603 return cdata->_effects; 00604 } 00605 00606 //////////////////////////////////////////////////////////////////// 00607 // Function: PandaNode::clear_effects 00608 // Access: Published 00609 // Description: Resets this node to have no render effects. 00610 //////////////////////////////////////////////////////////////////// 00611 INLINE void PandaNode:: 00612 clear_effects() { 00613 CDWriter cdata(_cycler); 00614 cdata->_effects = RenderEffects::make_empty(); 00615 } 00616 00617 //////////////////////////////////////////////////////////////////// 00618 // Function: PandaNode::set_transform 00619 // Access: Published 00620 // Description: Sets the transform that will be applied to this node 00621 // and below. This defines a new coordinate space at 00622 // this point in the scene graph and below. 00623 //////////////////////////////////////////////////////////////////// 00624 INLINE void PandaNode:: 00625 set_transform(const TransformState *transform) { 00626 CDWriter cdata(_cycler); 00627 cdata->_transform = transform; 00628 mark_bound_stale(); 00629 transform_changed(); 00630 } 00631 00632 //////////////////////////////////////////////////////////////////// 00633 // Function: PandaNode::get_transform 00634 // Access: Published 00635 // Description: Returns the transform that has been set on this 00636 // particular node. This is not the net transform from 00637 // the root, but simply the transform on this particular 00638 // node. 00639 //////////////////////////////////////////////////////////////////// 00640 INLINE const TransformState *PandaNode:: 00641 get_transform() const { 00642 CDReader cdata(_cycler); 00643 return cdata->_transform; 00644 } 00645 00646 //////////////////////////////////////////////////////////////////// 00647 // Function: PandaNode::clear_transform 00648 // Access: Published 00649 // Description: Resets the transform on this node to the identity 00650 // transform. 00651 //////////////////////////////////////////////////////////////////// 00652 INLINE void PandaNode:: 00653 clear_transform() { 00654 CDWriter cdata(_cycler); 00655 cdata->_transform = TransformState::make_identity(); 00656 mark_bound_stale(); 00657 transform_changed(); 00658 } 00659 00660 //////////////////////////////////////////////////////////////////// 00661 // Function: PandaNode::ls 00662 // Access: Published 00663 // Description: Lists all the nodes at and below the current path 00664 // hierarchically. 00665 //////////////////////////////////////////////////////////////////// 00666 INLINE void PandaNode:: 00667 ls(ostream &out, int indent_level) const { 00668 r_list_descendants(out, indent_level); 00669 } 00670 00671 //////////////////////////////////////////////////////////////////// 00672 // Function: PandaNode::set_draw_mask 00673 // Access: Published 00674 // Description: Sets the hide/show bits of this particular node. 00675 // 00676 // During the cull traversal, a node is not visited if 00677 // none of its draw mask bits intersect with the 00678 // camera's draw mask bits. These masks can be used to 00679 // selectively hide and show different parts of the 00680 // scene graph from different cameras that are otherwise 00681 // viewing the same scene. See 00682 // Camera::set_camera_mask(). 00683 //////////////////////////////////////////////////////////////////// 00684 INLINE void PandaNode:: 00685 set_draw_mask(DrawMask mask) { 00686 CDWriter cdata(_cycler); 00687 cdata->_draw_mask = mask; 00688 } 00689 00690 //////////////////////////////////////////////////////////////////// 00691 // Function: PandaNode::get_draw_mask 00692 // Access: Published 00693 // Description: Returns the hide/show bits of this particular node. 00694 // See set_draw_mask(). 00695 //////////////////////////////////////////////////////////////////// 00696 INLINE DrawMask PandaNode:: 00697 get_draw_mask() const { 00698 CDReader cdata(_cycler); 00699 return cdata->_draw_mask; 00700 } 00701 00702 //////////////////////////////////////////////////////////////////// 00703 // Function: PandaNode::get_net_collide_mask 00704 // Access: Published 00705 // Description: Returns the union of all into_collide_mask() values 00706 // set at CollisionNodes at this level and below. 00707 //////////////////////////////////////////////////////////////////// 00708 INLINE CollideMask PandaNode:: 00709 get_net_collide_mask() const { 00710 // Call get_bound() first to ensure the mask is recomputed. 00711 BoundedObject::get_bound(); 00712 CDReader cdata(_cycler); 00713 return cdata->_net_collide_mask; 00714 } 00715 00716 //////////////////////////////////////////////////////////////////// 00717 // Function: PandaNode::set_bound 00718 // Access: Published 00719 // Description: Sets the type of the external bounding volume that is 00720 // placed around this node and all of its children. 00721 //////////////////////////////////////////////////////////////////// 00722 INLINE void PandaNode:: 00723 set_bound(BoundingVolumeType type) { 00724 CDWriter cdata(_cycler); 00725 cdata->_fixed_internal_bound = false; 00726 BoundedObject::set_bound(type); 00727 } 00728 00729 //////////////////////////////////////////////////////////////////// 00730 // Function: PandaNode::set_bound 00731 // Access: Published 00732 // Description: Resets the internal bounding volume so that it is the 00733 // indicated volume. The external bounding volume as 00734 // returned by get_bound() (which includes all of the 00735 // node's children) will be adjusted to include this 00736 // internal volume. 00737 //////////////////////////////////////////////////////////////////// 00738 INLINE void PandaNode:: 00739 set_bound(const BoundingVolume &volume) { 00740 CDWriter cdata(_cycler); 00741 cdata->_fixed_internal_bound = true; 00742 _internal_bound.set_bound(volume); 00743 changed_internal_bound(); 00744 } 00745 00746 //////////////////////////////////////////////////////////////////// 00747 // Function: PandaNode::get_bound 00748 // Access: Published 00749 // Description: Returns the node's external bounding volume. This is 00750 // the bounding volume around the node and all of its 00751 // children. 00752 //////////////////////////////////////////////////////////////////// 00753 INLINE const BoundingVolume &PandaNode:: 00754 get_bound() const { 00755 return BoundedObject::get_bound(); 00756 } 00757 00758 //////////////////////////////////////////////////////////////////// 00759 // Function: PandaNode::get_internal_bound 00760 // Access: Published 00761 // Description: Returns the node's internal bounding volume. This is 00762 // the bounding volume around the node alone, without 00763 // including children. 00764 //////////////////////////////////////////////////////////////////// 00765 INLINE const BoundingVolume &PandaNode:: 00766 get_internal_bound() const { 00767 CDReader cdata(_cycler); 00768 if (!cdata->_fixed_internal_bound && 00769 (is_bound_stale() || _internal_bound.is_bound_stale())) { 00770 ((PandaNode *)this)->recompute_internal_bound(); 00771 } 00772 return _internal_bound.get_bound(); 00773 } 00774 00775 //////////////////////////////////////////////////////////////////// 00776 // Function: PandaNode::changed_internal_bound 00777 // Access: Protected 00778 // Description: Should be called whenever you adjust the 00779 // _internal_bound member, to force the external 00780 // bounding volume to be recomputed. 00781 //////////////////////////////////////////////////////////////////// 00782 INLINE void PandaNode:: 00783 changed_internal_bound() { 00784 BoundedObject::mark_bound_stale(); 00785 } 00786 00787 //////////////////////////////////////////////////////////////////// 00788 // Function: PandaNode::add_net_collide_mask 00789 // Access: Protected 00790 // Description: Adds the indicated bits into the net_collide_mask for 00791 // this node. This is normally called only by 00792 // CollisionNode::recompute_bound(). 00793 //////////////////////////////////////////////////////////////////// 00794 INLINE void PandaNode:: 00795 add_net_collide_mask(CollideMask mask) { 00796 CDWriter cdata(_cycler); 00797 cdata->_net_collide_mask |= mask; 00798 } 00799 00800 //////////////////////////////////////////////////////////////////// 00801 // Function: PandaNode::get_children 00802 // Access: Public 00803 // Description: Returns an object that can be used to walk through 00804 // the list of children of the node. When you intend to 00805 // visit multiple children, using this is slightly 00806 // faster than calling get_child() directly on the 00807 // PandaNode, since this object keeps the PipelineCycler 00808 // open the whole time. 00809 // 00810 // However, this object does not protect you from 00811 // self-modifying loops (e.g. adding or removing 00812 // children during traversal). 00813 //////////////////////////////////////////////////////////////////// 00814 INLINE PandaNode::Children PandaNode:: 00815 get_children() const { 00816 CDReader cdata(_cycler); 00817 return Children(cdata); 00818 } 00819 00820 //////////////////////////////////////////////////////////////////// 00821 // Function: PandaNode::get_children_copy 00822 // Access: Public 00823 // Description: Returns an object that can be used to walk through 00824 // the list of children of the node. Unlike 00825 // get_children(), this function actually returns an 00826 // object that protects you from self-modifying loops, 00827 // because it makes and returns a copy of the complete 00828 // children list. 00829 //////////////////////////////////////////////////////////////////// 00830 INLINE PandaNode::ChildrenCopy PandaNode:: 00831 get_children_copy() const { 00832 CDReader cdata(_cycler); 00833 return ChildrenCopy(cdata); 00834 } 00835