EASING functions for moving Objects

Share your advanced PureBasic knowledge/code with the community.
User avatar
eddy
Addict
Addict
Posts: 1479
Joined: Mon May 26, 2003 3:07 pm
Location: Nantes

EASING functions for moving Objects

Post by eddy »

Here is some easing functions.
It can be used to code motions or effects.
(Need 4.4x)

Code: Select all

Enumeration ;list of EASING types 
   #EASE_Linear=0
   #EASE_Min_In
   #EASE_Min_Out
   #EASE_Min_InOut
   #EASE_Light_In
   #EASE_Light_Out
   #EASE_Light_InOut
   #EASE_Medium_In
   #EASE_Medium_Out
   #EASE_Medium_InOut
   #EASE_Heavy_In
   #EASE_Heavy_Out
   #EASE_Heavy_InOut
   #EASE_Max_In
   #EASE_Max_Out
   #EASE_Max_InOut
   
   #EASE_Sine_In
   #EASE_Sine_Out
   #EASE_Sine_InOut
   #EASE_Circular_In
   #EASE_Circular_Out
   #EASE_Circular_InOut
   #EASE_Back_In
   #EASE_Back_Out
   #EASE_Back_InOut
   #EASE_Bounce_In
   #EASE_Bounce_Out
   #EASE_Bounce_InOut
   #EASE_Elastic_In
   #EASE_Elastic_Out
   #EASE_Elastic_InOut
   #EASE_last
EndEnumeration

#MAX_EASING=$10000
Global Dim EASING.f(#EASE_last-1, #MAX_EASING)
Procedure InitEase()
   Protected.i i, b=0, c=1, d=#MAX_EASING, in=0, out=0, ease
   Protected.f s=1.70158, s1=s*1.525
   Protected.f p=d*0.3, p1=p*1.5
   
   For i=0 To d
      Protected t.f=i/d
      Protected k.f=t*2
      If k<1 : in=1 : out=0 : Else : in=0 : out=1 : EndIf
      
      EASING(#EASE_Linear, i)=t
      
      Protected t1.f=t-1
      Protected k1.f=k-1
      Protected k2.f=k-2
      EASING(#EASE_Min_In, i)=c*t*t+b
      EASING(#EASE_Min_Out, i)=-c*t*(t-2)+b
      If in : EASING(#EASE_Min_InOut, i)=(c/2*k*k+b) : EndIf
      If out : EASING(#EASE_Min_InOut, i)=(-c/2*(k1*(k1-2)-1)+b) : EndIf
      
      EASING(#EASE_Light_In, i)=c*t*t*t+b
      EASING(#EASE_Light_Out, i)=c*(t1*t1*t1+1)+b
      If in : EASING(#EASE_Light_InOut, i)=(c/2*k*k*k+b) : EndIf
      If out : EASING(#EASE_Light_InOut, i)=(c/2*(k2*k2*k2+2)+b) : EndIf
      
      EASING(#EASE_Medium_In, i)=c*t*t*t*t+b
      EASING(#EASE_Medium_Out, i)=-c*(t1*t1*t1*t1-1)+b
      If in : EASING(#EASE_Medium_InOut, i)=(c/2*k*k*k*k+b) : EndIf
      If out : EASING(#EASE_Medium_InOut, i)=(-c/2*(k2*k2*k2*k2-2)+b) : EndIf
      
      EASING(#EASE_Heavy_In, i)=c*t*t*t*t*t+b
      EASING(#EASE_Heavy_Out, i)=c*(t1*t1*t1*t1*t1+1)+b
      If in : EASING(#EASE_Heavy_InOut, i)=(c/2*k*k*k*k*k+b) : EndIf
      If out : EASING(#EASE_Heavy_InOut, i)=(c/2*(k2*k2*k2*k2*k2+2)+b) : EndIf
      
      EASING(#EASE_Max_In, i)=c*Pow(2, 10*(t1))+b : If i=0 : EASING(#EASE_Max_In, i)=b : EndIf
      EASING(#EASE_Max_Out, i)=c*(-Pow(2, -10*t)+1)+b : If i=d : EASING(#EASE_Max_Out, i)=b+c : EndIf
      If in : EASING(#EASE_Max_InOut, i)=(c/2*Pow(2, 10*k1)+b) : EndIf
      If out : EASING(#EASE_Max_InOut, i)=(c/2*(-Pow(2, -10*k1)+2)+b) : EndIf
      
      EASING(#EASE_Sine_In, i)=-c*Cos(t*(#PI/2))+c+b
      EASING(#EASE_Sine_Out, i)=c*Sin(t*(#PI/2))+b
      EASING(#EASE_Sine_InOut, i)=-c/2*(Cos(#PI*t)-1)+b
      
      EASING(#EASE_Circular_In, i)=-c*(Sqr(1-t*t)-1)+b
      EASING(#EASE_Circular_Out, i)=c*Sqr(1-t1*t1)+b
      If in : EASING(#EASE_Circular_InOut, i)=(-c/2*(Sqr(1-k*k)-1)+b) : EndIf
      If out : EASING(#EASE_Circular_InOut, i)=(c/2*(Sqr(1-k2*k2)+1)+b) : EndIf
      
      EASING(#EASE_Back_In, i)=c*t*t*((s+1)*t-s)+b
      EASING(#EASE_Back_Out, i)=c*(t1*t1*((s+1)*t1+s)+1)+b
      If in : EASING(#EASE_Back_InOut, i)=(c/2*(k*k*((s1+1)*k-s1))+b) : EndIf
      If out : EASING(#EASE_Back_InOut, i)=(c/2*(k2*k2*((s1+1)*k2+s1)+2)+b) : EndIf
      
      If (t=0)
         EASING(#EASE_Elastic_In, i)=b
         EASING(#EASE_Elastic_Out, i)=b
         EASING(#EASE_Elastic_InOut, i)=b
      ElseIf (t=1)
         EASING(#EASE_Elastic_In, i)=b+c
         EASING(#EASE_Elastic_Out, i)=b+c
         EASING(#EASE_Elastic_InOut, i)=b+c
      Else
         Protected.f a, se, se1
         If (a=0 Or a<Abs(c))
            a=c
            se=p/4
            se1=p1/4
         Else
            se=p/(2*#PI)*ASin(c/a)
            se1=p1/(2*#PI)*ASin(c/a)
         EndIf
         EASING(#EASE_Elastic_In, i)=-(a*Pow(2, 10*t1)*Sin((t1*d-se)*(2*#PI)/p))+b
         EASING(#EASE_Elastic_Out, i)=(a*Pow(2, -10*t)*Sin((t*d-se)*(2*#PI)/p)+c+b)
         If in : EASING(#EASE_Elastic_InOut, i)=(-0.5*(a*Pow(2, 10*(k1))*Sin((k1*d-se1)*(2*#PI)/p1))+b) : EndIf
         If out : EASING(#EASE_Elastic_InOut, i)=(a*Pow(2, -10*(k1))*Sin((k1*d-se1)*(2*#PI)/p1)*0.5+c+b) : EndIf
      EndIf
      
      If (t<(1/2.75))
         EASING(#EASE_Bounce_Out, i)=c*(7.5625*t*t)+b
      ElseIf (t<(2/2.75))
         t-(1.5/2.75)
         EASING(#EASE_Bounce_Out, i)=c*(7.5625*t*t+0.75)+b
      ElseIf (t<(2.5/2.75))
         t-(2.25/2.75)
         EASING(#EASE_Bounce_Out, i)=c*(7.5625*t*t+0.9375)+b
      Else
         t-(2.625/2.75)
         EASING(#EASE_Bounce_Out, i)=c*(7.5625*t*t+0.984375)+b
      EndIf
      EASING(#EASE_Bounce_In, d-i)=c-EASING(#EASE_Bounce_Out, i)+2*b
   Next
   For i=0 To d
      t.f=i/d
      k.f=t*2
      If k<1 : in=1 : out=0 : Else : in=0 : out=1 : EndIf
      
      If in : EASING(#EASE_Bounce_InOut, i)=EASING(#EASE_Bounce_In, i*2)*0.5+b : EndIf
      If out : EASING(#EASE_Bounce_InOut, i)=EASING(#EASE_Bounce_Out, i*2-d)*0.5+c*0.5+b : EndIf
   Next
   
EndProcedure
Procedure.f EasingTime(time, duration, easing)
   Protected i=#MAX_EASING*time/duration
   If i<0 Or i>#MAX_EASING
      ProcedureReturn #False
   Else
      ProcedureReturn EASING(easing, i)
   EndIf
EndProcedure
Procedure.f EasingPercent(percent, easing)
   Protected i=#MAX_EASING*percent/100.0
   If i<0 Or i>#MAX_EASING
      ProcedureReturn #False
   Else
      ProcedureReturn EASING(easing, i)
   EndIf
EndProcedure
InitEase()

; ********************
; TEST
; ********************

Procedure.i PositionCalculation(TimeInSecond, DurationInSecond, Start, Distance)
   Protected Position=Start+Distance*EasingTime(TimeInSecond, DurationInSecond, #EASE_Light_In)
   ProcedureReturn Position
EndProcedure

Procedure.i PositionCalculation2(ProgressInPercent, Start, Distance)
   Protected Position=Start+Distance*EasingPercent(ProgressInPercent, #EASE_Light_In)
   ProcedureReturn Position
EndProcedure

Debug PositionCalculation(20, 60, 10, 1000) ;// 20s ellapsed
Debug PositionCalculation2(40, 10, 1000) ;// 40% 
Imagewin10 x64 5.72 | IDE | PB plugin | Tools | Sprite | JSON | visual tool
User avatar
eddy
Addict
Addict
Posts: 1479
Joined: Mon May 26, 2003 3:07 pm
Location: Nantes

Re: EASING functions

Post by eddy »

Easing effects on motion :mrgreen:

Image
Imagewin10 x64 5.72 | IDE | PB plugin | Tools | Sprite | JSON | visual tool
User avatar
Fluid Byte
Addict
Addict
Posts: 2336
Joined: Fri Jul 21, 2006 4:41 am
Location: Berlin, Germany

Re: EASING functions

Post by Fluid Byte »

---------------------------
PureBasic
---------------------------
Line 40: Syntax error.
---------------------------
OK
---------------------------
Windows 10 Pro, 64-Bit / Whose Hoff is it anyway?
User avatar
Kaeru Gaman
Addict
Addict
Posts: 4826
Joined: Sun Mar 19, 2006 1:57 pm
Location: Germany

Re: EASING functions

Post by Kaeru Gaman »

@eddy
give your code a Header wich states the Version it runs with.
if you publish code that runs with a beta but not with the stable you name in your signature, you should at least tell the folks.

Additionally, some Documentation how to use this code and what to do with it would be nice ... no, even necessary!
debugging two values is no description.
It may be some great functionallity, but atm you don't see nothing, it's just disappointing to run it.
the screenshot is the only thing that gives a slight idea what it is all about.
to most people "easing" is what they do on the toilet, so you should give a whole bunch of information what this is all about.
oh... and have a nice day.
Seymour Clufley
Addict
Addict
Posts: 1265
Joined: Wed Feb 28, 2007 9:13 am
Location: London

Re: EASING functions for moving Objects

Post by Seymour Clufley »

Eddy,

First, thank you for all the fine code you post on this forum.

However, the code isn't much good without a demo program. The screenshot looks amazing, but I need to know how to use the code to make an image like that!

Thank you,
Seymour.
JACK WEBB: "Coding in C is like sculpting a statue using only sandpaper. You can do it, but the result wouldn't be any better. So why bother? Just use the right tools and get the job done."
User avatar
Rook Zimbabwe
Addict
Addict
Posts: 4322
Joined: Tue Jan 02, 2007 8:16 pm
Location: Cypress TX
Contact:

Re: EASING functions for moving Objects

Post by Rook Zimbabwe »

I redid it to werk with PB4.3

Code: Select all


Procedure InitEase()
   Protected i, b=0, c=1, d=#MAX_EASING, INp=0, OUTp=0, ease
   Protected s=1.70158, s1=s*1.525
   Protected p=d*0.3, p1=p*1.5
   
   For i=0 To d
      Protected t.f=i/d
      Protected k.f=t*2
      If k<1 : INp=1 : OUTp=0 : Else : INp=0 : OUTp=1 : EndIf
      
      EASING(#EASE_Linear, i)=t
      
      Protected t1.f=t-1
      Protected k1.f=k-1
      Protected k2.f=k-2
      EASING(#EASE_Min_In, i)=c*t*t+b
      EASING(#EASE_Min_Out, i)=-c*t*(t-2)+b
      If INp : EASING(#EASE_Min_InOut, i)=(c/2*k*k+b) : EndIf
      If OUTp : EASING(#EASE_Min_InOut, i)=(-c/2*(k1*(k1-2)-1)+b) : EndIf
      
      EASING(#EASE_Light_In, i)=c*t*t*t+b
      EASING(#EASE_Light_Out, i)=c*(t1*t1*t1+1)+b
      If INp : EASING(#EASE_Light_InOut, i)=(c/2*k*k*k+b) : EndIf
      If OUTp : EASING(#EASE_Light_InOut, i)=(c/2*(k2*k2*k2+2)+b) : EndIf
      
      EASING(#EASE_Medium_In, i)=c*t*t*t*t+b
      EASING(#EASE_Medium_Out, i)=-c*(t1*t1*t1*t1-1)+b
      If INp : EASING(#EASE_Medium_InOut, i)=(c/2*k*k*k*k+b) : EndIf
      If OUTp : EASING(#EASE_Medium_InOut, i)=(-c/2*(k2*k2*k2*k2-2)+b) : EndIf
      
      EASING(#EASE_Heavy_In, i)=c*t*t*t*t*t+b
      EASING(#EASE_Heavy_Out, i)=c*(t1*t1*t1*t1*t1+1)+b
      If INp : EASING(#EASE_Heavy_InOut, i)=(c/2*k*k*k*k*k+b) : EndIf
      If OUTp : EASING(#EASE_Heavy_InOut, i)=(c/2*(k2*k2*k2*k2*k2+2)+b) : EndIf
      
      EASING(#EASE_Max_In, i)=c*Pow(2, 10*(t1))+b : If i=0 : EASING(#EASE_Max_In, i)=b : EndIf
      EASING(#EASE_Max_Out, i)=c*(-Pow(2, -10*t)+1)+b : If i=d : EASING(#EASE_Max_Out, i)=b+c : EndIf
      If INp : EASING(#EASE_Max_InOut, i)=(c/2*Pow(2, 10*k1)+b) : EndIf
      If OUTp : EASING(#EASE_Max_InOut, i)=(c/2*(-Pow(2, -10*k1)+2)+b) : EndIf
      
      EASING(#EASE_Sine_In, i)=-c*Cos(t*(#PI/2))+c+b
      EASING(#EASE_Sine_Out, i)=c*Sin(t*(#PI/2))+b
      EASING(#EASE_Sine_InOut, i)=-c/2*(Cos(#PI*t)-1)+b
      
      EASING(#EASE_Circular_In, i)=-c*(Sqr(1-t*t)-1)+b
      EASING(#EASE_Circular_Out, i)=c*Sqr(1-t1*t1)+b
      If INp : EASING(#EASE_Circular_InOut, i)=(-c/2*(Sqr(1-k*k)-1)+b) : EndIf
      If OUTp : EASING(#EASE_Circular_InOut, i)=(c/2*(Sqr(1-k2*k2)+1)+b) : EndIf
      
      EASING(#EASE_Back_In, i)=c*t*t*((s+1)*t-s)+b
      EASING(#EASE_Back_Out, i)=c*(t1*t1*((s+1)*t1+s)+1)+b
      If INp : EASING(#EASE_Back_InOut, i)=(c/2*(k*k*((s1+1)*k-s1))+b) : EndIf
      If OUTp : EASING(#EASE_Back_InOut, i)=(c/2*(k2*k2*((s1+1)*k2+s1)+2)+b) : EndIf
      
      If (t=0)
         EASING(#EASE_Elastic_In, i)=b
         EASING(#EASE_Elastic_Out, i)=b
         EASING(#EASE_Elastic_InOut, i)=b
      ElseIf (t=1)
         EASING(#EASE_Elastic_In, i)=b+c
         EASING(#EASE_Elastic_Out, i)=b+c
         EASING(#EASE_Elastic_InOut, i)=b+c
      Else
         Protected a, se, se1
         If (a=0 Or a<Abs(c))
            a=c
            se=p/4
            se1=p1/4
         Else
            se=p/(2*#PI)*ASin(c/a)
            se1=p1/(2*#PI)*ASin(c/a)
         EndIf
         EASING(#EASE_Elastic_In, i)=-(a*Pow(2, 10*t1)*Sin((t1*d-se)*(2*#PI)/p))+b
         EASING(#EASE_Elastic_Out, i)=(a*Pow(2, -10*t)*Sin((t*d-se)*(2*#PI)/p)+c+b)
         If INp : EASING(#EASE_Elastic_InOut, i)=(-0.5*(a*Pow(2, 10*(k1))*Sin((k1*d-se1)*(2*#PI)/p1))+b) : EndIf
         If OUTp : EASING(#EASE_Elastic_InOut, i)=(a*Pow(2, -10*(k1))*Sin((k1*d-se1)*(2*#PI)/p1)*0.5+c+b) : EndIf
      EndIf
      
      If (t<(1/2.75))
         EASING(#EASE_Bounce_Out, i)=c*(7.5625*t*t)+b
      ElseIf (t<(2/2.75))
         t-(1.5/2.75)
         EASING(#EASE_Bounce_Out, i)=c*(7.5625*t*t+0.75)+b
      ElseIf (t<(2.5/2.75))
         t-(2.25/2.75)
         EASING(#EASE_Bounce_Out, i)=c*(7.5625*t*t+0.9375)+b
      Else
         t-(2.625/2.75)
         EASING(#EASE_Bounce_Out, i)=c*(7.5625*t*t+0.984375)+b
      EndIf
      EASING(#EASE_Bounce_In, d-i)=c-EASING(#EASE_Bounce_Out, i)+2*b
   Next
   For i=0 To d
      t.f=i/d
      k.f=t*2
      If k<1 : INp=1 : OUTp=0 : Else : INp=0 : OUTp=1 : EndIf
      
      If INp : EASING(#EASE_Bounce_InOut, i)=EASING(#EASE_Bounce_In, i*2)*0.5+b : EndIf
      If OUTp : EASING(#EASE_Bounce_InOut, i)=EASING(#EASE_Bounce_Out, i*2-d)*0.5+c*0.5+b : EndIf
   Next
   
EndProcedure
Replace theis procedure... It gives me two values in the debugger is all... console only gives me nada.

Does need to draw or plot something on a window though...
Binarily speaking... it takes 10 to Tango!!!

Image
http://www.bluemesapc.com/
User avatar
eddy
Addict
Addict
Posts: 1479
Joined: Mon May 26, 2003 3:07 pm
Location: Nantes

Re: EASING functions for moving Objects

Post by eddy »

It's just an extract from my sprite lib : http://www.purebasic.fr/english/viewtop ... 12&t=38447

If you need more infos, there's a thread about this functionality : http://www.purebasic.fr/english/viewtop ... 16&t=39259
I took time to convert the actionscript to PB.
Sorry but I can't convert the whole project. :|

If you have time to code a simple example, you can post here.
Imagewin10 x64 5.72 | IDE | PB plugin | Tools | Sprite | JSON | visual tool
User avatar
thyphoon
Enthusiast
Enthusiast
Posts: 355
Joined: Sat Dec 25, 2004 2:37 pm

Re: EASING functions for moving Objects

Post by thyphoon »

Excellent !

Can you add juste a little exemple with a Sprite to understand how to use it ?

Very good job thanks to share with us !
aonyn
User
User
Posts: 43
Joined: Tue May 05, 2009 5:20 am

Re: EASING functions for moving Objects

Post by aonyn »

Very Nice!

I was just browsing back a way in the Tips forum, and stumbled on this.
Very useful, and seems to work well, I have been playing with it for the past hour.

Thanks for sharing Eddy.

regards,
Dave
Post Reply