Maxon Developers Maxon Developers
    • Documentation
      • Cinema 4D Python API
      • Cinema 4D C++ API
      • Cineware 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

    Nested Cloners [SOLVED]

    SDK Help
    0
    26
    13.6k
    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

      On 25/08/2014 at 04:27, xxxxxxxx wrote:

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

      ---------
      Hi,

      does anybody know if it's possible to retrieve modata from a nested cloner (i.e. the cloner is a child of another cloner)?

      MSG_GET_MODATA works with the parent cloner but for the child cloner I don't even get a modata tag, which is the actual problem. I don't even get to the point of retrieval for that child cloner.

      Is this a bug or how is it supposed to work? Anybody tried that already?

      Thanks

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

        On 25/08/2014 at 05:42, xxxxxxxx wrote:

        I also checked if there are several modata tags on the parent cloner but there aren't.
        Also there is only one valid modata for index = 0. Other indices are uninitialised.

        Right now I cannot think of anything else... 😕

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

          On 25/08/2014 at 06:13, xxxxxxxx wrote:

          I found only this thread with the forum search for a related posting:
          https://developers.maxon.net/forum/topic/6927/7783_cloner--tag-with-excprioritygenerator&KW=cloner

          It's not exactly the same issue but the presented issue occurs with nested cloners as well (though it might be a priority issue)...so still no real hint if it is possible at all to retrieve modata for a nested cloner.
          This is really needed. 😞

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

            On 14/09/2015 at 10:43, xxxxxxxx wrote:

            I am coming back to this one year later becaue it's still not resolved. I am still looking for a way to read out nested cloners.

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

              On 15/09/2015 at 01:37, xxxxxxxx wrote:

              Hello,

              what exactly is your situation, are you trying to write an Effector or some other kind of plugin? If you could share some code showing what you are doing it would help us to understand the issue.

              Best wishes,
              Sebastian

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

                On 15/09/2015 at 02:29, xxxxxxxx wrote:

                Hi Sebastian,

                thanks. I am in a Scene Hook::Execute() and I simply get the cloner (in that case nested cloners parent), the according motag and then use the message system to retrieve the modata accordingly. Something like this:

                  
                    
                    
                    static inline bool get_cloner_modata(BaseObject* maincloner, GetMoDataMessage& msg_data, int moindex = 0)  
                    	{  
                    		/* Find the MoData tag. */  
                    		BaseTag* tag = maincloner->GetTag(ID_MOTAGDATA); if (!tag) return false;  
                      
                    //if the passed moindex is not 0 I would loop through available motags via tag->GetNext() but there is only 1 motag on the parent cloner  
                    		  
                    		/* Retrieve the MoData. */  
                    		if (!tag->Message(MSG_GET_MODATA, &msg_data)) { return false; }  
                    		if (!msg_data.modata) {  
                    			GePrint("MSG_GET_MODATA did not return a MoData pointer.");  
                    			return false;  
                    		}  
                    		return true;  
                    	}
                
                Once I have the modata I browse the cloner's children accordingly with GetDown()/GetNext() (This works all fine. I get the matrix, offset etc. arrays from the modata accordingly. modata->GetCount() returns correctly the amount of clones that cloner produces).  
                If one of the children is a cloner, I recurse with the same code.  
                Pseudocode:  
                
                  
                    void get_mo_clones(BaseObject* root_cloner, BaseObject* cloner)  
                    {  
                            
                    GetMoDataMessage msg;  
                    if(!get_cloner_modata(cloner,msg)) return; //returns here for child cloners because no motag is found  
                      
                    clone_source_i = cloner->GetDown()  
                    browse_cloner_children(cs){  
                      //I cache them here for later use  
                      cs = cs->GetNext();  
                    }  
                      
                    MoData* md = msg.modata;  
                    for_each_clone(child, md->GetCount()){  
                       if(childtype == MOGRAPH_CLONER_ID)  
                          get_mo_clones(root_cloner, child)  
                       else{  
                           //Do stuff...e.g. md->GetMatrixArray(MODATA_MATRIX)[i] etc.  
                    }  
                    
                
                but on that cloner child cloner of course and that's what is not working as I explained in the above posts. There is no motag on that child cloner. Also there is only one modata available in the parent cloner and only a single motag (so no multiple data for child clones).  
                  
                All caches etc should be built when my SceneHook is evaluated, so the data should be there I guess. The question is where to get the motag/modata for possible nested child cloners. Any idea?  
                
                1 Reply Last reply Reply Quote 0
                • H
                  Helper
                  last edited by

                  On 15/09/2015 at 03:46, xxxxxxxx wrote:

                  did you check activeobject plugin?

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

                    On 15/09/2015 at 03:50, xxxxxxxx wrote:

                    activeobject plugin? What do you mean by that Mohamed? All pointers are verified yes, if you mean that.

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

                      On 15/09/2015 at 06:01, xxxxxxxx wrote:

                      no, not meaning that Samir, there is a plugin example in the SDK, under GUI plugins, ActiveObject.cpp

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

                        On 15/09/2015 at 06:10, xxxxxxxx wrote:

                        Ok. Yes, I know the gui example, but how is it supposed to help me with this issue? Not sure I understand. Can you elaborate?

                        Except for the effector examples there's nothing MoGraph related in the sdk examples.

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

                          On 15/09/2015 at 06:13, xxxxxxxx wrote:

                          just create your nested clones in the object manager, then open the plugin, check how the hierarchy looks, it should do exactly what you want.

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

                            On 15/09/2015 at 06:20, xxxxxxxx wrote:

                            No, it does nothing what I want (at least I don't see anything helpful in my situation but I could be blind).
                            Please be more exact or post some code that shows how to retrieve the Modata/motag from a nested cloner with valid transformation matrix informations, so I know what you mean.

                            Imo the activeobject example does nothing but showing the hierarchy in a treeview. All the classes there are meant to let the treeview element handle a hierarchy. How is it supposed to help me with nested cloners and modata retrieval?

                            The hierarchy is known and I don't need direct access to the clones geometry (that is retrieved with GetDeformedCache for example) but to the internal procedural clone data of the cloner which the modata provides.

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

                              On 15/09/2015 at 07:04, xxxxxxxx wrote:

                              you will need to get that cached object, access its container.

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

                                On 15/09/2015 at 09:08, xxxxxxxx wrote:

                                Hello,

                                I could no reproduce any problems. You told that you browse the cloner's children with GetDown(). But these children (objects you see in the Object Manager) are no clones. The only clones exist in the cache of the cloner. When you access the cache of the cloner and access the cloned cloners there, they will have a MoGraph tag.

                                Best wishes,
                                Sebastian

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

                                  On 15/09/2015 at 10:36, xxxxxxxx wrote:

                                  ok, I am absof**kinglutely stupid and you guys are totally darn right! Really, this is so basic, I feel ashamed. I haven't had the slightest thought about virtuality of the result that it never even crossed my mind to look that way (even though I was talking about the procedural data. Someone please hit me).

                                  My apologies to Mohamed as well. You pointed in the right direction but as I mentioned I was totally ignorant about thinking this out further. Apparently I don't need sleep, I need vacation. 😵

                                  Anyway, will try this first thing in the morning but it seems that was my missing piece. Hate myself right now.

                                  Thanks guys (also for being patient sometimes with me !Ermm[URL-REMOVED])!!


                                  [URL-REMOVED] @maxon: This section contained a non-resolving link which has been removed.

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

                                    On 15/09/2015 at 11:22, xxxxxxxx wrote:

                                    this is common Samir, I always do this "test a lot , get a whole picture, and miss a small detail".
                                    glad that it helped

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

                                      On 23/10/2015 at 04:43, xxxxxxxx wrote:

                                      Hi,

                                      sorry guys, gotta steal your time once again as I now know why I used the "normal" clones in the first place (sorry, didn't recall before but only today when I indeed tried this). I am in a SceneHook Execute() function and GetCache as well as GetDeformCache always return a nullptr.

                                      SendModellingCommand only seems to return the final polygonal hierarchy. So is there a way to access the virtual cache from here anyhow?

                                      Maybe I need to clone the doc somehow, let the cache be rebuilt (which would probably impose a performance penalty if dynamics need to be recalculated for the frame of retrieval?) and read the cache then? I'd rather not because this would also include my own dynamic calculations to be redone which is really no option (it could be hours of simulation time for previous frames...worst case scenario).

                                      Maybe there is a way to rebuilt the caches?

                                      Thanks again!

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

                                        On 26/10/2015 at 01:53, xxxxxxxx wrote:

                                        Hello,

                                        what exactly are you doing in you SceneHook and when? In AddToExecution() you can define when in the execution pipeline your scene hook is called.

                                        Best wishes,
                                        Sebastian

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

                                          On 26/10/2015 at 05:49, xxxxxxxx wrote:

                                          Hi,

                                          what exactly do you mean by "what exactly are you doing"?

                                          I am grabbing an object from the OM (my own object plugin) and reading out an object (in this case the Cloner but it doesn't matter what object, it's always nullptr) from a link field of it. Then trying to get the cache.

                                          obj = my_op->GetDataInstance()->GetObjectLink(ID);
                                          obj->GetCache()

                                          execution pipeline priority is EXECUTIONPRIORITY_DYNAMICS (which I want to be in btw.)

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

                                            On 26/10/2015 at 06:06, xxxxxxxx wrote:

                                            I assume caches are not yet built (but will be only in EXECUTIONPRIORITY_GENERATORS) so I guess I need pre-built caches?

                                            Can I use the Hierarchy class for this purpose?

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