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

    Select the Children of a Selected Object. Then, Store it in a List

    Cinema 4D SDK
    r20 python
    3
    4
    1.5k
    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.
    • B
      bentraje
      last edited by

      Hi,

      I have a joint chain of shoulder_jnt > elbow_jnt > wrist_jnt
      I want it to store it in a list. Here is the code so far:

      def GetObjects(obj):
            objList = [obj]
            for kid in obj.GetChildren():        
                GetObjects(kid)
                objList += kid
            return objList # should return the parent/selected obejct and all its chidlren
      
      test = doc.SearchObject("shoulder_jnt")          
      ikJointChain = GetObjects(test)
      

      It gives me an error of

      Traceback (most recent call last):
        File "scriptmanager", line 9, in <module>
        File "scriptmanager", line 4, in GetObjects
        File "scriptmanager", line 5, in GetObjects
      TypeError: 'c4d.modules.character.CAJointObject' object is not iterable
      

      The code is modified from this post:
      https://developers.maxon.net/forum/topic/6923

      There is also another code in that post, but I can't really understand it.
      So I chose the most simpler one.

      Thank you for looking at the problem.

      1 Reply Last reply Reply Quote 0
      • M
        mp5gosu
        last edited by mp5gosu

        SearchObject() returns a single BaseObject.
        You might want to create a dedicated function that walks through your document and returns a list with all the filtered objects.

        Unfortunately, there's no function that I know of, that automatically does what you want.

        To iterate hierarchies, see this blogpost[URL-REMOVED] (this is about the code in the thread you linked).
        Those are helper functions, you should always use them, when it comes to hierarchies.


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

        1 Reply Last reply Reply Quote 2
        • CairynC
          Cairyn
          last edited by Cairyn

          Your two lines

          GetObjects(kid)
          objList += kid
          

          make no sense. The first one calls the recursion but then throws the result away as it is not stored anywhere (objList is a local variable for the function, not a global, and does not exist beyond the context of the current method execution). The second tries to extend a list by a single object instead of another list (the operator += works like extend, not like append) and fails because it cannot iterate through a single object. (Even if you had used the append method or listified kid it would still fail logically because you have already added the kid in the recursion call and then threw it all away.)

          What you need to do is extend the local objList by the result list of the recursion call:

          objList += GetObjects(kid)
          

          or in context,

          import c4d
          from c4d import gui
          
          def GetObjects(obj):
                objList = [obj]
                for kid in obj.GetChildren(): 
                    objList += GetObjects(kid)
                return objList # should return the parent/selected obejct and all its chidlren
          
          def main():
              test = doc.SearchObject("shoulder_jnt")          
              ikJointChain = GetObjects(test)
              print ikJointChain
          
          if __name__=='__main__':
              main()
          
          1 Reply Last reply Reply Quote 5
          • B
            bentraje
            last edited by

            @mp5gosu

            Thanks for the response and for the link regarding recursive and nonrecusive distinction, but I think the recursive version is shorter to write

            @Cairyn

            Thanks for the revised script. Works as expected. To be honest, I really do not know Python in C4D per se. I'm just winging it. Hahaha.
            So, thanks for the explanation!

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