Wayback Machinekoobas.hobune.stream
May JUN Jul
Previous capture 13 Next capture
2021 2022 2023
1 capture
13 Jun 22 - 13 Jun 22
sparklines
Close Help
  • Products
  • Solutions
  • Made with Unity
  • Learning
  • Support & Services
  • Community
  • Asset Store
  • Get Unity

UNITY ACCOUNT

You need a Unity Account to shop in the Online and Asset Stores, participate in the Unity Community and manage your license portfolio. Login Create account
  • Blog
  • Forums
  • Answers
  • Evangelists
  • User Groups
  • Beta Program
  • Advisory Panel

Navigation

  • Home
  • Products
  • Solutions
  • Made with Unity
  • Learning
  • Support & Services
  • Community
    • Blog
    • Forums
    • Answers
    • Evangelists
    • User Groups
    • Beta Program
    • Advisory Panel

Unity account

You need a Unity Account to shop in the Online and Asset Stores, participate in the Unity Community and manage your license portfolio. Login Create account

Language

  • Chinese
  • Spanish
  • Japanese
  • Korean
  • Portuguese
  • Ask a question
  • Spaces
    • Default
    • Help Room
    • META
    • Moderators
    • Topics
    • Questions
    • Users
    • Badges
  • Home /
avatar image
1
Question by barbe63 · Jun 20, 2015 at 12:11 AM · lerpcurve

Curve between Lerps

Hi,

I'm doing an overview of my level before starting it so I set some Vector3 array for positions and another for rotations. I'm using the method posted here so I can have lerps that occurs with a constant speed: http://www.blueraja.com/blog/404/how-to-use-unity-3ds-linear-interpolation-vector3-lerp-correctly

It's working fine but what I would need is to add some curves between the different lerps.

A little sheme to explain my problem: alt text

My script so far:

 IEnumerator StartOverview()
     {
         //those are not important
         cameraScript=GameObject.FindGameObjectWithTag("Camera").GetComponent<GravityChange>();
         cameraScript.SetControl(false);                  
         GameControl.Instance.canAccessMenu=false;
         Transform cameraTrans = cameraScript.transform;
         //it starts here by declaring some variables
         int i=1;
         float _timeStartedLerping;
         Vector3 _startPosition;
         Vector3 _endPosition;
         Quaternion _startRotation;
         Quaternion _endRotation;
         float timeSinceStarted;
         float percentageComplete;
         float timeTakenDuringLerp;
         Quaternion rot=Quaternion.Euler(rotations[0]);
         //setting the camera position+rotation to the first position+rotation
         cameraTrans.position=positions[0];
         cameraTrans.rotation=rot;
         while(!HUDScript.instance.touch) //while screen is not touched
         {
             //those are ensuring the lerp is going the same speed all along (time according to distance)
             if(i!=0)
                 timeTakenDuringLerp=Vector3.Distance(positions[i], positions[i-1]);
             else 
                 timeTakenDuringLerp=Vector3.Distance(positions[i], positions[positions.Length-1]);
             timeTakenDuringLerp/=10;
             //initiating values
             _timeStartedLerping = Time.time;
             _startPosition = cameraTrans.position;
             _endPosition = positions[i];
             _startRotation = cameraTrans.rotation;
             _endRotation = Quaternion.Euler(rotations[i]); 
             percentageComplete=0;
             while(percentageComplete<1)
             {
                 //the lerp with the method I provided in the link
                 timeSinceStarted = Time.time - _timeStartedLerping;
                 percentageComplete = timeSinceStarted / timeTakenDuringLerp;
                 cameraTrans.position = Vector3.Lerp (_startPosition, _endPosition, percentageComplete);
                 cameraTrans.rotation=Quaternion.Lerp(_startRotation, _endRotation, percentageComplete);
                 yield return null;
             }
             i++;
             if(i==positions.Length)
                 i=0;
         }
         //not important
         HUDScript.instance.overviewOver=true;
         cameraScript.SetControl(true);
         GameControl.Instance.canAccessMenu=true;
     }

What I've tried without success:

 //where _nextposition is positions[i+1] or position[0] if we have to finish the loop
 _endPosition = positions[i]*(1-percentageComplete) + _nextPosition*percentageComplete; 
 
 cameraTrans.position = Vector3.Lerp (_startPosition, _endPosition, percentageComplete)*(1-percentageComplete) + _nextPosition*percentageComplete;

 cameraTrans.position = Vector3.Lerp (_startPosition, _endPosition, percentageComplete)*(1-percentageComplete) + Vector3.Lerp (_endPosition, _nextPosition, percentageComplete)* percentageComplete;
 

All of these 3 methods lead to quite the same result being the lerps aren't regular anymore since I play with the end of the lerp. But i don't see how I would do without playing with it.

All help would really be appreciated!

curves.jpg (27.4 kB)
Comment
Add comment · Show 1
10 |3000 characters needed characters left characters exceeded
▼
  • Viewable by all users
  • Viewable by moderators
  • Viewable by moderators and the original poster
  • Advanced visibility
Viewable by all users
avatar image barbe63 · Jun 20, 2015 at 01:06 AM 0
Share

I found a part of the solution here: http://devmag.org.za/2011/04/05/bzier-curves-a-tutorial/ Now I'm about to find a good way to implement this.

3 Replies

· Add your reply
  • Sort: 
avatar image
1
Best Answer

Answer by barbe63 · Jun 20, 2015 at 04:10 AM

Fixed it after a night struggling!

Here is my new script for those who would be interested to do the same thing (uncommented):

  IEnumerator StartOverview()
     {        
         int i=0;
         float _timeStartedLerping;
         float timeSinceStarted;
         float percentageComplete;
         float timeTakenDuringLerp;
         Vector3 _P0, _P1, _P2, _P3;
         Vector3 lastPosition=cameraTrans.position;
         Vector3 direction=cameraTrans.position;
         bool mustChangeDirection=true;
         cameraTrans.position=positions[0];
         cameraTrans.rotation=Quaternion.LookRotation(CalculateBezierPoint(0.05f, positions[0], positions[1], positions[2], positions[3])-cameraTrans.position);
         while(!HUDScript.instance.touch) //while screen is not touched
         {
             if(i==0)
                 timeTakenDuringLerp=Vector3.Distance(positions[i], positions[i+1])+ Vector3.Distance(positions[i+1], positions[i+2])+Vector3.Distance(positions[i+2], positions[i+3]);
             else if(i!=positions.Length-1)
                 timeTakenDuringLerp=Vector3.Distance(positions[i], positions[i-1]+(positions[i]-positions[i-1])*2)+ Vector3.Distance(positions[i-1]+(positions[i]-positions[i-1])*2, positions[i+1])+Vector3.Distance(positions[i+1], positions[i+2]);
             else 
                 timeTakenDuringLerp=Vector3.Distance(positions[i], positions[i-1]+(positions[i]-positions[i-1])*2)+ Vector3.Distance(positions[i-1]+(positions[i]-positions[i-1])*2, positions[1]+(positions[0]-positions[1])*2)+Vector3.Distance(positions[1]+(positions[0]-positions[1])*2, positions[0]);
             timeTakenDuringLerp/=10;
             _timeStartedLerping = Time.time;
             _P0 = positions[i];
             if(i!=0 && i!=positions.Length-1)
             {
                 _P1=positions[i-1]+(positions[i]-positions[i-1])*2;
                 _P2=positions[i+1];
                 _P3=positions[i+2];
             }
             else if(i==0)
             {
                 _P1=positions[1];
                 _P2=positions[2];
                 _P3=positions[3];
             }
             else
             {
                 _P1=positions[i-1]+(positions[i]-positions[i-1])*2;
                 _P2=positions[1]+(positions[0]-positions[1])*2;
                 _P3=positions[0];
             }
             percentageComplete=0;
             while(percentageComplete<1)
             {
                 timeSinceStarted = Time.time - _timeStartedLerping;
                 percentageComplete = timeSinceStarted / timeTakenDuringLerp;
                 cameraTrans.position = CalculateBezierPoint(percentageComplete, _P0, _P1, _P2, _P3);
                 if(mustChangeDirection)
                     direction=cameraTrans.position-lastPosition;
                 else
                     mustChangeDirection=true;
                 cameraTrans.rotation=Quaternion.Lerp(cameraTrans.rotation, Quaternion.LookRotation(direction), Time.deltaTime);
                 lastPosition=cameraTrans.position;
                 yield return null;
             }
             mustChangeDirection=false;
             if(i!=0)
                 i+=2;
             else
                 i+=3;
             if(i>=positions.Length)
                 i=0;
         }        
     }

     Vector3 CalculateBezierPoint(float t, Vector3 p0, Vector3 p1, Vector3 p2, Vector3 p3)
     {
         float u = 1 - t;
         float tt = t * t;
         float uu = u * u;
         float uuu = uu * u;
         float ttt = tt * t;
         
         Vector3 p = uuu * p0; 
         
         p += 3 * uu * t * p1; 
         p += 3 * u * tt * p2; 
         p += ttt * p3; 
         return p;
         
     }
 

The rotations are now handled based on the direction of the camera.

The array positions is to be set like this: The first point, the first bezier anchor of the first point, the second bezier anchor of the first point, the second point, the second bezier anchor of the second point, the third point, the second bezier anchor of the third point ...etc and finally the last point.

Comment
Add comment · Share
10 |3000 characters needed characters left characters exceeded
▼
  • Viewable by all users
  • Viewable by moderators
  • Viewable by moderators and the original poster
  • Advanced visibility
Viewable by all users
avatar image
3

Answer by Bunny83 · Jun 20, 2015 at 01:28 AM

Bezier curves are actually quite simple. Your example is a quadratic bezier curve and could be calculated with 3 lerps as you can see in the animated image on the wiki page. However usually you use a single folmula to directly get the position for a certain "t" value based on the 3 points: (start, contol1, end).

 public static Vector3 Bezier2(Vector3 s, Vector3 p, Vector3 e, float t)
 {
     float rt = 1-t;
     return rt*rt * s + 2 * rt * t * p + t*t* e;
 }




Comment
Add comment · Show 1 · Share
10 |3000 characters needed characters left characters exceeded
▼
  • Viewable by all users
  • Viewable by moderators
  • Viewable by moderators and the original poster
  • Advanced visibility
Viewable by all users
avatar image barbe63 · Jun 20, 2015 at 04:03 AM 0
Share

Yes I found a degree-three version of that and I solved my issue with it. Thanks anyway!

avatar image
0

Answer by iluqmansharif · Dec 16, 2017 at 09:22 PM

Hey! @barbe63 Can you send me your whole script? I kinda need it for similar task. Thanks in advance!

Comment
Add comment · Share
10 |3000 characters needed characters left characters exceeded
▼
  • Viewable by all users
  • Viewable by moderators
  • Viewable by moderators and the original poster
  • Advanced visibility
Viewable by all users

Your answer

Hint: You can notify a user about this post by typing @username

Up to 2 attachments (including images) can be used with a maximum of 524.3 kB each and 1.0 MB total.

Follow this Question

Answers Answers and Comments

23 People are following this question.

avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image

Related Questions

crouch Uncrouch speed with animation curve 1 Answer

How can I make a Lerp move in an arc instead of a straight line? 2 Answers

moving a gamobject in vacum 2 Answers

Vector3.Lerp doesn't work on build 0 Answers

Lerp tutorial missing variable value 1 Answer


Enterprise
Social Q&A

Social
Subscribe on YouTube social-youtube Follow on LinkedIn social-linkedin Follow on Twitter social-twitter Follow on Facebook social-facebook Follow on Instagram social-instagram

Footer

  • Purchase
    • Products
    • Subscription
    • Asset Store
    • Unity Gear
    • Resellers
  • Education
    • Students
    • Educators
    • Certification
    • Learn
    • Center of Excellence
  • Download
    • Unity
    • Beta Program
  • Unity Labs
    • Labs
    • Publications
  • Resources
    • Learn platform
    • Community
    • Documentation
    • Unity QA
    • FAQ
    • Services Status
    • Connect
  • About Unity
    • About Us
    • Blog
    • Events
    • Careers
    • Contact
    • Press
    • Partners
    • Affiliates
    • Security
Copyright © 2020 Unity Technologies
  • Legal
  • Privacy Policy
  • Cookies
  • Do Not Sell My Personal Information
  • Cookies Settings
"Unity", Unity logos, and other Unity trademarks are trademarks or registered trademarks of Unity Technologies or its affiliates in the U.S. and elsewhere (more info here). Other names or brands are trademarks of their respective owners.
  • Anonymous
  • Sign in
  • Create
  • Ask a question
  • Spaces
  • Default
  • Help Room
  • META
  • Moderators
  • Explore
  • Topics
  • Questions
  • Users
  • Badges