POV-Ray : Newsgroups : povray.beta-test : Filling in T values in splines : Re: Filling in T values in splines Server Time
30 Jul 2024 06:23:24 EDT (-0400)
  Re: Filling in T values in splines  
From: Christopher James Huff
Date: 24 Feb 2002 13:56:57
Message: <chrishuff-A6AAB1.13564924022002@netplex.aussie.org>
In article <3c7919a9@news.povray.org>,
 "Rune" <run### [at] mobilixnetdk> wrote:

> I've done that before and it's not that slow. However, a solution I'd like
> to try is to return a new spline which has many more control points than the
> original and where those control points are arranged to give constant speed.

I've done that before, but never finished because of bugs in the spline 
feature. Here are the (partially complete) macros:

//  Persistence of Vision Ray Tracer version 3.5 Include File
//  File: splines.inc
//  Last updated: 2001.8.8
//  Description: Spline-handling and interpolation macros

#ifndef(SPLINES_INC_TEMP)
#declare SPLINES_INC_TEMP = version;
#version 3.5;

#declare LINEAR_SPLINE = 0;
#declare QUADRATIC_SPLINE = 1;
#declare CUBIC_SPLINE = 2;


#macro SPLINE_TYPE(Type)
    #switch(Type)
        #case(LINEAR_SPLINE)
            linear_spline
        #break
        #case(QUADRATIC_SPLINE)
            quadratic_spline
        #break
        #case(CUBIC_SPLINE)
            cubic_spline
        #break
    #end
#end


//Assumes spline T is in range [0, 1]
#macro Spline_Length(Spline, Intervals)
    #local Len = 0;
    #local PtA = 0+Spline(0);
    #local J = 0;
    #while(J < Intervals)
        #local PtB = 0+Spline((J + 1)/Intervals);
        #local Len = Len + vlength(PtB - PtA);
        #local PtA = PtB;
        #local J = J + 1;
    #end
    
    (Len)
#end

#macro Spline_Interval_Length(Spline, StartT, EndT, Intervals)
    #local Len = 0;
    #local PtA = (Spline(StartT));
    #local J = 0;
    #while(J < Intervals)
        #local PtB = 0+Spline((EndT - StartT)*(J + 1)/Intervals + 
StartT);
        #local Len = Len + vlength(PtB - PtA);
        #local PtA = PtB;
        #local J = J + 1;
    #end
    
    (Len)
#end

#macro Constant_Speed_Spline(Spline, Type, Intervals, Samples)
    #local SplineLen = Spline_Length(Spline, Intervals*Samples);
    
    spline {SPLINE_TYPE(Type)
        0, < 0, 0, 0>+Spline(0)
        #local DistPassed = 0;
        #local J = 0;
        #while(J < Intervals)
            #local IntLen = Spline_Interval_Length(Spline, J/Intervals, 
(J + 1)/Intervals, Samples);
            #local DistPassed = DistPassed + IntLen;
            DistPassed/SplineLen, < 0, 0, 0>+Spline((J + 1)/Intervals)
            #local J = J + 1;
        #end
    }
#end

#macro SPLINE_FindNextT(StIdx, Array)
    #local PointNum = dimension_size(Array, 1);
    #local K = StIdx;
    #local Res = StIdx;
    #while(K < PointNum)
        #if(!VEq(Array[K][0], x))
            #local Res = K;
            #break
        #else
            #local K = K + 1;
        #end
    #end
    (Res)
#end

#macro Spline_From_Array(Type, ConstantSpeedSamples, Array)
    #local PointNum = dimension_size(Array, 1);
    #if(ConstantSpeedSamples > 0)
        #local Method = 3;
    #else
        #local Method = dimensions(Array);
    #end
    spline {SPLINE_TYPE(Type)
        #switch(Method)
            #case(1)
                //No T values specified, autocompute all with even time 
gaps
                #debug "Spline_From_Array() method 1"
                #local J = 0;
                #while(J < PointNum - 1)
                    J/(PointNum - 1), Array[J],
                    #local J = J + 1;
                #end
                1, Array[PointNum - 1]
            #break
            
            #case(2)
                //T values specified, autocompute only for gaps
                #debug "Spline_From_Array() method 2"
                #local J = 0;
                #local NextTIdx = SPLINE_FindNextT(1, Array);
                #while(J < PointNum - 1)
                    #if(VEq(Array[J][0], x))
                        #if(J > NextIdx)
                            #local NextTIdx = SPLINE_FindNextT(StIdx, 
Array);
                        #end
                                                
                        #local LastT = Array[LastTIdx][0].y;                        
                        
#local NextT = Array[NextTIdx][0].y;
                        #local Offset = (J - LastTIdx)/(NextTIdx - 
LastTIdx);
                        #local TVal = (NextT - LastT)*Offset + LastT;
                    #else
                        #local LastTIdx = J;
                        #local TVal = Array[J][0].y;
                    #end
                    TVal, Array[J][1],
                    #local J = J + 1;
                #end
                1, Array[PointNum - 1][1]
            #break
            
            #case(3)
                #debug "Spline_From_Array() method 3"
                #warning "This method is not yet implemented"
                //Ignore any T values specified, autocompute all for 
constant speed
                #local Reference = Spline_From_Array(Type, no, Array)
                #local SplLen = Spline_Length(Reference, 
PointNum*ConstantSpeedSamples);
                #local DistPassed = 0;
                #local J = 0;
                #if(dimensions(Array) = 1)
                    0, Array[0],
                    #while(J < PointNum - 1)
                        #local IntLen = 
Spline_Interval_Length(Reference, Array[J][0].y, Array[J + 1][0].y, 
ConstantSpeedSamples);
                        #local DistPassed = DistPassed + IntLen;
                            DistPassed/SplLen, Array[J + 1],
                        #local J = J + 1;
                    #end
                #else
                    0, Array[0][1],
                    #while(J < PointNum - 1)
                        #local IntLen = 
Spline_Interval_Length(Reference, Array[J][0].y, Array[J + 1][0].y, 
ConstantSpeedSamples);
                        #local DistPassed = DistPassed + IntLen;
                            DistPassed/SplLen, Array[J + 1][1],
                        #local J = J + 1;
                    #end
                #end
            #break
        #end
    }
#end

#version SPLINES_INC_TEMP;
#end//splines.inc

-- 
Christopher James Huff - chr### [at] maccom, 
http://homepage.mac.com/chrishuff/
TAG: chr### [at] tagpovrayorg, http://tag.povray.org/

<><

-- 
Christopher James Huff <chr### [at] maccom>
POV-Ray TAG e-mail: chr### [at] tagpovrayorg
TAG web site: http://tag.povray.org/


Post a reply to this message

Copyright 2003-2023 Persistence of Vision Raytracer Pty. Ltd.