Browse Source

weird state...make sure the hierarchy is fixed...i think that is the key to make it work

Asad M. Zaman 22 years ago
parent
commit
7249626033

+ 2 - 2
pandatool/src/softegg/soft2Egg.c

@@ -1331,8 +1331,8 @@ LoadSoft()
                 {
                     SAA_frame2Seconds( &scene, frame, &time );
                     SAA_updatelistEvalScene( &scene, time );
-										sginap( 100 );
-										SAA_updatelistEvalScene( &scene, time );
+                    sginap( 100 );
+                    SAA_updatelistEvalScene( &scene, time );
                     fprintf( outStream, "\n> animating frame %d\n", frame );
 
                     // for each model

+ 117 - 19
pandatool/src/softegg/softNodeDesc.cxx

@@ -26,21 +26,21 @@ TypeHandle SoftNodeDesc::_type_handle;
 //  Description: 
 ////////////////////////////////////////////////////////////////////
 SoftNodeDesc::
-SoftNodeDesc(const string &name) :
-  Namable(name)
-  //  _parent(parent)
+SoftNodeDesc(SoftNodeDesc *parent, const string &name) :
+  Namable(name),
+  _parent(parent)
 {
   _model = (SAA_Elem *)NULL;
   _egg_group = (EggGroup *)NULL;
   _egg_table = (EggTable *)NULL;
   _anim = (EggXfmSAnim *)NULL;
   _joint_type = JT_none;
-#if 0
+
   // Add ourselves to our parent.
   if (_parent != (SoftNodeDesc *)NULL) {
     _parent->_children.push_back(this);
   }
-#endif
+
   fullname = NULL;
 
   numTexLoc = 0;
@@ -117,6 +117,16 @@ bool SoftNodeDesc::
 is_joint() const {
   return _joint_type == JT_joint || _joint_type == JT_pseudo_joint;
 }
+
+////////////////////////////////////////////////////////////////////
+//     Function: SoftNodeDesc::set_joint
+//       Access: Private
+//  Description: sets the _joint_type to JT_joint
+////////////////////////////////////////////////////////////////////
+void SoftNodeDesc::
+set_joint() {
+  _joint_type = JT_joint; // || _joint_type == JT_pseudo_joint;
+}
 #if 0
 ////////////////////////////////////////////////////////////////////
 //     Function: SoftNodeDesc::is_joint_parent
@@ -232,7 +242,7 @@ check_pseudo_joints(bool joint_above) {
 //               and applies it to the corresponding Egg node.
 ////////////////////////////////////////////////////////////////////
 void SoftNodeDesc::
-get_transform(SAA_Scene *scene, EggGroup *egg_group) {
+get_transform(SAA_Scene *scene, EggGroup *egg_group, bool set_transform) {
   // Get the model's matrix
   SAA_modelGetMatrix( scene, get_model(), SAA_COORDSYS_GLOBAL,  matrix );
 
@@ -241,30 +251,118 @@ get_transform(SAA_Scene *scene, EggGroup *egg_group) {
   cout << "model matrix = " << matrix[2][0] << " " << matrix[2][1] << " " << matrix[2][2] << " " << matrix[2][3] << "\n";
   cout << "model matrix = " << matrix[3][0] << " " << matrix[3][1] << " " << matrix[3][2] << " " << matrix[3][3] << "\n";
 
-#if 0 // this is not needed according to drose: verified by asad
-  LMatrix4d m4d(matrix[0][0], matrix[0][1], matrix[0][2], matrix[0][3],
-                matrix[1][0], matrix[1][1], matrix[1][2], matrix[1][3],
-                matrix[2][0], matrix[2][1], matrix[2][2], matrix[2][3],
-                matrix[3][0], matrix[3][1], matrix[3][2], matrix[3][3]);
-  if (!m4d.almost_equal(LMatrix4d::ident_mat(), 0.0001)) {
-    egg_group->add_matrix(m4d);
-    cout << "added matrix in egg_group\n";
+  if (set_transform) {
+    LMatrix4d m4d(matrix[0][0], matrix[0][1], matrix[0][2], matrix[0][3],
+                  matrix[1][0], matrix[1][1], matrix[1][2], matrix[1][3],
+                  matrix[2][0], matrix[2][1], matrix[2][2], matrix[2][3],
+                  matrix[3][0], matrix[3][1], matrix[3][2], matrix[3][3]);
+    if (!m4d.almost_equal(LMatrix4d::ident_mat(), 0.0001)) {
+      egg_group->set_transform(m4d);
+      cout << "set transform in egg_group\n";
+    }
   }
-#endif
-
   return;
 }
 
 ////////////////////////////////////////////////////////////////////
-//     Function: SoftToEggConverter::make_polyset
+//     Function: SoftNodeDesc::get_joint_transform
+//       Access: Private
+//  Description: Extracts the transform on the indicated Soft node,
+//               as appropriate for a joint in an animated character,
+//               and applies it to the indicated node.  This is
+//               different from get_transform() in that it does not
+//               respect the _transform_type flag, and it does not
+//               consider the relative transforms within the egg file.
+//               more added functionality: now fills in components of
+//               anim (EffXfmSAnim) class (masad).
+////////////////////////////////////////////////////////////////////
+void SoftNodeDesc::
+get_joint_transform(SAA_Scene *scene,  EggGroup *egg_group, EggXfmSAnim *anim) {
+  //  SI_Error result;
+  SAA_Elem *skeletonPart = _model;
+  const char *name = get_name().c_str();
+
+  if ( skeletonPart != NULL ) {
+    float i,j,k;
+    float h,p,r;
+    float x,y,z;
+    int size;
+    SAA_Boolean globalFlag = FALSE;
+    SAA_Boolean bigEndian;
+
+    cout << "\n\nanimating child " << name << endl;
+
+    SAA_elementGetUserDataSize( scene, skeletonPart, "GLOBAL", &size );
+        
+    if ( size != 0 )
+      SAA_elementGetUserData( scene, skeletonPart, "GLOBAL", 
+                              sizeof( SAA_Boolean), &bigEndian, (void *)&globalFlag );
+ 
+    if ( globalFlag ) {
+      cout << " using global matrix\n";
+
+      //get SAA orientation
+      SAA_modelGetRotation( scene, skeletonPart, SAA_COORDSYS_GLOBAL, 
+                            &p, &h, &r );
+
+      //get SAA translation
+      SAA_modelGetTranslation( scene, skeletonPart, SAA_COORDSYS_GLOBAL, 
+                               &x, &y, &z );
+
+      //get SAA scaling
+      SAA_modelGetScaling( scene, skeletonPart, SAA_COORDSYS_GLOBAL, 
+                           &i, &j, &k );
+    }
+    else {
+      cout << "using local matrix\n";
+
+      //get SAA orientation
+      SAA_modelGetRotation( scene, skeletonPart, SAA_COORDSYS_LOCAL, 
+                            &p, &h, &r );
+
+      //get SAA translation
+      SAA_modelGetTranslation( scene, skeletonPart, SAA_COORDSYS_LOCAL, 
+                               &x, &y, &z );
+      
+      //get SAA scaling
+      SAA_modelGetScaling( scene, skeletonPart, SAA_COORDSYS_LOCAL, 
+                           &i, &j, &k );
+    }
+    
+    cout << "\nanim data: " << i << " " << j << " " << k << endl;
+    cout << "\t" << p << " " << h << " " << r << endl;
+    cout << "\t" << x << " " << y << " " << z << endl;
+
+    // make sure the ordering is correct
+    anim->set_order(anim->get_standard_order());
+
+    // Add each component by their names
+    anim->add_component_data("i", i);
+    anim->add_component_data("j", j);
+    anim->add_component_data("k", k);
+    anim->add_component_data("p", p);
+    anim->add_component_data("h", h);
+    anim->add_component_data("r", r);
+    anim->add_component_data("x", x);
+    anim->add_component_data("y", y);
+    anim->add_component_data("z", z);
+  }
+  else {
+    cout << "Cannot build anim table - no skeleton\n";
+  }
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: SoftNodeDesc::load_model
 //       Access: Private
 //  Description: Converts the indicated Soft polyset to a bunch of
 //               EggPolygons and parents them to the indicated egg
 //               group.
 ////////////////////////////////////////////////////////////////////
 void SoftNodeDesc::
-load_model(SAA_Scene *scene, SAA_ModelType type, char *name) {
-  SI_Error            result;
+load_model(SAA_Scene *scene, SAA_ModelType type) {
+  SI_Error result;
+  const char *name = get_name().c_str();
   
   int i;
   int id = 0;

+ 9 - 8
pandatool/src/softegg/softNodeDesc.h

@@ -47,7 +47,7 @@ class EggXfmSAnim;
 ////////////////////////////////////////////////////////////////////
 class SoftNodeDesc : public ReferenceCount, public Namable {
 public:
-  SoftNodeDesc(const string &name = string());
+  SoftNodeDesc(SoftNodeDesc *parent=NULL, const string &name = string());
   ~SoftNodeDesc();
 
   void set_model(SAA_Elem *model);
@@ -55,11 +55,12 @@ public:
   SAA_Elem *get_model() const;
 
   bool is_joint() const;
+  void set_joint();
   //  bool is_joint_parent() const;
 
-  //  SoftNodeDesc *_parent;
-  //  typedef pvector< PT(SoftNodeDesc) > Children;
-  //  Children _children;
+  SoftNodeDesc *_parent;
+  typedef pvector< PT(SoftNodeDesc) > Children;
+  Children _children;
   
 private:
   void clear_egg();
@@ -67,7 +68,7 @@ private:
   //  void check_pseudo_joints(bool joint_above);
 
   SAA_ModelType type;
-  char *fullname;
+  const char *fullname;
 
   SAA_Elem *_model;
 
@@ -108,9 +109,9 @@ public:
   SAA_SubElem *triangles;
   SAA_GeomType gtype;
 
-
-  void get_transform(SAA_Scene *scene, EggGroup *egg_group);
-  void load_model(SAA_Scene *scene, SAA_ModelType type, char *name);
+  void get_transform(SAA_Scene *scene, EggGroup *egg_group, bool set_transform=FALSE);
+  void get_joint_transform(SAA_Scene *scene, EggGroup *egg_group, EggXfmSAnim *anim);
+  void load_model(SAA_Scene *scene, SAA_ModelType type);
 
   static TypeHandle get_class_type() {
     return _type_handle;

+ 117 - 39
pandatool/src/softegg/softNodeTree.cxx

@@ -38,9 +38,10 @@
 ////////////////////////////////////////////////////////////////////
 SoftNodeTree::
 SoftNodeTree() {
-  //  _root = new SoftNodeDesc;
-  _root = NULL;
+  _root = new SoftNodeDesc;
   _fps = 0.0;
+  _use_prefix = 0;
+  _search_prefix = NULL;
   _egg_data = (EggData *)NULL;
   _egg_root = (EggGroupNode *)NULL;
   _skeleton_node = (EggGroupNode *)NULL;
@@ -55,7 +56,7 @@ char *SoftNodeTree::
 GetName( SAA_Scene *scene, SAA_Elem *element ) {
   int nameLen;
   char *name;
-
+  
   // get the name
   SAA_elementGetNameLength( scene, element, &nameLen ); 
   name = new char[++nameLen];
@@ -158,21 +159,6 @@ GetRootName( const char *name ) {
   return( root );
 }
 
-////////////////////////////////////////////////////////////////////
-//     Function: SoftNodeTree::build_node
-//       Access: Public
-//  Description: Returns a pointer to the node corresponding to the
-//               indicated dag_path object, creating it first if
-//               necessary.
-////////////////////////////////////////////////////////////////////
-SoftNodeDesc *SoftNodeTree::
-build_node(SAA_Elem *model, const char *name) {
-  string node_name = name;
-  SoftNodeDesc *node_desc = r_build_node(node_name);
-  node_desc->set_model(model);
-  return node_desc;
-}
-
 ////////////////////////////////////////////////////////////////////
 //     Function: SoftNodeTree::build_complete_hierarchy
 //       Access: Public
@@ -186,7 +172,7 @@ build_complete_hierarchy(SAA_Scene &scene, SAA_Database &database) {
   // Get the entire Soft scene.
   int numModels;
   SAA_Elem *models;
-  
+
   SAA_sceneGetNbModels( &scene, &numModels ); 
   cout << "Scene has " << numModels << " model(s)...\n";
   
@@ -203,12 +189,13 @@ build_complete_hierarchy(SAA_Scene &scene, SAA_Database &database) {
       for ( int i = 0; i < numModels; i++ ) {
         int level;
         status = SAA_elementGetHierarchyLevel( &scene, &models[i], &level );
-        cout << "level " << level << endl;
+        cout << "model[" << i << "]" << endl;
+        cout << " level " << level << endl;
+        cout << " status is " << status << "\n";
+        
         //        if (!level) {
-          char *name = GetName(&scene, &models[i]);
-          SoftNodeDesc *node_desc = build_node(&models[i], name);
+          build_node(&scene, &models[i]);
           //        }
-        cout << "status is " << status << "\n";
       }
     }
   }
@@ -438,10 +425,10 @@ get_egg_group(SoftNodeDesc *node_desc) {
     //    egg_group->set_user_data(user_data);
     node_desc->_egg_group = egg_group;
   }
-
+  
   return node_desc->_egg_group;
 }
-#if 0
+
 ////////////////////////////////////////////////////////////////////
 //     Function: SoftNodeTree::get_egg_table
 //       Access: Public
@@ -453,29 +440,30 @@ EggTable *SoftNodeTree::
 get_egg_table(SoftNodeDesc *node_desc) {
   nassertr(_skeleton_node != (EggGroupNode *)NULL, NULL);
   nassertr(node_desc->is_joint(), NULL);
-
+  
   if (node_desc->_egg_table == (EggTable *)NULL) {
+    cout << "creating a new table\n";
     // We need to make a new table node.
-    nassertr(node_desc->_parent != (SoftNodeDesc *)NULL, NULL);
-
+    //    nassertr(node_desc->_parent != (SoftNodeDesc *)NULL, NULL);
+    
     EggTable *egg_table = new EggTable(node_desc->get_name());
     node_desc->_anim = new EggXfmSAnim("xform", _egg_data->get_coordinate_system());
     node_desc->_anim->set_fps(_fps);
     egg_table->add_child(node_desc->_anim);
-
-    if (!node_desc->_parent->is_joint()) {
-      // The parent is not a joint; put it at the top.
-      _skeleton_node->add_child(egg_table);
-
+    
+    //    if (!node_desc->_parent->is_joint()) {
+    // The parent is not a joint; put it at the top.
+    _skeleton_node->add_child(egg_table);
+    /*
     } else {
       // The parent is another joint.
       EggTable *parent_egg_table = get_egg_table(node_desc->_parent);
       parent_egg_table->add_child(egg_table);
     }
-
+    */
     node_desc->_egg_table = egg_table;
   }
-
+  
   return node_desc->_egg_table;
 }
 
@@ -491,21 +479,111 @@ get_egg_anim(SoftNodeDesc *node_desc) {
   get_egg_table(node_desc);
   return node_desc->_anim;
 }
-#endif
+
+////////////////////////////////////////////////////////////////////
+//     Function: SoftNodeTree::build_node
+//       Access: Public
+//  Description: Returns a pointer to the node corresponding to the
+//               indicated dag_path object, creating it first if
+//               necessary.
+////////////////////////////////////////////////////////////////////
+void SoftNodeTree::
+build_node(SAA_Scene *scene, SAA_Elem *model) {
+  char *name;
+  string node_name;
+  int numChildren;
+  int thisChild;
+  SAA_Elem *children;
+  SAA_Boolean isSkeleton = FALSE;
+
+  if (_use_prefix)
+    name = GetFullName(scene, model);
+  else
+    name = GetName(scene, model);
+
+  node_name = name;
+
+  ///////////////////////////////////////////////////////////////////////
+  // check to see if this is a branch we don't want to descend - this
+  // will prevent creating geometry for animation control structures
+  ///////////////////////////////////////////////////////////////////////
+
+  /*
+  if ( (strstr(name, "con-") == NULL) && 
+       (strstr(name, "con_") == NULL) && 
+       (strstr(name, "fly_") == NULL) && 
+       (strstr(name, "fly-") == NULL) && 
+       (strstr(name, "camRIG") == NULL) &&
+       (strstr(name, "bars") == NULL) && 
+       // split
+       (!_search_prefix || (strstr(name, _search_prefix) != NULL)) )
+    {
+  */
+      SoftNodeDesc *node_desc = r_build_node(NULL, node_name);
+      node_desc->set_model(model);
+      SAA_modelIsSkeleton( scene, model, &isSkeleton );
+      if (isSkeleton || (strstr(node_desc->get_name().c_str(), "joint") != NULL))
+        node_desc->set_joint();
+      
+      SAA_modelGetNbChildren( scene, model, &numChildren );
+      cout << " Model " << node_name << " children: " << numChildren << endl;
+      
+      if ( numChildren ) {
+        children = new SAA_Elem[numChildren];
+        SAA_modelGetChildren( scene, model, numChildren, children );
+        if (!children)
+          cout << "Not enough Memory for children...\n";
+        
+        for ( thisChild = 0; thisChild < numChildren; thisChild++ ) {
+          if (_use_prefix)
+            node_name = GetFullName(scene, &children[thisChild]);
+          else
+            node_name = GetName(scene, &children[thisChild]);
+          
+          cout << " building child " << thisChild << "...";
+
+          SoftNodeDesc *node_child = r_build_node(node_desc, node_name);
+          node_child->set_model(&children[thisChild]);
+          
+          //  if (strstr(name, "joint") != NULL)
+          SAA_modelIsSkeleton( scene, &children[thisChild], &isSkeleton );
+          if (isSkeleton || (strstr(node_child->get_name().c_str(), "joint") != NULL))
+            node_child->set_joint();
+        }
+      }
+      //    }
+  return;
+}
+
 ////////////////////////////////////////////////////////////////////
 //     Function: SoftNodeTree::r_build_node
 //       Access: Private
 //  Description: The recursive implementation of build_node().
 ////////////////////////////////////////////////////////////////////
 SoftNodeDesc *SoftNodeTree::
-r_build_node(const string &name) {
+r_build_node(SoftNodeDesc *parent_node, const string &name) {
+  // If we have already encountered this pathname, return the
+  // corresponding MayaNodeDesc immediately.
+  NodesByName::const_iterator ni = _nodes_by_name.find(name);
+  if (ni != _nodes_by_name.end()) {
+    cout << (*ni).first << endl;
+    return (*ni).second;
+  }
+
   // Otherwise, we have to create it.  Do this recursively, so we
   // create each node along the path.
   SoftNodeDesc *node_desc;
-
-  node_desc = new SoftNodeDesc(name);
+  if (!parent_node) {
+    node_desc = _root;
+  }
+  else {
+    node_desc = new SoftNodeDesc(parent_node, name);
+  }
+  cout << " node name : " << name << endl;
   _nodes.push_back(node_desc);
 
+  _nodes_by_name.insert(NodesByName::value_type(name, node_desc));
+
   return node_desc;
 }
 

+ 9 - 6
pandatool/src/softegg/softNodeTree.h

@@ -39,7 +39,7 @@ class EggGroupNode;
 class SoftNodeTree {
 public:
   SoftNodeTree();
-  SoftNodeDesc *build_node(SAA_Elem *model, const char *name);
+  void build_node(SAA_Scene *scene, SAA_Elem *model);
   bool build_complete_hierarchy(SAA_Scene &scene, SAA_Database &database);
   //  bool build_selected_hierarchy(SAA_Scene *s, SAA_Database *d, char *scene_name);
 
@@ -59,6 +59,9 @@ public:
 
   PT(SoftNodeDesc) _root;
   float _fps;
+  int _use_prefix;
+  char *_search_prefix;
+  
 
 private:
 
@@ -66,11 +69,11 @@ private:
   EggGroupNode *_egg_root;
   EggGroupNode *_skeleton_node;
 
-  SoftNodeDesc *r_build_node(const string &path);
-#if 0
-  typedef pmap<string, SoftNodeDesc *> NodesByPath;
-  NodesByPath _nodes_by_path;
-#endif
+  SoftNodeDesc *r_build_node(SoftNodeDesc *parent_node, const string &path);
+
+  typedef pmap<string, SoftNodeDesc *> NodesByName;
+  NodesByName _nodes_by_name;
+
   typedef pvector<SoftNodeDesc *> Nodes;
   Nodes _nodes;
 };

+ 169 - 131
pandatool/src/softegg/softToEggConverter.cxx

@@ -571,133 +571,40 @@ convert_soft(bool from_selection) {
     exit(1);
   }
 
+  _tree._use_prefix = use_prefix;
+  _tree._search_prefix = search_prefix;
   all_ok = _tree.build_complete_hierarchy(scene, database);
+  //  exit(1);
+
   char *root_name = _tree.GetRootName( eggFileName );
   cout << "main group name: " << root_name << endl;
   if (root_name)
     _character_name = root_name;
+  
+  if (make_poly) {
+    if (!convert_char_model()) {
+      all_ok = false;
+    }
 
-  if (!convert_char_model()) {
-    all_ok = false;
-  }
-  //  reparent_decals(&get_egg_data());
-  cout << softegg_cat.info() << "Converted Softimage file\n";
-
-  // write out the egg file
-  _egg_data->write_egg(Filename(eggFileName));
-  cout << softegg_cat.info() << "Write Egg file\n";
-
-  /*
-  _shaders.clear();
-
-  if (!open_api()) {
-    softegg_cat.error()
-      << "Soft is not available.\n";
-    return false;
-  }
-
-  if (_egg_data->get_coordinate_system() == CS_default) {
-    _egg_data->set_coordinate_system(_maya->get_coordinate_system());
-  }
-
-  softegg_cat.info()
-    << "Converting from Soft.\n";
-
-  // Figure out the animation parameters.
-  double start_frame, end_frame, frame_inc, input_frame_rate, output_frame_rate;
-  if (has_start_frame()) {
-    start_frame = get_start_frame();
-  } else {
-    start_frame = MAnimControl::minTime().value();
-  }
-  if (has_end_frame()) {
-    end_frame = get_end_frame();
-  } else {
-    end_frame = MAnimControl::maxTime().value();
-  }
-  if (has_frame_inc()) {
-    frame_inc = get_frame_inc();
-  } else {
-    frame_inc = 1.0;
-  }
-  if (has_input_frame_rate()) {
-    input_frame_rate = get_input_frame_rate();
-  } else {
-    MTime time(1.0, MTime::kSeconds);
-    input_frame_rate = time.as(MTime::uiUnit());
-  }
-  if (has_output_frame_rate()) {
-    output_frame_rate = get_output_frame_rate();
-  } else {
-    output_frame_rate = input_frame_rate;
-  }
-
-  bool all_ok = true;
+    //  reparent_decals(&get_egg_data());
+    cout << softegg_cat.info() << "Converted Softimage file\n";
 
-  if (_from_selection) {
-    all_ok = _tree.build_selected_hierarchy();
-  } else {
-    all_ok = _tree.build_complete_hierarchy();
+    // write out the egg model file
+    _egg_data->write_egg(Filename(eggFileName));
+    cout << softegg_cat.info() << "Wrote Egg file " << eggFileName << endl;
   }
+  if (make_anim) {
+    if (!convert_char_chan()) {
+      all_ok = false;
+    }
 
-  if (all_ok) {
-    switch (get_animation_convert()) {
-    case AC_pose:
-      // pose: set to a specific frame, then get out the static geometry.
-      softegg_cat.info(false)
-        << "frame " << start_frame << "\n";
-      MGlobal::viewFrame(MTime(start_frame, MTime::uiUnit()));
-      // fall through
-      
-    case AC_none:
-      // none: just get out a static model, no animation.
-      all_ok = convert_hierarchy(&get_egg_data());
-      break;
-      
-    case AC_flip:
-    case AC_strobe:
-      // flip or strobe: get out a series of static models, one per
-      // frame, under a sequence node for AC_flip.
-      all_ok = convert_flip(start_frame, end_frame, frame_inc,
-                            output_frame_rate);
-      break;
-
-    case AC_model:
-      // model: get out an animatable model with joints and vertex
-      // membership.
-      all_ok = convert_char_model();
-      break;
-
-    case AC_chan:
-      // chan: get out a series of animation tables.
-      all_ok = convert_char_chan(start_frame, end_frame, frame_inc,
-                                 output_frame_rate);
-      break;
-      
-    case AC_both:
-      // both: Put a model and its animation into the same egg file.
-      _animation_convert = AC_model;
-      if (!convert_char_model()) {
-        all_ok = false;
-      }
-      _animation_convert = AC_chan;
-      if (!convert_char_chan(start_frame, end_frame, frame_inc,
-                             output_frame_rate)) {
-        all_ok = false;
-      }
-      break;
-    };
-
-    reparent_decals(&get_egg_data());
-  }
-  if (all_ok) {
-    softegg_cat.info()
-      << "Converted, no errors.\n";
-  } else {
-    softegg_cat.info()
-      << "Errors encountered in conversion.\n";
+    //  reparent_decals(&get_egg_data());
+    cout << softegg_cat.info() << "Converted Softimage file\n";
+    
+    // write out the egg model file
+    _egg_data->write_egg(Filename(animFileName));
+    cout << softegg_cat.info() << "Wrote Anim file " << animFileName << endl;
   }
-  */
   return all_ok;
 }
 
@@ -730,6 +637,17 @@ open_api() {
     softegg_cat.info() << "Error: Couldn't load scene " << scene_name << "!\n";
     exit( 1 );
   }
+  if ( SAA_updatelistGet( &scene ) == SI_SUCCESS ) {
+    float time;
+    
+    softegg_cat.info() << "setting Scene to frame " << pose_frame << "...\n";
+    //SAA_sceneSetPlayCtrlCurrentFrame( &scene, pose_frame );
+    SAA_frame2Seconds( &scene, pose_frame, &time );
+    SAA_updatelistEvalScene( &scene, time );
+    if ( make_pose )
+      SAA_sceneFreeze(&scene);
+  } 
+  
   // if no egg filename specified, make up a name
   if ( eggFileName == NULL ) {
     string madeName;
@@ -743,8 +661,16 @@ open_api() {
     }
     eggFileName = new char[madeName.size()+1];
     strcpy(eggFileName, madeName.c_str());
+
+    // if no anim filename specified, make up a name
+    if ( animFileName == NULL ) {
+      madeName.assign(tempName.substr(0,end));
+      madeName.insert(madeName.size(), "-chan.egg");
+      animFileName = new char[strlen(scene_name)+ 10];
+      strcpy(animFileName, madeName.c_str());
+    }
   }
-  
+
   return true;
 }
 
@@ -784,6 +710,103 @@ convert_char_model() {
   return convert_hierarchy(char_node);
 }
 
+////////////////////////////////////////////////////////////////////
+//     Function: SoftToEggConverter::convert_char_chan
+//       Access: Private
+//  Description: Converts the animation as a series of tables to apply
+//               to the character model, as retrieved earlier via
+//               AC_model.
+////////////////////////////////////////////////////////////////////
+bool SoftToEggConverter::
+convert_char_chan() {
+  int start_frame = -1;
+  int end_frame = -1;
+  int frame_inc, frame;
+  double output_frame_rate = anim_rate;
+  
+  float time;
+
+  EggTable *root_table_node = new EggTable();
+  get_egg_data().add_child(root_table_node);
+  EggTable *bundle_node = new EggTable(_character_name);
+  bundle_node->set_table_type(EggTable::TT_bundle);
+  root_table_node->add_child(bundle_node);
+  EggTable *skeleton_node = new EggTable("<skeleton>");
+  bundle_node->add_child(skeleton_node);
+
+  // Set the frame rate before we start asking for anim tables to be
+  // created.
+  SAA_sceneGetPlayCtrlStartFrame(&scene, &start_frame);
+  SAA_sceneGetPlayCtrlEndFrame(&scene, &end_frame);
+  SAA_sceneGetPlayCtrlFrameStep( &scene, &frame_inc );
+  
+  cout << "animation start frame: " << start_frame << " end frame: " << end_frame << endl;
+  cout << "animation frame inc: " << frame_inc << endl;
+  
+  _tree._fps = output_frame_rate / frame_inc;
+  _tree.clear_egg(&get_egg_data(), NULL, skeleton_node);
+
+  // Now we can get the animation data by walking through all of the
+  // frames, one at a time, and getting the joint angles at each
+  // frame.
+
+  // This is just a temporary EggGroup to receive the transform for
+  // each joint each frame.
+  PT(EggGroup) tgroup = new EggGroup;
+
+  int num_nodes = _tree.get_num_nodes();
+  int i;
+
+  //  MTime frame(start_frame, MTime::uiUnit());
+  //  MTime frame_stop(end_frame, MTime::uiUnit());
+  // start at first frame and go to last
+  for ( frame = start_frame; frame <= end_frame; frame += frame_inc) {
+    SAA_frame2Seconds( &scene, frame, &time );
+    SAA_updatelistEvalScene( &scene, time );
+    cout << "\n> animating frame " << frame << endl;
+
+    //    if (softegg_cat.is_debug()) {
+    //      softegg_cat.debug(false)
+    softegg_cat.info() << "frame " << time << "\n";
+    //} else {
+      // We have to write to cerr instead of softegg_cat to allow
+      // flushing without writing a newline.
+    //      cerr << "." << flush;
+    //    }
+    //    MGlobal::viewFrame(frame);
+
+    for (i = 0; i < num_nodes; i++) {
+      SoftNodeDesc *node_desc = _tree.get_node(i);
+      if (node_desc->is_joint()) {
+        if (softegg_cat.is_spam()) {
+          softegg_cat.spam()
+            << "joint " << node_desc->get_name() << "\n";
+        }
+        EggXfmSAnim *anim = _tree.get_egg_anim(node_desc);
+        // following function fills in the anim structure
+        node_desc->get_joint_transform(&scene, tgroup, anim);
+      }
+    }
+
+    //    frame += frame_inc;
+  }
+
+  // Now optimize all of the tables we just filled up, for no real
+  // good reason, except that it makes the resulting egg file a little
+  // easier to read.
+  for (i = 0; i < num_nodes; i++) {
+    SoftNodeDesc *node_desc = _tree.get_node(i);
+    if (node_desc->is_joint()) {
+      _tree.get_egg_anim(node_desc)->optimize();
+    }
+  }
+
+  softegg_cat.info(false)
+    << "\n";
+
+  return true;
+}
+
 ////////////////////////////////////////////////////////////////////
 //     Function: SoftToEggConverter::convert_hierarchy
 //       Access: Private
@@ -795,10 +818,12 @@ convert_hierarchy(EggGroupNode *egg_root) {
   int num_nodes = _tree.get_num_nodes();
 
   _tree.clear_egg(&get_egg_data(), egg_root, NULL);
+  cout << "num_nodes = " << num_nodes << endl;
   for (int i = 0; i < num_nodes; i++) {
     if (!process_model_node(_tree.get_node(i))) {
       return false;
     }
+    softegg_cat.info() << i << endl;
   }
   return true;
 }
@@ -814,10 +839,11 @@ convert_hierarchy(EggGroupNode *egg_root) {
 bool SoftToEggConverter::
 process_model_node(SoftNodeDesc *node_desc) {
   EggGroup *egg_group = NULL;
-  char *name = NULL;
+  const char *name = NULL;
   char *fullname = NULL;
   SAA_ModelType type;
 
+#if 0
   // Get the name of the model
   if ( use_prefix ) {
     // Get the FULL name of the model
@@ -827,15 +853,17 @@ process_model_node(SoftNodeDesc *node_desc) {
     // Get the name of the trim curve
     name = _tree.GetName( &scene, node_desc->get_model() );
   }
+#endif
+  name = node_desc->get_name().c_str();
   cout << "element name <" << name << ">\n";
 
   // find out what type of node we're dealing with
   result = SAA_modelGetType( &scene, node_desc->get_model(), &type );
+  egg_group = _tree.get_egg_group(node_desc);
   cout << "encountered ";
   switch(type){
   case SAA_MNILL:
     cout << "null\n";
-    egg_group = _tree.get_egg_group(node_desc);
     node_desc->get_transform(&scene, egg_group);
     handle_null(node_desc->get_model(), egg_group, type, name);
     break;
@@ -847,9 +875,8 @@ process_model_node(SoftNodeDesc *node_desc) {
     break;
   case SAA_MSMSH:
     cout << "mesh\n";
-    egg_group = _tree.get_egg_group(node_desc);
     node_desc->get_transform(&scene, egg_group);
-    make_polyset(node_desc, egg_group, type, name);
+    make_polyset(node_desc, egg_group, type);
     break;
   case SAA_MJNT:
     cout << "joint\n";
@@ -873,6 +900,9 @@ process_model_node(SoftNodeDesc *node_desc) {
     cout << "unknown type: " << type << "\n";
   }
 
+  if (node_desc->is_joint())
+    node_desc->get_transform(&scene, egg_group, TRUE);
+
   return true;
 }
 
@@ -884,8 +914,8 @@ process_model_node(SoftNodeDesc *node_desc) {
 //               group.
 ////////////////////////////////////////////////////////////////////
 void SoftToEggConverter::
-make_polyset(SoftNodeDesc *node_desc, EggGroup *egg_group, SAA_ModelType type, char *node_name) {
-  string name = node_name;
+make_polyset(SoftNodeDesc *node_desc, EggGroup *egg_group, SAA_ModelType type) {
+  string name = node_desc->get_name();
   int id = 0;
 
   float *uCoords = NULL;
@@ -915,7 +945,7 @@ make_polyset(SoftNodeDesc *node_desc, EggGroup *egg_group, SAA_ModelType type, c
        )
     {
       // load all node data from soft for this node_desc
-      node_desc->load_model(&scene, type, node_name);
+      node_desc->load_model(&scene, type);
 
       string vpool_name = name + ".verts";
       EggVertexPool *vpool = new EggVertexPool(vpool_name);
@@ -1073,12 +1103,20 @@ make_polyset(SoftNodeDesc *node_desc, EggGroup *egg_group, SAA_ModelType type, c
         
         // Now apply the shader.
         if (node_desc->textures != NULL) {
-          if (node_desc->numTexLoc)
-            set_shader_attributes(node_desc, *egg_poly, node_desc->texNameArray[idx]);
-          else
-            set_shader_attributes(node_desc, *egg_poly, node_desc->texNameArray[0]);
+          if (node_desc->numTexLoc) {
+            if (!strstr(node_desc->texNameArray[idx], "noIcon"))
+              set_shader_attributes(node_desc, *egg_poly, node_desc->texNameArray[idx]);
+            else
+              cout << "texname :" << node_desc->texNameArray[idx] << endl;
+          }
+          else {
+            if (!strstr(node_desc->texNameArray[0], "noIcon"))
+              set_shader_attributes(node_desc, *egg_poly, node_desc->texNameArray[0]);
+            else 
+              cout << "texname :" << node_desc->texNameArray[0] << endl;
         }
       }
+      }
 #if 0
   come back to it later
   // Now that we've added all the polygons (and created all the
@@ -1129,8 +1167,8 @@ make_polyset(SoftNodeDesc *node_desc, EggGroup *egg_group, SAA_ModelType type, c
 //               group.
 ////////////////////////////////////////////////////////////////////
 void SoftToEggConverter::
-handle_null(SAA_Elem *model, EggGroup *egg_group, SAA_ModelType type, char *node_name) {
-  char *name = node_name;
+handle_null(SAA_Elem *model, EggGroup *egg_group, SAA_ModelType type, const char *node_name) {
+  const char *name = node_name;
   SAA_AlgorithmType    algo;
   
   SAA_modelGetAlgorithm( &scene, model, &algo );

+ 3 - 4
pandatool/src/softegg/softToEggConverter.h

@@ -81,8 +81,7 @@ private:
                     double frame_inc, double output_frame_rate);
 
   bool convert_char_model();
-  bool convert_char_chan(double start_frame, double end_frame, 
-                         double frame_inc, double output_frame_rate);
+  bool convert_char_chan();
   bool convert_hierarchy(EggGroupNode *egg_root);
   bool process_model_node(SoftNodeDesc *node_desc);
 
@@ -103,8 +102,8 @@ private:
                         const MFnNurbsCurve &curve,
                         EggGroup *group);
   */
-  void make_polyset(SoftNodeDesc *node_Desc, EggGroup *egg_group, SAA_ModelType type, char *node_name);
-  void handle_null(SAA_Elem *model, EggGroup *egg_group, SAA_ModelType type, char *node_name);
+  void make_polyset(SoftNodeDesc *node_Desc, EggGroup *egg_group, SAA_ModelType type);
+  void handle_null(SAA_Elem *model, EggGroup *egg_group, SAA_ModelType type, const char *node_name);
   /*
   void make_locator(const MDagPath &dag_path, const MFnDagNode &dag_node,
                     EggGroup *egg_group);