summaryrefslogtreecommitdiff
path: root/Library/PackageCache/com.unity.timeline@1.2.13/Editor/CustomEditors/CustomTimelineEditorCache.cs
diff options
context:
space:
mode:
Diffstat (limited to 'Library/PackageCache/com.unity.timeline@1.2.13/Editor/CustomEditors/CustomTimelineEditorCache.cs')
-rw-r--r--Library/PackageCache/com.unity.timeline@1.2.13/Editor/CustomEditors/CustomTimelineEditorCache.cs155
1 files changed, 155 insertions, 0 deletions
diff --git a/Library/PackageCache/com.unity.timeline@1.2.13/Editor/CustomEditors/CustomTimelineEditorCache.cs b/Library/PackageCache/com.unity.timeline@1.2.13/Editor/CustomEditors/CustomTimelineEditorCache.cs
new file mode 100644
index 0000000..8211a98
--- /dev/null
+++ b/Library/PackageCache/com.unity.timeline@1.2.13/Editor/CustomEditors/CustomTimelineEditorCache.cs
@@ -0,0 +1,155 @@
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using UnityEngine;
+using UnityEngine.Playables;
+using UnityEngine.Timeline;
+
+namespace UnityEditor.Timeline
+{
+ class CustomTimelineEditorCache
+ {
+ static class SubClassCache<TEditorClass> where TEditorClass : class, new()
+ {
+ private static Type[] s_SubClasses = null;
+ private static readonly TEditorClass s_DefaultInstance = new TEditorClass();
+ private static readonly Dictionary<System.Type, TEditorClass> s_TypeMap = new Dictionary<Type, TEditorClass>();
+
+ public static TEditorClass DefaultInstance
+ {
+ get { return s_DefaultInstance; }
+ }
+
+ static Type[] SubClasses
+ {
+ get
+ {
+ // order the subclass array by built-ins then user defined so built-in classes are chosen first
+ return s_SubClasses ??
+ (s_SubClasses = TypeCache.GetTypesDerivedFrom<TEditorClass>().OrderBy(t => t.Assembly == typeof(UnityEditor.Timeline.TimelineEditor).Assembly ? 1 : 0).ToArray());
+ }
+ }
+
+ public static TEditorClass GetEditorForType(Type type)
+ {
+ TEditorClass editorClass = null;
+ if (!s_TypeMap.TryGetValue(type, out editorClass) || editorClass == null)
+ {
+ Type editorClassType = null;
+ Type searchType = type;
+ while (searchType != null)
+ {
+ // search our way up the runtime class hierarchy so we get the best match
+ editorClassType = GetExactEditorClassForType(searchType);
+ if (editorClassType != null)
+ break;
+ searchType = searchType.BaseType;
+ }
+
+ if (editorClassType == null)
+ {
+ editorClass = s_DefaultInstance;
+ }
+ else
+ {
+ try
+ {
+ editorClass = (TEditorClass)Activator.CreateInstance(editorClassType);
+ }
+ catch (Exception e)
+ {
+ Debug.LogWarningFormat("Could not create a Timeline editor class of type {0}: {1}", editorClassType, e.Message);
+ editorClass = s_DefaultInstance;
+ }
+ }
+
+ s_TypeMap[type] = editorClass;
+ }
+
+ return editorClass;
+ }
+
+ private static Type GetExactEditorClassForType(Type type)
+ {
+ foreach (var subClass in SubClasses)
+ {
+ // first check for exact match
+ var attr = (CustomTimelineEditorAttribute)Attribute.GetCustomAttribute(subClass, typeof(CustomTimelineEditorAttribute), false);
+ if (attr != null && attr.classToEdit == type)
+ {
+ return subClass;
+ }
+ }
+
+ return null;
+ }
+
+ public static void Clear()
+ {
+ s_TypeMap.Clear();
+ s_SubClasses = null;
+ }
+ }
+
+ public static TEditorClass GetEditorForType<TEditorClass, TRuntimeClass>(Type type) where TEditorClass : class, new()
+ {
+ if (type == null)
+ throw new ArgumentNullException(nameof(type));
+
+ if (!typeof(TRuntimeClass).IsAssignableFrom(type))
+ throw new ArgumentException(type.FullName + " does not inherit from" + typeof(TRuntimeClass));
+
+ return SubClassCache<TEditorClass>.GetEditorForType(type);
+ }
+
+ public static void ClearCache<TEditorClass>() where TEditorClass : class, new()
+ {
+ SubClassCache<TEditorClass>.Clear();
+ }
+
+ public static ClipEditor GetClipEditor(TimelineClip clip)
+ {
+ if (clip == null)
+ throw new ArgumentNullException(nameof(clip));
+
+ var type = typeof(IPlayableAsset);
+ if (clip.asset != null)
+ type = clip.asset.GetType();
+
+ if (!typeof(IPlayableAsset).IsAssignableFrom(type))
+ return GetDefaultClipEditor();
+
+ return GetEditorForType<ClipEditor, IPlayableAsset>(type);
+ }
+
+ public static ClipEditor GetDefaultClipEditor()
+ {
+ return SubClassCache<ClipEditor>.DefaultInstance;
+ }
+
+ public static TrackEditor GetTrackEditor(TrackAsset track)
+ {
+ if (track == null)
+ throw new ArgumentNullException(nameof(track));
+
+ return GetEditorForType<TrackEditor, TrackAsset>(track.GetType());
+ }
+
+ public static TrackEditor GetDefaultTrackEditor()
+ {
+ return SubClassCache<TrackEditor>.DefaultInstance;
+ }
+
+ public static MarkerEditor GetMarkerEditor(IMarker marker)
+ {
+ if (marker == null)
+ throw new ArgumentNullException(nameof(marker));
+ return GetEditorForType<MarkerEditor, IMarker>(marker.GetType());
+ }
+
+ public static MarkerEditor GetDefaultMarkerEditor()
+ {
+ return SubClassCache<MarkerEditor>.DefaultInstance;
+ }
+ }
+}