Search Unity

Custom inspector editor for timeline clips?

Discussion in 'Timeline' started by DGordon, Jul 14, 2017.

  1. DGordon

    DGordon

    Joined:
    Dec 8, 2013
    Posts:
    649
    Any chance we're going to be able to write custom editors for our clips in the tracks? It would really come in handy ... if we're already able to, please let me know how :).
     
  2. AndrewKaninchen

    AndrewKaninchen

    Joined:
    Oct 30, 2016
    Posts:
    149
    Yeah, we can already do it.



    Code (CSharp):
    1. using UnityEngine.Playables;
    2.  
    3. [CustomPropertyDrawer(typeof(EnemyControlBehaviour))]
    4. public class EnemyControlDrawer : PropertyDrawer
    5. {
    6.     public override float GetPropertyHeight (SerializedProperty property, GUIContent label)
    7.     {
    8.         int fieldCount = 1;
    9.         return fieldCount * EditorGUIUtility.singleLineHeight;
    10.     }
    11.  
    12.     public override void OnGUI (Rect position, SerializedProperty property, GUIContent label)
    13.     {
    14.         SerializedProperty prefab = property.FindPropertyRelative("prefab");
    15.         SerializedProperty color = property.FindPropertyRelative("color");
    16.  
    17.         Rect singleFieldRect = new Rect(position.x, position.y, position.width, EditorGUIUtility.singleLineHeight);
    18.         EditorGUILayout.PropertyField(prefab);
    19.         EditorGUILayout.PropertyField(color);
    20.     }
    21. }

    This is one of mine. It's messy because I rushed it without actually reading what it was doing at first, but it works. The way he does in the video looks better, I think.
     
    Deadcow_ and DGordon like this.
  3. DGordon

    DGordon

    Joined:
    Dec 8, 2013
    Posts:
    649
    Woah had no idea this was implemented. Thank you sooo much.
     
  4. Infrid

    Infrid

    Joined:
    Jan 14, 2012
    Posts:
    67
    How to do this for a track? I've got it only the clips.. works well; but I'd love to be able to do this on a track
     
  5. seant_unity

    seant_unity

    Unity Technologies

    Joined:
    Aug 25, 2015
    Posts:
    1,516
    For a track you can simply use an Editor as described here.
     
    Deadcow_ likes this.
  6. senkal_

    senkal_

    Joined:
    May 22, 2018
    Posts:
    86
    I know it's an old post, but it's something I am struggling with at the moment.
    In general I understand the idea.
    But I would like to combine two worlds.

    Ability to record animations (example 4 from https://blogs.unity3d.com/2018/09/05/extending-timeline-a-practical-guide/)
    And custom editor.
    If I follow the property drawer idea, yes I can override the inspector, but I can no longer record animations on that clip/behaviour inspector.
    The red(record) button is visible and I can click it but no key frames can be recorded.

    Before, with the automatic editor and the fact it generated "template" fields out of the box, I could record animations on clip inspector.
    For now I need to choose, ability to record animation from clip inspector with automatic template fields generations or custom clip editor.

    Is it me or maybe there is something missing in the video example?


    [Update]
    In general I only need to add some graphical element base on values so I can display default inspector and some added bits. Don't need to change any values in my custom editor bit.
     
    Last edited: Dec 5, 2018
  7. senkal_

    senkal_

    Joined:
    May 22, 2018
    Posts:
    86
    After some more digging I realized that extending behaviour editor wasn't the issue.
    Looks like I can't really record animations on none float variables.
    Maybe it has somethign to do with mixer and the fact there are calculations on float for input weight etc.
    Sorry, my issue is not related to the custom behaviour editor.
     
  8. Deadcow_

    Deadcow_

    Joined:
    Mar 13, 2014
    Posts:
    135
    I'm unable to write PropertyDrawer for my TimelineBehaviour with script AndrewKaninchen provided. I also tried to bind PropertyDrawer to MyCustomClip. I found no other info about it.

    I'm also very interested in how AudioTrack drawing custom grapics (audio track presentation) over clips in Timeline window. I'm just curious, I bet I'll come up with some interesting ideas with custom graphics and ui elements over clips :)
    At least I hope when timeline will be available as package we'll be able to dig it through and see how it's acheived
     
  9. Deadcow_

    Deadcow_

    Joined:
    Mar 13, 2014
    Posts:
    135
    Oh dang it was really stupid tiny mistake I made. I figured out how to write PropertyDriwer
     
  10. seant_unity

    seant_unity

    Unity Technologies

    Joined:
    Aug 25, 2015
    Posts:
    1,516
    Timeline is (sort-of) a package in 2019.1. The package ships with Unity instead of using Package Manager (that might change in the future). But it means you can drag a local copy into your package folder and have a locally modified version.

    Also - 2019.2 has added ClipEditors, TrackEditors and MarkerEditors to help customize. The waveforms are done using a ClipEditor, so it's definitely possible. In fact, if you are deriving from AudioPlayableAsset, then you will get the waveform drawing by default.
     
    Deadcow_ likes this.
  11. Deadcow_

    Deadcow_

    Joined:
    Mar 13, 2014
    Posts:
    135
    What a great future is coming :D I'm hacking into Timeline extensively in my current project. With tracks generation and manipulation through custom node editor. It's cool to hear there is more to come. I love how we may extend some tools in unity in a ways it not intended to be used :)
     
  12. Bugfoot

    Bugfoot

    Joined:
    Jan 9, 2009
    Posts:
    533
    Hey Sean, would have some sample code on how to extend the markers? I've written a custom inspector for my new marker (derived from the standard "Editor" inspector class) in order to add some QoL improvements on top of the default inspector behavior. I've overriden OnInspectorGUI() and called DrawDefaultInspector() from it but I'm not getting the same behavior as the Unity default. For instance, I can no longer edit the marker name in the inspector header (I have a workaround but it's not ideal):
    upload_2019-9-4_14-51-11.png


    And this how it looks using the default marker inspector:
    upload_2019-9-4_14-52-6.png

    I figured I should probably derive my custom inspector from something like a more specialized "MarkerEditor" base class but this one doesn't seem to derive from the base Editor inspector class.

    Any pointers please?
     
  13. seant_unity

    seant_unity

    Unity Technologies

    Joined:
    Aug 25, 2015
    Posts:
    1,516
    @spk that is a very fair question, and unfortunately the answer isn't trivial :(

    Timeline does have the base class you are looking for, it's call MarkerInspector. However, it is not a public class. Because timeline is a package, the source code is available to look at, and even change if you make the package local (not recommended unless you never plan on upgrading).

    The marker inspector is using protected internal methods (OnHeaderTitleGUI) from UnityEditor.Editor to achieve the title bar editing.

    You can override OnHeaderGUI in your custom inspector, but you need to re-implement the entire header, not just the title.

    One approach that might work for you is to not use your own Editor (i.e. inspector) class, but use PropertyDrawers on individual members of your marker class. That should use the built-in marker inspector, and give you the title edit feature, and let you customize the OnGUI for individual fields of your marker class.

    I hope that helps.

    The MarkerEditor class that is public is to aid in the drawing of markers on the timeline, and not in the inspector. I've attached a sample that uses that for markers that act as snap points. Not completely relevant to your question, but if you are trying to customize markers it's a useful example. Note that markers also support .uss files that let you customize the styling of the marker, which is a great way to get custom looks for the different markers.
     

    Attached Files:

  14. Bugfoot

    Bugfoot

    Joined:
    Jan 9, 2009
    Posts:
    533
    Thanks for the detailed answer, sean! I can easily work around the title bar renaming feature by simply adding a custom text field to my inspector to update name property of the marker, but yeah it's not ideal. I'll give the property drawer approach a go, but in my case I would like to control the visibility of several fields depending on the value of an enum property so I'm not sure this approach would work here.
     
  15. Bugfoot

    Bugfoot

    Joined:
    Jan 9, 2009
    Posts:
    533
    @seant_unity while I've got you on the line... is there an equivalent of Marker.parent (TrackAsset) for timeline clips in the editor? I'm trying to do a custom inspector for a new timeline clip that has a property that should list markers on the timeline the clip is on. Unfortunately the PlayableAsset class from which my custom clip derives from does not know about the timeline track it's on, so I cannot enumerate the markers it contains.

    Is there a more specialized base-class to derive from for timeline clips? As in, the equivalent of the Marker class but for clips?
     
  16. seant_unity

    seant_unity

    Unity Technologies

    Joined:
    Aug 25, 2015
    Posts:
    1,516
    For the property drawer approach, you can put the enum and associated fields in a struct which has it's own property drawer.

    For clips, not really. By design, markers are a bit different than clips. Clips are classes (not UnityEngine.Object derived) and are serialized with the track, and have a reference to a playable asset. Markers are themselves ScriptableObjects that live as sub assets of the timeline, and implement the IMarker interface.

    There are posts about how to assign the clip to the playable asset (e.g. custom clip class) using TrackAsset.CreateTrackMixer, but you can also use the clip editor to do it. Something like

    public override ClipDrawOptions GetClipOptions(TimelineClip clip)
    {
    var asset = (MyCustomClip) clip.asset;
    asset.parentClip = clip; // assumes parentClip is a property of MyCustomClip, and not a serialized field.
    return base.GetClipOptions(clip);
    }

    Alternately in your custom editor you can search TimelineEditor.inspectedAsset for the clip that has your particular asset. Not the most efficient way, but if done in OnEnable, it is probably fine.

    If you store a reference to the clip, because careful not to serialize it. Because TimelineClip is a plain old serializable class, when the timeline is reloaded off disk, that will create a copy and no longer refer to the original. This can cause a lot of bugs and confusion.
     
    senkal_ likes this.