Reorder gradient knots by position



  • Hello,
    I'm searching a method to get gradient Knot by position not by index, the problem with gradient->GetKnot(i) is that when user change the knots position and knots order, the knot index stay the same for each knot.

    I had create the following python function to get knot by position and I sorted them from lower to higher knot position.

    def GetKnotByPos(gradient, index): 
        KnotDict = {}
        
        knotCount = gradient.GetKnotCount()
        
        for i in range(knotCount) :
            KnotDict[gradient.GetKnot(i)['pos']] = gradient.GetKnot(i)
        
        # dictionary’s keys select.
        Ks = list(KnotDict.keys())
        Ks.sort()
        return KnotDict[Ks[index]]['col']
    
    # Use
    gradient = op[c4d.MYOBJECT_GRADIENT]
    for index in range(gradient.GetKnotCount()):
        color = GetKnotByPos(gradient, index)
    
    

    I'm searching how to do the same thing but using c++.

    const Int32 knotCount = gradient->GetKnotCount();
    for (Int32 i = 0; i < knotCount; i++)
    {
    	GradientKnot knot = gradient->GetKnot(i);
    	const Vector color = knot.col;
    
    	result += String::VectorToString(color) + "\n";
    }
    


  • Hello,

    you can use a maxon::BaseArray to store elements in a list. You can use maxon::BaseSort to define a class that is able to sort the elements of such a BaseArray.

    In the case of GradientKnots, it could look like this:

    // custom BaseSort based class
    class GradientSort : public maxon::BaseSort<GradientSort, maxon::BASESORTFLAGS::NONE>
    {
    public:
      static inline Bool LessThan(GradientKnot a, GradientKnot b)
      {
        return a.pos < b.pos;
      }
    };
    
    const Int32 knotCount = gradient->GetKnotCount();
    
    // prepare array
    maxon::BaseArray<GradientKnot> knots;
    knots.EnsureCapacity(knotCount) iferr_return;
    
    // fill array
    for (Int32 i = 0; i < knotCount; i++)
    {
      GradientKnot knot = gradient->GetKnot(i);
      knots.Append(knot) iferr_return;
    }
    
    // sort the elements stored in the array
    GradientSort sort;
    sort.Sort(knots);
    
    // check order
    for (GradientKnot& knot : knots)
    {
      DiagnosticOutput("Pos: @", knot.pos);
    }
    

    best wishes,
    Sebastian



  • @s_bach

    Hi Sebastian,
    Perfect, thank you very much.

    Best regards,
    Mustapha


Log in to reply