[unity] Some code cleanup.

This commit is contained in:
pharan 2018-05-11 06:31:18 +08:00
parent 093090875f
commit afc0b3ff4e
4 changed files with 200 additions and 201 deletions

View File

@ -73,15 +73,14 @@ namespace Spine.Unity.Editor {
#region SkeletonAnimator's Mecanim Clips #region SkeletonAnimator's Mecanim Clips
#if SPINE_SKELETON_ANIMATOR #if SPINE_SKELETON_ANIMATOR
public static void GenerateMecanimAnimationClips (SkeletonDataAsset skeletonDataAsset) { public static void GenerateMecanimAnimationClips (SkeletonDataAsset skeletonDataAsset) {
//skeletonDataAsset.Clear();
var data = skeletonDataAsset.GetSkeletonData(true); var data = skeletonDataAsset.GetSkeletonData(true);
if (data == null) { if (data == null) {
Debug.LogError("SkeletonData failed!", skeletonDataAsset); Debug.LogError("SkeletonData loading failed!", skeletonDataAsset);
return; return;
} }
string dataPath = AssetDatabase.GetAssetPath(skeletonDataAsset); string dataPath = AssetDatabase.GetAssetPath(skeletonDataAsset);
string controllerPath = dataPath.Replace("_SkeletonData", "_Controller").Replace(".asset", ".controller"); string controllerPath = dataPath.Replace(SpineEditorUtilities.SkeletonDataSuffix, "_Controller").Replace(".asset", ".controller");
UnityEditor.Animations.AnimatorController controller; UnityEditor.Animations.AnimatorController controller;
if (skeletonDataAsset.controller != null) { if (skeletonDataAsset.controller != null) {
controller = (UnityEditor.Animations.AnimatorController)skeletonDataAsset.controller; controller = (UnityEditor.Animations.AnimatorController)skeletonDataAsset.controller;
@ -123,40 +122,35 @@ namespace Spine.Unity.Editor {
} }
} }
foreach (var anim in data.Animations) { foreach (var animations in data.Animations) {
string name = anim.Name; string animationName = animations.Name; // Review for unsafe names. Requires runtime implementation too.
spineAnimationTable.Add(name, anim); spineAnimationTable.Add(animationName, animations);
if (unityAnimationClipTable.ContainsKey(name) == false) { if (unityAnimationClipTable.ContainsKey(animationName) == false) {
//generate new dummy clip AnimationClip newClip = new AnimationClip {
AnimationClip newClip = new AnimationClip(); name = animationName
newClip.name = name; };
//AssetDatabase.CreateAsset(newClip, Path.GetDirectoryName(dataPath) + "/" + animationName + ".asset");
AssetDatabase.AddObjectToAsset(newClip, controller); AssetDatabase.AddObjectToAsset(newClip, controller);
unityAnimationClipTable.Add(name, newClip); unityAnimationClipTable.Add(animationName, newClip);
} }
AnimationClip clip = unityAnimationClipTable[name]; AnimationClip clip = unityAnimationClipTable[animationName];
clip.SetCurve("", typeof(GameObject), "dummy", AnimationCurve.Linear(0, 0, animations.Duration, 0));
clip.SetCurve("", typeof(GameObject), "dummy", AnimationCurve.Linear(0, 0, anim.Duration, 0));
var settings = AnimationUtility.GetAnimationClipSettings(clip); var settings = AnimationUtility.GetAnimationClipSettings(clip);
settings.stopTime = anim.Duration; settings.stopTime = animations.Duration;
SetAnimationSettings(clip, settings); SetAnimationSettings(clip, settings);
AnimationUtility.SetAnimationEvents(clip, new AnimationEvent[0]); AnimationUtility.SetAnimationEvents(clip, new AnimationEvent[0]);
foreach (Timeline t in animations.Timelines) {
foreach (Timeline t in anim.Timelines) { if (t is EventTimeline)
if (t is EventTimeline) {
ParseEventTimeline((EventTimeline)t, clip, SendMessageOptions.DontRequireReceiver); ParseEventTimeline((EventTimeline)t, clip, SendMessageOptions.DontRequireReceiver);
}
} }
EditorUtility.SetDirty(clip); EditorUtility.SetDirty(clip);
unityAnimationClipTable.Remove(animationName);
unityAnimationClipTable.Remove(name);
} }
//clear no longer used animations
foreach (var clip in unityAnimationClipTable.Values) { foreach (var clip in unityAnimationClipTable.Values) {
AnimationClip.DestroyImmediate(clip, true); AnimationClip.DestroyImmediate(clip, true);
} }

View File

@ -36,7 +36,6 @@ using System.Collections.Generic;
using UnityEditor; using UnityEditor;
using UnityEngine; using UnityEngine;
using Spine; using Spine;
namespace Spine.Unity.Editor { namespace Spine.Unity.Editor {
@ -80,6 +79,12 @@ namespace Spine.Unity.Editor {
void OnDestroy () { void OnDestroy () {
HandleOnDestroyPreview(); HandleOnDestroyPreview();
AppDomain.CurrentDomain.DomainUnload -= OnDomainUnload;
EditorApplication.update -= preview.HandleEditorUpdate;
}
private void OnDomainUnload (object sender, EventArgs e) {
OnDestroy();
} }
void InitializeEditor () { void InitializeEditor () {
@ -105,7 +110,11 @@ namespace Spine.Unity.Editor {
#else #else
// Analysis disable once ConvertIfToOrExpression // Analysis disable once ConvertIfToOrExpression
if (newAtlasAssets) atlasAssets.isExpanded = true; if (newAtlasAssets) atlasAssets.isExpanded = true;
#endif #endif
// This handles the case where the managed editor assembly is unloaded before recompilation when code changes.
AppDomain.CurrentDomain.DomainUnload -= OnDomainUnload;
AppDomain.CurrentDomain.DomainUnload += OnDomainUnload;
EditorApplication.update -= preview.HandleEditorUpdate; EditorApplication.update -= preview.HandleEditorUpdate;
EditorApplication.update += preview.HandleEditorUpdate; EditorApplication.update += preview.HandleEditorUpdate;
@ -678,23 +687,43 @@ namespace Spine.Unity.Editor {
set { if (IsValid) skeletonAnimation.timeScale = value; } set { if (IsValid) skeletonAnimation.timeScale = value; }
} }
public bool IsPlayingAnimation { public bool IsPlayingAnimation { get {
get {
if (!IsValid) return false; if (!IsValid) return false;
var currentTrack = skeletonAnimation.AnimationState.GetCurrent(0); var currentTrack = skeletonAnimation.AnimationState.GetCurrent(0);
return currentTrack != null && currentTrack.TimeScale > 0; return currentTrack != null && currentTrack.TimeScale > 0;
} }
} }
public TrackEntry ActiveTrack { public TrackEntry ActiveTrack { get { return IsValid ? skeletonAnimation.AnimationState.GetCurrent(0) : null; } }
get { return IsValid ? skeletonAnimation.AnimationState.GetCurrent(0) : null; }
}
public Vector3 PreviewCameraPosition { public Vector3 PreviewCameraPosition {
get { return PreviewUtilityCamera.transform.position; } get { return PreviewUtilityCamera.transform.position; }
set { PreviewUtilityCamera.transform.position = value; } set { PreviewUtilityCamera.transform.position = value; }
} }
public void HandleDrawSettings () {
const float SliderWidth = 150;
const float SliderSnap = 0.25f;
const float SliderMin = 0f;
const float SliderMax = 2f;
if (IsValid) {
float timeScale = GUILayout.HorizontalSlider(TimeScale, SliderMin, SliderMax, GUILayout.MaxWidth(SliderWidth));
timeScale = Mathf.RoundToInt(timeScale / SliderSnap) * SliderSnap;
TimeScale = timeScale;
}
}
public void HandleEditorUpdate () {
AdjustCamera();
if (IsPlayingAnimation) {
RefreshOnNextUpdate();
Repaint();
} else if (requiresRefresh) {
Repaint();
}
}
public void Initialize (Action repaintCallback, SkeletonDataAsset skeletonDataAsset, string skinName = "") { public void Initialize (Action repaintCallback, SkeletonDataAsset skeletonDataAsset, string skinName = "") {
if (skeletonDataAsset == null) return; if (skeletonDataAsset == null) return;
if (skeletonDataAsset.GetSkeletonData(false) == null) { if (skeletonDataAsset.GetSkeletonData(false) == null) {
@ -715,7 +744,7 @@ namespace Spine.Unity.Editor {
previewRenderUtility = new PreviewRenderUtility(true); previewRenderUtility = new PreviewRenderUtility(true);
animationLastTime = Time.realtimeSinceStartup; animationLastTime = Time.realtimeSinceStartup;
const int PreviewLayer = 31; const int PreviewLayer = 30;
const int PreviewCameraCullingMask = 1 << PreviewLayer; const int PreviewCameraCullingMask = 1 << PreviewLayer;
{ {
@ -743,49 +772,136 @@ namespace Spine.Unity.Editor {
previewGameObject.GetComponent<Renderer>().enabled = false; previewGameObject.GetComponent<Renderer>().enabled = false;
} }
AdjustCameraGoals(true); if (this.ActiveTrack != null) cameraAdjustEndFrame = EditorApplication.timeSinceStartup + skeletonAnimation.AnimationState.GetCurrent(0).Alpha;
AdjustCameraGoals();
} catch { } catch {
DestroyPreviewGameObject(); DestroyPreviewGameObject();
} }
RefreshOnNextUpdate();
} }
} }
} }
public void HandleDrawSettings () { public void HandleInteractivePreviewGUI (Rect r, GUIStyle background) {
const float SliderWidth = 150; if (Event.current.type == EventType.Repaint) {
const float SliderSnap = 0.25f; if (requiresRefresh) {
const float SliderMin = 0f; previewRenderUtility.BeginPreview(r, background);
const float SliderMax = 2f; DoRenderPreview(true);
previewTexture = previewRenderUtility.EndPreview();
requiresRefresh = false;
}
if (previewTexture != null)
GUI.DrawTexture(r, previewTexture, ScaleMode.StretchToFill, false);
}
if (IsValid) { DrawSkinToolbar(r);
float timeScale = GUILayout.HorizontalSlider(TimeScale, SliderMin, SliderMax, GUILayout.MaxWidth(SliderWidth)); //DrawSetupPoseButton(r);
timeScale = Mathf.RoundToInt(timeScale / SliderSnap) * SliderSnap; DrawTimeBar(r);
TimeScale = timeScale; HandleMouseScroll(r);
}
public Texture2D GetStaticPreview (int width, int height) {
var c = this.PreviewUtilityCamera;
if (c == null)
return null;
RefreshOnNextUpdate();
AdjustCameraGoals();
c.orthographicSize = cameraOrthoGoal / 2;
c.transform.position = cameraPositionGoal;
previewRenderUtility.BeginStaticPreview(new Rect(0, 0, width, height));
DoRenderPreview(false);
var tex = previewRenderUtility.EndStaticPreview();
return tex;
}
public void DoRenderPreview (bool drawHandles) {
if (this.PreviewUtilityCamera.activeTexture == null || this.PreviewUtilityCamera.targetTexture == null)
return;
GameObject go = previewGameObject;
if (requiresRefresh && go != null) {
var renderer = go.GetComponent<Renderer>();
renderer.enabled = true;
if (!EditorApplication.isPlaying) {
skeletonAnimation.Update((Time.realtimeSinceStartup - animationLastTime));
skeletonAnimation.LateUpdate();
animationLastTime = Time.realtimeSinceStartup;
}
var thisPreviewUtilityCamera = this.PreviewUtilityCamera;
if (drawHandles) {
Handles.SetCamera(thisPreviewUtilityCamera);
Handles.color = OriginColor;
// Draw Cross
float scale = skeletonDataAsset.scale;
float cl = 1000 * scale;
Handles.DrawLine(new Vector3(-cl, 0), new Vector3(cl, 0));
Handles.DrawLine(new Vector3(0, cl), new Vector3(0, -cl));
}
thisPreviewUtilityCamera.Render();
if (drawHandles) {
Handles.SetCamera(thisPreviewUtilityCamera);
SpineHandles.DrawBoundingBoxes(skeletonAnimation.transform, skeletonAnimation.skeleton);
if (SkeletonDataAssetInspector.showAttachments)
SpineHandles.DrawPaths(skeletonAnimation.transform, skeletonAnimation.skeleton);
}
renderer.enabled = false;
} }
} }
public void OnDestroy () { public void AdjustCamera () {
DisposePreviewRenderUtility(); if (previewRenderUtility == null)
DestroyPreviewGameObject(); return;
}
public void Clear () { if (EditorApplication.timeSinceStartup < cameraAdjustEndFrame)
DisposePreviewRenderUtility(); AdjustCameraGoals();
DestroyPreviewGameObject();
}
void DisposePreviewRenderUtility () { lastCameraPositionGoal = cameraPositionGoal;
if (previewRenderUtility != null) { lastCameraOrthoGoal = cameraOrthoGoal;
previewRenderUtility.Cleanup();
previewRenderUtility = null; var c = this.PreviewUtilityCamera;
float orthoSet = Mathf.Lerp(c.orthographicSize, cameraOrthoGoal, 0.1f);
c.orthographicSize = orthoSet;
float dist = Vector3.Distance(c.transform.position, cameraPositionGoal);
if (dist > 0f) {
Vector3 pos = Vector3.Lerp(c.transform.position, cameraPositionGoal, 0.1f);
pos.x = 0;
c.transform.position = pos;
c.transform.rotation = Quaternion.identity;
RefreshOnNextUpdate();
} }
} }
void DestroyPreviewGameObject () { void AdjustCameraGoals () {
if (previewGameObject != null) { if (previewGameObject == null) return;
GameObject.DestroyImmediate(previewGameObject);
previewGameObject = null; Bounds bounds = previewGameObject.GetComponent<Renderer>().bounds;
cameraOrthoGoal = bounds.size.y;
cameraPositionGoal = bounds.center + new Vector3(0, 0, -10f);
}
void HandleMouseScroll (Rect position) {
Event current = Event.current;
int controlID = GUIUtility.GetControlID(SliderHash, FocusType.Passive);
switch (current.GetTypeForControl(controlID)) {
case EventType.ScrollWheel:
if (position.Contains(current.mousePosition)) {
cameraOrthoGoal += current.delta.y * 0.06f;
cameraOrthoGoal = Mathf.Max(0.01f, cameraOrthoGoal);
GUIUtility.hotControl = controlID;
current.Use();
}
break;
} }
} }
@ -820,7 +936,7 @@ namespace Spine.Unity.Editor {
var targetAnimation = skeletonData.FindAnimation(animationName); var targetAnimation = skeletonData.FindAnimation(animationName);
if (targetAnimation != null) { if (targetAnimation != null) {
var currentTrack = skeletonAnimation.AnimationState.GetCurrent(0); var currentTrack = this.ActiveTrack;
bool isEmpty = (currentTrack == null); bool isEmpty = (currentTrack == null);
bool isNewAnimation = isEmpty || currentTrack.Animation != targetAnimation; bool isNewAnimation = isEmpty || currentTrack.Animation != targetAnimation;
@ -859,128 +975,6 @@ namespace Spine.Unity.Editor {
} }
public void HandleInteractivePreviewGUI (Rect r, GUIStyle background) {
if (Event.current.type == EventType.Repaint) {
if (requiresRefresh) {
previewRenderUtility.BeginPreview(r, background);
DoRenderPreview(true);
previewTexture = previewRenderUtility.EndPreview();
requiresRefresh = false;
}
if (previewTexture != null)
GUI.DrawTexture(r, previewTexture, ScaleMode.StretchToFill, false);
}
DrawSkinToolbar(r);
//DrawSetupPoseButton(r);
DrawTimeBar(r);
MouseScroll(r);
}
void AdjustCameraGoals (bool calculateMixTime = false) {
if (previewGameObject == null)
return;
if (calculateMixTime) {
if (skeletonAnimation.AnimationState.GetCurrent(0) != null)
cameraAdjustEndFrame = EditorApplication.timeSinceStartup + skeletonAnimation.AnimationState.GetCurrent(0).Alpha;
}
Bounds bounds = previewGameObject.GetComponent<Renderer>().bounds;
cameraOrthoGoal = bounds.size.y;
cameraPositionGoal = bounds.center + new Vector3(0, 0, -10f);
}
public void AdjustCamera () {
if (previewRenderUtility == null)
return;
if (EditorApplication.timeSinceStartup < cameraAdjustEndFrame)
AdjustCameraGoals();
lastCameraPositionGoal = cameraPositionGoal;
lastCameraOrthoGoal = cameraOrthoGoal;
var c = this.PreviewUtilityCamera;
float orthoSet = Mathf.Lerp(c.orthographicSize, cameraOrthoGoal, 0.1f);
c.orthographicSize = orthoSet;
float dist = Vector3.Distance(c.transform.position, cameraPositionGoal);
if (dist > 0f) {
Vector3 pos = Vector3.Lerp(c.transform.position, cameraPositionGoal, 0.1f);
pos.x = 0;
c.transform.position = pos;
c.transform.rotation = Quaternion.identity;
RefreshOnNextUpdate();
}
}
public Texture2D GetStaticPreview (int width, int height) {
var c = this.PreviewUtilityCamera;
if (c == null) return null;
RefreshOnNextUpdate();
AdjustCameraGoals();
c.orthographicSize = cameraOrthoGoal / 2;
c.transform.position = cameraPositionGoal;
previewRenderUtility.BeginStaticPreview(new Rect(0, 0, width, height));
DoRenderPreview(false);
var tex = previewRenderUtility.EndStaticPreview();
return tex;
}
public void HandleEditorUpdate () {
AdjustCamera();
if (IsPlayingAnimation) {
RefreshOnNextUpdate();
Repaint();
} else if (requiresRefresh) {
Repaint();
}
}
public void DoRenderPreview (bool drawHandles) {
if (this.PreviewUtilityCamera.activeTexture == null || this.PreviewUtilityCamera.targetTexture == null )
return;
GameObject go = previewGameObject;
if (requiresRefresh && go != null) {
go.GetComponent<Renderer>().enabled = true;
if (!EditorApplication.isPlaying)
skeletonAnimation.Update((Time.realtimeSinceStartup - animationLastTime));
animationLastTime = Time.realtimeSinceStartup;
if (!EditorApplication.isPlaying)
skeletonAnimation.LateUpdate();
var thisPreviewUtilityCamera = this.PreviewUtilityCamera;
if (drawHandles) {
Handles.SetCamera(thisPreviewUtilityCamera);
Handles.color = OriginColor;
float scale = skeletonDataAsset.scale;
Handles.DrawLine(new Vector3(-1000 * scale, 0, 0), new Vector3(1000 * scale, 0, 0));
Handles.DrawLine(new Vector3(0, 1000 * scale, 0), new Vector3(0, -1000 * scale, 0));
}
thisPreviewUtilityCamera.Render();
if (drawHandles) {
Handles.SetCamera(thisPreviewUtilityCamera);
SpineHandles.DrawBoundingBoxes(skeletonAnimation.transform, skeletonAnimation.skeleton);
if (SkeletonDataAssetInspector.showAttachments) SpineHandles.DrawPaths(skeletonAnimation.transform, skeletonAnimation.skeleton);
}
go.GetComponent<Renderer>().enabled = false;
}
}
void DrawSkinToolbar (Rect r) { void DrawSkinToolbar (Rect r) {
if (!this.IsValid) return; if (!this.IsValid) return;
@ -1053,7 +1047,7 @@ namespace Spine.Unity.Editor {
GUI.Box(barRect, ""); GUI.Box(barRect, "");
Rect lineRect = new Rect(barRect); Rect lineRect = new Rect(barRect);
float width = lineRect.width; float lineRectWidth = lineRect.width;
TrackEntry t = skeletonAnimation.AnimationState.GetCurrent(0); TrackEntry t = skeletonAnimation.AnimationState.GetCurrent(0);
if (t != null) { if (t != null) {
@ -1062,7 +1056,7 @@ namespace Spine.Unity.Editor {
float normalizedTime = currentTime / t.Animation.Duration; float normalizedTime = currentTime / t.Animation.Duration;
float wrappedTime = normalizedTime % 1; float wrappedTime = normalizedTime % 1;
lineRect.x = barRect.x + (width * wrappedTime) - 0.5f; lineRect.x = barRect.x + (lineRectWidth * wrappedTime) - 0.5f;
lineRect.width = 2; lineRect.width = 2;
GUI.color = Color.red; GUI.color = Color.red;
@ -1071,13 +1065,14 @@ namespace Spine.Unity.Editor {
for (int i = 0; i < currentAnimationEvents.Count; i++) { for (int i = 0; i < currentAnimationEvents.Count; i++) {
float fr = currentAnimationEventTimes[i]; float fr = currentAnimationEventTimes[i];
var userEventIcon = Icons.userEvent;
var evRect = new Rect(barRect) { var evRect = new Rect(barRect) {
x = Mathf.Clamp(((fr / t.Animation.Duration) * width) - (Icons.userEvent.width / 2), barRect.x, float.MaxValue), x = Mathf.Clamp(((fr / t.Animation.Duration) * lineRectWidth) - (userEventIcon.width / 2), barRect.x, float.MaxValue),
y = barRect.y + Icons.userEvent.height, y = barRect.y + userEventIcon.height,
width = Icons.userEvent.width, width = userEventIcon.width,
height = Icons.userEvent.height height = userEventIcon.height
}; };
GUI.DrawTexture(evRect, Icons.userEvent); GUI.DrawTexture(evRect, userEventIcon);
Event ev = Event.current; Event ev = Event.current;
if (ev.type == EventType.Repaint) { if (ev.type == EventType.Repaint) {
@ -1095,18 +1090,27 @@ namespace Spine.Unity.Editor {
} }
} }
void MouseScroll (Rect position) { public void OnDestroy () {
Event current = Event.current; DisposePreviewRenderUtility();
int controlID = GUIUtility.GetControlID(SliderHash, FocusType.Passive); DestroyPreviewGameObject();
switch (current.GetTypeForControl(controlID)) { }
case EventType.ScrollWheel:
if (position.Contains(current.mousePosition)) { public void Clear () {
cameraOrthoGoal += current.delta.y * 0.06f; DisposePreviewRenderUtility();
cameraOrthoGoal = Mathf.Max(0.01f, cameraOrthoGoal); DestroyPreviewGameObject();
GUIUtility.hotControl = controlID; }
current.Use();
} void DisposePreviewRenderUtility () {
break; if (previewRenderUtility != null) {
previewRenderUtility.Cleanup();
previewRenderUtility = null;
}
}
void DestroyPreviewGameObject () {
if (previewGameObject != null) {
GameObject.DestroyImmediate(previewGameObject);
previewGameObject = null;
} }
} }
} }

View File

@ -1189,10 +1189,11 @@ namespace Spine.Unity.Editor {
#endregion #endregion
#region Import SkeletonData (json or binary) #region Import SkeletonData (json or binary)
public const string SkeletonDataSuffix = "_SkeletonData";
static SkeletonDataAsset IngestSpineProject (TextAsset spineJson, params AtlasAsset[] atlasAssets) { static SkeletonDataAsset IngestSpineProject (TextAsset spineJson, params AtlasAsset[] atlasAssets) {
string primaryName = Path.GetFileNameWithoutExtension(spineJson.name); string primaryName = Path.GetFileNameWithoutExtension(spineJson.name);
string assetPath = Path.GetDirectoryName(AssetDatabase.GetAssetPath(spineJson)); string assetPath = Path.GetDirectoryName(AssetDatabase.GetAssetPath(spineJson));
string filePath = assetPath + "/" + primaryName + "_SkeletonData.asset"; string filePath = assetPath + "/" + primaryName + SkeletonDataSuffix + ".asset";
#if SPINE_TK2D #if SPINE_TK2D
if (spineJson != null) { if (spineJson != null) {