Maxon Developers Maxon Developers
    • Documentation
      • Cinema 4D Python API
      • Cinema 4D C++ API
      • Cineware API
      • ZBrush Python API
      • ZBrush GoZ API
      • Code Examples on Github
    • Forum
    • Downloads
    • Support
      • Support Procedures
      • Registered Developer Program
      • Plugin IDs
      • Contact Us
    • Categories
      • Overview
      • News & Information
      • Cinema 4D SDK Support
      • Cineware SDK Support
      • ZBrush 4D SDK Support
      • Bugs
      • General Talk
    • Unread
    • Recent
    • Tags
    • Users
    • Login

    Problems with MorphMixer and Bones

    SDK Help
    0
    3
    315
    Loading More Posts
    • Oldest to Newest
    • Newest to Oldest
    • Most Votes
    Reply
    • Reply as topic
    Log in to reply
    This topic has been deleted. Only users with topic management privileges can see it.
    • H
      Helper
      last edited by

      THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED

      On 15/10/2004 at 14:29, xxxxxxxx wrote:

      User Information:
      Cinema 4D Version:   8.503 
      Platform:   Windows  ;   
      Language(s) :     C++  ;

      ---------
      Instead of morph Objects, I'm storing the morph information in tags attached to the bones (just for organization - no direct effect on bones). But, the MorphMixer object is causing problems with the geometry as long as bones are fixed. Here's the general hierarchy:

      PolygonObject
      -- MorphMixer Object
      -- Bone MorphTag|MorphTag|...
      -----Bone MorphTag|MorphTag|...
      -----Bone MorphTag|MorphTag|...
      -----etc. on Bone Hierarchy

      Now, the morph sliders are working, the morphs are working, but the cause of the distortion on the overall geometry is hard to determine. Well, here's is the code for applying the morphs. If you see a problem needing attention or have an alternative methodology, please help!

        
      // Create morphed object  
      BaseObject *MorphMixerObject::GetVirtualObjects(PluginObject *op, HierarchyHelp *hh)  
      {  
           Bool               dirty;  
           LONG               index = MORPHMIXER_POSEOFFSET;  
           Vector               *destadr = NULL;  
           BaseObject          *ret = NULL, *orig;  
           BaseContainer     *data = op->GetDataInstance();  
        
           // Get Polygonal Object receiving morphs, return NULL if none  
           if (!(orig = op->GetUp()) || !orig->IsInstanceOf(Opoint)) return NULL;  
        
           // check cache for validity and check master object for changes  
           dirty = op->CheckCache(hh) || op->IsDirty(DIRTY_DATA);  
           orig->Touch();  
           if (!dirty) return op->GetCache(hh);  
        
           // Clone base object  
           if (!(ret = (BaseObject* )orig->GetClone(COPY_NO_HIERARCHY|COPY_NO_ANIMATION|COPY_NO_BITS,NULL))) return NULL;  
           // and transfer tags  
           if (!op->CopyTagsTo(ret,NOTOK,NOTOK,FALSE,NULL))  
           {  
                BaseObject::Free(ret);  
                return NULL;  
           }  
           // transfer name  
           ret->SetName(op->GetName());  
        
           // retrieve destination and base points  
           destadr = ((PolygonObject* )ret)->GetPoint();  
        
           ApplyMorph(GetActiveDocument(), op->GetNext(), orig, destadr, data, &index;);  
        
           // send update message  
           ret->Message(MSG_UPDATE);  
           return ret;  
      }  
      // Apply Morph to MorphMixer- recursive  
      void MorphMixerObject::ApplyMorph(BaseDocument *doc, BaseObject *obj, BaseObject *mobj, Vector *dest, BaseContainer *bc, LONG *index)  
      {  
           LONG               nr;  
           Real               strength;  
           LONG               *indices, *lind;  
           Vector               *deltas;  
           BaseContainer     *pbc;  
           BaseObject          *mo;  
           PluginTag          *pt;  
           struct morphData mData;  
           mData.bGet = TRUE;  
           mData.indices = NULL;  
        
           for (; obj; obj = obj->GetNext())  
           {  
                // Apply related Morphs to MorphMixer list  
                for (nr = 0; pt = (PluginTag* )obj->GetTag(ID_MORPHTAG, nr); nr++)  
                {  
                     // Verify morph object  
                     pbc = pt->GetDataInstance();  
                     if ((mo = pbc->GetObjectLink(MORPHTAG_OPOLYGON_LINK, doc)) != mobj) continue;  
        
                     // Get morph percentage from slider  
                     strength = bc->GetReal(*index);  
        
                     // Get morph point count, indices, and deltas  
                     pt->Message(MSG_CHANGE, &mData;);  
                     indices = mData.indices;  
                     deltas = mData.morphs;  
                     lind = indices+pbc->GetLong(MORPHTAG_MCOUNT_LONG);  
        
                     // Add weighted morph  
                     for (; indices != lind; indices++, deltas++)  
                          dest[*indices] += (*deltas * strength);  
        
                     (*index)++;  
                }  
                ApplyMorph(doc, obj->GetDown(), mobj, dest, bc, index);  
           }  
      }  
      

      Thanks,
      Robert

      1 Reply Last reply Reply Quote 0
      • H
        Helper
        last edited by

        THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED

        On 15/10/2004 at 17:22, xxxxxxxx wrote:

        Addendum:

        I find that if I move the MorphMixer object above the mesh object (the one being morphed) and change all of my references to boot, the distortion of the mesh object disappears (yay!), but now, as in another message, the bones do not respond (do not deform the mesh). If I disable the MorphMixer object, the bones work. If I enable it, they don't.

        What needs to be done to fix this?

        Thanks,
        Robert

        1 Reply Last reply Reply Quote 0
        • H
          Helper
          last edited by

          THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED

          On 16/10/2004 at 23:58, xxxxxxxx wrote:

          Anyone? Here's the updated code which seems to allow bones to work, but now the morphs 'snap' back as soon as the slider is released. Note that I'm fiddling with the GetClone() flags to see if something works.

            
          // Create morphed object  
          BaseObject *MorphMixerObject::GetVirtualObjects(PluginObject *op, HierarchyHelp *hh)  
          {  
               Bool               dirty;  
               LONG               index = MORPHMIXER_POSEOFFSET;  
               Vector               *destadr;  
               BaseObject          *ret, *orig;  
               BaseContainer     *data = op->GetDataInstance();  
            
               // Get Polygonal Object receiving morphs, return NULL if none  
               if (!(orig = op->GetDown()) || !orig->IsInstanceOf(Opoint)) return NULL;  
            
               // check cache for validity and check master object for changes  
               //op->CheckCache(hh) ||   
               dirty = op->IsDirty(DIRTY_DATA|DIRTY_MATRIX);  
               op->Touch();  
               if (!dirty) return op->GetCache(hh);  
            
               // Clone base object  
               if (!(ret = (BaseObject* )orig->GetClone(COPY_NO_HIERARCHY/*|COPY_NO_ANIMATION|COPY_NO_BITS*/,NULL))) return NULL; //throw ErrorException(ERROR_MEMORY, "MorphMixerObject.GetVirtualObjects.ret");  
               // and transfer tags  
               if (!op->CopyTagsTo(ret,TRUE,FALSE,FALSE,NULL))  
               {  
                    BaseObject::Free(ret);  
                    return NULL; //throw ErrorException(ERROR_MEMORY, "MorphMixerObject.GetVirtualObjects.CopyTagsTo()");  
               }  
               // transfer name  
               ret->SetName(op->GetName());  
            
               // retrieve destination and base points  
               destadr = ToPoly(ret)->GetPoint();  
            
               ApplyMorph(GetActiveDocument(), orig->GetDown(), orig, destadr, data, &index;);  
            
               // send update message  
               ret->Message(MSG_UPDATE);  
               return ret;  
          }  
          

          Thanks,
          Robert

          1 Reply Last reply Reply Quote 0
          • First post
            Last post