Browse Source

first pass multi-texture support on maya2egg. Bugs are expected, please report to asad, if you see some model problems

Asad M. Zaman 21 years ago
parent
commit
1c6c6f4cda

+ 54 - 22
pandatool/src/maya/mayaShader.cxx

@@ -55,7 +55,6 @@ MayaShader(MObject engine) {
   if (!shader_plug.isNull()) {
   if (!shader_plug.isNull()) {
     MPlugArray shader_pa;
     MPlugArray shader_pa;
     shader_plug.connectedTo(shader_pa, true, false);
     shader_plug.connectedTo(shader_pa, true, false);
-
     for (size_t i = 0; i < shader_pa.length() && !found_shader; i++) {
     for (size_t i = 0; i < shader_pa.length() && !found_shader; i++) {
       MObject shader = shader_pa[0].node();
       MObject shader = shader_pa[0].node();
       found_shader = read_surface_shader(shader);
       found_shader = read_surface_shader(shader);
@@ -70,6 +69,9 @@ MayaShader(MObject engine) {
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 MayaShader::
 MayaShader::
 ~MayaShader() {
 ~MayaShader() {
+  for (size_t i=0; i<_color.size(); ++i) {
+    _color.pop_back();
+  }
 }
 }
 
 
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
@@ -91,11 +93,23 @@ void MayaShader::
 write(ostream &out) const {
 write(ostream &out) const {
   out << "Shader " << get_name() << "\n"
   out << "Shader " << get_name() << "\n"
       << "  color:\n";
       << "  color:\n";
-  _color.write(out);
+  for (size_t i=0; i<_color.size(); ++i) {
+    _color[i]->write(out);
+  }
   out << "  transparency:\n";
   out << "  transparency:\n";
   _transparency.write(out);
   _transparency.write(out);
 }
 }
 
 
+////////////////////////////////////////////////////////////////////
+//     Function: MayaShader::get_color_def
+//       Access: Public
+//  Description: Now that the shaders can have multiple textures
+//               return the color def i.e. texture at idx
+////////////////////////////////////////////////////////////////////
+MayaShaderColorDef *MayaShader::
+get_color_def(size_t idx) const {
+  return _color[idx];
+}
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 //     Function: MayaShader::get_rgba
 //     Function: MayaShader::get_rgba
 //       Access: Public
 //       Access: Public
@@ -110,13 +124,13 @@ write(ostream &out) const {
 //               is true), this value is not used by Maya.
 //               is true), this value is not used by Maya.
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 Colorf MayaShader::
 Colorf MayaShader::
-get_rgba() const {
+get_rgba(size_t idx) const {
   Colorf rgba(1.0f, 1.0f, 1.0f, 1.0f);
   Colorf rgba(1.0f, 1.0f, 1.0f, 1.0f);
 
 
-  if (_color._has_flat_color) {
-    rgba[0] = (float)_color._flat_color[0];
-    rgba[1] = (float)_color._flat_color[1];
-    rgba[2] = (float)_color._flat_color[2];
+  if (_color[idx]->_has_flat_color) {
+    rgba[0] = (float)_color[idx]->_flat_color[0];
+    rgba[1] = (float)_color[idx]->_flat_color[1];
+    rgba[2] = (float)_color[idx]->_flat_color[2];
   }
   }
 
 
   if (_transparency._has_flat_color) {
   if (_transparency._has_flat_color) {
@@ -143,7 +157,7 @@ bool MayaShader::
 read_surface_shader(MObject shader) {
 read_surface_shader(MObject shader) {
   MStatus status;
   MStatus status;
   MFnDependencyNode shader_fn(shader);
   MFnDependencyNode shader_fn(shader);
-
+  
   if (maya_cat.is_spam()) {
   if (maya_cat.is_spam()) {
     maya_cat.spam()
     maya_cat.spam()
       << "  Reading surface shader " << shader_fn.name().asChar() << "\n";
       << "  Reading surface shader " << shader_fn.name().asChar() << "\n";
@@ -160,13 +174,21 @@ read_surface_shader(MObject shader) {
     // used.
     // used.
     color_plug = shader_fn.findPlug("outColor");
     color_plug = shader_fn.findPlug("outColor");
   }
   }
-    
+
   if (!color_plug.isNull()) {
   if (!color_plug.isNull()) {
     MPlugArray color_pa;
     MPlugArray color_pa;
     color_plug.connectedTo(color_pa, true, false);
     color_plug.connectedTo(color_pa, true, false);
 
 
+    MayaShaderColorDef *color_p = new MayaShaderColorDef;
     for (size_t i = 0; i < color_pa.length(); i++) {
     for (size_t i = 0; i < color_pa.length(); i++) {
-      _color.read_surface_color(this, color_pa[0].node());
+      maya_cat.spam() << "color_pa[" << i << "]:" << color_pa[i].name() << endl;
+      color_p->read_surface_color(this, color_pa[0].node());
+    }
+
+    if (color_pa.length() < 1) {
+      // assign a blank default color to this shader
+      maya_cat.spam() << shader_fn.name().asChar() << " was not connected to texture" << endl;
+      this->_color.push_back(color_p);
     }
     }
   }
   }
 
 
@@ -181,32 +203,42 @@ read_surface_shader(MObject shader) {
     trans_plug.connectedTo(trans_pa, true, false);
     trans_plug.connectedTo(trans_pa, true, false);
 
 
     for (size_t i = 0; i < trans_pa.length(); i++) {
     for (size_t i = 0; i < trans_pa.length(); i++) {
-      _transparency.read_surface_color(this, trans_pa[0].node());
+      maya_cat.spam() << "read a transparency texture" << endl;
+      _transparency.read_surface_color(this, trans_pa[0].node(), true);
     }
     }
   }
   }
 
 
   // Also try to get the ordinary color directly from the surface
   // Also try to get the ordinary color directly from the surface
   // shader.
   // shader.
+  bool b_color_def = true;
   if (shader.hasFn(MFn::kLambert)) {
   if (shader.hasFn(MFn::kLambert)) {
     MFnLambertShader lambert_fn(shader);
     MFnLambertShader lambert_fn(shader);
     MColor color = lambert_fn.color(&status);
     MColor color = lambert_fn.color(&status);
     if (status) {
     if (status) {
       // Warning! The alpha component of color doesn't mean
       // Warning! The alpha component of color doesn't mean
       // transparency in Maya.
       // transparency in Maya.
-      _color._has_flat_color = true;
-      _color._flat_color.set(color.r, color.g, color.b, color.a);
-      _transparency._flat_color.set(0.0, 0.0, 0.0, 0.0);
-
-      // Get the transparency separately.
-      color = lambert_fn.transparency(&status);
-      if (status) {
-        _transparency._has_flat_color = true;
-        _transparency._flat_color.set(color.r, color.g, color.b, color.a);
+      for (size_t i=0; i<_color.size(); ++i) {
+        _color[i]->_has_flat_color = true;
+        _color[i]->_flat_color.set(color.r, color.g, color.b, color.a);
+        maya_cat.spam() << shader_fn.name().asChar() << " set shader color" << endl;
+        // needed to print the final check
+        if (!_color[i]->_has_flat_color && !_color[i]->_has_texture)
+          b_color_def = false;
+
+        _transparency._flat_color.set(0.0, 0.0, 0.0, 0.0);
+        
+        // Get the transparency separately.
+        color = lambert_fn.transparency(&status);
+        if (status) {
+          _transparency._has_flat_color = true;
+          _transparency._flat_color.set(color.r, color.g, color.b, color.a);
+        }
       }
       }
     }
     }
   }
   }
-
-  if (!_color._has_flat_color && !_color._has_texture) {
+  //  if (!_color._has_flat_color && !_color._has_texture) {
+  if (!b_color_def) {
+    maya_cat.info() << shader_fn.name().asChar() << "Color def not found" << endl;
     if (maya_cat.is_spam()) {
     if (maya_cat.is_spam()) {
       maya_cat.spam()
       maya_cat.spam()
         << "  Color definition not found.\n";
         << "  Color definition not found.\n";

+ 6 - 2
pandatool/src/maya/mayaShader.h

@@ -44,10 +44,14 @@ public:
   void output(ostream &out) const;
   void output(ostream &out) const;
   void write(ostream &out) const;
   void write(ostream &out) const;
 
 
-  Colorf get_rgba() const;
+  Colorf get_rgba(size_t idx=0) const;
+  MayaShaderColorDef *get_color_def(size_t idx=0) const;
 
 
-  MayaShaderColorDef _color;
   MayaShaderColorDef _transparency;
   MayaShaderColorDef _transparency;
+  //MayaShaderColorDef _color;
+  // There could be multiple textures, so create an array of these colordefs
+  typedef pvector<MayaShaderColorDef *> ColorDef;
+  ColorDef _color;
 
 
 private:
 private:
   bool read_surface_shader(MObject shader);
   bool read_surface_shader(MObject shader);

+ 107 - 6
pandatool/src/maya/mayaShaderColorDef.cxx

@@ -44,6 +44,8 @@ MayaShaderColorDef() {
   _flat_color.set(0.0, 0.0, 0.0, 0.0);
   _flat_color.set(0.0, 0.0, 0.0, 0.0);
 
 
   _has_texture = false;
   _has_texture = false;
+  _texture_name = "";
+  _uvset_name = "map1";
   _projection_type = PT_off;
   _projection_type = PT_off;
   _map_uvs = NULL;
   _map_uvs = NULL;
 
 
@@ -63,6 +65,44 @@ MayaShaderColorDef() {
   _color_object = (MObject *)NULL;
   _color_object = (MObject *)NULL;
 }
 }
 
 
+////////////////////////////////////////////////////////////////////
+//     Function: MayaShaderColorDef::Constructor
+//       Access: Public
+//  Description: 
+////////////////////////////////////////////////////////////////////
+MayaShaderColorDef::
+MayaShaderColorDef(MayaShaderColorDef &copy) {
+  _has_texture = copy._has_texture;
+  _texture_filename = copy._texture_filename;
+  _texture_name = copy._texture_name;
+  _uvset_name = copy._uvset_name;
+  _color_gain = copy._color_gain;
+
+  _has_flat_color = copy._has_flat_color;
+  _flat_color = copy._flat_color;
+
+  _projection_type = copy._projection_type;
+  _projection_matrix = copy._projection_matrix;
+  _u_angle = copy._u_angle;
+  _v_angle = copy._v_angle;
+
+  _coverage = copy._coverage;
+  _translate_frame = copy._translate_frame;
+  _rotate_frame = copy._rotate_frame;
+
+  _mirror = copy._mirror;
+  _stagger = copy._stagger;
+  _wrap_u = copy._wrap_u;
+  _wrap_v = copy._wrap_v;
+
+  _repeat_uv = copy._repeat_uv;
+  _offset = copy._offset;
+  _rotate_uv = copy._rotate_uv;
+
+  _map_uvs = copy._map_uvs;
+  _color_object = copy._color_object;
+}
+
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 //     Function: MayaShaderColorDef::Destructor
 //     Function: MayaShaderColorDef::Destructor
 //       Access: Public
 //       Access: Public
@@ -130,7 +170,9 @@ project_uv(const LPoint3d &pos, const LPoint3d &centroid) const {
 void MayaShaderColorDef::
 void MayaShaderColorDef::
 write(ostream &out) const {
 write(ostream &out) const {
   if (_has_texture) {
   if (_has_texture) {
-    out << "    texture is " << _texture << "\n"
+    out << "    texture filename is " << _texture_filename << "\n"
+        << "    texture name is " << _texture_name << "\n"
+        << "    uv_set name is " << _uvset_name << "\n"
         << "    coverage is " << _coverage << "\n"
         << "    coverage is " << _coverage << "\n"
         << "    translate_frame is " << _translate_frame << "\n"
         << "    translate_frame is " << _translate_frame << "\n"
         << "    rotate_frame is " << _rotate_frame << "\n"
         << "    rotate_frame is " << _rotate_frame << "\n"
@@ -159,7 +201,7 @@ reset_maya_texture(const Filename &texture) {
   if (_color_object != (MObject *)NULL) {
   if (_color_object != (MObject *)NULL) {
     _has_texture = set_string_attribute(*_color_object, "fileTextureName", 
     _has_texture = set_string_attribute(*_color_object, "fileTextureName", 
                                         texture.to_os_generic());
                                         texture.to_os_generic());
-    _texture = texture;
+    _texture_filename = texture;
 
 
     if (!_has_texture) {
     if (!_has_texture) {
       maya_cat.error()
       maya_cat.error()
@@ -182,7 +224,7 @@ reset_maya_texture(const Filename &texture) {
 //               properties.
 //               properties.
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 void MayaShaderColorDef::
 void MayaShaderColorDef::
-read_surface_color(const MayaShader *shader, MObject color) {
+read_surface_color(MayaShader *shader, MObject color, bool trans) {
   RGBColorf color_gain;
   RGBColorf color_gain;
   if (get_vec3f_attribute(color, "colorGain", color_gain)) {
   if (get_vec3f_attribute(color, "colorGain", color_gain)) {
     _color_gain[0] *= color_gain[0];
     _color_gain[0] *= color_gain[0];
@@ -193,15 +235,14 @@ read_surface_color(const MayaShader *shader, MObject color) {
   if (get_maya_attribute(color, "alphaGain", alpha_gain)) {
   if (get_maya_attribute(color, "alphaGain", alpha_gain)) {
     _color_gain[3] *= alpha_gain;
     _color_gain[3] *= alpha_gain;
   }
   }
-
   if (color.hasFn(MFn::kFileTexture)) {
   if (color.hasFn(MFn::kFileTexture)) {
     _color_object = new MObject(color);
     _color_object = new MObject(color);
     string filename;
     string filename;
     _has_texture = get_string_attribute(color, "fileTextureName", filename);
     _has_texture = get_string_attribute(color, "fileTextureName", filename);
     _has_texture = _has_texture && !filename.empty();
     _has_texture = _has_texture && !filename.empty();
     if (_has_texture) {
     if (_has_texture) {
-      _texture = Filename::from_os_specific(filename);
-      if (_texture.is_directory()) {
+      _texture_filename = Filename::from_os_specific(filename);
+      if (_texture_filename.is_directory()) {
         maya_cat.warning()
         maya_cat.warning()
           << "Shader " << shader->get_name() 
           << "Shader " << shader->get_name() 
           << " references texture filename " << filename
           << " references texture filename " << filename
@@ -224,7 +265,13 @@ read_surface_color(const MayaShader *shader, MObject color) {
     get_vec2f_attribute(color, "offset", _offset);
     get_vec2f_attribute(color, "offset", _offset);
     get_angle_attribute(color, "rotateUV", _rotate_uv);
     get_angle_attribute(color, "rotateUV", _rotate_uv);
 
 
+    if (!trans) {
+      maya_cat.debug() << "pushed a file texture" << endl;
+      shader->_color.push_back(this);
+    }
+
   } else if (color.hasFn(MFn::kProjection)) {
   } else if (color.hasFn(MFn::kProjection)) {
+    maya_cat.debug() << "reading a projection texture" << endl;
     // This is a projected texture.  We will have to step one level
     // This is a projected texture.  We will have to step one level
     // deeper to find the actual texture.
     // deeper to find the actual texture.
     MFnDependencyNode projection_fn(color);
     MFnDependencyNode projection_fn(color);
@@ -256,6 +303,60 @@ read_surface_color(const MayaShader *shader, MObject color) {
       set_projection_type(type);
       set_projection_type(type);
     }
     }
 
 
+  } else if (color.hasFn(MFn::kLayeredTexture)) {
+    maya_cat.debug() << "Found layered texture" << endl;
+    //list_maya_attributes(color);
+    //shader->_multi_texture = true;
+    //get_enum_attribute(color,"blendMode",shader->_blend_mode);
+    //maya_cat.debug() << "blend mode :" << shader->_blend_mode << endl;
+    MFnDependencyNode layered_fn(color);
+    MPlugArray color_pa;
+    MStatus status = layered_fn.getConnections(color_pa);
+    maya_cat.debug() << "number of connections: " << color_pa.length() << endl;
+    bool first = true;
+    for (size_t i=0; i<color_pa.length(); ++i) {
+      MPlug pl = color_pa[i];
+      MPlugArray pla;
+      pl.connectedTo(pla, true, false);
+      for (size_t j=0; j<pla.length(); ++j) {
+        //maya_cat.debug() << pl.name() << " is(pl) " << pl.node().apiTypeStr() << endl;
+        //maya_cat.debug() << pla[j].name() << " is(pla) " << pla[j].node().apiTypeStr() << endl;
+        if (!first) {
+          maya_cat.debug() << pl.name() << "next:connectedTo: " << pla[j].name() << endl;
+          MayaShaderColorDef *color_p = new MayaShaderColorDef;
+          color_p->read_surface_color(shader, pla[j].node());
+          color_p->_texture_name.assign(pla[j].name().asChar());
+          int loc = color_p->_texture_name.find('.',0);
+          if( loc != string::npos )
+            color_p->_texture_name.resize(loc);
+          maya_cat.debug() << "uv_name : " << color_p->_texture_name << endl;
+        }
+        else {
+          maya_cat.debug() << pl.name() << " first:connectedTo: " << pla[j].name() << endl;
+          read_surface_color(shader, pla[j].node());
+          _texture_name.assign(pla[j].name().asChar());
+          int loc = _texture_name.find('.',0);
+          if( loc != string::npos )
+            _texture_name.resize(loc);
+          maya_cat.debug() << "uv_name : " << _texture_name << endl;
+          first = false;
+        }
+
+        // lets see what this is connected to!?
+        MPlug pl_temp = pla[j];
+        MPlugArray pla_temp;
+        pl_temp.connectedTo(pla_temp, true, false);
+        maya_cat.debug() << pl_temp.name() << "connectedTo:" << pla_temp.length() << " plugs\n";
+      }
+      /*
+      string blah;
+      get_enum_attribute(pl.node(),"blendMode",blah);
+      maya_cat.debug() << "blend mode :" << blah << endl;
+      float alpha;
+      get_maya_attribute(pl.node(),"alpha",alpha);
+      maya_cat.debug() << "alpha :" << alpha << endl;
+      */
+    }
   } else {
   } else {
     // This shader wasn't understood.
     // This shader wasn't understood.
     if (maya_cat.is_debug()) {
     if (maya_cat.is_debug()) {

+ 5 - 2
pandatool/src/maya/mayaShaderColorDef.h

@@ -36,6 +36,7 @@ class MayaShader;
 class MayaShaderColorDef {
 class MayaShaderColorDef {
 public:
 public:
   MayaShaderColorDef();
   MayaShaderColorDef();
+  MayaShaderColorDef(MayaShaderColorDef&);
   ~MayaShaderColorDef();
   ~MayaShaderColorDef();
   
   
   LMatrix3d compute_texture_matrix() const;
   LMatrix3d compute_texture_matrix() const;
@@ -58,7 +59,9 @@ public:
   };
   };
 
 
   bool _has_texture;
   bool _has_texture;
-  Filename _texture;
+  Filename _texture_filename;
+  string _texture_name;
+  string _uvset_name;
   Colorf _color_gain;
   Colorf _color_gain;
   
   
   bool _has_flat_color;
   bool _has_flat_color;
@@ -83,7 +86,7 @@ public:
   double _rotate_uv;
   double _rotate_uv;
   
   
 private:
 private:
-  void read_surface_color(const MayaShader *shader, MObject color);
+  void read_surface_color(MayaShader *shader, MObject color, bool trans=false);
   void set_projection_type(const string &type);
   void set_projection_type(const string &type);
 
 
   LPoint2d map_planar(const LPoint3d &pos, const LPoint3d &centroid) const;
   LPoint2d map_planar(const LPoint3d &pos, const LPoint3d &centroid) const;

+ 89 - 29
pandatool/src/maya/maya_funcs.cxx

@@ -29,7 +29,9 @@
 #include <maya/MPlug.h>
 #include <maya/MPlug.h>
 #include <maya/MFnAttribute.h>
 #include <maya/MFnAttribute.h>
 #include <maya/MFnTypedAttribute.h>
 #include <maya/MFnTypedAttribute.h>
+#include <maya/MFnNumericAttribute.h>
 #include <maya/MFnEnumAttribute.h>
 #include <maya/MFnEnumAttribute.h>
+#include <maya/MFnCompoundAttribute.h>
 #include <maya/MFnMatrixData.h>
 #include <maya/MFnMatrixData.h>
 #include <maya/MMatrix.h>
 #include <maya/MMatrix.h>
 #include "post_maya_include.h"
 #include "post_maya_include.h"
@@ -170,7 +172,7 @@ get_bool_attribute(MObject &node, const string &attribute_name,
   }
   }
 
 
   if (!get_maya_attribute(node, attribute_name, value)) {
   if (!get_maya_attribute(node, attribute_name, value)) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Attribute " << attribute_name
       << "Attribute " << attribute_name
       << " does not have a bool value.\n";
       << " does not have a bool value.\n";
     describe_maya_attribute(node, attribute_name);
     describe_maya_attribute(node, attribute_name);
@@ -189,7 +191,7 @@ get_angle_attribute(MObject &node, const string &attribute_name,
                     double &value) {
                     double &value) {
   MAngle maya_value;
   MAngle maya_value;
   if (!get_maya_attribute(node, attribute_name, maya_value)) {
   if (!get_maya_attribute(node, attribute_name, maya_value)) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Attribute " << attribute_name
       << "Attribute " << attribute_name
       << " does not have an angle value.\n";
       << " does not have an angle value.\n";
     describe_maya_attribute(node, attribute_name);
     describe_maya_attribute(node, attribute_name);
@@ -211,7 +213,7 @@ get_vec2f_attribute(MObject &node, const string &attribute_name,
 
 
   MObject vec2f_object;
   MObject vec2f_object;
   if (!get_maya_attribute(node, attribute_name, vec2f_object)) {
   if (!get_maya_attribute(node, attribute_name, vec2f_object)) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Attribute " << attribute_name
       << "Attribute " << attribute_name
       << " does not have a vec2f object value.\n";
       << " does not have a vec2f object value.\n";
     describe_maya_attribute(node, attribute_name);
     describe_maya_attribute(node, attribute_name);
@@ -220,7 +222,7 @@ get_vec2f_attribute(MObject &node, const string &attribute_name,
 
 
   MFnNumericData data(vec2f_object, &status);
   MFnNumericData data(vec2f_object, &status);
   if (!status) {
   if (!status) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Attribute " << attribute_name << " is of type "
       << "Attribute " << attribute_name << " is of type "
       << vec2f_object.apiTypeStr() << ", not a NumericData.\n";
       << vec2f_object.apiTypeStr() << ", not a NumericData.\n";
     return false;
     return false;
@@ -228,7 +230,7 @@ get_vec2f_attribute(MObject &node, const string &attribute_name,
 
 
   status = data.getData(value[0], value[1]);
   status = data.getData(value[0], value[1]);
   if (!status) {
   if (!status) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Unable to extract 2 floats from " << attribute_name
       << "Unable to extract 2 floats from " << attribute_name
       << ", of type " << vec2f_object.apiTypeStr() << "\n";
       << ", of type " << vec2f_object.apiTypeStr() << "\n";
   }
   }
@@ -248,7 +250,7 @@ get_vec3f_attribute(MObject &node, const string &attribute_name,
 
 
   MObject vec3f_object;
   MObject vec3f_object;
   if (!get_maya_attribute(node, attribute_name, vec3f_object)) {
   if (!get_maya_attribute(node, attribute_name, vec3f_object)) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Attribute " << attribute_name
       << "Attribute " << attribute_name
       << " does not have a vec3f object value.\n";
       << " does not have a vec3f object value.\n";
     describe_maya_attribute(node, attribute_name);
     describe_maya_attribute(node, attribute_name);
@@ -257,7 +259,7 @@ get_vec3f_attribute(MObject &node, const string &attribute_name,
 
 
   MFnNumericData data(vec3f_object, &status);
   MFnNumericData data(vec3f_object, &status);
   if (!status) {
   if (!status) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Attribute " << attribute_name << " is of type "
       << "Attribute " << attribute_name << " is of type "
       << vec3f_object.apiTypeStr() << ", not a NumericData.\n";
       << vec3f_object.apiTypeStr() << ", not a NumericData.\n";
     return false;
     return false;
@@ -265,7 +267,7 @@ get_vec3f_attribute(MObject &node, const string &attribute_name,
 
 
   status = data.getData(value[0], value[1], value[2]);
   status = data.getData(value[0], value[1], value[2]);
   if (!status) {
   if (!status) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Unable to extract 3 floats from " << attribute_name
       << "Unable to extract 3 floats from " << attribute_name
       << ", of type " << vec3f_object.apiTypeStr() << "\n";
       << ", of type " << vec3f_object.apiTypeStr() << "\n";
   }
   }
@@ -285,7 +287,7 @@ get_vec2d_attribute(MObject &node, const string &attribute_name,
 
 
   MObject vec2d_object;
   MObject vec2d_object;
   if (!get_maya_attribute(node, attribute_name, vec2d_object)) {
   if (!get_maya_attribute(node, attribute_name, vec2d_object)) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Attribute " << attribute_name
       << "Attribute " << attribute_name
       << " does not have a vec2d object value.\n";
       << " does not have a vec2d object value.\n";
     describe_maya_attribute(node, attribute_name);
     describe_maya_attribute(node, attribute_name);
@@ -294,7 +296,7 @@ get_vec2d_attribute(MObject &node, const string &attribute_name,
 
 
   MFnNumericData data(vec2d_object, &status);
   MFnNumericData data(vec2d_object, &status);
   if (!status) {
   if (!status) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Attribute " << attribute_name << " is of type "
       << "Attribute " << attribute_name << " is of type "
       << vec2d_object.apiTypeStr() << ", not a NumericData.\n";
       << vec2d_object.apiTypeStr() << ", not a NumericData.\n";
     return false;
     return false;
@@ -302,7 +304,7 @@ get_vec2d_attribute(MObject &node, const string &attribute_name,
 
 
   status = data.getData(value[0], value[1]);
   status = data.getData(value[0], value[1]);
   if (!status) {
   if (!status) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Unable to extract 2 doubles from " << attribute_name
       << "Unable to extract 2 doubles from " << attribute_name
       << ", of type " << vec2d_object.apiTypeStr() << "\n";
       << ", of type " << vec2d_object.apiTypeStr() << "\n";
   }
   }
@@ -322,7 +324,7 @@ get_vec3d_attribute(MObject &node, const string &attribute_name,
 
 
   MObject vec3d_object;
   MObject vec3d_object;
   if (!get_maya_attribute(node, attribute_name, vec3d_object)) {
   if (!get_maya_attribute(node, attribute_name, vec3d_object)) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Attribute " << attribute_name
       << "Attribute " << attribute_name
       << " does not have a vec3d object value.\n";
       << " does not have a vec3d object value.\n";
     describe_maya_attribute(node, attribute_name);
     describe_maya_attribute(node, attribute_name);
@@ -331,7 +333,7 @@ get_vec3d_attribute(MObject &node, const string &attribute_name,
 
 
   MFnNumericData data(vec3d_object, &status);
   MFnNumericData data(vec3d_object, &status);
   if (!status) {
   if (!status) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Attribute " << attribute_name << " is of type "
       << "Attribute " << attribute_name << " is of type "
       << vec3d_object.apiTypeStr() << ", not a NumericData.\n";
       << vec3d_object.apiTypeStr() << ", not a NumericData.\n";
     return false;
     return false;
@@ -339,7 +341,7 @@ get_vec3d_attribute(MObject &node, const string &attribute_name,
 
 
   status = data.getData(value[0], value[1], value[2]);
   status = data.getData(value[0], value[1], value[2]);
   if (!status) {
   if (!status) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Unable to extract 3 doubles from " << attribute_name
       << "Unable to extract 3 doubles from " << attribute_name
       << ", of type " << vec3d_object.apiTypeStr() << "\n";
       << ", of type " << vec3d_object.apiTypeStr() << "\n";
   }
   }
@@ -362,7 +364,7 @@ get_mat4d_attribute(MObject &node, const string &attribute_name,
 
 
   MFnMatrixData matrix_data(matrix, &status);
   MFnMatrixData matrix_data(matrix, &status);
   if (!status) {
   if (!status) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Attribute " << attribute_name << " is of type "
       << "Attribute " << attribute_name << " is of type "
       << node.apiTypeStr() << ", not a Matrix.\n";
       << node.apiTypeStr() << ", not a Matrix.\n";
     return false;
     return false;
@@ -395,7 +397,7 @@ get_enum_attribute(MObject &node, const string &attribute_name,
   MObject attrib = plug.attribute();
   MObject attrib = plug.attribute();
   MFnEnumAttribute enum_attrib(attrib, &status);
   MFnEnumAttribute enum_attrib(attrib, &status);
   if (!status) {
   if (!status) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Not an enum attribute: " << attribute_name << "\n";
       << "Not an enum attribute: " << attribute_name << "\n";
     return false;
     return false;
   }
   }
@@ -403,7 +405,7 @@ get_enum_attribute(MObject &node, const string &attribute_name,
   short index;
   short index;
   status = plug.getValue(index);
   status = plug.getValue(index);
   if (!status) {
   if (!status) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Could not get numeric value of " << attribute_name << "\n";
       << "Could not get numeric value of " << attribute_name << "\n";
     status.perror("MPlug::getValue(short)");
     status.perror("MPlug::getValue(short)");
     return false;
     return false;
@@ -411,7 +413,7 @@ get_enum_attribute(MObject &node, const string &attribute_name,
 
 
   MString name = enum_attrib.fieldName(index, &status);
   MString name = enum_attrib.fieldName(index, &status);
   if (!status) {
   if (!status) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Invalid value for " << attribute_name << ": " << index << "\n";
       << "Invalid value for " << attribute_name << ": " << index << "\n";
     status.perror("MFnEnumAttribute::fieldName()");
     status.perror("MFnEnumAttribute::fieldName()");
     return false;
     return false;
@@ -433,7 +435,7 @@ get_string_attribute(MObject &node, const string &attribute_name,
 
 
   MObject string_object;
   MObject string_object;
   if (!get_maya_attribute(node, attribute_name, string_object)) {
   if (!get_maya_attribute(node, attribute_name, string_object)) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Attribute " << attribute_name
       << "Attribute " << attribute_name
       << " does not have an string object value.\n";
       << " does not have an string object value.\n";
     describe_maya_attribute(node, attribute_name);
     describe_maya_attribute(node, attribute_name);
@@ -442,7 +444,7 @@ get_string_attribute(MObject &node, const string &attribute_name,
 
 
   MFnStringData data(string_object, &status);
   MFnStringData data(string_object, &status);
   if (!status) {
   if (!status) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Attribute " << attribute_name << " is of type "
       << "Attribute " << attribute_name << " is of type "
       << string_object.apiTypeStr() << ", not a StringData.\n";
       << string_object.apiTypeStr() << ", not a StringData.\n";
     return false;
     return false;
@@ -465,7 +467,7 @@ set_string_attribute(MObject &node, const string &attribute_name,
   // First, we get the string_object, then we set its string.
   // First, we get the string_object, then we set its string.
   MObject string_object;
   MObject string_object;
   if (!get_maya_attribute(node, attribute_name, string_object)) {
   if (!get_maya_attribute(node, attribute_name, string_object)) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Attribute " << attribute_name
       << "Attribute " << attribute_name
       << " does not have a string object value.\n";
       << " does not have a string object value.\n";
     describe_maya_attribute(node, attribute_name);
     describe_maya_attribute(node, attribute_name);
@@ -474,7 +476,7 @@ set_string_attribute(MObject &node, const string &attribute_name,
 
 
   MFnStringData data(string_object, &status);
   MFnStringData data(string_object, &status);
   if (!status) {
   if (!status) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Attribute " << attribute_name << " is of type "
       << "Attribute " << attribute_name << " is of type "
       << string_object.apiTypeStr() << ", not a StringData.\n";
       << string_object.apiTypeStr() << ", not a StringData.\n";
     return false;
     return false;
@@ -489,7 +491,7 @@ set_string_attribute(MObject &node, const string &attribute_name,
 
 
   // And it appears we now need to set the string object back.
   // And it appears we now need to set the string object back.
   if (!set_maya_attribute(node, attribute_name, string_object)) {
   if (!set_maya_attribute(node, attribute_name, string_object)) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Attribute " << attribute_name
       << "Attribute " << attribute_name
       << " suddenly does not have a string object value.\n";
       << " suddenly does not have a string object value.\n";
     return false;
     return false;
@@ -498,9 +500,63 @@ set_string_attribute(MObject &node, const string &attribute_name,
   return true;
   return true;
 }
 }
 
 
+////////////////////////////////////////////////////////////////////
+//     Function: describe_compound_attribute
+//  Description: Extracts the children of this attribute from the
+//               MObject. test for now
+////////////////////////////////////////////////////////////////////
+bool 
+describe_compound_attribute(MObject &node) {
+  MStatus status;
+  
+  MFnCompoundAttribute comp_attr(node, &status);
+
+  maya_cat.info() << "comp_attr has:" << comp_attr.numChildren() << " children" << endl;
+  for (size_t i = 0; i < comp_attr.numChildren(); i++) {
+    MObject child = comp_attr.child(i, &status);
+    if (child.apiType() == MFn::kAttribute3Float){
+      RGBColorf color;
+      /*
+      if (get_vec3f_attribute(child, "color", color)) {
+        maya_cat.info() << "color: " << color << endl;
+      }
+      */
+    }
+    else if (child.apiType() == MFn::kNumericAttribute) {
+      MFnNumericAttribute numeric(child, &status);
+      if (status) {
+        switch(numeric.unitType()) {
+        case MFnNumericData::kFloat :
+          float alpha;
+          status = numeric.getDefault(alpha);
+          maya_cat.info() << "found a float :" << alpha << endl;
+          break;
+        case MFnNumericData::kBoolean :
+          bool v;
+          status = numeric.getDefault(v);
+          maya_cat.info() << "found a bool :" << v << endl;
+        default:
+          maya_cat.info() << numeric.unitType() << endl;
+        }
+      }
+    }
+    else if (child.apiType() == MFn::kEnumAttribute) {
+      MFnEnumAttribute enu(child, &status);
+      if (status) {
+        MString blah;
+        status = enu.getDefault(blah);
+        maya_cat.info() << "found a string :" << blah << endl;
+        MPlug plug = MPlug(node, child);
+        maya_cat.info() << "plug name" << plug.name() << endl;
+      }
+    }
+  }
+  return true;
+}
+
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 //     Function: describe_maya_attribute
 //     Function: describe_maya_attribute
-//  Description: Writes some error output about the indicated Maya
+//  Description: Writes some warning output about the indicated Maya
 //               attribute.
 //               attribute.
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 void
 void
@@ -508,20 +564,20 @@ describe_maya_attribute(MObject &node, const string &attribute_name) {
   MStatus status;
   MStatus status;
   MFnDependencyNode node_fn(node, &status);
   MFnDependencyNode node_fn(node, &status);
   if (!status) {
   if (!status) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Object is a " << node.apiTypeStr() << ", not a DependencyNode.\n";
       << "Object is a " << node.apiTypeStr() << ", not a DependencyNode.\n";
     return;
     return;
   }
   }
 
 
   MObject attr = node_fn.attribute(attribute_name.c_str(), &status);
   MObject attr = node_fn.attribute(attribute_name.c_str(), &status);
   if (!status) {
   if (!status) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Object " << node_fn.name().asChar() << " does not support attribute "
       << "Object " << node_fn.name().asChar() << " does not support attribute "
       << attribute_name << "\n";
       << attribute_name << "\n";
     return;
     return;
   }
   }
 
 
-  maya_cat.error()
+  maya_cat.warning()
     << "Attribute " << attribute_name << " on object "
     << "Attribute " << attribute_name << " on object "
     << node_fn.name().asChar() << " has type " << attr.apiTypeStr() << "\n";
     << node_fn.name().asChar() << " has type " << attr.apiTypeStr() << "\n";
 }
 }
@@ -608,7 +664,7 @@ list_maya_attributes(MObject &node) {
   MStatus status;
   MStatus status;
   MFnDependencyNode node_fn(node, &status);
   MFnDependencyNode node_fn(node, &status);
   if (!status) {
   if (!status) {
-    maya_cat.error()
+    maya_cat.warning()
       << "Object is a " << node.apiTypeStr() << ", not a DependencyNode.\n";
       << "Object is a " << node.apiTypeStr() << ", not a DependencyNode.\n";
     return;
     return;
   }
   }
@@ -631,6 +687,10 @@ list_maya_attributes(MObject &node) {
         << "  " << i << ". " << plug.name().asChar() << ", "
         << "  " << i << ". " << plug.name().asChar() << ", "
         << plug.attribute().apiTypeStr() << ", " 
         << plug.attribute().apiTypeStr() << ", " 
         << plug.node().apiTypeStr();
         << plug.node().apiTypeStr();
+      if (plug.attribute().apiType() == MFn::kCompoundAttribute) {
+        //maya_cat.info() << plug.info();
+        //describe_compound_attribute(plug.attribute());
+      }
       if (plug.isConnected()) {
       if (plug.isConnected()) {
         maya_cat.info(false)
         maya_cat.info(false)
           << " (*)";
           << " (*)";
@@ -639,7 +699,7 @@ list_maya_attributes(MObject &node) {
         << "\n";
         << "\n";
     }
     }
   }
   }
-    
+
   maya_cat.info()
   maya_cat.info()
     << name << " has " << node_fn.attributeCount() << " attributes.\n";
     << name << " has " << node_fn.attributeCount() << " attributes.\n";
   for (i = 0; i < node_fn.attributeCount(); i++) {
   for (i = 0; i < node_fn.attributeCount(); i++) {

+ 3 - 0
pandatool/src/maya/maya_funcs.h

@@ -100,6 +100,9 @@ set_string_attribute(MObject &node, const string &attribute_name,
 void
 void
 describe_maya_attribute(MObject &node, const string &attribute_name);
 describe_maya_attribute(MObject &node, const string &attribute_name);
 
 
+bool
+describe_compound_attribute(MObject &node);
+
 string
 string
 string_mfndata_type(MFnData::Type type);
 string_mfndata_type(MFnData::Type type);
 
 

+ 166 - 100
pandatool/src/mayaegg/mayaToEggConverter.cxx

@@ -50,7 +50,6 @@
 #include <maya/MFnNurbsCurve.h>
 #include <maya/MFnNurbsCurve.h>
 #include <maya/MFnMesh.h>
 #include <maya/MFnMesh.h>
 #include <maya/MFnMeshData.h>
 #include <maya/MFnMeshData.h>
-#include <maya/MItMeshPolygon.h>
 #include <maya/MFnPlugin.h>
 #include <maya/MFnPlugin.h>
 #include <maya/MItDag.h>
 #include <maya/MItDag.h>
 #include <maya/MLibrary.h>
 #include <maya/MLibrary.h>
@@ -740,7 +739,6 @@ convert_hierarchy(EggGroupNode *egg_root) {
       return false;
       return false;
     }
     }
   }
   }
-
   return true;
   return true;
 }
 }
 
 
@@ -1652,6 +1650,16 @@ make_polyset(MayaNodeDesc *node_desc, const MDagPath &dag_path,
     }
     }
   }
   }
 
 
+  MStringArray uvset_names;
+  status = mesh.getUVSetNames(uvset_names);
+  if (!status) {
+    status.perror("MFnMesh getUVSetNames not found");
+    //return;
+  }
+  for (size_t ui=0; ui<uvset_names.length(); ++ui) {
+    mayaegg_cat.debug() << "uv_set[" << ui << "] name: " << uvset_names[ui] << endl;
+  }
+
   while (!pi.isDone()) {
   while (!pi.isDone()) {
     EggPolygon *egg_poly = new EggPolygon;
     EggPolygon *egg_poly = new EggPolygon;
     egg_group->add_child(egg_poly);
     egg_group->add_child(egg_poly);
@@ -1675,10 +1683,10 @@ make_polyset(MayaNodeDesc *node_desc, const MDagPath &dag_path,
 
 
     // And apply the shader properties to the polygon.
     // And apply the shader properties to the polygon.
     if (shader != (MayaShader *)NULL) {
     if (shader != (MayaShader *)NULL) {
-      set_shader_attributes(*egg_poly, *shader);
+      set_shader_attributes(*egg_poly, *shader, &pi);
     }
     }
 
 
-    const MayaShaderColorDef &color_def = shader->_color;
+    const MayaShaderColorDef *color_def = shader->get_color_def();
 
 
     // Should we extract the color from the vertices?  Normally, in
     // Should we extract the color from the vertices?  Normally, in
     // Maya a texture completely replaces the vertex color, so we
     // Maya a texture completely replaces the vertex color, so we
@@ -1694,7 +1702,7 @@ make_polyset(MayaNodeDesc *node_desc, const MDagPath &dag_path,
     // that the "vertex-color" flag is always set.
     // that the "vertex-color" flag is always set.
     bool ignore_vertex_color = false;
     bool ignore_vertex_color = false;
     if (shader != (MayaShader *)NULL) {
     if (shader != (MayaShader *)NULL) {
-      ignore_vertex_color = color_def._has_texture && !(egg_vertex_color || _always_show_vertex_color);
+      ignore_vertex_color = color_def->_has_texture && !(egg_vertex_color || _always_show_vertex_color);
     }
     }
 
 
     Colorf poly_color(1.0f, 1.0f, 1.0f, 1.0f);
     Colorf poly_color(1.0f, 1.0f, 1.0f, 1.0f);
@@ -1711,7 +1719,7 @@ make_polyset(MayaNodeDesc *node_desc, const MDagPath &dag_path,
     long i;
     long i;
     LPoint3d centroid(0.0, 0.0, 0.0);
     LPoint3d centroid(0.0, 0.0, 0.0);
 
 
-    if (shader != (MayaShader *)NULL && color_def.has_projection()) {
+    if (shader != (MayaShader *)NULL && color_def->has_projection()) {
       // If the shader has a projection, we may need to compute the
       // If the shader has a projection, we may need to compute the
       // polygon's centroid to avoid seams at the edges.
       // polygon's centroid to avoid seams at the edges.
       for (i = 0; i < num_verts; i++) {
       for (i = 0; i < num_verts; i++) {
@@ -1722,7 +1730,6 @@ make_polyset(MayaNodeDesc *node_desc, const MDagPath &dag_path,
       }
       }
       centroid /= (double)num_verts;
       centroid /= (double)num_verts;
     }
     }
-
     for (i = 0; i < num_verts; i++) {
     for (i = 0; i < num_verts; i++) {
       EggVertex vert;
       EggVertex vert;
 
 
@@ -1741,19 +1748,41 @@ make_polyset(MayaNodeDesc *node_desc, const MDagPath &dag_path,
         vert.set_normal(n3d);
         vert.set_normal(n3d);
       }
       }
 
 
-      if (shader != (MayaShader *)NULL && color_def.has_projection()) {
-        // If the shader has a projection, use it instead of the
-        // polygon's built-in UV's.
-        vert.set_uv(color_def.project_uv(p3d, centroid));
+      string uv_name("");
+      if (shader != (MayaShader *)NULL && color_def->_has_texture) {
+        // Go thru all the texture references for this primitive and set uvs
+        mayaegg_cat.debug() << "shader->_color.size is " << shader->_color.size() << endl;
+        mayaegg_cat.debug() << "primitive->tref.size is " << egg_poly->get_num_textures() << endl;
+        for (int ti=0; ti< egg_poly->get_num_textures(); ++ti) {
+          // get the eggTexture pointer
+          EggTexture *tex_p = egg_poly->get_texture(ti);
+          mayaegg_cat.debug() << "tex->uvset_name :" << tex_p->get_uv_name() << endl;
+
+          // get the shader color def that matches this EggTexture
+          for (size_t tj=0; tj< shader->_color.size(); ++tj) {
+            color_def = shader->get_color_def(tj);
+            if (color_def->_texture_name == tex_p->get_uv_name()) {
+              mayaegg_cat.debug() << "matched colordef idx: " << tj << endl;
+              break;
+            }
+          }
+          mayaegg_cat.debug() << "color_def->uvset_name :" << color_def->_uvset_name << endl;
+          uv_name = color_def->_uvset_name;  // this is the name to look up by in maya
 
 
-      } else if (pi.hasUVs()) {
-        // Get the UV's from the polygon.
-        float2 uvs;
-        status = pi.getUV(i, uvs);
-        if (!status) {
-          status.perror("MItMeshPolygon::getUV");
-        } else {
-          vert.set_uv(TexCoordd(uvs[0], uvs[1]));
+          if (color_def->has_projection()) {
+            // If the shader has a projection, use it instead of the
+            // polygon's built-in UV's.
+            vert.set_uv(tex_p->get_uv_name(),color_def->project_uv(p3d, centroid));
+          } else {
+            // Get the UV's from the polygon.
+            float2 uvs;
+            status = pi.getUV(i, uvs, &MString(uv_name.c_str()));
+            if (!status) {
+              status.perror("MItMeshPolygon::getUV");
+            } else {
+              vert.set_uv(tex_p->get_uv_name(),TexCoordd(uvs[0], uvs[1]));
+            }
+          }
         }
         }
       }
       }
 
 
@@ -1808,7 +1837,9 @@ make_polyset(MayaNodeDesc *node_desc, const MDagPath &dag_path,
     }
     }
       
       
     pi.next();
     pi.next();
+
   }
   }
+  mayaegg_cat.spam() << "done traversing polys" << endl;
 
 
   // Now that we've added all the polygons (and created all the
   // Now that we've added all the polygons (and created all the
   // vertices), go back through the vertex pool and set up the
   // vertices), go back through the vertex pool and set up the
@@ -2166,99 +2197,134 @@ get_vertex_weights(const MDagPath &dag_path, const MFnNurbsSurface &surface,
 //               egg primitive.
 //               egg primitive.
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 void MayaToEggConverter::
 void MayaToEggConverter::
-set_shader_attributes(EggPrimitive &primitive, const MayaShader &shader) {
+set_shader_attributes(EggPrimitive &primitive, const MayaShader &shader, const MItMeshPolygon *pi) {
   // In Maya, a polygon is either textured or colored.  The texture,
   // In Maya, a polygon is either textured or colored.  The texture,
-  // if present, replaces the color.
-  const MayaShaderColorDef &color_def = shader._color;
+  // if present, replaces the color. Also now there could be multiple textures
+  MayaShaderColorDef *color_def;
   const MayaShaderColorDef &trans_def = shader._transparency;
   const MayaShaderColorDef &trans_def = shader._transparency;
-  if (color_def._has_texture || trans_def._has_texture) {
-    EggTexture tex(shader.get_name(), "");
-
-    if (color_def._has_texture) {
-      // If we have a texture on color, apply it as the filename.
-      Filename filename = Filename::from_os_specific(color_def._texture);
-      Filename fullpath = 
-        _path_replace->match_path(filename, get_texture_path());
-      tex.set_filename(_path_replace->store_path(fullpath));
-      tex.set_fullpath(fullpath);
-      apply_texture_properties(tex, color_def);
-
-      // If we also have a texture on transparency, apply it as the
-      // alpha filename.
-      if (trans_def._has_texture) {
-        if (color_def._wrap_u != trans_def._wrap_u ||
-            color_def._wrap_u != trans_def._wrap_u) {
-          mayaegg_cat.warning()
-            << "Shader " << shader.get_name()
-            << " has contradictory wrap modes on color and texture.\n";
-        }
+  for (size_t i=0; i<shader._color.size(); ++i) {
+    color_def = shader.get_color_def(i);
+    if (color_def->_has_texture || trans_def._has_texture) {
+      EggTexture tex(shader.get_name(), "");
+      string uvset_name = color_def->_texture_name;
+      
+      //maya_cat.debug() << "got shader name:" << shader.get_name() << endl;
+      maya_cat.debug() << "ssa:texture name[" << i << "]: " << color_def->_texture_name << endl;
+      
+      if (color_def->_has_texture) {
+        // If we have a texture on color, apply it as the filename.
+        //mayaegg_cat.debug() << "ssa:got texture name" << color_def->_texture_filename << endl;
+        Filename filename = Filename::from_os_specific(color_def->_texture_filename);
+        Filename fullpath = 
+          _path_replace->match_path(filename, get_texture_path());
+        tex.set_filename(_path_replace->store_path(fullpath));
+        tex.set_fullpath(fullpath);
+        apply_texture_properties(tex, *color_def);
+        
+        // If we also have a texture on transparency, apply it as the
+        // alpha filename.
+        if (trans_def._has_texture) {
+          if (color_def->_wrap_u != trans_def._wrap_u ||
+              color_def->_wrap_u != trans_def._wrap_u) {
+            mayaegg_cat.warning()
+              << "Shader " << shader.get_name()
+              << " has contradictory wrap modes on color and texture.\n";
+          }
           
           
-        if (!compare_texture_properties(tex, trans_def)) {
-          // Only report each broken shader once.
-          static pset<string> bad_shaders;
-          if (bad_shaders.insert(shader.get_name()).second) {
-            mayaegg_cat.error()
-              << "Color and transparency texture properties differ on shader "
-              << shader.get_name() << "\n";
+          if (!compare_texture_properties(tex, trans_def)) {
+            // Only report each broken shader once.
+            static pset<string> bad_shaders;
+            if (bad_shaders.insert(shader.get_name()).second) {
+              mayaegg_cat.error()
+                << "Color and transparency texture properties differ on shader "
+                << shader.get_name() << "\n";
+            }
           }
           }
-        }
-        tex.set_format(EggTexture::F_rgba);
+          //tex.set_format(EggTexture::F_rgba);
           
           
-        // We should try to be smarter about whether the transparency
-        // value is connected to the texture's alpha channel or to its
-        // grayscale channel.  However, I'm not sure how to detect
-        // this at the moment; rather than spending days trying to
-        // figure out, for now I'll just assume that if the same
-        // texture image is used for both color and transparency, then
-        // the artist meant to use the alpha channel for transparency.
-        if (trans_def._texture == color_def._texture) {
-          // That means that we don't need to do anything special: use
-          // all the channels of the texture.
-
+          // We should try to be smarter about whether the transparency
+          // value is connected to the texture's alpha channel or to its
+          // grayscale channel.  However, I'm not sure how to detect
+          // this at the moment; rather than spending days trying to
+          // figure out, for now I'll just assume that if the same
+          // texture image is used for both color and transparency, then
+          // the artist meant to use the alpha channel for transparency.
+          if (trans_def._texture_filename == color_def->_texture_filename) {
+            // That means that we don't need to do anything special: use
+            // all the channels of the texture.
+            
+          } else {
+            // Otherwise, pull the alpha channel from the other image
+            // file.  Ideally, we should figure out which channel from
+            // the other image supplies alpha (and specify this via
+            // set_alpha_file_channel()), but for now we assume it comes
+            // from the grayscale data.
+            filename = Filename::from_os_specific(trans_def._texture_filename);
+            fullpath = _path_replace->match_path(filename, get_texture_path());
+            tex.set_alpha_filename(_path_replace->store_path(fullpath));
+            tex.set_alpha_fullpath(fullpath);
+          }
         } else {
         } else {
-          // Otherwise, pull the alpha channel from the other image
-          // file.  Ideally, we should figure out which channel from
-          // the other image supplies alpha (and specify this via
-          // set_alpha_file_channel()), but for now we assume it comes
-          // from the grayscale data.
-          filename = Filename::from_os_specific(trans_def._texture);
-          fullpath = _path_replace->match_path(filename, get_texture_path());
-          tex.set_alpha_filename(_path_replace->store_path(fullpath));
-          tex.set_alpha_fullpath(fullpath);
+          // If there is no transparency texture specified, we don't
+          // have any transparency, so tell the egg format to ignore any
+          // alpha channel that might be on the color texture.
+          //tex.set_format(EggTexture::F_rgb);
+        }
+        
+        // if multi-textured, first texture in maya is on top, so
+        // default it to decal
+        if ((shader._color.size() > 1) && (i!=shader._color.size()-1))
+          tex.set_env_type(EggTexture::ET_decal);
+        
+      } else {  // trans_def._has_texture
+        // We have a texture on transparency only.  Apply it as the
+        // primary filename, and set the format accordingly.
+        Filename filename = Filename::from_os_specific(trans_def._texture_filename);
+        Filename fullpath = 
+          _path_replace->match_path(filename, get_texture_path());
+        tex.set_filename(_path_replace->store_path(fullpath));
+        tex.set_fullpath(fullpath);
+        //tex.set_format(EggTexture::F_alpha);
+        apply_texture_properties(tex, trans_def);
+      }
+      
+      //mayaegg_cat.debug() << "ssa:tref_name:" << tex.get_name() << endl;
+      EggTexture *new_tex =
+        _textures.create_unique_texture(tex, ~0);
+      //_textures.create_unique_texture(tex, ~EggTexture::E_tref_name);
+      
+      if (pi && shader._color.size() > 1) {
+        // see if the uvset_name exists for this polygon, if yes, add the texture to primitive
+        if (pi->hasUVs(MString(uvset_name.c_str()))) {
+          primitive.add_texture(new_tex);
+          color_def->_uvset_name.assign(uvset_name.c_str());
+          new_tex->set_uv_name(color_def->_texture_name);
+        } else {
+          // if the uvset is under different name, try taking out the
+          // numeric from the uv name. This was a compromise to support
+          // one uvset but different layered texture for layer1 texture
+          uvset_name.resize(uvset_name.length()-1);
+          mayaegg_cat.debug() << "ssa:trying uvset_name: " << uvset_name << endl;
+          if (pi->hasUVs(MString(uvset_name.c_str()))) {
+            primitive.add_texture(new_tex);
+            color_def->_uvset_name.assign(uvset_name.c_str());
+            new_tex->set_uv_name(color_def->_texture_name);
+          } else {
+            mayaegg_cat.debug() << "ssa: didn't find uvset_name: " << uvset_name << endl;
+          }
         }
         }
-
       } else {
       } else {
-        // If there is no transparency texture specified, we don't
-        // have any transparency, so tell the egg format to ignore any
-        // alpha channel that might be on the color texture.
-        tex.set_format(EggTexture::F_rgb);
+        primitive.add_texture(new_tex);
+        new_tex->set_uv_name(color_def->_uvset_name);
       }
       }
-
-    } else {  // trans_def._has_texture
-      // We have a texture on transparency only.  Apply it as the
-      // primary filename, and set the format accordingly.
-      Filename filename = Filename::from_os_specific(trans_def._texture);
-      Filename fullpath = 
-        _path_replace->match_path(filename, get_texture_path());
-      tex.set_filename(_path_replace->store_path(fullpath));
-      tex.set_fullpath(fullpath);
-      tex.set_format(EggTexture::F_alpha);
-      apply_texture_properties(tex, trans_def);
     }
     }
-  
-    EggTexture *new_tex =
-      _textures.create_unique_texture(tex, ~EggTexture::E_tref_name);
-    
-    primitive.set_texture(new_tex);
-
   }
   }
-
   // Also apply an overall color to the primitive.
   // Also apply an overall color to the primitive.
   Colorf rgba = shader.get_rgba();
   Colorf rgba = shader.get_rgba();
 
 
   // The existence of a texture on either color channel completely
   // The existence of a texture on either color channel completely
   // replaces the corresponding flat color.
   // replaces the corresponding flat color.
-  if (color_def._has_texture) {
+  if (color_def->_has_texture) {
     rgba[0] = 1.0f;
     rgba[0] = 1.0f;
     rgba[1] = 1.0f;
     rgba[1] = 1.0f;
     rgba[2] = 1.0f;
     rgba[2] = 1.0f;
@@ -2268,10 +2334,10 @@ set_shader_attributes(EggPrimitive &primitive, const MayaShader &shader) {
   }
   }
 
 
   // But the color gain always gets applied.
   // But the color gain always gets applied.
-  rgba[0] *= color_def._color_gain[0];
-  rgba[1] *= color_def._color_gain[1];
-  rgba[2] *= color_def._color_gain[2];
-  rgba[3] *= color_def._color_gain[3];
+  rgba[0] *= color_def->_color_gain[0];
+  rgba[1] *= color_def->_color_gain[1];
+  rgba[2] *= color_def->_color_gain[2];
+  rgba[3] *= color_def->_color_gain[3];
 
 
   primitive.set_color(rgba);
   primitive.set_color(rgba);
 }
 }

+ 4 - 1
pandatool/src/mayaegg/mayaToEggConverter.h

@@ -33,6 +33,7 @@
 
 
 #include "pre_maya_include.h"
 #include "pre_maya_include.h"
 #include <maya/MDagPath.h>
 #include <maya/MDagPath.h>
+#include <maya/MItMeshPolygon.h>
 #include "post_maya_include.h"
 #include "post_maya_include.h"
 
 
 class EggData;
 class EggData;
@@ -133,8 +134,10 @@ private:
                           pvector<EggGroup *> &joints, MFloatArray &weights);
                           pvector<EggGroup *> &joints, MFloatArray &weights);
   bool get_vertex_weights(const MDagPath &dag_path, const MFnNurbsSurface &surface,
   bool get_vertex_weights(const MDagPath &dag_path, const MFnNurbsSurface &surface,
                           pvector<EggGroup *> &joints, MFloatArray &weights);
                           pvector<EggGroup *> &joints, MFloatArray &weights);
+  //  void set_shader_attributes(EggPrimitive &primitive,
+  //                             const MayaShader &shader);
   void set_shader_attributes(EggPrimitive &primitive,
   void set_shader_attributes(EggPrimitive &primitive,
-                             const MayaShader &shader);
+                             const MayaShader &shader, const MItMeshPolygon *pi=NULL);
   void apply_texture_properties(EggTexture &tex, 
   void apply_texture_properties(EggTexture &tex, 
                                 const MayaShaderColorDef &color_def);
                                 const MayaShaderColorDef &color_def);
   bool compare_texture_properties(EggTexture &tex, 
   bool compare_texture_properties(EggTexture &tex, 

+ 5 - 3
pandatool/src/mayaprogs/mayaCopy.cxx

@@ -167,8 +167,10 @@ copy_maya_file(const Filename &source, const Filename &dest,
   int num_shaders = _shaders.get_num_shaders();
   int num_shaders = _shaders.get_num_shaders();
   for (int i = 0; i < num_shaders; i++) {
   for (int i = 0; i < num_shaders; i++) {
     MayaShader *shader = _shaders.get_shader(i);
     MayaShader *shader = _shaders.get_shader(i);
-    if (!extract_texture(shader->_color, dir)) {
-      return false;
+    for (size_t j = 0; j < shader->_color.size(); j++) {
+      if (!extract_texture(*shader->get_color_def(j), dir)) {
+        return false;
+      }
     }
     }
     if (!extract_texture(shader->_transparency, dir)) {
     if (!extract_texture(shader->_transparency, dir)) {
       return false;
       return false;
@@ -227,7 +229,7 @@ bool MayaCopy::
 extract_texture(MayaShaderColorDef &color_def, CVSSourceDirectory *dir) {
 extract_texture(MayaShaderColorDef &color_def, CVSSourceDirectory *dir) {
   if (color_def._has_texture) {
   if (color_def._has_texture) {
     Filename texture_filename = 
     Filename texture_filename = 
-      _path_replace->convert_path(color_def._texture);
+      _path_replace->convert_path(color_def._texture_filename);
     if (!texture_filename.exists()) {
     if (!texture_filename.exists()) {
       nout << "*** Warning: texture " << texture_filename
       nout << "*** Warning: texture " << texture_filename
            << " does not exist.\n";
            << " does not exist.\n";