Panda3D
 All Classes Functions Variables Enumerations
characterJoint.cxx
1 // Filename: characterJoint.cxx
2 // Created by: drose (23Feb99)
3 //
4 ////////////////////////////////////////////////////////////////////
5 //
6 // PANDA 3D SOFTWARE
7 // Copyright (c) Carnegie Mellon University. All rights reserved.
8 //
9 // All use of this software is subject to the terms of the revised BSD
10 // license. You should have received a copy of this license along
11 // with this source code in a file named "LICENSE."
12 //
13 ////////////////////////////////////////////////////////////////////
14 
15 #include "characterJoint.h"
16 #include "config_char.h"
17 #include "jointVertexTransform.h"
18 #include "characterJointEffect.h"
19 #include "datagram.h"
20 #include "datagramIterator.h"
21 #include "bamReader.h"
22 #include "bamWriter.h"
23 
24 TypeHandle CharacterJoint::_type_handle;
25 
26 ////////////////////////////////////////////////////////////////////
27 // Function: CharacterJoint::Default Constructor
28 // Access: Protected
29 // Description: For internal use only.
30 ////////////////////////////////////////////////////////////////////
31 CharacterJoint::
32 CharacterJoint() :
33  _character(NULL)
34 {
35 }
36 
37 ////////////////////////////////////////////////////////////////////
38 // Function: CharacterJoint::Copy Constructor
39 // Access: Protected
40 // Description:
41 ////////////////////////////////////////////////////////////////////
42 CharacterJoint::
43 CharacterJoint(const CharacterJoint &copy) :
44  MovingPartMatrix(copy),
45  _character(NULL),
46  _net_transform(copy._net_transform),
47  _initial_net_transform_inverse(copy._initial_net_transform_inverse)
48 {
49  // We don't copy the sets of transform nodes.
50 }
51 
52 ////////////////////////////////////////////////////////////////////
53 // Function: CharacterJoint::Constructor
54 // Access: Public
55 // Description:
56 ////////////////////////////////////////////////////////////////////
57 CharacterJoint::
58 CharacterJoint(Character *character,
59  PartBundle *root, PartGroup *parent, const string &name,
60  const LMatrix4 &default_value) :
61  MovingPartMatrix(parent, name, default_value),
62  _character(character)
63 {
64  Thread *current_thread = Thread::get_current_thread();
65 
66  // Now that we've constructed and we're in the tree, let's call
67  // update_internals() to get our _net_transform set properly.
68  update_internals(root, parent, true, false, current_thread);
69 
70  // And then compute its inverse. This is needed for
71  // ComputedVertices, during animation.
72  _initial_net_transform_inverse = invert(_net_transform);
73 }
74 
75 ////////////////////////////////////////////////////////////////////
76 // Function: CharacterJoint::Destructor
77 // Access: Public, Virtual
78 // Description:
79 ////////////////////////////////////////////////////////////////////
80 CharacterJoint::
81 ~CharacterJoint() {
82  nassertv(_vertex_transforms.empty());
83  nassertv(_character == (Character *)NULL);
84 }
85 
86 ////////////////////////////////////////////////////////////////////
87 // Function: CharacterJoint::is_character_joint
88 // Access: Public, Virtual
89 // Description: Returns true if this part is a CharacterJoint, false
90 // otherwise. This is a tiny optimization over
91 // is_of_type(CharacterType::get_class_type()).
92 ////////////////////////////////////////////////////////////////////
95  return true;
96 }
97 
98 ////////////////////////////////////////////////////////////////////
99 // Function: CharacterJoint::make_copy
100 // Access: Public, Virtual
101 // Description: Allocates and returns a new copy of the node.
102 // Children are not copied, but see copy_subgraph().
103 ////////////////////////////////////////////////////////////////////
105 make_copy() const {
106  return new CharacterJoint(*this);
107 }
108 
109 ////////////////////////////////////////////////////////////////////
110 // Function: CharacterJoint::update_internals
111 // Access: Public, Virtual
112 // Description: This is called by do_update() whenever the part or
113 // some ancestor has changed values. It is a hook for
114 // derived classes to update whatever cache they may
115 // have that depends on these.
116 //
117 // The return value is true if the part has changed as a
118 // result of the update, or false otherwise.
119 //
120 // In the case of a CharacterJoint, of course, it means
121 // to recompute the joint angles and associated
122 // transforms for this particular joint.
123 ////////////////////////////////////////////////////////////////////
124 bool CharacterJoint::
125 update_internals(PartBundle *root, PartGroup *parent, bool self_changed,
126  bool parent_changed, Thread *current_thread) {
127  nassertr(parent != (PartGroup *)NULL, false);
128 
129  bool net_changed = false;
130  if (parent->is_character_joint()) {
131  // The joint is not a toplevel joint; its parent therefore affects
132  // its net transform.
133  if (parent_changed || self_changed) {
134  CharacterJoint *parent_joint = DCAST(CharacterJoint, parent);
135 
136  _net_transform = _value * parent_joint->_net_transform;
137  net_changed = true;
138  }
139 
140  } else {
141  // The joint is a toplevel joint, so therefore it gets its root
142  // transform from the bundle.
143  if (self_changed) {
144  _net_transform = _value * root->get_root_xform();
145  net_changed = true;
146  }
147  }
148 
149  if (net_changed) {
150  if (!_net_transform_nodes.empty()) {
151  CPT(TransformState) t = TransformState::make_mat(_net_transform);
152 
153  NodeList::iterator ai;
154  for (ai = _net_transform_nodes.begin();
155  ai != _net_transform_nodes.end();
156  ++ai) {
157  PandaNode *node = *ai;
158  node->set_transform(t, current_thread);
159  }
160  }
161 
162  // Also tell our related JointVertexTransforms that they now need
163  // to recompute themselves.
164  VertexTransforms::iterator vti;
165  for (vti = _vertex_transforms.begin(); vti != _vertex_transforms.end(); ++vti) {
166  (*vti)->_matrix_stale = true;
167  (*vti)->mark_modified(current_thread);
168  }
169  }
170 
171  if (self_changed && !_local_transform_nodes.empty()) {
172  CPT(TransformState) t = TransformState::make_mat(_value);
173 
174  NodeList::iterator ai;
175  for (ai = _local_transform_nodes.begin();
176  ai != _local_transform_nodes.end();
177  ++ai) {
178  PandaNode *node = *ai;
179  node->set_transform(t, current_thread);
180  }
181  }
182 
183  return self_changed || net_changed;
184 }
185 
186 ////////////////////////////////////////////////////////////////////
187 // Function: CharacterJoint::do_xform
188 // Access: Public, Virtual
189 // Description: Called by PartBundle::xform(), this indicates the
190 // indicated transform is being applied to the root
191 // joint.
192 ////////////////////////////////////////////////////////////////////
193 void CharacterJoint::
194 do_xform(const LMatrix4 &mat, const LMatrix4 &inv_mat) {
195  _initial_net_transform_inverse = inv_mat * _initial_net_transform_inverse;
196 
197  MovingPartMatrix::do_xform(mat, inv_mat);
198 }
199 
200 
201 
202 ////////////////////////////////////////////////////////////////////
203 // Function: CharacterJoint::add_net_transform
204 // Access: Published
205 // Description: Adds the indicated node to the list of nodes that will
206 // be updated each frame with the joint's net transform
207 // from the root. Returns true if the node is
208 // successfully added, false if it had already been
209 // added.
210 //
211 // A CharacterJointEffect for this joint's Character
212 // will automatically be added to the specified node.
213 ////////////////////////////////////////////////////////////////////
214 bool CharacterJoint::
216  if (_character != (Character *)NULL) {
217  node->set_effect(CharacterJointEffect::make(_character));
218  }
219  CPT(TransformState) t = TransformState::make_mat(_net_transform);
221  return _net_transform_nodes.insert(node).second;
222 }
223 
224 ////////////////////////////////////////////////////////////////////
225 // Function: CharacterJoint::remove_net_transform
226 // Access: Published
227 // Description: Removes the indicated node from the list of nodes that
228 // will be updated each frame with the joint's net
229 // transform from the root. Returns true if the node is
230 // successfully removed, false if it was not on the
231 // list.
232 //
233 // If the node has a CharacterJointEffect that matches
234 // this joint's Character, it will be cleared.
235 ////////////////////////////////////////////////////////////////////
236 bool CharacterJoint::
238  CPT(RenderEffect) effect = node->get_effect(CharacterJointEffect::get_class_type());
239  if (effect != (RenderEffect *)NULL &&
240  DCAST(CharacterJointEffect, effect)->get_character() == _character) {
241  node->clear_effect(CharacterJointEffect::get_class_type());
242  }
243 
244  return (_net_transform_nodes.erase(node) > 0);
245 }
246 
247 ////////////////////////////////////////////////////////////////////
248 // Function: CharacterJoint::has_net_transform
249 // Access: Published
250 // Description: Returns true if the node is on the list of nodes that
251 // will be updated each frame with the joint's net
252 // transform from the root, false otherwise.
253 ////////////////////////////////////////////////////////////////////
254 bool CharacterJoint::
256  return (_net_transform_nodes.count(node) > 0);
257 }
258 
259 ////////////////////////////////////////////////////////////////////
260 // Function: CharacterJoint::clear_net_transforms
261 // Access: Published
262 // Description: Removes all nodes from the list of nodes that will be
263 // updated each frame with the joint's net transform
264 // from the root.
265 ////////////////////////////////////////////////////////////////////
266 void CharacterJoint::
268  NodeList::iterator ai;
269  for (ai = _net_transform_nodes.begin();
270  ai != _net_transform_nodes.end();
271  ++ai) {
272  PandaNode *node = *ai;
273 
274  CPT(RenderEffect) effect = node->get_effect(CharacterJointEffect::get_class_type());
275  if (effect != (RenderEffect *)NULL &&
276  DCAST(CharacterJointEffect, effect)->get_character() == _character) {
277  node->clear_effect(CharacterJointEffect::get_class_type());
278  }
279  }
280 
281  _net_transform_nodes.clear();
282 }
283 
284 ////////////////////////////////////////////////////////////////////
285 // Function: CharacterJoint::get_net_transforms
286 // Access: Published
287 // Description: Returns a list of the net transforms set for this
288 // node. Note that this returns a list of NodePaths,
289 // even though the net transforms are actually a list of
290 // PandaNodes.
291 ////////////////////////////////////////////////////////////////////
294  NodePathCollection npc;
295 
296  NodeList::iterator ai;
297  for (ai = _net_transform_nodes.begin();
298  ai != _net_transform_nodes.end();
299  ++ai) {
300  PandaNode *node = *ai;
301  npc.add_path(NodePath::any_path(node));
302  }
303 
304  return npc;
305 }
306 
307 ////////////////////////////////////////////////////////////////////
308 // Function: CharacterJoint::add_local_transform
309 // Access: Published
310 // Description: Adds the indicated node to the list of nodes that will
311 // be updated each frame with the joint's local
312 // transform from its parent. Returns true if the node
313 // is successfully added, false if it had already been
314 // added.
315 //
316 // The Character pointer should be the Character object
317 // that owns this joint; this will be used to create a
318 // CharacterJointEffect for this node. If it is NULL,
319 // no such effect will be created.
320 //
321 // A CharacterJointEffect for this joint's Character
322 // will automatically be added to the specified node.
323 ////////////////////////////////////////////////////////////////////
324 bool CharacterJoint::
326  if (_character != (Character *)NULL) {
327  node->set_effect(CharacterJointEffect::make(_character));
328  }
329  CPT(TransformState) t = TransformState::make_mat(_value);
331  return _local_transform_nodes.insert(node).second;
332 }
333 
334 ////////////////////////////////////////////////////////////////////
335 // Function: CharacterJoint::remove_local_transform
336 // Access: Published
337 // Description: Removes the indicated node from the list of nodes that
338 // will be updated each frame with the joint's local
339 // transform from its parent. Returns true if the node
340 // is successfully removed, false if it was not on the
341 // list.
342 //
343 // If the node has a CharacterJointEffect that matches
344 // this joint's Character, it will be cleared.
345 ////////////////////////////////////////////////////////////////////
346 bool CharacterJoint::
348  CPT(RenderEffect) effect = node->get_effect(CharacterJointEffect::get_class_type());
349  if (effect != (RenderEffect *)NULL &&
350  DCAST(CharacterJointEffect, effect)->get_character() == _character) {
351  node->clear_effect(CharacterJointEffect::get_class_type());
352  }
353 
354  return (_local_transform_nodes.erase(node) > 0);
355 }
356 
357 ////////////////////////////////////////////////////////////////////
358 // Function: CharacterJoint::has_local_transform
359 // Access: Published
360 // Description: Returns true if the node is on the list of nodes that
361 // will be updated each frame with the joint's local
362 // transform from its parent, false otherwise.
363 ////////////////////////////////////////////////////////////////////
364 bool CharacterJoint::
366  return (_local_transform_nodes.count(node) > 0);
367 }
368 
369 ////////////////////////////////////////////////////////////////////
370 // Function: CharacterJoint::clear_local_transforms
371 // Access: Published
372 // Description: Removes all nodes from the list of nodes that will be
373 // updated each frame with the joint's local transform
374 // from its parent.
375 ////////////////////////////////////////////////////////////////////
376 void CharacterJoint::
378  NodeList::iterator ai;
379  for (ai = _local_transform_nodes.begin();
380  ai != _local_transform_nodes.end();
381  ++ai) {
382  PandaNode *node = *ai;
383 
384  CPT(RenderEffect) effect = node->get_effect(CharacterJointEffect::get_class_type());
385  if (effect != (RenderEffect *)NULL &&
386  DCAST(CharacterJointEffect, effect)->get_character() == _character) {
387  node->clear_effect(CharacterJointEffect::get_class_type());
388  }
389  }
390 
391  _local_transform_nodes.clear();
392 }
393 
394 ////////////////////////////////////////////////////////////////////
395 // Function: CharacterJoint::get_local_transforms
396 // Access: Published
397 // Description: Returns a list of the local transforms set for this
398 // node. Note that this returns a list of NodePaths,
399 // even though the local transforms are actually a list of
400 // PandaNodes.
401 ////////////////////////////////////////////////////////////////////
404  NodePathCollection npc;
405 
406  NodeList::iterator ai;
407  for (ai = _local_transform_nodes.begin();
408  ai != _local_transform_nodes.end();
409  ++ai) {
410  PandaNode *node = *ai;
411  npc.add_path(NodePath::any_path(node));
412  }
413 
414  return npc;
415 }
416 
417 ////////////////////////////////////////////////////////////////////
418 // Function: CharacterJoint::get_transform
419 // Access: Published
420 // Description: Copies the joint's current transform into the
421 // indicated matrix.
422 ////////////////////////////////////////////////////////////////////
423 void CharacterJoint::
424 get_transform(LMatrix4 &transform) const {
425  transform = _value;
426 }
427 
428 CPT(TransformState) CharacterJoint::
429 get_transform_state() const {
430  return TransformState::make_mat( _value );
431 }
432 
433 ////////////////////////////////////////////////////////////////////
434 // Function: CharacterJoint::get_net_transform
435 // Access: Published
436 // Description: Copies the joint's current net transform (composed
437 // from the root of the character joint hierarchy) into
438 // the indicated matrix.
439 ////////////////////////////////////////////////////////////////////
440 void CharacterJoint::
441 get_net_transform(LMatrix4 &transform) const {
442  transform = _net_transform;
443 }
444 
445 ////////////////////////////////////////////////////////////////////
446 // Function: CharacterJoint::get_character
447 // Access: Published
448 // Description: Returns the Character that owns this joint.
449 ////////////////////////////////////////////////////////////////////
451 get_character() const {
452  return _character;
453 }
454 
455 ////////////////////////////////////////////////////////////////////
456 // Function: CharacterJoint::set_character
457 // Access: Private
458 // Description: Changes the Character that owns this joint.
459 ////////////////////////////////////////////////////////////////////
460 void CharacterJoint::
461 set_character(Character *character) {
462  if (character != _character) {
463 
464  if (character != (Character *)NULL) {
465  // Change or set a _character pointer on each joint's exposed
466  // node.
467  NodeList::iterator ai;
468  for (ai = _net_transform_nodes.begin();
469  ai != _net_transform_nodes.end();
470  ++ai) {
471  PandaNode *node = *ai;
472  node->set_effect(CharacterJointEffect::make(character));
473  }
474  for (ai = _local_transform_nodes.begin();
475  ai != _local_transform_nodes.end();
476  ++ai) {
477  PandaNode *node = *ai;
478  node->set_effect(CharacterJointEffect::make(character));
479  }
480 
481  } else { // (character == (Character *)NULL)
482  // Clear the _character pointer on each joint's exposed node.
483  NodeList::iterator ai;
484  for (ai = _net_transform_nodes.begin();
485  ai != _net_transform_nodes.end();
486  ++ai) {
487  PandaNode *node = *ai;
488 
489  CPT(RenderEffect) effect = node->get_effect(CharacterJointEffect::get_class_type());
490  if (effect != (RenderEffect *)NULL &&
491  DCAST(CharacterJointEffect, effect)->get_character() == _character) {
492  node->clear_effect(CharacterJointEffect::get_class_type());
493  }
494  }
495  for (ai = _local_transform_nodes.begin();
496  ai != _local_transform_nodes.end();
497  ++ai) {
498  PandaNode *node = *ai;
499 
500  CPT(RenderEffect) effect = node->get_effect(CharacterJointEffect::get_class_type());
501  if (effect != (RenderEffect *)NULL &&
502  DCAST(CharacterJointEffect, effect)->get_character() == _character) {
503  node->clear_effect(CharacterJointEffect::get_class_type());
504  }
505  }
506  }
507  }
508 
509  _character = character;
510 }
511 
512 ////////////////////////////////////////////////////////////////////
513 // Function: CharacterJoint::write_datagram
514 // Access: Public
515 // Description: Function to write the important information in
516 // the particular object to a Datagram
517 ////////////////////////////////////////////////////////////////////
518 void CharacterJoint::
520  NodeList::iterator ni;
522 
523  manager->write_pointer(me, _character);
524 
525  me.add_uint16(_net_transform_nodes.size());
526  for (ni = _net_transform_nodes.begin();
527  ni != _net_transform_nodes.end();
528  ni++) {
529  manager->write_pointer(me, (*ni));
530  }
531 
532  me.add_uint16(_local_transform_nodes.size());
533  for (ni = _local_transform_nodes.begin();
534  ni != _local_transform_nodes.end();
535  ni++) {
536  manager->write_pointer(me, (*ni));
537  }
538 
539  _initial_net_transform_inverse.write_datagram(me);
540 }
541 
542 ////////////////////////////////////////////////////////////////////
543 // Function: CharacterJoint::fillin
544 // Access: Protected
545 // Description: Function that reads out of the datagram (or asks
546 // manager to read) all of the data that is needed to
547 // re-create this object and stores it in the appropiate
548 // place
549 ////////////////////////////////////////////////////////////////////
550 void CharacterJoint::
551 fillin(DatagramIterator &scan, BamReader *manager) {
552  int i;
553  MovingPartMatrix::fillin(scan, manager);
554 
555  if (manager->get_file_minor_ver() >= 4) {
556  manager->read_pointer(scan);
557  }
558 
559  _num_net_nodes = scan.get_uint16();
560  for(i = 0; i < _num_net_nodes; i++) {
561  manager->read_pointer(scan);
562  }
563 
564  _num_local_nodes = scan.get_uint16();
565  for(i = 0; i < _num_local_nodes; i++) {
566  manager->read_pointer(scan);
567  }
568 
569  _initial_net_transform_inverse.read_datagram(scan);
570 }
571 
572 ////////////////////////////////////////////////////////////////////
573 // Function: CharacterJoint::complete_pointers
574 // Access: Public
575 // Description: Takes in a vector of pointers to TypedWritable
576 // objects that correspond to all the requests for
577 // pointers that this object made to BamReader.
578 ////////////////////////////////////////////////////////////////////
581  int pi = MovingPartMatrix::complete_pointers(p_list, manager);
582 
583  if (manager->get_file_minor_ver() >= 4) {
584  _character = DCAST(Character, p_list[pi++]);
585  } else {
586  _character = NULL;
587  }
588 
589  int i;
590  for (i = 0; i < _num_net_nodes; i++) {
591  PandaNode *node = DCAST(PandaNode, p_list[pi++]);
592  _net_transform_nodes.insert(node);
593  }
594 
595  for (i = 0; i < _num_local_nodes; i++) {
596  PandaNode *node = DCAST(PandaNode, p_list[pi++]);
597  _local_transform_nodes.insert(node);
598  }
599 
600  return pi;
601 }
602 
603 ////////////////////////////////////////////////////////////////////
604 // Function: CharacterJoint::make_CharacterJoint
605 // Access: Protected
606 // Description: Factory method to generate a CharacterJoint object
607 ////////////////////////////////////////////////////////////////////
610  CharacterJoint *me = new CharacterJoint;
611  DatagramIterator scan;
612  BamReader *manager;
613 
614  parse_params(params, scan, manager);
615  me->fillin(scan, manager);
616  return me;
617 }
618 
619 ////////////////////////////////////////////////////////////////////
620 // Function: CharacterJoint::register_with_factory
621 // Access: Public, Static
622 // Description: Factory method to generate a CharacterJoint object
623 ////////////////////////////////////////////////////////////////////
624 void CharacterJoint::
627 }
628 
629 
A basic node of the scene graph or data graph.
Definition: pandaNode.h:72
void add_path(const NodePath &node_path)
Adds a new NodePath to the collection.
bool empty() const
Returns true if the ordered vector is empty, false otherwise.
This is the fundamental interface for extracting binary objects from a Bam file, as generated by a Ba...
Definition: bamReader.h:122
An animated character, with skeleton-morph animation and either soft-skinned or hard-skinned vertices...
Definition: character.h:41
void clear()
Removes all elements from the ordered vector.
virtual void write_datagram(BamWriter *manager, Datagram &me)
Function to write the important information in the particular object to a Datagram.
This effect will be added automatically to a node by CharacterJoint::add_net_transform() and Characte...
size_type_0 count(const key_type_0 &key) const
Returns the number of elements that sort equivalent to the key that are in the vector.
Base class for objects that can be written to and read from Bam files.
Definition: typedWritable.h:37
iterator_0 begin()
Returns the iterator that marks the first element in the ordered vector.
const LMatrix4 & get_root_xform() const
Returns the transform matrix which is implicitly applied at the root of the animated hierarchy...
Definition: partBundle.I:186
bool add_net_transform(PandaNode *node)
Adds the indicated node to the list of nodes that will be updated each frame with the joint&#39;s net tra...
This is the fundamental interface for writing binary objects to a Bam file, to be extracted later by ...
Definition: bamWriter.h:73
This is the base class for a number of special render effects that may be set on scene graph nodes to...
Definition: renderEffect.h:56
iterator_0 end()
Returns the iterator that marks the end of the ordered vector.
virtual void do_xform(const LMatrix4 &mat, const LMatrix4 &inv_mat)
Called by PartBundle::xform(), this indicates the indicated transform is being applied to the root jo...
Definition: partGroup.cxx:555
virtual void write_datagram(BamWriter *manager, Datagram &me)
Writes the contents of this object to the datagram for shipping out to a Bam file.
PN_uint16 get_uint16()
Extracts an unsigned 16-bit integer.
static Thread * get_current_thread()
Returns a pointer to the currently-executing Thread object.
Definition: thread.I:145
void clear_local_transforms()
Removes all nodes from the list of nodes that will be updated each frame with the joint&#39;s local trans...
static TypedWritable * make_CharacterJoint(const FactoryParams &params)
Factory method to generate a CharacterJoint object.
static NodePath any_path(PandaNode *node, Thread *current_thread=Thread::get_current_thread())
Returns a new NodePath that represents any arbitrary path from the root to the indicated node...
Definition: nodePath.I:77
bool add_local_transform(PandaNode *node)
Adds the indicated node to the list of nodes that will be updated each frame with the joint&#39;s local t...
static void register_with_read_factory()
Factory method to generate a CharacterJoint object.
void write_datagram(Datagram &destination) const
Writes the matrix to the Datagram using add_stdfloat().
Definition: lmatrix.cxx:1148
virtual bool is_character_joint() const
Returns true if this part is a CharacterJoint, false otherwise.
Definition: partGroup.cxx:65
bool has_net_transform(PandaNode *node) const
Returns true if the node is on the list of nodes that will be updated each frame with the joint&#39;s net...
This is a 4-by-4 transform matrix.
Definition: lmatrix.h:451
bool has_local_transform(PandaNode *node) const
Returns true if the node is on the list of nodes that will be updated each frame with the joint&#39;s loc...
An instance of this class is passed to the Factory when requesting it to do its business and construc...
Definition: factoryParams.h:40
void set_effect(const RenderEffect *effect)
Adds the indicated render effect to the scene graph on this node.
Definition: pandaNode.cxx:1174
void read_datagram(DatagramIterator &source)
Reads the matrix from the Datagram using get_stdfloat().
Definition: lmatrix.cxx:1162
virtual int complete_pointers(TypedWritable **p_list, BamReader *manager)
Takes in a vector of pointers to TypedWritable objects that correspond to all the requests for pointe...
void register_factory(TypeHandle handle, CreateFunc *func)
Registers a new kind of thing the Factory will be able to create.
Definition: factory.I:90
void add_uint16(PN_uint16 value)
Adds an unsigned 16-bit integer to the datagram.
Definition: datagram.I:181
This is a particular kind of MovingPart that accepts a matrix each frame.
static WritableFactory * get_factory()
Returns the global WritableFactory for generating TypedWritable objects.
Definition: bamReader.I:213
A thread; that is, a lightweight process.
Definition: thread.h:51
This is the root of a MovingPart hierarchy.
Definition: partBundle.h:49
This represents one joint of the character&#39;s animation, containing an animating transform matrix...
bool remove_net_transform(PandaNode *node)
Removes the indicated node from the list of nodes that will be updated each frame with the joint&#39;s ne...
void clear_net_transforms()
Removes all nodes from the list of nodes that will be updated each frame with the joint&#39;s net transfo...
bool remove_local_transform(PandaNode *node)
Removes the indicated node from the list of nodes that will be updated each frame with the joint&#39;s lo...
virtual int complete_pointers(TypedWritable **plist, BamReader *manager)
Receives an array of pointers, one for each time manager-&gt;read_pointer() was called in fillin()...
virtual void do_xform(const LMatrix4 &mat, const LMatrix4 &inv_mat)
Called by PartBundle::xform(), this indicates the indicated transform is being applied to the root jo...
size_type_0 size() const
Returns the number of elements in the ordered vector.
virtual PartGroup * make_copy() const
Allocates and returns a new copy of the node.
A class to retrieve the individual data elements previously stored in a Datagram. ...
NodePathCollection get_local_transforms()
Returns a list of the local transforms set for this node.
void clear_effect(TypeHandle type)
Removes the render effect of the given type from this node.
Definition: pandaNode.cxx:1194
Character * get_character() const
Returns the Character that owns this joint.
int get_file_minor_ver() const
Returns the minor version number of the Bam file currently being read.
Definition: bamReader.I:105
TypeHandle is the identifier used to differentiate C++ class types.
Definition: typeHandle.h:85
NodePathCollection get_net_transforms()
Returns a list of the net transforms set for this node.
An ordered list of data elements, formatted in memory for transmission over a socket or writing to a ...
Definition: datagram.h:43
void set_transform(const TransformState *transform, Thread *current_thread=Thread::get_current_thread())
Sets the transform that will be applied to this node and below.
Definition: pandaNode.cxx:1267
virtual bool is_character_joint() const
Returns true if this part is a CharacterJoint, false otherwise.
void write_pointer(Datagram &packet, const TypedWritable *dest)
The interface for writing a pointer to another object to a Bam file.
Definition: bamWriter.cxx:279
void read_pointer(DatagramIterator &scan)
The interface for reading a pointer to another object from a Bam file.
Definition: bamReader.cxx:652
virtual bool update_internals(PartBundle *root, PartGroup *parent, bool self_changed, bool parent_changed, Thread *current_thread)
This is called by do_update() whenever the part or some ancestor has changed values.
const LMatrix4 & get_transform() const
Returns the transform matrix of the joint.
This is a set of zero or more NodePaths.
This is the base class for PartRoot and MovingPart.
Definition: partGroup.h:45