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. We have updated the language to the Editor Terms based on feedback from our employees and community. Learn more.
    Dismiss Notice
  3. Join us on November 16th, 2023, between 1 pm and 9 pm CET for Ask the Experts Online on Discord and on Unity Discussions.
    Dismiss Notice

Preview an Animation in Edit Mode

Discussion in 'Scripting' started by a.t.c., Jul 15, 2012.

  1. a.t.c.

    a.t.c.

    Joined:
    Jul 15, 2012
    Posts:
    2
    Hey,

    i am using UnityScript, working on an Editor Extension and currently try to implement a way to preview a chosen animation within the Sceneview during Edit Mode. Later on the goal is to control at which point of two animations a crossfade shall happen and to preview it.

    For test purpose, currently i am just working with a single animation. Within my EditorWindow is a Button, after clicking it, the animation is passed to the following function:

    Code (csharp):
    1.  
    2.     function previewAnimation(a:AnimationClip) {
    3.         var frames:int = Mathf.Round(a.length * a.frameRate);
    4.         var timePerFrame = a.length / frames;
    5.  
    6.         for (var i:int = 0; i < frames; i++) {
    7.             var previewTime: float = i * timePerFrame;
    8.             selectedObject.animation.Play(a.name,PlayMode.StopAll);
    9.             selectedObject.animation[a.name].time = previewTime;   
    10.             selectedObject.animation.Sample();
    11.             SceneView.RepaintAll();
    12.             //yield WaitForSeconds(timePerFrame);
    13.         }
    14.     }
    15.  

    It works so far, that after pushing the button, the for loop is instantly run and finished because there is no wait.

    I tried yield, but i guess it doesn't work, because it would require to be in Playmode. The statement that i commented out caused the function to be completly ignored (without failure notice or anything?) after pushing the "Preview"-button in my Editor Window.


    What i am looking for is some kind of wait function to slow down the execution of the for-loop. Either that or, in case my idea is totally the wrong attempt, then hopefully someone could point me into the right direction how to solve this task.

    I'm pretty new to Unity3d and might have missed some general practice in my limited view of things :)
     
  2. JohnnyA

    JohnnyA

    Joined:
    Apr 9, 2010
    Posts:
    5,039
    I think you might be better off using EditorApplication.update. You can use EditorApplication.timeSinceStartup to time the frame updates.
     
    Last edited: Jul 15, 2012
  3. a.t.c.

    a.t.c.

    Joined:
    Jul 15, 2012
    Posts:
    2
    Hi JohnnyA, thanks for the reply. Could you go a little bit more into detail how this would work? I tried it but failed so far :confused:


    I used EditorAppllication.timeSinceStartup in a while-loop, which does sample and repaint over the length of the animation. Something like that seems to actually happen, but it only shows the animations end position in the sceneview.

    Also, I couldn't put EditorApplication.update in any good use yet.


    Code (csharp):
    1.         var previewStartTime:double = EditorApplication.timeSinceStartup;  
    2.        
    3.         selectedObject.animation.Play(previewAnim.name,PlayMode.StopAll);
    4.         while(EditorApplication.timeSinceStartup - previewStartTime < previewAnim.length) {    
    5.             selectedObject.animation[previewAnim.name].time = EditorApplication.timeSinceStartup - previewStartTime;           
    6.             if (showDebugLog) Debug.Log(Time.realtimeSinceStartup + " " + selectedObject.animation[previewAnim.name].time);        
    7.             selectedObject.animation.Sample();
    8.             SceneView.RepaintAll();
    9.         }
     
  4. superpig

    superpig

    Drink more water! Unity Technologies

    Joined:
    Jan 16, 2011
    Posts:
    4,614
    You can't loop like that (you'll just hang the editor until it's finished). You need to hook into EditorApplication.update, and every time your hook function is called, update your animation. Like this:

    Code (csharp):
    1.  
    2. double previewStartTime;
    3. AnimationClip previewClip;
    4. GameObject targetObject;
    5.  
    6. void StartPreview()
    7. {
    8.    previewStartTime = EditorApplication.timeSinceStartup;
    9.    previewClip = GetClipToPreview();
    10.    targetObject = selectedObject.gameObject;
    11.    EditorApplication.update += DoPreview;
    12. }
    13.  
    14. void DoPreview()
    15. {
    16.    double timeElapsed = EditorApplication.timeSinceStartup - previewStartTime;
    17.    targetObject.SampleAnimation(previewClip, timeElapsed);
    18. }
    19.  
     
  5. startassets

    startassets

    Joined:
    Feb 13, 2017
    Posts:
    11
    Hi a.t.c, I've just finished my own preview asset, maybe it will be useful for you: https://forum.unity3d.com/threads/powerful-preview.460157/
    If you have any questions, write me a letter: startassets@gmail.com