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

    Find Lowest Position of Object

    Scheduled Pinned Locked Moved PYTHON Development
    6 Posts 0 Posters 1.8k Views
    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 Offline
      Helper
      last edited by

      On 10/08/2018 at 11:19, xxxxxxxx wrote:

      I'm looking for a way to find the lowest position of an object, whether primitive or poly. I thought this would be easy, just get the bounding box and find get it's minimum position. It seems the python bounding box doesn't have this kind of function. I can use GetRad() but that doesn't technically find the lowest position either. I'm pretty sure Xpresso even has this ability but as far as python I'm kind of stumped:/

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

        On 13/08/2018 at 03:07, xxxxxxxx wrote:

        Hi Motion4D, there is no such function in the SDK.
        Since the Bounding box is in local space in some situation, if you are looking for global space minus, it can give you a wrong result.
        So the only reliable way to do it is by iterating over all points and get its global position.

        Here a quick sample.

        import c4d
          
        def main() :
            objs = doc.GetActiveObjects(0)
            for obj in objs:
                if not obj.CheckType(c4d.Opolygon) :
                    continue
          
                pts = obj.GetAllPoints()
                if not pts:
                    continue
          
                mg = obj.GetMg()
          
                minPos = c4d.Vector(obj.GetPoint(0) * mg).y
                minId = None
          
                for i in xrange(obj.GetPointCount()) :
                    bufferMin = c4d.Vector(obj.GetPoint(i) * mg).y
                    minPos = min(minPos, bufferMin)
                    if minPos == bufferMin:
                        minId = i
          
                print "{} : MinId = {} : MinPos = {}".format(obj.GetName(), minId, minPos)
          
            return True
          
          
        if __name__=='__main__':
            main()
        

        If you have any questions please, let me know 🙂
        Cheers,
        Maxime!

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

          On 13/08/2018 at 11:16, xxxxxxxx wrote:

          Hey MaximeA!

          Thank you that detailed explanation and all of the helpful code!

          Worked perfectly for poly objects. Is it possible to find on Primitives as well? I'm assuming GetPoint() doesn't work for them?

          At that point would you have to make a copy, convert to poly, find lowest point, delete copy?

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

            On 13/08/2018 at 12:34, xxxxxxxx wrote:

            So I found that the GetBBox() function in the Utils module will do it even for primitives. All you have to do is feed in a standard zero'd out matrix for the second argument. It gives you the Center position along with the Radius number needed to find the lowest position:) At least it's working so far.

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

              On 14/08/2018 at 06:56, xxxxxxxx wrote:

              Hi Motion4D, sadly GetBBox don't produce the result you would expect since BoundingBox is cubes and not rectangles. That have a huge impact, for example, let's take a cube. Simply rotate the Z axis (Banking) in pivot mode, so the cube doesn't move, but the pivot actually move. If you call GetBBox you will end with a point lower than the actual real lowest point position. In the display mode switch to box (N~K) you will see the actual bounding box, which is a cube where the whole object is contained in.

              With that said, each generator store a cache of a PolygonObject. To access such cache I recommend you to read this topic which gets the solution.
              https://developers.maxon.net/forum/topic/398/13533_get-deformed-points-solved&PID=53669#53669 or even the C++ manual about BaseObject Cache.

              If you have any questions please, let me know 🙂
              Cheers,
              Maxime!

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

                On 14/08/2018 at 14:15, xxxxxxxx wrote:

                Yep thanks again Maxime!

                It worked perfectly with primitive cubes but as soon as the anchor point changed from the center or things got deformed it fell apart. It sounds like your suggestion of the BaseObject Cache is what I need to look at. Thanks for the suggestion!

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