Search Unity

  1. Welcome to the Unity Forums! Please take the time to read our Code of Conduct to familiarize yourself with the forum rules and how to post constructively.
  2. Dismiss Notice

AnimationCurve set tangent mode from script

Discussion in 'Animation' started by Vincent454, Nov 3, 2018.

  1. Vincent454

    Vincent454

    Joined:
    Oct 26, 2014
    Posts:
    161
    Hello, I've been changing the tangent mode of an animation curve I have through script by using
    Code (CSharp):
    1. UnityEditor.AnimationUtility.SetKeyLeftTangentMode(difficultyRange, i, UnityEditor.AnimationUtility.TangentMode.Linear);
    However, since this is a UnityEditor function I cannot use it in my build. There used to be
    Code (CSharp):
    1. keys[i].tangentMode
    for each key, but thats deprecated and it tells me to use the Editor function which I cannot use as this is needed for the build.

    Are there any other options I have to get this working? I just want to change the tangent mode of a keyframe from script.
     
    ModLunar likes this.
  2. BBIT-SOLUTIONS

    BBIT-SOLUTIONS

    Joined:
    Feb 21, 2013
    Posts:
    38
    Have the same problem.
    One possibility would be to create the AnimationCurve in the inspector manually.
    But as soon as you have to change it dynamically during runtime, this is not working anymore.

    Did you find a solution?
     
  3. Vincent454

    Vincent454

    Joined:
    Oct 26, 2014
    Posts:
    161
    Sadly I did not, but in my case I simply needed to have a straight line between two of the points in the curve instead of an actual curve, so I could just interpolate linearly between two values.

    But apart from that I think it's just not possible sadly.
     
  4. HummeL_AL

    HummeL_AL

    Joined:
    May 31, 2019
    Posts:
    10
    Same problem. I want to generate curve what should be X-pos of the camera, but curve always stay linear...
     
  5. Laioyu

    Laioyu

    Joined:
    Sep 4, 2017
    Posts:
    4
    • Same problem, After two years, is the problem still unresolved?
     
  6. xLeo

    xLeo

    Joined:
    Sep 21, 2010
    Posts:
    177
    FYI: We have the same issue here.

    Any suggested workaround?
     
  7. Vincent454

    Vincent454

    Joined:
    Oct 26, 2014
    Posts:
    161
    Sadly I still haven't found one :(
     
  8. Yandalf

    Yandalf

    Joined:
    Feb 11, 2014
    Posts:
    491
    Reading API documentation can help ;)
    To modify a Keyframe tangent, you need to use KeyFrame.inTangent and outTangent.
    However, there's a little trap: the keys of an AnimationCurve are not given to you by reference, but by value.
    If you don't know what that means, it means that when you call AnimationCurve.keys, it gives you a copy of the actual keys rather than the keys itself. Any changes you try to push on that way will only affect the copy, not the original.
    To fix that, you can copy the whole key struct locally and make changes there, then reassign the new key to the array.
    Pseudocode example:

    Code (CSharp):
    1. AnimationCurve curve;
    2. KeyFrame newKey = curve.keys[n]; //copy key we want to edit
    3. newKey.inTangent = x; //change the tangents
    4. newKey.outTangent = y; //change the tangents
    5. curve.keys[n] = newKey; //reassign to the same place we copied earlier
    The downside to this is that you will have to do some math to figure out where your tangents should be.
    Alternatively you could look into using keyframe.inWeight, outWeight, and weightedMode, but I've never used those myself so can't readily tell you how to use them to achieve the desired effect. Experiment a bit.
     
    ModLunar likes this.
  9. AlanMattano

    AlanMattano

    Joined:
    Aug 22, 2013
    Posts:
    1,500
    To change the tangent mode of an animation curve through script you can use this code example:

    Code (CSharp):
    1.  
    2.        AnimationCurve myCurve = new AnimationCurve(myKeyframes.ToArray());
    3.  
    4.         // Set here the keyframe tangents to Auto.
    5.         for (int i = 0; i < myCurve.length; i++)
    6.         {
    7.             myCurve.SmoothTangents(i, 0);
    8.         }
     
  10. mihailpetker

    mihailpetker

    Joined:
    Nov 15, 2021
    Posts:
    1
    made this code

    Code (CSharp):
    1. for (int i = 0; i < curveAnimation.length; i++)
    2. {
    3.     Keyframe frame = curveAnimation[i];
    4.     if (i > 0&& i != curveAnimation.length - 1)
    5.     {
    6.         var nextFrame=curveAnimation[i+1];
    7.         var prefFrame=curveAnimation[i-1];
    8.         float inTangent = (float) (((double) frame.value - (double) prefFrame.value) / ((double) frame.time - (double)  prefFrame.time ));
    9.         float outTangent = (float) (((double) nextFrame.value - (double) frame.value) / ((double) nextFrame.time - (double)  frame.time ));
    10.         frame.inTangent = inTangent;
    11.         frame.outTangent = outTangent;
    12.     }
    13.     else
    14.     {
    15.         if (i == 0)
    16.         {
    17.             var nextFrame=curveAnimation[i+1];
    18.             float outTangent = (float) (((double) nextFrame.value - (double) frame.value) / ((double) nextFrame.time - (double)  frame.time ));
    19.             frame.outTangent = outTangent;
    20.         }
    21.         else if (i == curveAnimation.length - 1)
    22.         {
    23.             var prefFrame=curveAnimation[i-1];
    24.             float inTangent = (float) (((double) frame.value - (double) prefFrame.value) / ((double) frame.time - (double)  prefFrame.time ));
    25.             frame.inTangent = inTangent;
    26.         }
    27.     }
    28.     keyframes.Add(frame);
    29. }
    30. curveAnimation.keys = keyframes.ToArray();
    it makes every keyframe be linear
     
    Vincent454 likes this.