00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015 #include "characterMaker.h"
00016 #include "eggLoader.h"
00017 #include "config_egg2pg.h"
00018 #include "eggBinner.h"
00019 #include "eggGroup.h"
00020 #include "eggPrimitive.h"
00021 #include "eggBin.h"
00022 #include "partGroup.h"
00023 #include "characterJoint.h"
00024 #include "characterJointBundle.h"
00025 #include "characterSlider.h"
00026 #include "character.h"
00027 #include "geomNode.h"
00028 #include "transformState.h"
00029 #include "eggSurface.h"
00030 #include "eggCurve.h"
00031 #include "modelNode.h"
00032 #include "characterVertexSlider.h"
00033 #include "jointVertexTransform.h"
00034 #include "userVertexTransform.h"
00035 #include "eggAnimPreload.h"
00036 #include "animPreloadTable.h"
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047 CharacterMaker::
00048 CharacterMaker(EggGroup *root, EggLoader &loader, bool structured)
00049 : _loader(loader), _egg_root(root) {
00050
00051 _character_node = new Character(_egg_root->get_name());
00052 _bundle = _character_node->get_bundle(0);
00053
00054 _morph_root = (PartGroup *)NULL;
00055 _skeleton_root = new PartGroup(_bundle, "<skeleton>");
00056 _structured = structured;
00057 }
00058
00059
00060
00061
00062
00063
00064 Character *CharacterMaker::
00065 make_node() {
00066 make_bundle();
00067 return _character_node;
00068 }
00069
00070
00071
00072
00073
00074
00075 string CharacterMaker::
00076 get_name() const {
00077 return _egg_root->get_name();
00078 }
00079
00080
00081
00082
00083
00084
00085
00086
00087
00088 PartGroup *CharacterMaker::
00089 egg_to_part(EggNode *egg_node) const {
00090 int index = egg_to_index(egg_node);
00091 if (index < 0) {
00092
00093
00094 return _bundle;
00095 }
00096 nassertr(index < (int)_parts.size(), NULL);
00097 return _parts[index];
00098 }
00099
00100
00101
00102
00103
00104
00105
00106
00107
00108
00109 VertexTransform *CharacterMaker::
00110 egg_to_transform(EggNode *egg_node) {
00111 int index = egg_to_index(egg_node);
00112 if (index < 0) {
00113
00114 return get_identity_transform();
00115 }
00116
00117 VertexTransforms::iterator vi = _vertex_transforms.find(index);
00118 if (vi != _vertex_transforms.end()) {
00119 return (*vi).second;
00120 }
00121
00122 PartGroup *part = _parts[index];
00123 CharacterJoint *joint;
00124 DCAST_INTO_R(joint, part, get_identity_transform());
00125
00126 PT(VertexTransform) vt = new JointVertexTransform(joint);
00127 _vertex_transforms[index] = vt;
00128
00129 return vt;
00130 }
00131
00132
00133
00134
00135
00136
00137
00138 int CharacterMaker::
00139 egg_to_index(EggNode *egg_node) const {
00140 NodeMap::const_iterator nmi = _node_map.find(egg_node);
00141 if (nmi == _node_map.end()) {
00142 return -1;
00143 }
00144 return (*nmi).second;
00145 }
00146
00147
00148
00149
00150
00151
00152
00153
00154
00155 PandaNode *CharacterMaker::
00156 part_to_node(PartGroup *part, const string &name) const {
00157 PandaNode *node = _character_node;
00158
00159 if (part->is_of_type(CharacterJoint::get_class_type())) {
00160 CharacterJoint *joint = DCAST(CharacterJoint, part);
00161 if (joint->_geom_node != (PandaNode *)NULL) {
00162 node = joint->_geom_node;
00163 }
00164 }
00165
00166
00167
00168
00169
00170
00171 if (node->is_geom_node() && node->get_name() == name) {
00172 return node;
00173 }
00174 for (int i = 0; i < node->get_num_children(); i++) {
00175 PandaNode *child = node->get_child(i);
00176 if (child->is_geom_node() && child->get_name() == name) {
00177 return child;
00178 }
00179 }
00180 PT(GeomNode) geom_node = new GeomNode(name);
00181 node->add_child(geom_node);
00182 return geom_node;
00183 }
00184
00185
00186
00187
00188
00189
00190
00191
00192 int CharacterMaker::
00193 create_slider(const string &name) {
00194 if (_morph_root == (PartGroup *)NULL) {
00195 _morph_root = new PartGroup(_bundle, "morph");
00196 }
00197 CharacterSlider *slider = new CharacterSlider(_morph_root, name);
00198 int index = _parts.size();
00199 _parts.push_back(slider);
00200 return index;
00201 }
00202
00203
00204
00205
00206
00207
00208
00209 VertexSlider *CharacterMaker::
00210 egg_to_slider(const string &name) {
00211 VertexSliders::iterator vi = _vertex_sliders.find(name);
00212 if (vi != _vertex_sliders.end()) {
00213 return (*vi).second;
00214 }
00215
00216 int index = create_slider(name);
00217 PT(VertexSlider) slider =
00218 new CharacterVertexSlider(DCAST(CharacterSlider, _parts[index]));
00219 _vertex_sliders[name] = slider;
00220 return slider;
00221 }
00222
00223
00224
00225
00226
00227
00228
00229 CharacterJointBundle *CharacterMaker::
00230 make_bundle() {
00231 build_joint_hierarchy(_egg_root, _skeleton_root, -1);
00232
00233
00234 if(!_structured) {
00235 make_geometry(_egg_root);
00236 }
00237 _bundle->sort_descendants();
00238 parent_joint_nodes(_skeleton_root);
00239
00240
00241
00242
00243 _bundle->force_update();
00244
00245 return _bundle;
00246 }
00247
00248
00249
00250
00251
00252
00253 void CharacterMaker::
00254 build_joint_hierarchy(EggNode *egg_node, PartGroup *part, int index) {
00255 if (egg_node->is_of_type(EggAnimPreload::get_class_type())) {
00256 EggAnimPreload *egg_anim_preload = DCAST(EggAnimPreload, egg_node);
00257
00258 double fps = 24.0;
00259 if (egg_anim_preload->has_fps()) {
00260 fps = egg_anim_preload->get_fps();
00261 }
00262
00263 int num_frames = 1;
00264 if (egg_anim_preload->has_num_frames()) {
00265 num_frames = egg_anim_preload->get_num_frames();
00266 }
00267
00268 PT(AnimPreloadTable) anim_preload = _bundle->modify_anim_preload();
00269 if (anim_preload == (AnimPreloadTable *)NULL) {
00270 anim_preload = new AnimPreloadTable;
00271 _bundle->set_anim_preload(anim_preload);
00272 }
00273 anim_preload->add_anim(egg_node->get_name(), fps, num_frames);
00274 return;
00275 }
00276
00277 if (egg_node->is_of_type(EggGroup::get_class_type())) {
00278 EggGroup *egg_group = DCAST(EggGroup, egg_node);
00279
00280
00281
00282 if (egg_group->get_group_type() == EggGroup::GT_joint) {
00283
00284
00285 LMatrix4d matd;
00286
00287
00288
00289 if (egg_group->has_transform()) {
00290 matd = egg_group->get_transform3d();
00291 } else {
00292 matd = LMatrix4d::ident_mat();
00293 }
00294
00295 LMatrix4 matf = LCAST(PN_stdfloat, matd);
00296
00297 CharacterJoint *joint =
00298 new CharacterJoint(_character_node, _character_node->get_bundle(0),
00299 part, egg_group->get_name(), matf);
00300 index = _parts.size();
00301 _parts.push_back(joint);
00302
00303
00304
00305
00306 if (egg_group->get_default_pose().has_transform()) {
00307 matd = egg_group->get_default_pose().get_transform3d();
00308 matf = LCAST(PN_stdfloat, matd);
00309 joint->_default_value = matf;
00310 joint->_value = matf;
00311 }
00312
00313 if (egg_group->has_dcs_type()) {
00314
00315
00316 PT(ModelNode) geom_node = new ModelNode(egg_group->get_name());
00317
00318
00319
00320 geom_node->set_preserve_transform(ModelNode::PT_net);
00321
00322 joint->_geom_node = geom_node.p();
00323 }
00324
00325 part = joint;
00326 }
00327
00328 EggGroup::const_iterator ci;
00329 for (ci = egg_group->begin(); ci != egg_group->end(); ++ci) {
00330 build_joint_hierarchy((*ci), part, index);
00331 }
00332 }
00333
00334 _node_map[egg_node] = index;
00335 }
00336
00337
00338
00339
00340
00341
00342
00343
00344 void CharacterMaker::
00345 parent_joint_nodes(PartGroup *part) {
00346 if (part->is_of_type(CharacterJoint::get_class_type())) {
00347 CharacterJoint *joint = DCAST(CharacterJoint, part);
00348 PandaNode *joint_node = joint->_geom_node;
00349 if (joint_node != NULL) {
00350 _character_node->add_child(joint_node);
00351 joint->add_net_transform(joint_node);
00352 joint_node->set_transform(TransformState::make_mat(joint->_net_transform));
00353 }
00354 }
00355
00356 for (int i = 0; i < part->get_num_children(); i++) {
00357 parent_joint_nodes(part->get_child(i));
00358 }
00359 }
00360
00361
00362
00363
00364
00365
00366
00367
00368
00369 void CharacterMaker::
00370 make_geometry(EggNode *egg_node) {
00371 if (egg_node->is_of_type(EggBin::get_class_type())) {
00372 EggBin *egg_bin = DCAST(EggBin, egg_node);
00373
00374 if (!egg_bin->empty() &&
00375 egg_bin->get_bin_number() == EggBinner::BN_polyset) {
00376 EggGroupNode *bin_home = determine_bin_home(egg_bin);
00377
00378 bool is_dynamic;
00379 if (bin_home == (EggGroupNode *)NULL) {
00380
00381
00382 bin_home = _egg_root;
00383 is_dynamic = true;
00384 } else {
00385
00386
00387 is_dynamic = false;
00388 }
00389
00390 PandaNode *parent = part_to_node(egg_to_part(bin_home), egg_bin->get_name());
00391 LMatrix4d transform =
00392 egg_bin->get_vertex_frame() *
00393 bin_home->get_node_frame_inv();
00394
00395 _loader.make_polyset(egg_bin, parent, &transform, is_dynamic,
00396 this);
00397 }
00398 }
00399
00400 if (egg_node->is_of_type(EggGroupNode::get_class_type())) {
00401 EggGroupNode *egg_group = DCAST(EggGroupNode, egg_node);
00402
00403 EggGroupNode::const_iterator ci;
00404 for (ci = egg_group->begin(); ci != egg_group->end(); ++ci) {
00405 make_geometry(*ci);
00406 }
00407 }
00408 }
00409
00410
00411
00412
00413
00414
00415 EggGroupNode *CharacterMaker::
00416 determine_primitive_home(EggPrimitive *egg_primitive) {
00417
00418
00419
00420
00421
00422
00423
00424
00425
00426
00427
00428 EggGroupNode *home = NULL;
00429
00430 EggPrimitive::const_iterator vi;
00431 for (vi = egg_primitive->begin();
00432 vi != egg_primitive->end();
00433 ++vi) {
00434 EggVertex *vertex = (*vi);
00435 if (vertex->gref_size() > 1) {
00436
00437
00438 return NULL;
00439 }
00440
00441 if (!vertex->_dxyzs.empty() ||
00442 !vertex->_dnormals.empty() ||
00443 !vertex->_drgbas.empty()) {
00444
00445
00446 return NULL;
00447 }
00448 EggVertex::const_uv_iterator uvi;
00449 for (uvi = vertex->uv_begin(); uvi != vertex->uv_end(); ++uvi) {
00450 if (!(*uvi)->_duvs.empty()) {
00451
00452
00453 return NULL;
00454 }
00455 }
00456
00457 EggGroupNode *vertex_home;
00458
00459 if (vertex->gref_size() == 0) {
00460
00461
00462 vertex_home = egg_primitive->get_parent();
00463 } else {
00464 nassertr(vertex->gref_size() == 1, NULL);
00465
00466 vertex_home = *vertex->gref_begin();
00467 }
00468
00469 if (home != NULL && home != vertex_home) {
00470
00471
00472 return NULL;
00473 }
00474
00475 home = vertex_home;
00476 }
00477
00478
00479
00480 nassertr(home != NULL, NULL);
00481
00482
00483
00484
00485
00486
00487 EggGroup *egg_group = (EggGroup *)NULL;
00488 if (home->is_of_type(EggGroup::get_class_type())) {
00489 egg_group = DCAST(EggGroup, home);
00490 }
00491 while (egg_group != (EggGroup *)NULL &&
00492 egg_group->get_group_type() != EggGroup::GT_joint &&
00493 egg_group->get_dart_type() == EggGroup::DT_none) {
00494 nassertr(egg_group->get_parent() != (EggGroupNode *)NULL, NULL);
00495 home = egg_group->get_parent();
00496 egg_group = (EggGroup *)NULL;
00497 if (home->is_of_type(EggGroup::get_class_type())) {
00498 egg_group = DCAST(EggGroup, home);
00499 }
00500 }
00501
00502 if (egg_group != (EggGroup *)NULL &&
00503 egg_group->get_group_type() == EggGroup::GT_joint &&
00504 !egg_group->has_dcs_type()) {
00505
00506
00507
00508 return NULL;
00509 }
00510
00511
00512
00513
00514
00515 return home;
00516 }
00517
00518
00519
00520
00521
00522
00523
00524
00525
00526 EggGroupNode *CharacterMaker::
00527 determine_bin_home(EggBin *egg_bin) {
00528
00529
00530
00531
00532
00533
00534
00535
00536
00537 if (!egg_rigid_geometry) {
00538
00539
00540 return NULL;
00541 }
00542
00543
00544
00545 EggGroupNode *home = NULL;
00546
00547 EggGroupNode::const_iterator ci;
00548 for (ci = egg_bin->begin(); ci != egg_bin->end(); ++ci) {
00549 CPT(EggPrimitive) egg_primitive = DCAST(EggPrimitive, (*ci));
00550
00551 EggPrimitive::const_iterator vi;
00552 for (vi = egg_primitive->begin();
00553 vi != egg_primitive->end();
00554 ++vi) {
00555 EggVertex *vertex = (*vi);
00556 if (vertex->gref_size() > 1) {
00557
00558
00559 return NULL;
00560 }
00561
00562 if (!vertex->_dxyzs.empty() ||
00563 !vertex->_dnormals.empty() ||
00564 !vertex->_drgbas.empty()) {
00565
00566
00567 return NULL;
00568 }
00569 EggVertex::const_uv_iterator uvi;
00570 for (uvi = vertex->uv_begin(); uvi != vertex->uv_end(); ++uvi) {
00571 if (!(*uvi)->_duvs.empty()) {
00572
00573
00574 return NULL;
00575 }
00576 }
00577
00578 EggGroupNode *vertex_home;
00579
00580 if (vertex->gref_size() == 0) {
00581
00582
00583 vertex_home = egg_primitive->get_parent();
00584 } else {
00585 nassertr(vertex->gref_size() == 1, NULL);
00586
00587 vertex_home = *vertex->gref_begin();
00588 }
00589
00590 if (home != NULL && home != vertex_home) {
00591
00592
00593 return NULL;
00594 }
00595
00596 home = vertex_home;
00597 }
00598 }
00599
00600
00601
00602
00603 nassertr(home != NULL, NULL);
00604
00605
00606
00607
00608
00609
00610 EggGroup *egg_group = (EggGroup *)NULL;
00611 if (home->is_of_type(EggGroup::get_class_type())) {
00612 egg_group = DCAST(EggGroup, home);
00613 }
00614 while (egg_group != (EggGroup *)NULL &&
00615 egg_group->get_group_type() != EggGroup::GT_joint &&
00616 egg_group->get_dart_type() == EggGroup::DT_none) {
00617 nassertr(egg_group->get_parent() != (EggGroupNode *)NULL, NULL);
00618 home = egg_group->get_parent();
00619 egg_group = (EggGroup *)NULL;
00620 if (home->is_of_type(EggGroup::get_class_type())) {
00621 egg_group = DCAST(EggGroup, home);
00622 }
00623 }
00624
00625 if (egg_group != (EggGroup *)NULL &&
00626 egg_group->get_group_type() == EggGroup::GT_joint &&
00627 !egg_group->has_dcs_type()) {
00628
00629
00630
00631
00632 if (egg_group->get_dcs_type() == EggGroup::DC_none) {
00633
00634
00635
00636
00637
00638
00639
00640
00641
00642
00643 return NULL;
00644 }
00645
00646 CharacterJoint *joint;
00647 DCAST_INTO_R(joint, egg_to_part(egg_group), home);
00648 egg_group->set_dcs_type(EggGroup::DC_default);
00649
00650 PT(ModelNode) geom_node = new ModelNode(egg_group->get_name());
00651 geom_node->set_preserve_transform(ModelNode::PT_local);
00652 joint->_geom_node = geom_node.p();
00653 }
00654
00655 return home;
00656 }
00657
00658
00659
00660
00661
00662
00663
00664 VertexTransform *CharacterMaker::
00665 get_identity_transform() {
00666 if (_identity_transform == (VertexTransform *)NULL) {
00667 _identity_transform = new UserVertexTransform("root");
00668 }
00669 return _identity_transform;
00670 }