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

    Automatically adapting SoftSelection Radius

    Scheduled Pinned Locked Moved PYTHON Development
    8 Posts 0 Posters 577 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 07/02/2013 at 03:38, xxxxxxxx wrote:

      Hi everyone, first post in this forum. I'm a long time programmer (C++, C#) but relatively new to Python in Cinema 4D and I'm trying to create a simple script that automatically enables soft selection for move, scale and rotate tools and sets the radius to the radius of the current selection. My question is (sorry if it's obviuos) : what modeling command should I call in the SendModelingCommand instruction to access Move, Rotate and Scale tools since I can't find them in the list of available commands?
      Thanks in advance,
      Michele

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

        On 07/02/2013 at 05:10, xxxxxxxx wrote:

        the ids are ID_MODELING_MOVE, ...SCALE and ...ROTATE. but they are not modelling commands,
        but tools, so you should send them either with c4d.CallCommand or BaseDocument.SetActive .

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

          On 07/02/2013 at 06:17, xxxxxxxx wrote:

          Thanks a lot for the answer. So how can I set parameters like Soft Selection Radius if I can't send the values in the c4d.BaseContainer like with any other modeling command?
          Thanks for your time and help!

          Michele

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

            On 07/02/2013 at 06:18, xxxxxxxx wrote:

            You can't. You can try to use the SMC, but I don't know if it will work. It is however very easy to do the
            soft-offsetting manually. This would also give you more control.

            Edit: Oh wait, I think there was a method for getting the current tools
            container. Search for GetTool or something similar. I don't have the docs
            on m smartphone..

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

              On 07/02/2013 at 07:32, xxxxxxxx wrote:

              soft selections are not part of the move,rotate and scale tools, they are a separate plugin.

                  bp = c4d.plugins.FindPlugin(c4d.ID_MODELING_SOFTSELECTION)
                  bp[c4d.MDATA_SOFT_ENABLE] = not bp[c4d.MDATA_SOFT_ENABLE]
                
                  c4d.EventAdd()
              
              1 Reply Last reply Reply Quote 0
              • H Offline
                Helper
                last edited by

                On 07/02/2013 at 08:52, xxxxxxxx wrote:

                Thanks a lot ferdinand and NiklasR!

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

                  On 07/02/2013 at 09:39, xxxxxxxx wrote:

                  Hi larsen,

                  the following code has exactly the same effect as the soft-selection moving the points when using
                  it with radius = 100, falloff = linear and offsetting the points about (0, 0, 100).

                  Note that I used the c4dtools module for computing the midpoint. You can find the source-code
                  for this function here: https://github.com/NiklasRo...

                  import c4d
                  import c4dtools
                  import itertools
                  import collections
                    
                  def soft_move(op, sel, offset, falloff, radius) :
                      r"""
                      Move the points in the selection *sel* of *op* about the *offset*
                      with the falloff described by the callable object *falloff*.
                      @param op c4d.PointObject instance
                      @param sel c4d.BaseSelect instance
                      @param offset c4d.Vector instance
                      @param falloff Callable object accepting a floating-point value as
                      sole argument (between 0 and 1, including) and returning a
                      floating-point argument as multiplier.
                      @param radius The radius for the soft selection.
                      """
                    
                      if not isinstance(op, c4d.PointObject) :
                          raise TypeError('expected c4d.PointObject for parameter `op`')
                      if not isinstance(sel, c4d.BaseSelect) :
                          raise TypeError('expected c4d.BaseSelect for parameter `sel`')
                      if not isinstance(offset, c4d.Vector) :
                          raise TypeError('expected c4d.Vector for parameter `offset`')
                      if not isinstance(falloff, collections.Callable) :
                          raise TypeError('expected callable object for parameter `falloff`')
                    
                      points = op.GetAllPoints()
                      point_count = op.GetPointCount()
                      sel_count = sel.GetCount()
                    
                      if point_count <= 0 or sel_count <= 0:
                          return
                    
                      # Compute the mid-point of the selected points.
                      midp = []
                      for i, p in itertools.izip(xrange(point_count), points) :
                          if sel.IsSelected(i) :
                              midp.append(p)
                      midp = c4dtools.utils.vbbmid(midp)
                    
                      # Offset all points.
                      for i, p in itertools.izip(xrange(point_count), points) :
                          distance = (midp - p).GetLength()
                          if distance > radius:
                              continue
                    
                          x = falloff(distance / radius)
                          p = p + offset * x
                          op.SetPoint(i, p)
                    
                  def main() :
                      if not op or not op.CheckType(c4d.Opoint) :
                          return
                    
                      offset = c4d.Vector(0, 0, 100)
                      falloff = lambda x: (1-x)
                      radius = 100
                      doc.AddUndo(c4d.UNDOTYPE_CHANGE, op)
                      soft_move(op, op.GetPointS(), offset, falloff, radius)
                      op.Message(c4d.MSG_UPDATE)
                      c4d.EventAdd()
                    
                  if __name__ == "__main__":
                      main()
                  

                  Best,
                  Niklas

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

                    On 07/02/2013 at 10:33, xxxxxxxx wrote:

                    Niklas, thank you very much for taking the time to help me! Also your c4dtools module is great!
                    THANKS!

                    Kind regards,

                    Michele

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