瀏覽代碼

Merge branch '3.7-beta' into 3.7-beta-cpp

badlogic 6 年之前
父節點
當前提交
b2b2845f88
共有 34 個文件被更改,包括 2414 次插入782 次删除
  1. 5 5
      spine-csharp/src/ExposedList.cs
  2. 1 1
      spine-csharp/src/PathConstraint.cs
  3. 6 0
      spine-csharp/src/Skin.cs
  4. 14 0
      spine-libgdx/spine-libgdx/src/com/esotericsoftware/spine/Skin.java
  5. 2 1
      spine-sfml/cpp/example/main.cpp
  6. 125 47
      spine-ts/build/spine-all.d.ts
  7. 686 10
      spine-ts/build/spine-all.js
  8. 0 0
      spine-ts/build/spine-all.js.map
  9. 26 26
      spine-ts/build/spine-canvas.d.ts
  10. 7 3
      spine-ts/build/spine-canvas.js
  11. 0 0
      spine-ts/build/spine-canvas.js.map
  12. 21 21
      spine-ts/build/spine-core.d.ts
  13. 7 3
      spine-ts/build/spine-core.js
  14. 0 0
      spine-ts/build/spine-core.js.map
  15. 24 24
      spine-ts/build/spine-threejs.d.ts
  16. 7 3
      spine-ts/build/spine-threejs.js
  17. 0 0
      spine-ts/build/spine-threejs.js.map
  18. 34 34
      spine-ts/build/spine-webgl.d.ts
  19. 21 10
      spine-ts/build/spine-webgl.js
  20. 0 0
      spine-ts/build/spine-webgl.js.map
  21. 75 50
      spine-ts/build/spine-widget.d.ts
  22. 424 152
      spine-ts/build/spine-widget.js
  23. 0 0
      spine-ts/build/spine-widget.js.map
  24. 249 0
      spine-ts/widget/css/spine-player.css
  25. 8 125
      spine-ts/widget/example/player-test.html
  26. 562 211
      spine-ts/widget/src/Player.ts
  27. 1 2
      spine-unity/Assets/Spine/Runtime/spine-unity/Components/SkeletonAnimation.cs
  28. 50 14
      spine-unity/Assets/Spine/Runtime/spine-unity/Components/SkeletonRenderer.cs
  29. 13 6
      spine-unity/Assets/Spine/Runtime/spine-unity/Mesh Generation/SpineMesh.cs
  30. 5 11
      spine-unity/Assets/Spine/Runtime/spine-unity/Modules/AttachmentTools/AttachmentTools.cs
  31. 9 4
      spine-unity/Assets/Spine/Runtime/spine-unity/Modules/SkeletonGraphic/SkeletonGraphic.cs
  32. 12 5
      spine-unity/Assets/Spine/Runtime/spine-unity/Modules/SkeletonRenderSeparator/SkeletonRenderSeparator.cs
  33. 5 0
      spine-unity/Assets/Spine/Runtime/spine-unity/SkeletonUtility/SkeletonUtility.cs
  34. 15 14
      spine-unity/Assets/Spine/Runtime/spine-unity/SkeletonUtility/SkeletonUtilityBone.cs

+ 5 - 5
spine-csharp/src/ExposedList.cs

@@ -17,10 +17,10 @@
 // distribute, sublicense, and/or sell copies of the Software, and to
 // distribute, sublicense, and/or sell copies of the Software, and to
 // permit persons to whom the Software is furnished to do so, subject to
 // permit persons to whom the Software is furnished to do so, subject to
 // the following conditions:
 // the following conditions:
-//
+// 
 // The above copyright notice and this permission notice shall be
 // The above copyright notice and this permission notice shall be
 // included in all copies or substantial portions of the Software.
 // included in all copies or substantial portions of the Software.
-//
+// 
 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
@@ -82,8 +82,8 @@ namespace Spine {
 			version++;
 			version++;
 		}
 		}
 
 
-		public void GrowIfNeeded (int newCount) {
-			int minimumSize = Count + newCount;
+		public void GrowIfNeeded (int addedCount) {
+			int minimumSize = Count + addedCount;
 			if (minimumSize > Items.Length)
 			if (minimumSize > Items.Length)
 				Capacity = Math.Max(Math.Max(Capacity * 2, DefaultCapacity), minimumSize);
 				Capacity = Math.Max(Math.Max(Capacity * 2, DefaultCapacity), minimumSize);
 		}
 		}
@@ -466,7 +466,7 @@ namespace Spine {
 		public T Pop () {
 		public T Pop () {
 			if (Count == 0)
 			if (Count == 0)
 				throw new InvalidOperationException("List is empty. Nothing to pop.");
 				throw new InvalidOperationException("List is empty. Nothing to pop.");
-
+			
 			int i = Count - 1;
 			int i = Count - 1;
 			T item = Items[i];
 			T item = Items[i];
 			Items[i] = default(T);
 			Items[i] = default(T);

+ 1 - 1
spine-csharp/src/PathConstraint.cs

@@ -71,7 +71,7 @@ namespace Spine {
 		public void Apply () {
 		public void Apply () {
 			Update();
 			Update();
 		}
 		}
-
+			
 		public void Update () {
 		public void Update () {
 			PathAttachment attachment = target.Attachment as PathAttachment;
 			PathAttachment attachment = target.Attachment as PathAttachment;
 			if (attachment == null) return;
 			if (attachment == null) return;

+ 6 - 0
spine-csharp/src/Skin.cs

@@ -63,6 +63,12 @@ namespace Spine {
 			return attachment;
 			return attachment;
 		}
 		}
 
 
+		/// <summary> Removes the attachment in the skin for the specified slot index and name, if any.</summary>
+		public void RemoveAttachment (int slotIndex, string name) {
+			if (slotIndex < 0) throw new ArgumentOutOfRangeException("slotIndex", "slotIndex must be >= 0");
+			attachments.Remove(new AttachmentKeyTuple(slotIndex, name));
+		}
+
 		/// <summary>Finds the skin keys for a given slot. The results are added to the passed List(names).</summary>
 		/// <summary>Finds the skin keys for a given slot. The results are added to the passed List(names).</summary>
 		/// <param name="slotIndex">The target slotIndex. To find the slot index, use <see cref="Spine.Skeleton.FindSlotIndex"/> or <see cref="Spine.SkeletonData.FindSlotIndex"/>
 		/// <param name="slotIndex">The target slotIndex. To find the slot index, use <see cref="Spine.Skeleton.FindSlotIndex"/> or <see cref="Spine.SkeletonData.FindSlotIndex"/>
 		/// <param name="names">Found skin key names will be added to this list.</param>
 		/// <param name="names">Found skin key names will be added to this list.</param>

+ 14 - 0
spine-libgdx/spine-libgdx/src/com/esotericsoftware/spine/Skin.java

@@ -34,6 +34,7 @@ import com.badlogic.gdx.utils.Array;
 import com.badlogic.gdx.utils.ObjectMap;
 import com.badlogic.gdx.utils.ObjectMap;
 import com.badlogic.gdx.utils.ObjectMap.Entry;
 import com.badlogic.gdx.utils.ObjectMap.Entry;
 import com.badlogic.gdx.utils.Pool;
 import com.badlogic.gdx.utils.Pool;
+
 import com.esotericsoftware.spine.attachments.Attachment;
 import com.esotericsoftware.spine.attachments.Attachment;
 
 
 /** Stores attachments by slot index and attachment name.
 /** Stores attachments by slot index and attachment name.
@@ -77,6 +78,15 @@ public class Skin {
 		return attachments.get(lookup);
 		return attachments.get(lookup);
 	}
 	}
 
 
+	/** Removes the attachment in the skin for the specified slot index and name, if any. */
+	public void removeAttachment (int slotIndex, String name) {
+		if (slotIndex < 0) throw new IllegalArgumentException("slotIndex must be >= 0.");
+		Key key = keyPool.obtain();
+		key.set(slotIndex, name);
+		attachments.remove(key);
+		keyPool.free(key);
+	}
+
 	public void findNamesForSlot (int slotIndex, Array<String> names) {
 	public void findNamesForSlot (int slotIndex, Array<String> names) {
 		if (names == null) throw new IllegalArgumentException("names cannot be null.");
 		if (names == null) throw new IllegalArgumentException("names cannot be null.");
 		if (slotIndex < 0) throw new IllegalArgumentException("slotIndex must be >= 0.");
 		if (slotIndex < 0) throw new IllegalArgumentException("slotIndex must be >= 0.");
@@ -97,6 +107,10 @@ public class Skin {
 		attachments.clear(1024);
 		attachments.clear(1024);
 	}
 	}
 
 
+	public int size () {
+		return attachments.size;
+	}
+
 	/** The skin's name, which is unique within the skeleton. */
 	/** The skin's name, which is unique within the skeleton. */
 	public String getName () {
 	public String getName () {
 		return name;
 		return name;

+ 2 - 1
spine-sfml/cpp/example/main.cpp

@@ -444,7 +444,7 @@ void test (SkeletonData* skeletonData, Atlas* atlas) {
 	Skeleton skeleton(skeletonData);
 	Skeleton skeleton(skeletonData);
 	AnimationStateData animationStateData(skeletonData);
 	AnimationStateData animationStateData(skeletonData);
 	AnimationState animationState(&animationStateData);
 	AnimationState animationState(&animationStateData);
-	animationState.setAnimation(0, "drive", true);
+	animationState.setAnimation(0, "idle", true);
 
 
 	float d = 3;
 	float d = 3;
 	for (int i = 0; i < 1; i++) {
 	for (int i = 0; i < 1; i++) {
@@ -459,6 +459,7 @@ int main () {
 	DebugExtension dbgExtension(SpineExtension::getInstance());
 	DebugExtension dbgExtension(SpineExtension::getInstance());
 	SpineExtension::setInstance(&dbgExtension);
 	SpineExtension::setInstance(&dbgExtension);
 
 
+	testcase(test, "data/yellow_god.json", "data/yellow_god.skel", "data/yellow_god.atlas", 0.6f);
 	testcase(spineboy, "data/spineboy-pro.json", "data/spineboy-pro.skel", "data/spineboy.atlas", 0.6f);
 	testcase(spineboy, "data/spineboy-pro.json", "data/spineboy-pro.skel", "data/spineboy.atlas", 0.6f);
 	testcase(stretchymanStrechyIk, "data/stretchyman-stretchy-ik.json", "data/stretchyman-stretchy-ik.skel", "data/stretchyman.atlas", 0.6f);
 	testcase(stretchymanStrechyIk, "data/stretchyman-stretchy-ik.json", "data/stretchyman-stretchy-ik.skel", "data/stretchyman.atlas", 0.6f);
 	testcase(spineboy, "data/spineboy-ess.json", "data/spineboy-ess.skel", "data/spineboy.atlas", 0.6f);
 	testcase(spineboy, "data/spineboy-ess.json", "data/spineboy-ess.skel", "data/spineboy.atlas", 0.6f);

+ 125 - 47
spine-ts/build/spine-all.d.ts

@@ -16,11 +16,11 @@ declare module spine {
 		setup = 0,
 		setup = 0,
 		first = 1,
 		first = 1,
 		replace = 2,
 		replace = 2,
-		add = 3,
+		add = 3
 	}
 	}
 	enum MixDirection {
 	enum MixDirection {
 		in = 0,
 		in = 0,
-		out = 1,
+		out = 1
 	}
 	}
 	enum TimelineType {
 	enum TimelineType {
 		rotate = 0,
 		rotate = 0,
@@ -37,7 +37,7 @@ declare module spine {
 		pathConstraintPosition = 11,
 		pathConstraintPosition = 11,
 		pathConstraintSpacing = 12,
 		pathConstraintSpacing = 12,
 		pathConstraintMix = 13,
 		pathConstraintMix = 13,
-		twoColor = 14,
+		twoColor = 14
 	}
 	}
 	abstract class CurveTimeline implements Timeline {
 	abstract class CurveTimeline implements Timeline {
 		static LINEAR: number;
 		static LINEAR: number;
@@ -341,7 +341,7 @@ declare module spine {
 		end = 2,
 		end = 2,
 		dispose = 3,
 		dispose = 3,
 		complete = 4,
 		complete = 4,
-		event = 5,
+		event = 5
 	}
 	}
 	interface AnimationStateListener2 {
 	interface AnimationStateListener2 {
 		start(entry: TrackEntry): void;
 		start(entry: TrackEntry): void;
@@ -380,8 +380,8 @@ declare module spine {
 		private toLoad;
 		private toLoad;
 		private loaded;
 		private loaded;
 		constructor(textureLoader: (image: HTMLImageElement) => any, pathPrefix?: string);
 		constructor(textureLoader: (image: HTMLImageElement) => any, pathPrefix?: string);
-		private static downloadText(url, success, error);
-		private static downloadBinary(url, success, error);
+		private static downloadText;
+		private static downloadBinary;
 		loadText(path: string, success?: (path: string, text: string) => void, error?: (path: string, error: string) => void): void;
 		loadText(path: string, success?: (path: string, text: string) => void, error?: (path: string, error: string) => void): void;
 		loadTexture(path: string, success?: (path: string, image: HTMLImageElement) => void, error?: (path: string, error: string) => void): void;
 		loadTexture(path: string, success?: (path: string, image: HTMLImageElement) => void, error?: (path: string, error: string) => void): void;
 		loadTextureData(path: string, data: string, success?: (path: string, image: HTMLImageElement) => void, error?: (path: string, error: string) => void): void;
 		loadTextureData(path: string, data: string, success?: (path: string, image: HTMLImageElement) => void, error?: (path: string, error: string) => void): void;
@@ -414,7 +414,7 @@ declare module spine {
 		Normal = 0,
 		Normal = 0,
 		Additive = 1,
 		Additive = 1,
 		Multiply = 2,
 		Multiply = 2,
-		Screen = 3,
+		Screen = 3
 	}
 	}
 }
 }
 declare module spine {
 declare module spine {
@@ -483,7 +483,7 @@ declare module spine {
 		OnlyTranslation = 1,
 		OnlyTranslation = 1,
 		NoRotationOrReflection = 2,
 		NoRotationOrReflection = 2,
 		NoScale = 3,
 		NoScale = 3,
-		NoScaleOrReflection = 4,
+		NoScaleOrReflection = 4
 	}
 	}
 }
 }
 declare module spine {
 declare module spine {
@@ -593,17 +593,17 @@ declare module spine {
 	}
 	}
 	enum PositionMode {
 	enum PositionMode {
 		Fixed = 0,
 		Fixed = 0,
-		Percent = 1,
+		Percent = 1
 	}
 	}
 	enum SpacingMode {
 	enum SpacingMode {
 		Length = 0,
 		Length = 0,
 		Fixed = 1,
 		Fixed = 1,
-		Percent = 2,
+		Percent = 2
 	}
 	}
 	enum RotateMode {
 	enum RotateMode {
 		Tangent = 0,
 		Tangent = 0,
 		Chain = 1,
 		Chain = 1,
-		ChainScale = 2,
+		ChainScale = 2
 	}
 	}
 }
 }
 declare module spine {
 declare module spine {
@@ -614,12 +614,12 @@ declare module spine {
 		private rawAssets;
 		private rawAssets;
 		private errors;
 		private errors;
 		constructor(pathPrefix?: string);
 		constructor(pathPrefix?: string);
-		private queueAsset(clientId, textureLoader, path);
+		private queueAsset;
 		loadText(clientId: string, path: string): void;
 		loadText(clientId: string, path: string): void;
 		loadJson(clientId: string, path: string): void;
 		loadJson(clientId: string, path: string): void;
 		loadTexture(clientId: string, textureLoader: (image: HTMLImageElement) => any, path: string): void;
 		loadTexture(clientId: string, textureLoader: (image: HTMLImageElement) => any, path: string): void;
 		get(clientId: string, path: string): any;
 		get(clientId: string, path: string): any;
-		private updateClientAssets(clientAssets);
+		private updateClientAssets;
 		isLoadingComplete(clientId: string): boolean;
 		isLoadingComplete(clientId: string): boolean;
 		dispose(): void;
 		dispose(): void;
 		hasErrors(): boolean;
 		hasErrors(): boolean;
@@ -670,7 +670,7 @@ declare module spine {
 		findIkConstraint(constraintName: string): IkConstraint;
 		findIkConstraint(constraintName: string): IkConstraint;
 		findTransformConstraint(constraintName: string): TransformConstraint;
 		findTransformConstraint(constraintName: string): TransformConstraint;
 		findPathConstraint(constraintName: string): PathConstraint;
 		findPathConstraint(constraintName: string): PathConstraint;
-		getBounds(offset: Vector2, size: Vector2, temp: Array<number>): void;
+		getBounds(offset: Vector2, size: Vector2, temp?: Array<number>): void;
 		update(delta: number): void;
 		update(delta: number): void;
 	}
 	}
 }
 }
@@ -823,12 +823,12 @@ declare module spine {
 		MipMapNearestNearest = 9984,
 		MipMapNearestNearest = 9984,
 		MipMapLinearNearest = 9985,
 		MipMapLinearNearest = 9985,
 		MipMapNearestLinear = 9986,
 		MipMapNearestLinear = 9986,
-		MipMapLinearLinear = 9987,
+		MipMapLinearLinear = 9987
 	}
 	}
 	enum TextureWrap {
 	enum TextureWrap {
 		MirroredRepeat = 33648,
 		MirroredRepeat = 33648,
 		ClampToEdge = 33071,
 		ClampToEdge = 33071,
-		Repeat = 10497,
+		Repeat = 10497
 	}
 	}
 	class TextureRegion {
 	class TextureRegion {
 		renderObject: any;
 		renderObject: any;
@@ -855,7 +855,7 @@ declare module spine {
 		pages: TextureAtlasPage[];
 		pages: TextureAtlasPage[];
 		regions: TextureAtlasRegion[];
 		regions: TextureAtlasRegion[];
 		constructor(atlasText: string, textureLoader: (path: string) => any);
 		constructor(atlasText: string, textureLoader: (path: string) => any);
-		private load(atlasText, textureLoader);
+		private load;
 		findRegion(name: string): TextureAtlasRegion;
 		findRegion(name: string): TextureAtlasRegion;
 		dispose(): void;
 		dispose(): void;
 	}
 	}
@@ -931,9 +931,9 @@ declare module spine {
 		private polygonIndicesPool;
 		private polygonIndicesPool;
 		triangulate(verticesArray: ArrayLike<number>): Array<number>;
 		triangulate(verticesArray: ArrayLike<number>): Array<number>;
 		decompose(verticesArray: Array<number>, triangles: Array<number>): Array<Array<number>>;
 		decompose(verticesArray: Array<number>, triangles: Array<number>): Array<Array<number>>;
-		private static isConcave(index, vertexCount, vertices, indices);
-		private static positiveArea(p1x, p1y, p2x, p2y, p3x, p3y);
-		private static winding(p1x, p1y, p2x, p2y, p3x, p3y);
+		private static isConcave;
+		private static positiveArea;
+		private static winding;
 	}
 	}
 }
 }
 declare module spine {
 declare module spine {
@@ -1105,7 +1105,7 @@ declare module spine {
 		Mesh = 2,
 		Mesh = 2,
 		LinkedMesh = 3,
 		LinkedMesh = 3,
 		Path = 4,
 		Path = 4,
-		Point = 5,
+		Point = 5
 	}
 	}
 }
 }
 declare module spine {
 declare module spine {
@@ -1271,11 +1271,11 @@ declare module spine.canvas {
 		private tempColor;
 		private tempColor;
 		constructor(context: CanvasRenderingContext2D);
 		constructor(context: CanvasRenderingContext2D);
 		draw(skeleton: Skeleton): void;
 		draw(skeleton: Skeleton): void;
-		private drawImages(skeleton);
-		private drawTriangles(skeleton);
-		private drawTriangle(img, x0, y0, u0, v0, x1, y1, u1, v1, x2, y2, u2, v2);
-		private computeRegionVertices(slot, region, pma);
-		private computeMeshVertices(slot, mesh, pma);
+		private drawImages;
+		private drawTriangles;
+		private drawTriangle;
+		private computeRegionVertices;
+		private computeMeshVertices;
 	}
 	}
 }
 }
 declare module spine.webgl {
 declare module spine.webgl {
@@ -1330,7 +1330,7 @@ declare module spine.webgl {
 		touchesPool: Pool<Touch>;
 		touchesPool: Pool<Touch>;
 		private listeners;
 		private listeners;
 		constructor(element: HTMLElement);
 		constructor(element: HTMLElement);
-		private setupCallbacks(element);
+		private setupCallbacks;
 		addListener(listener: InputListener): void;
 		addListener(listener: InputListener): void;
 		removeListener(listener: InputListener): void;
 		removeListener(listener: InputListener): void;
 	}
 	}
@@ -1439,7 +1439,7 @@ declare module spine.webgl {
 		drawWithOffset(shader: Shader, primitiveType: number, offset: number, count: number): void;
 		drawWithOffset(shader: Shader, primitiveType: number, offset: number, count: number): void;
 		bind(shader: Shader): void;
 		bind(shader: Shader): void;
 		unbind(shader: Shader): void;
 		unbind(shader: Shader): void;
-		private update();
+		private update;
 		restore(): void;
 		restore(): void;
 		dispose(): void;
 		dispose(): void;
 	}
 	}
@@ -1465,7 +1465,7 @@ declare module spine.webgl {
 		constructor();
 		constructor();
 	}
 	}
 	enum VertexAttributeType {
 	enum VertexAttributeType {
-		Float = 0,
+		Float = 0
 	}
 	}
 }
 }
 declare module spine.webgl {
 declare module spine.webgl {
@@ -1484,7 +1484,7 @@ declare module spine.webgl {
 		begin(shader: Shader): void;
 		begin(shader: Shader): void;
 		setBlendMode(srcBlend: number, dstBlend: number): void;
 		setBlendMode(srcBlend: number, dstBlend: number): void;
 		draw(texture: GLTexture, vertices: ArrayLike<number>, indices: Array<number>): void;
 		draw(texture: GLTexture, vertices: ArrayLike<number>, indices: Array<number>): void;
-		private flush();
+		private flush;
 		end(): void;
 		end(): void;
 		getDrawCalls(): number;
 		getDrawCalls(): number;
 		dispose(): void;
 		dispose(): void;
@@ -1524,13 +1524,13 @@ declare module spine.webgl {
 		curve(x1: number, y1: number, cx1: number, cy1: number, cx2: number, cy2: number, x2: number, y2: number, segments: number, color?: Color): void;
 		curve(x1: number, y1: number, cx1: number, cy1: number, cx2: number, cy2: number, x2: number, y2: number, segments: number, color?: Color): void;
 		end(): void;
 		end(): void;
 		resize(resizeMode: ResizeMode): void;
 		resize(resizeMode: ResizeMode): void;
-		private enableRenderer(renderer);
+		private enableRenderer;
 		dispose(): void;
 		dispose(): void;
 	}
 	}
 	enum ResizeMode {
 	enum ResizeMode {
 		Stretch = 0,
 		Stretch = 0,
 		Expand = 1,
 		Expand = 1,
-		Fit = 2,
+		Fit = 2
 	}
 	}
 }
 }
 declare module spine.webgl {
 declare module spine.webgl {
@@ -1558,9 +1558,9 @@ declare module spine.webgl {
 		getVertexShaderSource(): string;
 		getVertexShaderSource(): string;
 		getFragmentSource(): string;
 		getFragmentSource(): string;
 		constructor(context: ManagedWebGLRenderingContext | WebGLRenderingContext, vertexShader: string, fragmentShader: string);
 		constructor(context: ManagedWebGLRenderingContext | WebGLRenderingContext, vertexShader: string, fragmentShader: string);
-		private compile();
-		private compileShader(type, source);
-		private compileProgram(vs, fs);
+		private compile;
+		private compileShader;
+		private compileProgram;
 		restore(): void;
 		restore(): void;
 		bind(): void;
 		bind(): void;
 		unbind(): void;
 		unbind(): void;
@@ -1607,16 +1607,16 @@ declare module spine.webgl {
 		polygon(polygonVertices: ArrayLike<number>, offset: number, count: number, color?: Color): void;
 		polygon(polygonVertices: ArrayLike<number>, offset: number, count: number, color?: Color): void;
 		circle(filled: boolean, x: number, y: number, radius: number, color?: Color, segments?: number): void;
 		circle(filled: boolean, x: number, y: number, radius: number, color?: Color, segments?: number): void;
 		curve(x1: number, y1: number, cx1: number, cy1: number, cx2: number, cy2: number, x2: number, y2: number, segments: number, color?: Color): void;
 		curve(x1: number, y1: number, cx1: number, cy1: number, cx2: number, cy2: number, x2: number, y2: number, segments: number, color?: Color): void;
-		private vertex(x, y, color);
+		private vertex;
 		end(): void;
 		end(): void;
-		private flush();
-		private check(shapeType, numVertices);
+		private flush;
+		private check;
 		dispose(): void;
 		dispose(): void;
 	}
 	}
 	enum ShapeType {
 	enum ShapeType {
 		Point = 0,
 		Point = 0,
 		Line = 1,
 		Line = 1,
-		Filled = 4,
+		Filled = 4
 	}
 	}
 }
 }
 declare module spine.webgl {
 declare module spine.webgl {
@@ -1756,9 +1756,9 @@ declare module spine.threejs {
 		private tempColor;
 		private tempColor;
 		constructor(skeletonData: SkeletonData);
 		constructor(skeletonData: SkeletonData);
 		update(deltaTime: number): void;
 		update(deltaTime: number): void;
-		private clearBatches();
-		private nextBatch();
-		private updateGeometry();
+		private clearBatches;
+		private nextBatch;
+		private updateGeometry;
 	}
 	}
 }
 }
 declare module spine.threejs {
 declare module spine.threejs {
@@ -1772,6 +1772,84 @@ declare module spine.threejs {
 		static toThreeJsTextureWrap(wrap: TextureWrap): THREE.Wrapping;
 		static toThreeJsTextureWrap(wrap: TextureWrap): THREE.Wrapping;
 	}
 	}
 }
 }
+declare module spine {
+	interface SpinePlayerConfig {
+		jsonUrl: string;
+		atlasUrl: string;
+		animation: string;
+		animations: string[];
+		skin: string;
+		skins: string[];
+		controlBones: string[];
+		premultipliedAlpha: boolean;
+		showControls: boolean;
+		debug: {
+			bones: boolean;
+			regions: boolean;
+			meshes: boolean;
+			bounds: boolean;
+			paths: boolean;
+			clipping: boolean;
+			points: boolean;
+			hulls: boolean;
+		};
+		viewport: {
+			x: number;
+			y: number;
+			width: number;
+			height: number;
+		};
+		alpha: boolean;
+		backgroundColor: string;
+		backgroundImage: {
+			url: string;
+			x: number;
+			y: number;
+			width: number;
+			height: number;
+		};
+		success: (widget: SpineWidget) => void;
+		error: (widget: SpineWidget, msg: string) => void;
+	}
+	class SpinePlayer {
+		private config;
+		static HOVER_COLOR_INNER: Color;
+		static HOVER_COLOR_OUTER: Color;
+		static NON_HOVER_COLOR_INNER: Color;
+		static NON_HOVER_COLOR_OUTER: Color;
+		private sceneRenderer;
+		private dom;
+		private playerControls;
+		private canvas;
+		private timelineSlider;
+		private playButton;
+		private context;
+		private loadingScreen;
+		private assetManager;
+		private loaded;
+		private skeleton;
+		private animationState;
+		private time;
+		private paused;
+		private playTime;
+		private speed;
+		private selectedBones;
+		constructor(parent: HTMLElement, config: SpinePlayerConfig);
+		validateConfig(config: SpinePlayerConfig): SpinePlayerConfig;
+		showError(error: string): void;
+		render(): HTMLElement;
+		showSpeedDialog(): void;
+		showAnimationsDialog(): void;
+		showSkinsDialog(): void;
+		showSettingsDialog(): void;
+		drawFrame(requestNextFrame?: boolean): void;
+		scale(sourceWidth: number, sourceHeight: number, targetWidth: number, targetHeight: number): Vector2;
+		loadSkeleton(): void;
+		setupInput(): void;
+		private play;
+		private pause;
+	}
+}
 declare module spine {
 declare module spine {
 	class SpineWidget {
 	class SpineWidget {
 		skeleton: Skeleton;
 		skeleton: Skeleton;
@@ -1793,10 +1871,10 @@ declare module spine {
 		private loaded;
 		private loaded;
 		private bounds;
 		private bounds;
 		constructor(element: HTMLElement | string, config: SpineWidgetConfig);
 		constructor(element: HTMLElement | string, config: SpineWidgetConfig);
-		private validateConfig(config);
-		private load();
-		private render();
-		private resize();
+		private validateConfig;
+		private load;
+		private render;
+		private resize;
 		pause(): void;
 		pause(): void;
 		play(): void;
 		play(): void;
 		isPlaying(): boolean;
 		isPlaying(): boolean;
@@ -1804,7 +1882,7 @@ declare module spine {
 		static loadWidgets(): void;
 		static loadWidgets(): void;
 		static loadWidget(widget: HTMLElement): void;
 		static loadWidget(widget: HTMLElement): void;
 		static pageLoaded: boolean;
 		static pageLoaded: boolean;
-		private static ready();
+		private static ready;
 		static setupDOMListener(): void;
 		static setupDOMListener(): void;
 	}
 	}
 	class SpineWidgetConfig {
 	class SpineWidgetConfig {

+ 686 - 10
spine-ts/build/spine-all.js

@@ -1,7 +1,10 @@
 var __extends = (this && this.__extends) || (function () {
 var __extends = (this && this.__extends) || (function () {
-	var extendStatics = Object.setPrototypeOf ||
-		({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||
-		function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; };
+	var extendStatics = function (d, b) {
+		extendStatics = Object.setPrototypeOf ||
+			({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||
+			function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; };
+		return extendStatics(d, b);
+	}
 	return function (d, b) {
 	return function (d, b) {
 		extendStatics(d, b);
 		extendStatics(d, b);
 		function __() { this.constructor = d; }
 		function __() { this.constructor = d; }
@@ -3826,6 +3829,7 @@ var spine;
 			return null;
 			return null;
 		};
 		};
 		Skeleton.prototype.getBounds = function (offset, size, temp) {
 		Skeleton.prototype.getBounds = function (offset, size, temp) {
+			if (temp === void 0) { temp = new Array(2); }
 			if (offset == null)
 			if (offset == null)
 				throw new Error("offset cannot be null.");
 				throw new Error("offset cannot be null.");
 			if (size == null)
 			if (size == null)
@@ -7226,7 +7230,7 @@ var spine;
 			}
 			}
 			Input.prototype.setupCallbacks = function (element) {
 			Input.prototype.setupCallbacks = function (element) {
 				var _this = this;
 				var _this = this;
-				element.addEventListener("mousedown", function (ev) {
+				var mouseDown = function (ev) {
 					if (ev instanceof MouseEvent) {
 					if (ev instanceof MouseEvent) {
 						var rect = element.getBoundingClientRect();
 						var rect = element.getBoundingClientRect();
 						var x = ev.clientX - rect.left;
 						var x = ev.clientX - rect.left;
@@ -7238,9 +7242,11 @@ var spine;
 						_this.lastX = x;
 						_this.lastX = x;
 						_this.lastY = y;
 						_this.lastY = y;
 						_this.buttonDown = true;
 						_this.buttonDown = true;
+						document.addEventListener("mousemove", mouseMove);
+						document.addEventListener("mouseup", mouseUp);
 					}
 					}
-				}, true);
-				element.addEventListener("mousemove", function (ev) {
+				};
+				var mouseMove = function (ev) {
 					if (ev instanceof MouseEvent) {
 					if (ev instanceof MouseEvent) {
 						var rect = element.getBoundingClientRect();
 						var rect = element.getBoundingClientRect();
 						var x = ev.clientX - rect.left;
 						var x = ev.clientX - rect.left;
@@ -7257,8 +7263,8 @@ var spine;
 						_this.lastX = x;
 						_this.lastX = x;
 						_this.lastY = y;
 						_this.lastY = y;
 					}
 					}
-				}, true);
-				element.addEventListener("mouseup", function (ev) {
+				};
+				var mouseUp = function (ev) {
 					if (ev instanceof MouseEvent) {
 					if (ev instanceof MouseEvent) {
 						var rect = element.getBoundingClientRect();
 						var rect = element.getBoundingClientRect();
 						var x = ev.clientX - rect.left;
 						var x = ev.clientX - rect.left;
@@ -7270,8 +7276,13 @@ var spine;
 						_this.lastX = x;
 						_this.lastX = x;
 						_this.lastY = y;
 						_this.lastY = y;
 						_this.buttonDown = false;
 						_this.buttonDown = false;
+						document.removeEventListener("mousemove", mouseMove);
+						document.removeEventListener("mouseup", mouseUp);
 					}
 					}
-				}, true);
+				};
+				element.addEventListener("mousedown", mouseDown, true);
+				element.addEventListener("mousemove", mouseMove, true);
+				element.addEventListener("mouseup", mouseUp, true);
 				element.addEventListener("touchstart", function (ev) {
 				element.addEventListener("touchstart", function (ev) {
 					if (_this.currTouch != null)
 					if (_this.currTouch != null)
 						return;
 						return;
@@ -7433,11 +7444,11 @@ var spine;
 				var renderer = this.renderer;
 				var renderer = this.renderer;
 				var canvas = renderer.canvas;
 				var canvas = renderer.canvas;
 				var gl = renderer.context.gl;
 				var gl = renderer.context.gl;
+				renderer.resize(webgl.ResizeMode.Stretch);
 				var oldX = renderer.camera.position.x, oldY = renderer.camera.position.y;
 				var oldX = renderer.camera.position.x, oldY = renderer.camera.position.y;
 				renderer.camera.position.set(canvas.width / 2, canvas.height / 2, 0);
 				renderer.camera.position.set(canvas.width / 2, canvas.height / 2, 0);
 				renderer.camera.viewportWidth = canvas.width;
 				renderer.camera.viewportWidth = canvas.width;
 				renderer.camera.viewportHeight = canvas.height;
 				renderer.camera.viewportHeight = canvas.height;
-				renderer.resize(webgl.ResizeMode.Stretch);
 				if (!complete) {
 				if (!complete) {
 					gl.clearColor(this.backgroundColor.r, this.backgroundColor.g, this.backgroundColor.b, this.backgroundColor.a);
 					gl.clearColor(this.backgroundColor.r, this.backgroundColor.g, this.backgroundColor.b, this.backgroundColor.a);
 					gl.clear(gl.COLOR_BUFFER_BIT);
 					gl.clear(gl.COLOR_BUFFER_BIT);
@@ -10055,6 +10066,671 @@ var spine;
 	})(threejs = spine.threejs || (spine.threejs = {}));
 	})(threejs = spine.threejs || (spine.threejs = {}));
 })(spine || (spine = {}));
 })(spine || (spine = {}));
 var spine;
 var spine;
+(function (spine) {
+	var Popup = (function () {
+		function Popup(parent, htmlContent) {
+			this.dom = createElement("\n\t\t\t\t<div class=\"spine-player-popup spine-player-hidden\">\n\t\t\t\t</div>\n\t\t\t");
+			this.dom.innerHTML = htmlContent;
+			parent.appendChild(this.dom);
+		}
+		Popup.prototype.show = function () {
+			var _this = this;
+			this.dom.classList.remove("spine-player-hidden");
+			var justClicked = true;
+			var windowClickListener = function (event) {
+				if (justClicked) {
+					justClicked = false;
+					return;
+				}
+				if (!isContained(_this.dom, event.target)) {
+					_this.dom.parentNode.removeChild(_this.dom);
+					window.removeEventListener("click", windowClickListener);
+				}
+			};
+			window.addEventListener("click", windowClickListener);
+		};
+		return Popup;
+	}());
+	var Switch = (function () {
+		function Switch(text) {
+			this.text = text;
+			this.enabled = false;
+		}
+		Switch.prototype.render = function () {
+			var _this = this;
+			this["switch"] = createElement("\n\t\t\t\t<div class=\"spine-player-switch\">\n\t\t\t\t\t<span class=\"spine-player-switch-text\">" + this.text + "</span>\n\t\t\t\t\t<div class=\"spine-player-switch-knob-area\">\n\t\t\t\t\t\t<div class=\"spine-player-switch-knob\"></div>\n\t\t\t\t\t</div>\n\t\t\t\t</div>\n\t\t\t");
+			this["switch"].addEventListener("click", function () {
+				_this.setEnabled(!_this.enabled);
+				if (_this.change)
+					_this.change(_this.enabled);
+			});
+			return this["switch"];
+		};
+		Switch.prototype.setEnabled = function (enabled) {
+			if (enabled)
+				this["switch"].classList.add("active");
+			else
+				this["switch"].classList.remove("active");
+			this.enabled = enabled;
+		};
+		Switch.prototype.isEnabled = function () {
+			return this.enabled;
+		};
+		return Switch;
+	}());
+	var Slider = (function () {
+		function Slider() {
+		}
+		Slider.prototype.render = function () {
+			var _this = this;
+			this.slider = createElement("\n\t\t\t\t<div class=\"spine-player-slider\">\n\t\t\t\t\t<div class=\"spine-player-slider-value\"></div>\n\t\t\t\t</div>\n\t\t\t");
+			this.value = findWithClass(this.slider, "spine-player-slider-value")[0];
+			this.setValue(0);
+			var input = new spine.webgl.Input(this.slider);
+			var dragging = false;
+			input.addListener({
+				down: function (x, y) {
+					dragging = true;
+				},
+				up: function (x, y) {
+					dragging = false;
+					var percentage = x / _this.slider.clientWidth;
+					percentage = Math.max(0, Math.min(percentage, 1));
+					_this.setValue(x / _this.slider.clientWidth);
+					if (_this.change)
+						_this.change(percentage);
+				},
+				moved: function (x, y) {
+					if (dragging) {
+						var percentage = x / _this.slider.clientWidth;
+						percentage = Math.max(0, Math.min(percentage, 1));
+						_this.setValue(x / _this.slider.clientWidth);
+						if (_this.change)
+							_this.change(percentage);
+					}
+				},
+				dragged: function (x, y) {
+					var percentage = x / _this.slider.clientWidth;
+					percentage = Math.max(0, Math.min(percentage, 1));
+					_this.setValue(x / _this.slider.clientWidth);
+					if (_this.change)
+						_this.change(percentage);
+				}
+			});
+			return this.slider;
+		};
+		Slider.prototype.setValue = function (percentage) {
+			percentage = Math.max(0, Math.min(1, percentage));
+			this.value.style.width = "" + (percentage * 100) + "%";
+		};
+		return Slider;
+	}());
+	var SpinePlayer = (function () {
+		function SpinePlayer(parent, config) {
+			this.config = config;
+			this.time = new spine.TimeKeeper();
+			this.paused = true;
+			this.playTime = 0;
+			this.speed = 1;
+			parent.appendChild(this.render());
+		}
+		SpinePlayer.prototype.validateConfig = function (config) {
+			if (!config)
+				throw new Error("Please pass a configuration to new.spine.SpinePlayer().");
+			if (!config.jsonUrl)
+				throw new Error("Please specify the URL of the skeleton JSON file.");
+			if (!config.atlasUrl)
+				throw new Error("Please specify the URL of the atlas file.");
+			if (!config.alpha)
+				config.alpha = false;
+			if (!config.backgroundColor)
+				config.backgroundColor = "#000000";
+			if (!config.premultipliedAlpha)
+				config.premultipliedAlpha = false;
+			if (!config.success)
+				config.success = function (widget) { };
+			if (!config.error)
+				config.error = function (widget, msg) { };
+			if (!config.debug)
+				config.debug = {
+					bones: false,
+					regions: false,
+					meshes: false,
+					bounds: false,
+					clipping: false,
+					paths: false,
+					points: false,
+					hulls: false
+				};
+			if (!config.debug.bones)
+				config.debug.bones = false;
+			if (!config.debug.bounds)
+				config.debug.bounds = false;
+			if (!config.debug.clipping)
+				config.debug.clipping = false;
+			if (!config.debug.hulls)
+				config.debug.hulls = false;
+			if (!config.debug.paths)
+				config.debug.paths = false;
+			if (!config.debug.points)
+				config.debug.points = false;
+			if (!config.debug.regions)
+				config.debug.regions = false;
+			if (!config.debug.meshes)
+				config.debug.meshes = false;
+			if (config.animations && config.animation) {
+				if (config.animations.indexOf(config.animation) < 0)
+					throw new Error("Default animation '" + config.animation + "' is not contained in the list of selectable animations " + escapeHtml(JSON.stringify(this.config.animations)) + ".");
+			}
+			if (config.skins && config.skin) {
+				if (config.skins.indexOf(config.skin) < 0)
+					throw new Error("Default skin '" + config.skin + "' is not contained in the list of selectable skins " + escapeHtml(JSON.stringify(this.config.skins)) + ".");
+			}
+			if (!config.controlBones)
+				config.controlBones = [];
+			if (!config.showControls)
+				config.showControls = true;
+			return config;
+		};
+		SpinePlayer.prototype.showError = function (error) {
+			var errorDom = findWithClass(this.dom, "spine-player-error")[0];
+			errorDom.classList.remove("spine-player-hidden");
+			errorDom.innerHTML = "<p style=\"text-align: center; align-self: center;\">" + error + "</p>";
+		};
+		SpinePlayer.prototype.render = function () {
+			var _this = this;
+			var config = this.config;
+			var dom = this.dom = createElement("\n\t\t\t\t<div class=\"spine-player\">\n\t\t\t\t\t<canvas class=\"spine-player-canvas\"></canvas>\n\t\t\t\t\t<div class=\"spine-player-error spine-player-hidden\"></div>\n\t\t\t\t\t<div class=\"spine-player-controls spine-player-popup-parent\">\n\t\t\t\t\t\t<div class=\"spine-player-timeline\">\n\t\t\t\t\t\t</div>\n\t\t\t\t\t\t<div class=\"spine-player-buttons\">\n\t\t\t\t\t\t\t<button id=\"spine-player-button-play-pause\" class=\"spine-player-button spine-player-button-icon-pause\"></button>\n\t\t\t\t\t\t\t<div class=\"spine-player-button-spacer\"></div>\n\t\t\t\t\t\t\t<button id=\"spine-player-button-speed\" class=\"spine-player-button spine-player-button-icon-speed\"></button>\n\t\t\t\t\t\t\t<button id=\"spine-player-button-animation\" class=\"spine-player-button spine-player-button-icon-animations\"></button>\n\t\t\t\t\t\t\t<button id=\"spine-player-button-skin\" class=\"spine-player-button spine-player-button-icon-skins\"></button>\n\t\t\t\t\t\t\t<button id=\"spine-player-button-settings\" class=\"spine-player-button spine-player-button-icon-settings\"></button>\n\t\t\t\t\t\t\t<button id=\"spine-player-button-fullscreen\" class=\"spine-player-button spine-player-button-icon-fullscreen\"></button>\n\t\t\t\t\t\t</div>\n\t\t\t\t\t</div>\n\t\t\t\t</div>\n\t\t\t");
+			try {
+				this.config = this.validateConfig(config);
+			}
+			catch (e) {
+				this.showError(e);
+				return dom;
+			}
+			try {
+				this.canvas = findWithClass(dom, "spine-player-canvas")[0];
+				var webglConfig = { alpha: config.alpha };
+				this.context = new spine.webgl.ManagedWebGLRenderingContext(this.canvas, webglConfig);
+				this.sceneRenderer = new spine.webgl.SceneRenderer(this.canvas, this.context, true);
+				this.loadingScreen = new spine.webgl.LoadingScreen(this.sceneRenderer);
+			}
+			catch (e) {
+				this.showError("Sorry, your browser does not support WebGL.<br><br>Please use the latest version of Firefox, Chrome, Edge, or Safari.");
+				return dom;
+			}
+			this.assetManager = new spine.webgl.AssetManager(this.context);
+			this.assetManager.loadText(config.jsonUrl);
+			this.assetManager.loadTextureAtlas(config.atlasUrl);
+			if (config.backgroundImage && config.backgroundImage.url)
+				this.assetManager.loadTexture(config.backgroundImage.url);
+			requestAnimationFrame(function () { return _this.drawFrame(); });
+			this.playerControls = findWithClass(dom, "spine-player-controls")[0];
+			var timeline = findWithClass(dom, "spine-player-timeline")[0];
+			this.timelineSlider = new Slider();
+			timeline.appendChild(this.timelineSlider.render());
+			this.playButton = findWithId(dom, "spine-player-button-play-pause")[0];
+			var speedButton = findWithId(dom, "spine-player-button-speed")[0];
+			var animationButton = findWithId(dom, "spine-player-button-animation")[0];
+			var skinButton = findWithId(dom, "spine-player-button-skin")[0];
+			var settingsButton = findWithId(dom, "spine-player-button-settings")[0];
+			var fullscreenButton = findWithId(dom, "spine-player-button-fullscreen")[0];
+			this.playButton.onclick = function () {
+				if (_this.paused)
+					_this.play();
+				else
+					_this.pause();
+			};
+			speedButton.onclick = function () {
+				_this.showSpeedDialog();
+			};
+			animationButton.onclick = function () {
+				_this.showAnimationsDialog();
+			};
+			skinButton.onclick = function () {
+				_this.showSkinsDialog();
+			};
+			settingsButton.onclick = function () {
+				_this.showSettingsDialog();
+			};
+			fullscreenButton.onclick = function () {
+				var doc = document;
+				if (doc.fullscreenElement || doc.webkitFullscreenElement || doc.mozFullScreenElement || doc.msFullscreenElement) {
+					if (doc.exitFullscreen)
+						doc.exitFullscreen();
+					else if (doc.mozCancelFullScreen)
+						doc.mozCancelFullScreen();
+					else if (doc.webkitExitFullscreen)
+						doc.webkitExitFullscreen();
+					else if (doc.msExitFullscreen)
+						doc.msExitFullscreen();
+				}
+				else {
+					var player = dom;
+					if (player.requestFullscreen)
+						player.requestFullscreen();
+					else if (player.webkitRequestFullScreen)
+						player.webkitRequestFullScreen();
+					else if (player.mozRequestFullScreen)
+						player.mozRequestFullScreen();
+					else if (player.msRequestFullscreen)
+						player.msRequestFullscreen();
+				}
+			};
+			window.onresize = function () {
+				_this.drawFrame(false);
+			};
+			if (!config.showControls)
+				findWithClass(dom, "spine-player-controls ")[0].classList.add("spine-player-hidden");
+			return dom;
+		};
+		SpinePlayer.prototype.showSpeedDialog = function () {
+			var _this = this;
+			var popup = new Popup(this.playerControls, "\n\t\t\t\t<div class=\"spine-player-row\" style=\"user-select: none; align-items: center; padding: 8px;\">\n\t\t\t\t\t<div style=\"margin-right: 16px;\">Speed</div>\n\t\t\t\t\t<div class=\"spine-player-column\">\n\t\t\t\t\t\t<div class=\"spine-player-speed-slider\" style=\"margin-bottom: 4px;\"></div>\n\t\t\t\t\t\t<div class=\"spine-player-row\" style=\"justify-content: space-between;\">\n\t\t\t\t\t\t\t<div>0.1x</div>\n\t\t\t\t\t\t\t<div>1x</div>\n\t\t\t\t\t\t\t<div>2x</div>\n\t\t\t\t\t\t</div>\n\t\t\t\t\t</div>\n\t\t\t\t</div>\n\t\t\t");
+			var sliderParent = findWithClass(popup.dom, "spine-player-speed-slider")[0];
+			var slider = new Slider();
+			sliderParent.appendChild(slider.render());
+			slider.setValue(this.speed / 2);
+			slider.change = function (percentage) {
+				_this.speed = percentage * 2;
+			};
+			popup.show();
+		};
+		SpinePlayer.prototype.showAnimationsDialog = function () {
+			var _this = this;
+			if (!this.skeleton || this.skeleton.data.animations.length == 0)
+				return;
+			var popup = new Popup(this.playerControls, "\n\t\t\t\t<div class=\"spine-player-popup-title\">Animations</div>\n\t\t\t\t<hr>\n\t\t\t\t<ul class=\"spine-player-list\"></ul>\n\t\t\t");
+			var rows = findWithClass(popup.dom, "spine-player-list")[0];
+			this.skeleton.data.animations.forEach(function (animation) {
+				if (_this.config.animations && _this.config.animations.indexOf(animation.name) < 0) {
+					return;
+				}
+				var row = createElement("\n\t\t\t\t\t<li class=\"spine-player-list-item selectable\">\n\t\t\t\t\t\t<div class=\"selectable-circle\">\n\t\t\t\t\t\t</div>\n\t\t\t\t\t\t<div class=\"selectable-text\">\n\t\t\t\t\t\t</div>\n\t\t\t\t\t</li>\n\t\t\t\t");
+				if (animation.name == _this.config.animation)
+					row.classList.add("selected");
+				findWithClass(row, "selectable-text")[0].innerText = animation.name;
+				rows.appendChild(row);
+				row.onclick = function () {
+					removeClass(rows.children, "selected");
+					row.classList.add("selected");
+					_this.config.animation = animation.name;
+					_this.playTime = 0;
+					_this.animationState.setAnimation(0, _this.config.animation, true);
+				};
+			});
+			popup.show();
+		};
+		SpinePlayer.prototype.showSkinsDialog = function () {
+			var _this = this;
+			if (!this.skeleton || this.skeleton.data.animations.length == 0)
+				return;
+			var popup = new Popup(this.playerControls, "\n\t\t\t\t<div class=\"spine-player-popup-title\">Skins</div>\n\t\t\t\t<hr>\n\t\t\t\t<ul class=\"spine-player-list\"></ul>\n\t\t\t");
+			var rows = findWithClass(popup.dom, "spine-player-list")[0];
+			this.skeleton.data.skins.forEach(function (skin) {
+				if (_this.config.skins && _this.config.skins.indexOf(skin.name) < 0) {
+					return;
+				}
+				var row = createElement("\n\t\t\t\t\t<li class=\"spine-player-list-item selectable\">\n\t\t\t\t\t\t<div class=\"selectable-circle\">\n\t\t\t\t\t\t</div>\n\t\t\t\t\t\t<div class=\"selectable-text\">\n\t\t\t\t\t\t</div>\n\t\t\t\t\t</li>\n\t\t\t\t");
+				if (skin.name == _this.config.skin)
+					row.classList.add("selected");
+				findWithClass(row, "selectable-text")[0].innerText = skin.name;
+				rows.appendChild(row);
+				row.onclick = function () {
+					removeClass(rows.children, "selected");
+					row.classList.add("selected");
+					_this.config.skin = skin.name;
+					_this.skeleton.setSkinByName(_this.config.skin);
+					_this.skeleton.setSlotsToSetupPose();
+				};
+			});
+			popup.show();
+		};
+		SpinePlayer.prototype.showSettingsDialog = function () {
+			var _this = this;
+			if (!this.skeleton || this.skeleton.data.animations.length == 0)
+				return;
+			var popup = new Popup(this.playerControls, "\n\t\t\t\t<div class=\"spine-player-popup-title\">Debug</div>\n\t\t\t\t<hr>\n\t\t\t\t<ul class=\"spine-player-list\">\n\t\t\t\t</li>\n\t\t\t");
+			var rows = findWithClass(popup.dom, "spine-player-list")[0];
+			var makeItem = function (label, name) {
+				var row = createElement("<li class=\"spine-player-list-item\"></li>");
+				var s = new Switch(label);
+				row.appendChild(s.render());
+				s.setEnabled(_this.config.debug[name]);
+				s.change = function (value) {
+					_this.config.debug[name] = value;
+				};
+				rows.appendChild(row);
+			};
+			makeItem("Show bones", "bones");
+			makeItem("Show regions", "regions");
+			makeItem("Show meshes", "meshes");
+			makeItem("Show bounds", "bounds");
+			makeItem("Show paths", "paths");
+			makeItem("Show clipping", "clipping");
+			makeItem("Show points", "points");
+			makeItem("Show hulls", "hulls");
+			popup.show();
+		};
+		SpinePlayer.prototype.drawFrame = function (requestNextFrame) {
+			var _this = this;
+			if (requestNextFrame === void 0) { requestNextFrame = true; }
+			if (requestNextFrame)
+				requestAnimationFrame(function () { return _this.drawFrame(); });
+			var ctx = this.context;
+			var gl = ctx.gl;
+			var bg = new spine.Color().setFromString(this.config.backgroundColor);
+			gl.clearColor(bg.r, bg.g, bg.b, bg.a);
+			gl.clear(gl.COLOR_BUFFER_BIT);
+			this.loadingScreen.draw(this.assetManager.isLoadingComplete());
+			if (this.assetManager.isLoadingComplete() && this.skeleton == null)
+				this.loadSkeleton();
+			this.sceneRenderer.resize(spine.webgl.ResizeMode.Expand);
+			if (this.loaded) {
+				if (!this.paused && this.config.animation) {
+					this.time.update();
+					var delta = this.time.delta * this.speed;
+					var animationDuration = this.animationState.getCurrent(0).animation.duration;
+					this.playTime += delta;
+					while (this.playTime >= animationDuration && animationDuration != 0) {
+						this.playTime -= animationDuration;
+					}
+					this.playTime = Math.max(0, Math.min(this.playTime, animationDuration));
+					this.timelineSlider.setValue(this.playTime / animationDuration);
+					this.animationState.update(delta);
+					this.animationState.apply(this.skeleton);
+					this.skeleton.updateWorldTransform();
+				}
+				var viewportSize = this.scale(this.config.viewport.width, this.config.viewport.height, this.canvas.width, this.canvas.height);
+				this.sceneRenderer.camera.zoom = this.config.viewport.width / viewportSize.x;
+				this.sceneRenderer.camera.position.x = this.config.viewport.x + this.config.viewport.width / 2;
+				this.sceneRenderer.camera.position.y = this.config.viewport.y + this.config.viewport.height / 2;
+				this.sceneRenderer.begin();
+				if (this.config.backgroundImage && this.config.backgroundImage.url) {
+					var bgImage = this.assetManager.get(this.config.backgroundImage.url);
+					if (!this.config.backgroundImage.x) {
+						this.sceneRenderer.drawTexture(bgImage, this.config.viewport.x, this.config.viewport.y, this.config.viewport.width, this.config.viewport.height);
+					}
+					else {
+						this.sceneRenderer.drawTexture(bgImage, this.config.backgroundImage.x, this.config.backgroundImage.y, this.config.backgroundImage.width, this.config.backgroundImage.height);
+					}
+				}
+				this.sceneRenderer.drawSkeleton(this.skeleton, this.config.premultipliedAlpha);
+				this.sceneRenderer.skeletonDebugRenderer.drawBones = this.config.debug.bones;
+				this.sceneRenderer.skeletonDebugRenderer.drawBoundingBoxes = this.config.debug.bounds;
+				this.sceneRenderer.skeletonDebugRenderer.drawClipping = this.config.debug.clipping;
+				this.sceneRenderer.skeletonDebugRenderer.drawMeshHull = this.config.debug.hulls;
+				this.sceneRenderer.skeletonDebugRenderer.drawPaths = this.config.debug.paths;
+				this.sceneRenderer.skeletonDebugRenderer.drawRegionAttachments = this.config.debug.regions;
+				this.sceneRenderer.skeletonDebugRenderer.drawMeshTriangles = this.config.debug.meshes;
+				this.sceneRenderer.drawSkeletonDebug(this.skeleton, this.config.premultipliedAlpha);
+				var controlBones = this.config.controlBones;
+				var selectedBones = this.selectedBones;
+				var skeleton = this.skeleton;
+				gl.lineWidth(2);
+				for (var i = 0; i < controlBones.length; i++) {
+					var bone = skeleton.findBone(controlBones[i]);
+					if (!bone)
+						continue;
+					var colorInner = selectedBones[i] !== null ? SpinePlayer.HOVER_COLOR_INNER : SpinePlayer.NON_HOVER_COLOR_INNER;
+					var colorOuter = selectedBones[i] !== null ? SpinePlayer.HOVER_COLOR_OUTER : SpinePlayer.NON_HOVER_COLOR_OUTER;
+					this.sceneRenderer.circle(true, skeleton.x + bone.worldX, skeleton.y + bone.worldY, 20, colorInner);
+					this.sceneRenderer.circle(false, skeleton.x + bone.worldX, skeleton.y + bone.worldY, 20, colorOuter);
+				}
+				gl.lineWidth(1);
+				this.sceneRenderer.end();
+				this.sceneRenderer.camera.zoom = 0;
+			}
+		};
+		SpinePlayer.prototype.scale = function (sourceWidth, sourceHeight, targetWidth, targetHeight) {
+			var targetRatio = targetHeight / targetWidth;
+			var sourceRatio = sourceHeight / sourceWidth;
+			var scale = targetRatio > sourceRatio ? targetWidth / sourceWidth : targetHeight / sourceHeight;
+			var temp = new spine.Vector2();
+			temp.x = sourceWidth * scale;
+			temp.y = sourceHeight * scale;
+			return temp;
+		};
+		SpinePlayer.prototype.loadSkeleton = function () {
+			var _this = this;
+			if (this.loaded)
+				return;
+			if (this.assetManager.hasErrors()) {
+				this.showError("Error: assets could not be loaded.<br><br>" + escapeHtml(JSON.stringify(this.assetManager.getErrors())));
+				return;
+			}
+			var atlas = this.assetManager.get(this.config.atlasUrl);
+			var jsonText = this.assetManager.get(this.config.jsonUrl);
+			var json = new spine.SkeletonJson(new spine.AtlasAttachmentLoader(atlas));
+			var skeletonData;
+			try {
+				skeletonData = json.readSkeletonData(jsonText);
+			}
+			catch (e) {
+				this.showError("Error: could not load skeleton .json.<br><br>" + escapeHtml(JSON.stringify(e)));
+				return;
+			}
+			this.skeleton = new spine.Skeleton(skeletonData);
+			var stateData = new spine.AnimationStateData(skeletonData);
+			stateData.defaultMix = 0.2;
+			this.animationState = new spine.AnimationState(stateData);
+			if (this.config.controlBones) {
+				this.config.controlBones.forEach(function (bone) {
+					if (!skeletonData.findBone(bone)) {
+						_this.showError("Error: control bone '" + bone + "' does not exist in skeleton.");
+					}
+				});
+			}
+			if (!this.config.skin) {
+				if (skeletonData.skins.length > 0) {
+					this.config.skin = skeletonData.skins[0].name;
+				}
+			}
+			if (this.config.skins && this.config.skin.length > 0) {
+				this.config.skins.forEach(function (skin) {
+					if (!_this.skeleton.data.findSkin(skin)) {
+						_this.showError("Error: skin '" + skin + "' in selectable skin list does not exist in skeleton.");
+						return;
+					}
+				});
+			}
+			if (this.config.skin) {
+				if (!this.skeleton.data.findSkin(this.config.skin)) {
+					this.showError("Error: skin '" + this.config.skin + "' does not exist in skeleton.");
+					return;
+				}
+				this.skeleton.setSkinByName(this.config.skin);
+				this.skeleton.setSlotsToSetupPose();
+			}
+			if (!this.config.viewport || !this.config.viewport.x || !this.config.viewport.y || !this.config.viewport.width || !this.config.viewport.height) {
+				this.config.viewport = {
+					x: 0,
+					y: 0,
+					width: 0,
+					height: 0
+				};
+				this.skeleton.updateWorldTransform();
+				var offset = new spine.Vector2();
+				var size = new spine.Vector2();
+				this.skeleton.getBounds(offset, size);
+				this.config.viewport.x = offset.x + size.x / 2 - size.x / 2 * 1.2;
+				this.config.viewport.y = offset.y + size.y / 2 - size.y / 2 * 1.2;
+				this.config.viewport.width = size.x * 1.2;
+				this.config.viewport.height = size.y * 1.2;
+			}
+			if (!this.config.animation) {
+				if (skeletonData.animations.length > 0) {
+					this.config.animation = skeletonData.animations[0].name;
+				}
+			}
+			if (this.config.animations && this.config.animations.length > 0) {
+				this.config.animations.forEach(function (animation) {
+					if (!_this.skeleton.data.findAnimation(animation)) {
+						_this.showError("Error: animation '" + animation + "' in selectable animation list does not exist in skeleton.");
+						return;
+					}
+				});
+			}
+			if (this.config.animation) {
+				if (!skeletonData.findAnimation(this.config.animation)) {
+					this.showError("Error: animation '" + this.config.animation + "' does not exist in skeleton.");
+					return;
+				}
+				this.play();
+				this.timelineSlider.change = function (percentage) {
+					_this.pause();
+					var animationDuration = _this.animationState.getCurrent(0).animation.duration;
+					var time = animationDuration * percentage;
+					_this.animationState.update(time - _this.playTime);
+					_this.animationState.apply(_this.skeleton);
+					_this.skeleton.updateWorldTransform();
+					_this.playTime = time;
+				};
+			}
+			this.setupInput();
+			this.loaded = true;
+		};
+		SpinePlayer.prototype.setupInput = function () {
+			var controlBones = this.config.controlBones;
+			var selectedBones = this.selectedBones = new Array(this.config.controlBones.length);
+			var canvas = this.canvas;
+			var input = new spine.webgl.Input(canvas);
+			var target = null;
+			var coords = new spine.webgl.Vector3();
+			var temp = new spine.webgl.Vector3();
+			var temp2 = new spine.Vector2();
+			var skeleton = this.skeleton;
+			var renderer = this.sceneRenderer;
+			input.addListener({
+				down: function (x, y) {
+					for (var i = 0; i < controlBones.length; i++) {
+						var bone = skeleton.findBone(controlBones[i]);
+						if (!bone)
+							continue;
+						renderer.camera.screenToWorld(coords.set(x, y, 0), canvas.width, canvas.height);
+						if (temp.set(skeleton.x + bone.worldX, skeleton.y + bone.worldY, 0).distance(coords) < 30) {
+							target = bone;
+						}
+					}
+				},
+				up: function (x, y) {
+					target = null;
+				},
+				dragged: function (x, y) {
+					if (target != null) {
+						renderer.camera.screenToWorld(coords.set(x, y, 0), canvas.width, canvas.height);
+						if (target.parent !== null) {
+							target.parent.worldToLocal(temp2.set(coords.x - skeleton.x, coords.y - skeleton.y));
+							target.x = temp2.x;
+							target.y = temp2.y;
+						}
+						else {
+							target.x = coords.x - skeleton.x;
+							target.y = coords.y - skeleton.y;
+						}
+					}
+				},
+				moved: function (x, y) {
+					for (var i = 0; i < controlBones.length; i++) {
+						var bone = skeleton.findBone(controlBones[i]);
+						if (!bone)
+							continue;
+						renderer.camera.screenToWorld(coords.set(x, y, 0), canvas.width, canvas.height);
+						if (temp.set(skeleton.x + bone.worldX, skeleton.y + bone.worldY, 0).distance(coords) < 30) {
+							selectedBones[i] = bone;
+						}
+						else {
+							selectedBones[i] = null;
+						}
+					}
+				}
+			});
+		};
+		SpinePlayer.prototype.play = function () {
+			this.paused = false;
+			this.playButton.classList.remove("spine-player-button-icon-play");
+			this.playButton.classList.add("spine-player-button-icon-pause");
+			if (this.config.animation) {
+				if (!this.animationState.getCurrent(0)) {
+					this.animationState.setAnimation(0, this.config.animation, true);
+				}
+			}
+		};
+		SpinePlayer.prototype.pause = function () {
+			this.paused = true;
+			this.playButton.classList.remove("spine-player-button-icon-pause");
+			this.playButton.classList.add("spine-player-button-icon-play");
+		};
+		SpinePlayer.HOVER_COLOR_INNER = new spine.Color(0.478, 0, 0, 0.25);
+		SpinePlayer.HOVER_COLOR_OUTER = new spine.Color(1, 1, 1, 1);
+		SpinePlayer.NON_HOVER_COLOR_INNER = new spine.Color(0.478, 0, 0, 0.5);
+		SpinePlayer.NON_HOVER_COLOR_OUTER = new spine.Color(1, 0, 0, 0.8);
+		return SpinePlayer;
+	}());
+	spine.SpinePlayer = SpinePlayer;
+	function isContained(dom, needle) {
+		if (dom === needle)
+			return true;
+		var findRecursive = function (dom, needle) {
+			for (var i = 0; i < dom.children.length; i++) {
+				var child = dom.children[i];
+				if (child === needle)
+					return true;
+				if (findRecursive(child, needle))
+					return true;
+			}
+			return false;
+		};
+		return findRecursive(dom, needle);
+	}
+	function findWithId(dom, id) {
+		var found = new Array();
+		var findRecursive = function (dom, id, found) {
+			for (var i = 0; i < dom.children.length; i++) {
+				var child = dom.children[i];
+				if (child.id === id)
+					found.push(child);
+				findRecursive(child, id, found);
+			}
+		};
+		findRecursive(dom, id, found);
+		return found;
+	}
+	function findWithClass(dom, className) {
+		var found = new Array();
+		var findRecursive = function (dom, className, found) {
+			for (var i = 0; i < dom.children.length; i++) {
+				var child = dom.children[i];
+				if (child.classList.contains(className))
+					found.push(child);
+				findRecursive(child, className, found);
+			}
+		};
+		findRecursive(dom, className, found);
+		return found;
+	}
+	function createElement(html) {
+		var dom = document.createElement("div");
+		dom.innerHTML = html;
+		return dom.children[0];
+	}
+	function removeClass(elements, clazz) {
+		for (var i = 0; i < elements.length; i++) {
+			elements[i].classList.remove(clazz);
+		}
+	}
+	function escapeHtml(str) {
+		if (!str)
+			return "";
+		return str
+			.replace(/&/g, "&amp;")
+			.replace(/</g, "&lt;")
+			.replace(/>/g, "&gt;")
+			.replace(/"/g, "&#34;")
+			.replace(/'/g, "&#39;");
+	}
+})(spine || (spine = {}));
+var spine;
 (function (spine) {
 (function (spine) {
 	var SpineWidget = (function () {
 	var SpineWidget = (function () {
 		function SpineWidget(element, config) {
 		function SpineWidget(element, config) {

文件差異過大導致無法顯示
+ 0 - 0
spine-ts/build/spine-all.js.map


+ 26 - 26
spine-ts/build/spine-canvas.d.ts

@@ -16,11 +16,11 @@ declare module spine {
 		setup = 0,
 		setup = 0,
 		first = 1,
 		first = 1,
 		replace = 2,
 		replace = 2,
-		add = 3,
+		add = 3
 	}
 	}
 	enum MixDirection {
 	enum MixDirection {
 		in = 0,
 		in = 0,
-		out = 1,
+		out = 1
 	}
 	}
 	enum TimelineType {
 	enum TimelineType {
 		rotate = 0,
 		rotate = 0,
@@ -37,7 +37,7 @@ declare module spine {
 		pathConstraintPosition = 11,
 		pathConstraintPosition = 11,
 		pathConstraintSpacing = 12,
 		pathConstraintSpacing = 12,
 		pathConstraintMix = 13,
 		pathConstraintMix = 13,
-		twoColor = 14,
+		twoColor = 14
 	}
 	}
 	abstract class CurveTimeline implements Timeline {
 	abstract class CurveTimeline implements Timeline {
 		static LINEAR: number;
 		static LINEAR: number;
@@ -341,7 +341,7 @@ declare module spine {
 		end = 2,
 		end = 2,
 		dispose = 3,
 		dispose = 3,
 		complete = 4,
 		complete = 4,
-		event = 5,
+		event = 5
 	}
 	}
 	interface AnimationStateListener2 {
 	interface AnimationStateListener2 {
 		start(entry: TrackEntry): void;
 		start(entry: TrackEntry): void;
@@ -380,8 +380,8 @@ declare module spine {
 		private toLoad;
 		private toLoad;
 		private loaded;
 		private loaded;
 		constructor(textureLoader: (image: HTMLImageElement) => any, pathPrefix?: string);
 		constructor(textureLoader: (image: HTMLImageElement) => any, pathPrefix?: string);
-		private static downloadText(url, success, error);
-		private static downloadBinary(url, success, error);
+		private static downloadText;
+		private static downloadBinary;
 		loadText(path: string, success?: (path: string, text: string) => void, error?: (path: string, error: string) => void): void;
 		loadText(path: string, success?: (path: string, text: string) => void, error?: (path: string, error: string) => void): void;
 		loadTexture(path: string, success?: (path: string, image: HTMLImageElement) => void, error?: (path: string, error: string) => void): void;
 		loadTexture(path: string, success?: (path: string, image: HTMLImageElement) => void, error?: (path: string, error: string) => void): void;
 		loadTextureData(path: string, data: string, success?: (path: string, image: HTMLImageElement) => void, error?: (path: string, error: string) => void): void;
 		loadTextureData(path: string, data: string, success?: (path: string, image: HTMLImageElement) => void, error?: (path: string, error: string) => void): void;
@@ -414,7 +414,7 @@ declare module spine {
 		Normal = 0,
 		Normal = 0,
 		Additive = 1,
 		Additive = 1,
 		Multiply = 2,
 		Multiply = 2,
-		Screen = 3,
+		Screen = 3
 	}
 	}
 }
 }
 declare module spine {
 declare module spine {
@@ -483,7 +483,7 @@ declare module spine {
 		OnlyTranslation = 1,
 		OnlyTranslation = 1,
 		NoRotationOrReflection = 2,
 		NoRotationOrReflection = 2,
 		NoScale = 3,
 		NoScale = 3,
-		NoScaleOrReflection = 4,
+		NoScaleOrReflection = 4
 	}
 	}
 }
 }
 declare module spine {
 declare module spine {
@@ -593,17 +593,17 @@ declare module spine {
 	}
 	}
 	enum PositionMode {
 	enum PositionMode {
 		Fixed = 0,
 		Fixed = 0,
-		Percent = 1,
+		Percent = 1
 	}
 	}
 	enum SpacingMode {
 	enum SpacingMode {
 		Length = 0,
 		Length = 0,
 		Fixed = 1,
 		Fixed = 1,
-		Percent = 2,
+		Percent = 2
 	}
 	}
 	enum RotateMode {
 	enum RotateMode {
 		Tangent = 0,
 		Tangent = 0,
 		Chain = 1,
 		Chain = 1,
-		ChainScale = 2,
+		ChainScale = 2
 	}
 	}
 }
 }
 declare module spine {
 declare module spine {
@@ -614,12 +614,12 @@ declare module spine {
 		private rawAssets;
 		private rawAssets;
 		private errors;
 		private errors;
 		constructor(pathPrefix?: string);
 		constructor(pathPrefix?: string);
-		private queueAsset(clientId, textureLoader, path);
+		private queueAsset;
 		loadText(clientId: string, path: string): void;
 		loadText(clientId: string, path: string): void;
 		loadJson(clientId: string, path: string): void;
 		loadJson(clientId: string, path: string): void;
 		loadTexture(clientId: string, textureLoader: (image: HTMLImageElement) => any, path: string): void;
 		loadTexture(clientId: string, textureLoader: (image: HTMLImageElement) => any, path: string): void;
 		get(clientId: string, path: string): any;
 		get(clientId: string, path: string): any;
-		private updateClientAssets(clientAssets);
+		private updateClientAssets;
 		isLoadingComplete(clientId: string): boolean;
 		isLoadingComplete(clientId: string): boolean;
 		dispose(): void;
 		dispose(): void;
 		hasErrors(): boolean;
 		hasErrors(): boolean;
@@ -670,7 +670,7 @@ declare module spine {
 		findIkConstraint(constraintName: string): IkConstraint;
 		findIkConstraint(constraintName: string): IkConstraint;
 		findTransformConstraint(constraintName: string): TransformConstraint;
 		findTransformConstraint(constraintName: string): TransformConstraint;
 		findPathConstraint(constraintName: string): PathConstraint;
 		findPathConstraint(constraintName: string): PathConstraint;
-		getBounds(offset: Vector2, size: Vector2, temp: Array<number>): void;
+		getBounds(offset: Vector2, size: Vector2, temp?: Array<number>): void;
 		update(delta: number): void;
 		update(delta: number): void;
 	}
 	}
 }
 }
@@ -823,12 +823,12 @@ declare module spine {
 		MipMapNearestNearest = 9984,
 		MipMapNearestNearest = 9984,
 		MipMapLinearNearest = 9985,
 		MipMapLinearNearest = 9985,
 		MipMapNearestLinear = 9986,
 		MipMapNearestLinear = 9986,
-		MipMapLinearLinear = 9987,
+		MipMapLinearLinear = 9987
 	}
 	}
 	enum TextureWrap {
 	enum TextureWrap {
 		MirroredRepeat = 33648,
 		MirroredRepeat = 33648,
 		ClampToEdge = 33071,
 		ClampToEdge = 33071,
-		Repeat = 10497,
+		Repeat = 10497
 	}
 	}
 	class TextureRegion {
 	class TextureRegion {
 		renderObject: any;
 		renderObject: any;
@@ -855,7 +855,7 @@ declare module spine {
 		pages: TextureAtlasPage[];
 		pages: TextureAtlasPage[];
 		regions: TextureAtlasRegion[];
 		regions: TextureAtlasRegion[];
 		constructor(atlasText: string, textureLoader: (path: string) => any);
 		constructor(atlasText: string, textureLoader: (path: string) => any);
-		private load(atlasText, textureLoader);
+		private load;
 		findRegion(name: string): TextureAtlasRegion;
 		findRegion(name: string): TextureAtlasRegion;
 		dispose(): void;
 		dispose(): void;
 	}
 	}
@@ -931,9 +931,9 @@ declare module spine {
 		private polygonIndicesPool;
 		private polygonIndicesPool;
 		triangulate(verticesArray: ArrayLike<number>): Array<number>;
 		triangulate(verticesArray: ArrayLike<number>): Array<number>;
 		decompose(verticesArray: Array<number>, triangles: Array<number>): Array<Array<number>>;
 		decompose(verticesArray: Array<number>, triangles: Array<number>): Array<Array<number>>;
-		private static isConcave(index, vertexCount, vertices, indices);
-		private static positiveArea(p1x, p1y, p2x, p2y, p3x, p3y);
-		private static winding(p1x, p1y, p2x, p2y, p3x, p3y);
+		private static isConcave;
+		private static positiveArea;
+		private static winding;
 	}
 	}
 }
 }
 declare module spine {
 declare module spine {
@@ -1105,7 +1105,7 @@ declare module spine {
 		Mesh = 2,
 		Mesh = 2,
 		LinkedMesh = 3,
 		LinkedMesh = 3,
 		Path = 4,
 		Path = 4,
-		Point = 5,
+		Point = 5
 	}
 	}
 }
 }
 declare module spine {
 declare module spine {
@@ -1271,10 +1271,10 @@ declare module spine.canvas {
 		private tempColor;
 		private tempColor;
 		constructor(context: CanvasRenderingContext2D);
 		constructor(context: CanvasRenderingContext2D);
 		draw(skeleton: Skeleton): void;
 		draw(skeleton: Skeleton): void;
-		private drawImages(skeleton);
-		private drawTriangles(skeleton);
-		private drawTriangle(img, x0, y0, u0, v0, x1, y1, u1, v1, x2, y2, u2, v2);
-		private computeRegionVertices(slot, region, pma);
-		private computeMeshVertices(slot, mesh, pma);
+		private drawImages;
+		private drawTriangles;
+		private drawTriangle;
+		private computeRegionVertices;
+		private computeMeshVertices;
 	}
 	}
 }
 }

+ 7 - 3
spine-ts/build/spine-canvas.js

@@ -1,7 +1,10 @@
 var __extends = (this && this.__extends) || (function () {
 var __extends = (this && this.__extends) || (function () {
-	var extendStatics = Object.setPrototypeOf ||
-		({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||
-		function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; };
+	var extendStatics = function (d, b) {
+		extendStatics = Object.setPrototypeOf ||
+			({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||
+			function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; };
+		return extendStatics(d, b);
+	}
 	return function (d, b) {
 	return function (d, b) {
 		extendStatics(d, b);
 		extendStatics(d, b);
 		function __() { this.constructor = d; }
 		function __() { this.constructor = d; }
@@ -3826,6 +3829,7 @@ var spine;
 			return null;
 			return null;
 		};
 		};
 		Skeleton.prototype.getBounds = function (offset, size, temp) {
 		Skeleton.prototype.getBounds = function (offset, size, temp) {
+			if (temp === void 0) { temp = new Array(2); }
 			if (offset == null)
 			if (offset == null)
 				throw new Error("offset cannot be null.");
 				throw new Error("offset cannot be null.");
 			if (size == null)
 			if (size == null)

文件差異過大導致無法顯示
+ 0 - 0
spine-ts/build/spine-canvas.js.map


+ 21 - 21
spine-ts/build/spine-core.d.ts

@@ -16,11 +16,11 @@ declare module spine {
 		setup = 0,
 		setup = 0,
 		first = 1,
 		first = 1,
 		replace = 2,
 		replace = 2,
-		add = 3,
+		add = 3
 	}
 	}
 	enum MixDirection {
 	enum MixDirection {
 		in = 0,
 		in = 0,
-		out = 1,
+		out = 1
 	}
 	}
 	enum TimelineType {
 	enum TimelineType {
 		rotate = 0,
 		rotate = 0,
@@ -37,7 +37,7 @@ declare module spine {
 		pathConstraintPosition = 11,
 		pathConstraintPosition = 11,
 		pathConstraintSpacing = 12,
 		pathConstraintSpacing = 12,
 		pathConstraintMix = 13,
 		pathConstraintMix = 13,
-		twoColor = 14,
+		twoColor = 14
 	}
 	}
 	abstract class CurveTimeline implements Timeline {
 	abstract class CurveTimeline implements Timeline {
 		static LINEAR: number;
 		static LINEAR: number;
@@ -341,7 +341,7 @@ declare module spine {
 		end = 2,
 		end = 2,
 		dispose = 3,
 		dispose = 3,
 		complete = 4,
 		complete = 4,
-		event = 5,
+		event = 5
 	}
 	}
 	interface AnimationStateListener2 {
 	interface AnimationStateListener2 {
 		start(entry: TrackEntry): void;
 		start(entry: TrackEntry): void;
@@ -380,8 +380,8 @@ declare module spine {
 		private toLoad;
 		private toLoad;
 		private loaded;
 		private loaded;
 		constructor(textureLoader: (image: HTMLImageElement) => any, pathPrefix?: string);
 		constructor(textureLoader: (image: HTMLImageElement) => any, pathPrefix?: string);
-		private static downloadText(url, success, error);
-		private static downloadBinary(url, success, error);
+		private static downloadText;
+		private static downloadBinary;
 		loadText(path: string, success?: (path: string, text: string) => void, error?: (path: string, error: string) => void): void;
 		loadText(path: string, success?: (path: string, text: string) => void, error?: (path: string, error: string) => void): void;
 		loadTexture(path: string, success?: (path: string, image: HTMLImageElement) => void, error?: (path: string, error: string) => void): void;
 		loadTexture(path: string, success?: (path: string, image: HTMLImageElement) => void, error?: (path: string, error: string) => void): void;
 		loadTextureData(path: string, data: string, success?: (path: string, image: HTMLImageElement) => void, error?: (path: string, error: string) => void): void;
 		loadTextureData(path: string, data: string, success?: (path: string, image: HTMLImageElement) => void, error?: (path: string, error: string) => void): void;
@@ -414,7 +414,7 @@ declare module spine {
 		Normal = 0,
 		Normal = 0,
 		Additive = 1,
 		Additive = 1,
 		Multiply = 2,
 		Multiply = 2,
-		Screen = 3,
+		Screen = 3
 	}
 	}
 }
 }
 declare module spine {
 declare module spine {
@@ -483,7 +483,7 @@ declare module spine {
 		OnlyTranslation = 1,
 		OnlyTranslation = 1,
 		NoRotationOrReflection = 2,
 		NoRotationOrReflection = 2,
 		NoScale = 3,
 		NoScale = 3,
-		NoScaleOrReflection = 4,
+		NoScaleOrReflection = 4
 	}
 	}
 }
 }
 declare module spine {
 declare module spine {
@@ -593,17 +593,17 @@ declare module spine {
 	}
 	}
 	enum PositionMode {
 	enum PositionMode {
 		Fixed = 0,
 		Fixed = 0,
-		Percent = 1,
+		Percent = 1
 	}
 	}
 	enum SpacingMode {
 	enum SpacingMode {
 		Length = 0,
 		Length = 0,
 		Fixed = 1,
 		Fixed = 1,
-		Percent = 2,
+		Percent = 2
 	}
 	}
 	enum RotateMode {
 	enum RotateMode {
 		Tangent = 0,
 		Tangent = 0,
 		Chain = 1,
 		Chain = 1,
-		ChainScale = 2,
+		ChainScale = 2
 	}
 	}
 }
 }
 declare module spine {
 declare module spine {
@@ -614,12 +614,12 @@ declare module spine {
 		private rawAssets;
 		private rawAssets;
 		private errors;
 		private errors;
 		constructor(pathPrefix?: string);
 		constructor(pathPrefix?: string);
-		private queueAsset(clientId, textureLoader, path);
+		private queueAsset;
 		loadText(clientId: string, path: string): void;
 		loadText(clientId: string, path: string): void;
 		loadJson(clientId: string, path: string): void;
 		loadJson(clientId: string, path: string): void;
 		loadTexture(clientId: string, textureLoader: (image: HTMLImageElement) => any, path: string): void;
 		loadTexture(clientId: string, textureLoader: (image: HTMLImageElement) => any, path: string): void;
 		get(clientId: string, path: string): any;
 		get(clientId: string, path: string): any;
-		private updateClientAssets(clientAssets);
+		private updateClientAssets;
 		isLoadingComplete(clientId: string): boolean;
 		isLoadingComplete(clientId: string): boolean;
 		dispose(): void;
 		dispose(): void;
 		hasErrors(): boolean;
 		hasErrors(): boolean;
@@ -670,7 +670,7 @@ declare module spine {
 		findIkConstraint(constraintName: string): IkConstraint;
 		findIkConstraint(constraintName: string): IkConstraint;
 		findTransformConstraint(constraintName: string): TransformConstraint;
 		findTransformConstraint(constraintName: string): TransformConstraint;
 		findPathConstraint(constraintName: string): PathConstraint;
 		findPathConstraint(constraintName: string): PathConstraint;
-		getBounds(offset: Vector2, size: Vector2, temp: Array<number>): void;
+		getBounds(offset: Vector2, size: Vector2, temp?: Array<number>): void;
 		update(delta: number): void;
 		update(delta: number): void;
 	}
 	}
 }
 }
@@ -823,12 +823,12 @@ declare module spine {
 		MipMapNearestNearest = 9984,
 		MipMapNearestNearest = 9984,
 		MipMapLinearNearest = 9985,
 		MipMapLinearNearest = 9985,
 		MipMapNearestLinear = 9986,
 		MipMapNearestLinear = 9986,
-		MipMapLinearLinear = 9987,
+		MipMapLinearLinear = 9987
 	}
 	}
 	enum TextureWrap {
 	enum TextureWrap {
 		MirroredRepeat = 33648,
 		MirroredRepeat = 33648,
 		ClampToEdge = 33071,
 		ClampToEdge = 33071,
-		Repeat = 10497,
+		Repeat = 10497
 	}
 	}
 	class TextureRegion {
 	class TextureRegion {
 		renderObject: any;
 		renderObject: any;
@@ -855,7 +855,7 @@ declare module spine {
 		pages: TextureAtlasPage[];
 		pages: TextureAtlasPage[];
 		regions: TextureAtlasRegion[];
 		regions: TextureAtlasRegion[];
 		constructor(atlasText: string, textureLoader: (path: string) => any);
 		constructor(atlasText: string, textureLoader: (path: string) => any);
-		private load(atlasText, textureLoader);
+		private load;
 		findRegion(name: string): TextureAtlasRegion;
 		findRegion(name: string): TextureAtlasRegion;
 		dispose(): void;
 		dispose(): void;
 	}
 	}
@@ -931,9 +931,9 @@ declare module spine {
 		private polygonIndicesPool;
 		private polygonIndicesPool;
 		triangulate(verticesArray: ArrayLike<number>): Array<number>;
 		triangulate(verticesArray: ArrayLike<number>): Array<number>;
 		decompose(verticesArray: Array<number>, triangles: Array<number>): Array<Array<number>>;
 		decompose(verticesArray: Array<number>, triangles: Array<number>): Array<Array<number>>;
-		private static isConcave(index, vertexCount, vertices, indices);
-		private static positiveArea(p1x, p1y, p2x, p2y, p3x, p3y);
-		private static winding(p1x, p1y, p2x, p2y, p3x, p3y);
+		private static isConcave;
+		private static positiveArea;
+		private static winding;
 	}
 	}
 }
 }
 declare module spine {
 declare module spine {
@@ -1105,7 +1105,7 @@ declare module spine {
 		Mesh = 2,
 		Mesh = 2,
 		LinkedMesh = 3,
 		LinkedMesh = 3,
 		Path = 4,
 		Path = 4,
-		Point = 5,
+		Point = 5
 	}
 	}
 }
 }
 declare module spine {
 declare module spine {

+ 7 - 3
spine-ts/build/spine-core.js

@@ -1,7 +1,10 @@
 var __extends = (this && this.__extends) || (function () {
 var __extends = (this && this.__extends) || (function () {
-	var extendStatics = Object.setPrototypeOf ||
-		({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||
-		function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; };
+	var extendStatics = function (d, b) {
+		extendStatics = Object.setPrototypeOf ||
+			({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||
+			function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; };
+		return extendStatics(d, b);
+	}
 	return function (d, b) {
 	return function (d, b) {
 		extendStatics(d, b);
 		extendStatics(d, b);
 		function __() { this.constructor = d; }
 		function __() { this.constructor = d; }
@@ -3826,6 +3829,7 @@ var spine;
 			return null;
 			return null;
 		};
 		};
 		Skeleton.prototype.getBounds = function (offset, size, temp) {
 		Skeleton.prototype.getBounds = function (offset, size, temp) {
+			if (temp === void 0) { temp = new Array(2); }
 			if (offset == null)
 			if (offset == null)
 				throw new Error("offset cannot be null.");
 				throw new Error("offset cannot be null.");
 			if (size == null)
 			if (size == null)

文件差異過大導致無法顯示
+ 0 - 0
spine-ts/build/spine-core.js.map


+ 24 - 24
spine-ts/build/spine-threejs.d.ts

@@ -16,11 +16,11 @@ declare module spine {
 		setup = 0,
 		setup = 0,
 		first = 1,
 		first = 1,
 		replace = 2,
 		replace = 2,
-		add = 3,
+		add = 3
 	}
 	}
 	enum MixDirection {
 	enum MixDirection {
 		in = 0,
 		in = 0,
-		out = 1,
+		out = 1
 	}
 	}
 	enum TimelineType {
 	enum TimelineType {
 		rotate = 0,
 		rotate = 0,
@@ -37,7 +37,7 @@ declare module spine {
 		pathConstraintPosition = 11,
 		pathConstraintPosition = 11,
 		pathConstraintSpacing = 12,
 		pathConstraintSpacing = 12,
 		pathConstraintMix = 13,
 		pathConstraintMix = 13,
-		twoColor = 14,
+		twoColor = 14
 	}
 	}
 	abstract class CurveTimeline implements Timeline {
 	abstract class CurveTimeline implements Timeline {
 		static LINEAR: number;
 		static LINEAR: number;
@@ -341,7 +341,7 @@ declare module spine {
 		end = 2,
 		end = 2,
 		dispose = 3,
 		dispose = 3,
 		complete = 4,
 		complete = 4,
-		event = 5,
+		event = 5
 	}
 	}
 	interface AnimationStateListener2 {
 	interface AnimationStateListener2 {
 		start(entry: TrackEntry): void;
 		start(entry: TrackEntry): void;
@@ -380,8 +380,8 @@ declare module spine {
 		private toLoad;
 		private toLoad;
 		private loaded;
 		private loaded;
 		constructor(textureLoader: (image: HTMLImageElement) => any, pathPrefix?: string);
 		constructor(textureLoader: (image: HTMLImageElement) => any, pathPrefix?: string);
-		private static downloadText(url, success, error);
-		private static downloadBinary(url, success, error);
+		private static downloadText;
+		private static downloadBinary;
 		loadText(path: string, success?: (path: string, text: string) => void, error?: (path: string, error: string) => void): void;
 		loadText(path: string, success?: (path: string, text: string) => void, error?: (path: string, error: string) => void): void;
 		loadTexture(path: string, success?: (path: string, image: HTMLImageElement) => void, error?: (path: string, error: string) => void): void;
 		loadTexture(path: string, success?: (path: string, image: HTMLImageElement) => void, error?: (path: string, error: string) => void): void;
 		loadTextureData(path: string, data: string, success?: (path: string, image: HTMLImageElement) => void, error?: (path: string, error: string) => void): void;
 		loadTextureData(path: string, data: string, success?: (path: string, image: HTMLImageElement) => void, error?: (path: string, error: string) => void): void;
@@ -414,7 +414,7 @@ declare module spine {
 		Normal = 0,
 		Normal = 0,
 		Additive = 1,
 		Additive = 1,
 		Multiply = 2,
 		Multiply = 2,
-		Screen = 3,
+		Screen = 3
 	}
 	}
 }
 }
 declare module spine {
 declare module spine {
@@ -483,7 +483,7 @@ declare module spine {
 		OnlyTranslation = 1,
 		OnlyTranslation = 1,
 		NoRotationOrReflection = 2,
 		NoRotationOrReflection = 2,
 		NoScale = 3,
 		NoScale = 3,
-		NoScaleOrReflection = 4,
+		NoScaleOrReflection = 4
 	}
 	}
 }
 }
 declare module spine {
 declare module spine {
@@ -593,17 +593,17 @@ declare module spine {
 	}
 	}
 	enum PositionMode {
 	enum PositionMode {
 		Fixed = 0,
 		Fixed = 0,
-		Percent = 1,
+		Percent = 1
 	}
 	}
 	enum SpacingMode {
 	enum SpacingMode {
 		Length = 0,
 		Length = 0,
 		Fixed = 1,
 		Fixed = 1,
-		Percent = 2,
+		Percent = 2
 	}
 	}
 	enum RotateMode {
 	enum RotateMode {
 		Tangent = 0,
 		Tangent = 0,
 		Chain = 1,
 		Chain = 1,
-		ChainScale = 2,
+		ChainScale = 2
 	}
 	}
 }
 }
 declare module spine {
 declare module spine {
@@ -614,12 +614,12 @@ declare module spine {
 		private rawAssets;
 		private rawAssets;
 		private errors;
 		private errors;
 		constructor(pathPrefix?: string);
 		constructor(pathPrefix?: string);
-		private queueAsset(clientId, textureLoader, path);
+		private queueAsset;
 		loadText(clientId: string, path: string): void;
 		loadText(clientId: string, path: string): void;
 		loadJson(clientId: string, path: string): void;
 		loadJson(clientId: string, path: string): void;
 		loadTexture(clientId: string, textureLoader: (image: HTMLImageElement) => any, path: string): void;
 		loadTexture(clientId: string, textureLoader: (image: HTMLImageElement) => any, path: string): void;
 		get(clientId: string, path: string): any;
 		get(clientId: string, path: string): any;
-		private updateClientAssets(clientAssets);
+		private updateClientAssets;
 		isLoadingComplete(clientId: string): boolean;
 		isLoadingComplete(clientId: string): boolean;
 		dispose(): void;
 		dispose(): void;
 		hasErrors(): boolean;
 		hasErrors(): boolean;
@@ -670,7 +670,7 @@ declare module spine {
 		findIkConstraint(constraintName: string): IkConstraint;
 		findIkConstraint(constraintName: string): IkConstraint;
 		findTransformConstraint(constraintName: string): TransformConstraint;
 		findTransformConstraint(constraintName: string): TransformConstraint;
 		findPathConstraint(constraintName: string): PathConstraint;
 		findPathConstraint(constraintName: string): PathConstraint;
-		getBounds(offset: Vector2, size: Vector2, temp: Array<number>): void;
+		getBounds(offset: Vector2, size: Vector2, temp?: Array<number>): void;
 		update(delta: number): void;
 		update(delta: number): void;
 	}
 	}
 }
 }
@@ -823,12 +823,12 @@ declare module spine {
 		MipMapNearestNearest = 9984,
 		MipMapNearestNearest = 9984,
 		MipMapLinearNearest = 9985,
 		MipMapLinearNearest = 9985,
 		MipMapNearestLinear = 9986,
 		MipMapNearestLinear = 9986,
-		MipMapLinearLinear = 9987,
+		MipMapLinearLinear = 9987
 	}
 	}
 	enum TextureWrap {
 	enum TextureWrap {
 		MirroredRepeat = 33648,
 		MirroredRepeat = 33648,
 		ClampToEdge = 33071,
 		ClampToEdge = 33071,
-		Repeat = 10497,
+		Repeat = 10497
 	}
 	}
 	class TextureRegion {
 	class TextureRegion {
 		renderObject: any;
 		renderObject: any;
@@ -855,7 +855,7 @@ declare module spine {
 		pages: TextureAtlasPage[];
 		pages: TextureAtlasPage[];
 		regions: TextureAtlasRegion[];
 		regions: TextureAtlasRegion[];
 		constructor(atlasText: string, textureLoader: (path: string) => any);
 		constructor(atlasText: string, textureLoader: (path: string) => any);
-		private load(atlasText, textureLoader);
+		private load;
 		findRegion(name: string): TextureAtlasRegion;
 		findRegion(name: string): TextureAtlasRegion;
 		dispose(): void;
 		dispose(): void;
 	}
 	}
@@ -931,9 +931,9 @@ declare module spine {
 		private polygonIndicesPool;
 		private polygonIndicesPool;
 		triangulate(verticesArray: ArrayLike<number>): Array<number>;
 		triangulate(verticesArray: ArrayLike<number>): Array<number>;
 		decompose(verticesArray: Array<number>, triangles: Array<number>): Array<Array<number>>;
 		decompose(verticesArray: Array<number>, triangles: Array<number>): Array<Array<number>>;
-		private static isConcave(index, vertexCount, vertices, indices);
-		private static positiveArea(p1x, p1y, p2x, p2y, p3x, p3y);
-		private static winding(p1x, p1y, p2x, p2y, p3x, p3y);
+		private static isConcave;
+		private static positiveArea;
+		private static winding;
 	}
 	}
 }
 }
 declare module spine {
 declare module spine {
@@ -1105,7 +1105,7 @@ declare module spine {
 		Mesh = 2,
 		Mesh = 2,
 		LinkedMesh = 3,
 		LinkedMesh = 3,
 		Path = 4,
 		Path = 4,
-		Point = 5,
+		Point = 5
 	}
 	}
 }
 }
 declare module spine {
 declare module spine {
@@ -1290,9 +1290,9 @@ declare module spine.threejs {
 		private tempColor;
 		private tempColor;
 		constructor(skeletonData: SkeletonData);
 		constructor(skeletonData: SkeletonData);
 		update(deltaTime: number): void;
 		update(deltaTime: number): void;
-		private clearBatches();
-		private nextBatch();
-		private updateGeometry();
+		private clearBatches;
+		private nextBatch;
+		private updateGeometry;
 	}
 	}
 }
 }
 declare module spine.threejs {
 declare module spine.threejs {

+ 7 - 3
spine-ts/build/spine-threejs.js

@@ -1,7 +1,10 @@
 var __extends = (this && this.__extends) || (function () {
 var __extends = (this && this.__extends) || (function () {
-	var extendStatics = Object.setPrototypeOf ||
-		({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||
-		function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; };
+	var extendStatics = function (d, b) {
+		extendStatics = Object.setPrototypeOf ||
+			({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||
+			function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; };
+		return extendStatics(d, b);
+	}
 	return function (d, b) {
 	return function (d, b) {
 		extendStatics(d, b);
 		extendStatics(d, b);
 		function __() { this.constructor = d; }
 		function __() { this.constructor = d; }
@@ -3826,6 +3829,7 @@ var spine;
 			return null;
 			return null;
 		};
 		};
 		Skeleton.prototype.getBounds = function (offset, size, temp) {
 		Skeleton.prototype.getBounds = function (offset, size, temp) {
+			if (temp === void 0) { temp = new Array(2); }
 			if (offset == null)
 			if (offset == null)
 				throw new Error("offset cannot be null.");
 				throw new Error("offset cannot be null.");
 			if (size == null)
 			if (size == null)

文件差異過大導致無法顯示
+ 0 - 0
spine-ts/build/spine-threejs.js.map


+ 34 - 34
spine-ts/build/spine-webgl.d.ts

@@ -16,11 +16,11 @@ declare module spine {
 		setup = 0,
 		setup = 0,
 		first = 1,
 		first = 1,
 		replace = 2,
 		replace = 2,
-		add = 3,
+		add = 3
 	}
 	}
 	enum MixDirection {
 	enum MixDirection {
 		in = 0,
 		in = 0,
-		out = 1,
+		out = 1
 	}
 	}
 	enum TimelineType {
 	enum TimelineType {
 		rotate = 0,
 		rotate = 0,
@@ -37,7 +37,7 @@ declare module spine {
 		pathConstraintPosition = 11,
 		pathConstraintPosition = 11,
 		pathConstraintSpacing = 12,
 		pathConstraintSpacing = 12,
 		pathConstraintMix = 13,
 		pathConstraintMix = 13,
-		twoColor = 14,
+		twoColor = 14
 	}
 	}
 	abstract class CurveTimeline implements Timeline {
 	abstract class CurveTimeline implements Timeline {
 		static LINEAR: number;
 		static LINEAR: number;
@@ -341,7 +341,7 @@ declare module spine {
 		end = 2,
 		end = 2,
 		dispose = 3,
 		dispose = 3,
 		complete = 4,
 		complete = 4,
-		event = 5,
+		event = 5
 	}
 	}
 	interface AnimationStateListener2 {
 	interface AnimationStateListener2 {
 		start(entry: TrackEntry): void;
 		start(entry: TrackEntry): void;
@@ -380,8 +380,8 @@ declare module spine {
 		private toLoad;
 		private toLoad;
 		private loaded;
 		private loaded;
 		constructor(textureLoader: (image: HTMLImageElement) => any, pathPrefix?: string);
 		constructor(textureLoader: (image: HTMLImageElement) => any, pathPrefix?: string);
-		private static downloadText(url, success, error);
-		private static downloadBinary(url, success, error);
+		private static downloadText;
+		private static downloadBinary;
 		loadText(path: string, success?: (path: string, text: string) => void, error?: (path: string, error: string) => void): void;
 		loadText(path: string, success?: (path: string, text: string) => void, error?: (path: string, error: string) => void): void;
 		loadTexture(path: string, success?: (path: string, image: HTMLImageElement) => void, error?: (path: string, error: string) => void): void;
 		loadTexture(path: string, success?: (path: string, image: HTMLImageElement) => void, error?: (path: string, error: string) => void): void;
 		loadTextureData(path: string, data: string, success?: (path: string, image: HTMLImageElement) => void, error?: (path: string, error: string) => void): void;
 		loadTextureData(path: string, data: string, success?: (path: string, image: HTMLImageElement) => void, error?: (path: string, error: string) => void): void;
@@ -414,7 +414,7 @@ declare module spine {
 		Normal = 0,
 		Normal = 0,
 		Additive = 1,
 		Additive = 1,
 		Multiply = 2,
 		Multiply = 2,
-		Screen = 3,
+		Screen = 3
 	}
 	}
 }
 }
 declare module spine {
 declare module spine {
@@ -483,7 +483,7 @@ declare module spine {
 		OnlyTranslation = 1,
 		OnlyTranslation = 1,
 		NoRotationOrReflection = 2,
 		NoRotationOrReflection = 2,
 		NoScale = 3,
 		NoScale = 3,
-		NoScaleOrReflection = 4,
+		NoScaleOrReflection = 4
 	}
 	}
 }
 }
 declare module spine {
 declare module spine {
@@ -593,17 +593,17 @@ declare module spine {
 	}
 	}
 	enum PositionMode {
 	enum PositionMode {
 		Fixed = 0,
 		Fixed = 0,
-		Percent = 1,
+		Percent = 1
 	}
 	}
 	enum SpacingMode {
 	enum SpacingMode {
 		Length = 0,
 		Length = 0,
 		Fixed = 1,
 		Fixed = 1,
-		Percent = 2,
+		Percent = 2
 	}
 	}
 	enum RotateMode {
 	enum RotateMode {
 		Tangent = 0,
 		Tangent = 0,
 		Chain = 1,
 		Chain = 1,
-		ChainScale = 2,
+		ChainScale = 2
 	}
 	}
 }
 }
 declare module spine {
 declare module spine {
@@ -614,12 +614,12 @@ declare module spine {
 		private rawAssets;
 		private rawAssets;
 		private errors;
 		private errors;
 		constructor(pathPrefix?: string);
 		constructor(pathPrefix?: string);
-		private queueAsset(clientId, textureLoader, path);
+		private queueAsset;
 		loadText(clientId: string, path: string): void;
 		loadText(clientId: string, path: string): void;
 		loadJson(clientId: string, path: string): void;
 		loadJson(clientId: string, path: string): void;
 		loadTexture(clientId: string, textureLoader: (image: HTMLImageElement) => any, path: string): void;
 		loadTexture(clientId: string, textureLoader: (image: HTMLImageElement) => any, path: string): void;
 		get(clientId: string, path: string): any;
 		get(clientId: string, path: string): any;
-		private updateClientAssets(clientAssets);
+		private updateClientAssets;
 		isLoadingComplete(clientId: string): boolean;
 		isLoadingComplete(clientId: string): boolean;
 		dispose(): void;
 		dispose(): void;
 		hasErrors(): boolean;
 		hasErrors(): boolean;
@@ -670,7 +670,7 @@ declare module spine {
 		findIkConstraint(constraintName: string): IkConstraint;
 		findIkConstraint(constraintName: string): IkConstraint;
 		findTransformConstraint(constraintName: string): TransformConstraint;
 		findTransformConstraint(constraintName: string): TransformConstraint;
 		findPathConstraint(constraintName: string): PathConstraint;
 		findPathConstraint(constraintName: string): PathConstraint;
-		getBounds(offset: Vector2, size: Vector2, temp: Array<number>): void;
+		getBounds(offset: Vector2, size: Vector2, temp?: Array<number>): void;
 		update(delta: number): void;
 		update(delta: number): void;
 	}
 	}
 }
 }
@@ -823,12 +823,12 @@ declare module spine {
 		MipMapNearestNearest = 9984,
 		MipMapNearestNearest = 9984,
 		MipMapLinearNearest = 9985,
 		MipMapLinearNearest = 9985,
 		MipMapNearestLinear = 9986,
 		MipMapNearestLinear = 9986,
-		MipMapLinearLinear = 9987,
+		MipMapLinearLinear = 9987
 	}
 	}
 	enum TextureWrap {
 	enum TextureWrap {
 		MirroredRepeat = 33648,
 		MirroredRepeat = 33648,
 		ClampToEdge = 33071,
 		ClampToEdge = 33071,
-		Repeat = 10497,
+		Repeat = 10497
 	}
 	}
 	class TextureRegion {
 	class TextureRegion {
 		renderObject: any;
 		renderObject: any;
@@ -855,7 +855,7 @@ declare module spine {
 		pages: TextureAtlasPage[];
 		pages: TextureAtlasPage[];
 		regions: TextureAtlasRegion[];
 		regions: TextureAtlasRegion[];
 		constructor(atlasText: string, textureLoader: (path: string) => any);
 		constructor(atlasText: string, textureLoader: (path: string) => any);
-		private load(atlasText, textureLoader);
+		private load;
 		findRegion(name: string): TextureAtlasRegion;
 		findRegion(name: string): TextureAtlasRegion;
 		dispose(): void;
 		dispose(): void;
 	}
 	}
@@ -931,9 +931,9 @@ declare module spine {
 		private polygonIndicesPool;
 		private polygonIndicesPool;
 		triangulate(verticesArray: ArrayLike<number>): Array<number>;
 		triangulate(verticesArray: ArrayLike<number>): Array<number>;
 		decompose(verticesArray: Array<number>, triangles: Array<number>): Array<Array<number>>;
 		decompose(verticesArray: Array<number>, triangles: Array<number>): Array<Array<number>>;
-		private static isConcave(index, vertexCount, vertices, indices);
-		private static positiveArea(p1x, p1y, p2x, p2y, p3x, p3y);
-		private static winding(p1x, p1y, p2x, p2y, p3x, p3y);
+		private static isConcave;
+		private static positiveArea;
+		private static winding;
 	}
 	}
 }
 }
 declare module spine {
 declare module spine {
@@ -1105,7 +1105,7 @@ declare module spine {
 		Mesh = 2,
 		Mesh = 2,
 		LinkedMesh = 3,
 		LinkedMesh = 3,
 		Path = 4,
 		Path = 4,
-		Point = 5,
+		Point = 5
 	}
 	}
 }
 }
 declare module spine {
 declare module spine {
@@ -1299,7 +1299,7 @@ declare module spine.webgl {
 		touchesPool: Pool<Touch>;
 		touchesPool: Pool<Touch>;
 		private listeners;
 		private listeners;
 		constructor(element: HTMLElement);
 		constructor(element: HTMLElement);
-		private setupCallbacks(element);
+		private setupCallbacks;
 		addListener(listener: InputListener): void;
 		addListener(listener: InputListener): void;
 		removeListener(listener: InputListener): void;
 		removeListener(listener: InputListener): void;
 	}
 	}
@@ -1408,7 +1408,7 @@ declare module spine.webgl {
 		drawWithOffset(shader: Shader, primitiveType: number, offset: number, count: number): void;
 		drawWithOffset(shader: Shader, primitiveType: number, offset: number, count: number): void;
 		bind(shader: Shader): void;
 		bind(shader: Shader): void;
 		unbind(shader: Shader): void;
 		unbind(shader: Shader): void;
-		private update();
+		private update;
 		restore(): void;
 		restore(): void;
 		dispose(): void;
 		dispose(): void;
 	}
 	}
@@ -1434,7 +1434,7 @@ declare module spine.webgl {
 		constructor();
 		constructor();
 	}
 	}
 	enum VertexAttributeType {
 	enum VertexAttributeType {
-		Float = 0,
+		Float = 0
 	}
 	}
 }
 }
 declare module spine.webgl {
 declare module spine.webgl {
@@ -1453,7 +1453,7 @@ declare module spine.webgl {
 		begin(shader: Shader): void;
 		begin(shader: Shader): void;
 		setBlendMode(srcBlend: number, dstBlend: number): void;
 		setBlendMode(srcBlend: number, dstBlend: number): void;
 		draw(texture: GLTexture, vertices: ArrayLike<number>, indices: Array<number>): void;
 		draw(texture: GLTexture, vertices: ArrayLike<number>, indices: Array<number>): void;
-		private flush();
+		private flush;
 		end(): void;
 		end(): void;
 		getDrawCalls(): number;
 		getDrawCalls(): number;
 		dispose(): void;
 		dispose(): void;
@@ -1493,13 +1493,13 @@ declare module spine.webgl {
 		curve(x1: number, y1: number, cx1: number, cy1: number, cx2: number, cy2: number, x2: number, y2: number, segments: number, color?: Color): void;
 		curve(x1: number, y1: number, cx1: number, cy1: number, cx2: number, cy2: number, x2: number, y2: number, segments: number, color?: Color): void;
 		end(): void;
 		end(): void;
 		resize(resizeMode: ResizeMode): void;
 		resize(resizeMode: ResizeMode): void;
-		private enableRenderer(renderer);
+		private enableRenderer;
 		dispose(): void;
 		dispose(): void;
 	}
 	}
 	enum ResizeMode {
 	enum ResizeMode {
 		Stretch = 0,
 		Stretch = 0,
 		Expand = 1,
 		Expand = 1,
-		Fit = 2,
+		Fit = 2
 	}
 	}
 }
 }
 declare module spine.webgl {
 declare module spine.webgl {
@@ -1527,9 +1527,9 @@ declare module spine.webgl {
 		getVertexShaderSource(): string;
 		getVertexShaderSource(): string;
 		getFragmentSource(): string;
 		getFragmentSource(): string;
 		constructor(context: ManagedWebGLRenderingContext | WebGLRenderingContext, vertexShader: string, fragmentShader: string);
 		constructor(context: ManagedWebGLRenderingContext | WebGLRenderingContext, vertexShader: string, fragmentShader: string);
-		private compile();
-		private compileShader(type, source);
-		private compileProgram(vs, fs);
+		private compile;
+		private compileShader;
+		private compileProgram;
 		restore(): void;
 		restore(): void;
 		bind(): void;
 		bind(): void;
 		unbind(): void;
 		unbind(): void;
@@ -1576,16 +1576,16 @@ declare module spine.webgl {
 		polygon(polygonVertices: ArrayLike<number>, offset: number, count: number, color?: Color): void;
 		polygon(polygonVertices: ArrayLike<number>, offset: number, count: number, color?: Color): void;
 		circle(filled: boolean, x: number, y: number, radius: number, color?: Color, segments?: number): void;
 		circle(filled: boolean, x: number, y: number, radius: number, color?: Color, segments?: number): void;
 		curve(x1: number, y1: number, cx1: number, cy1: number, cx2: number, cy2: number, x2: number, y2: number, segments: number, color?: Color): void;
 		curve(x1: number, y1: number, cx1: number, cy1: number, cx2: number, cy2: number, x2: number, y2: number, segments: number, color?: Color): void;
-		private vertex(x, y, color);
+		private vertex;
 		end(): void;
 		end(): void;
-		private flush();
-		private check(shapeType, numVertices);
+		private flush;
+		private check;
 		dispose(): void;
 		dispose(): void;
 	}
 	}
 	enum ShapeType {
 	enum ShapeType {
 		Point = 0,
 		Point = 0,
 		Line = 1,
 		Line = 1,
-		Filled = 4,
+		Filled = 4
 	}
 	}
 }
 }
 declare module spine.webgl {
 declare module spine.webgl {

+ 21 - 10
spine-ts/build/spine-webgl.js

@@ -1,7 +1,10 @@
 var __extends = (this && this.__extends) || (function () {
 var __extends = (this && this.__extends) || (function () {
-	var extendStatics = Object.setPrototypeOf ||
-		({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||
-		function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; };
+	var extendStatics = function (d, b) {
+		extendStatics = Object.setPrototypeOf ||
+			({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||
+			function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; };
+		return extendStatics(d, b);
+	}
 	return function (d, b) {
 	return function (d, b) {
 		extendStatics(d, b);
 		extendStatics(d, b);
 		function __() { this.constructor = d; }
 		function __() { this.constructor = d; }
@@ -3826,6 +3829,7 @@ var spine;
 			return null;
 			return null;
 		};
 		};
 		Skeleton.prototype.getBounds = function (offset, size, temp) {
 		Skeleton.prototype.getBounds = function (offset, size, temp) {
+			if (temp === void 0) { temp = new Array(2); }
 			if (offset == null)
 			if (offset == null)
 				throw new Error("offset cannot be null.");
 				throw new Error("offset cannot be null.");
 			if (size == null)
 			if (size == null)
@@ -6960,7 +6964,7 @@ var spine;
 			}
 			}
 			Input.prototype.setupCallbacks = function (element) {
 			Input.prototype.setupCallbacks = function (element) {
 				var _this = this;
 				var _this = this;
-				element.addEventListener("mousedown", function (ev) {
+				var mouseDown = function (ev) {
 					if (ev instanceof MouseEvent) {
 					if (ev instanceof MouseEvent) {
 						var rect = element.getBoundingClientRect();
 						var rect = element.getBoundingClientRect();
 						var x = ev.clientX - rect.left;
 						var x = ev.clientX - rect.left;
@@ -6972,9 +6976,11 @@ var spine;
 						_this.lastX = x;
 						_this.lastX = x;
 						_this.lastY = y;
 						_this.lastY = y;
 						_this.buttonDown = true;
 						_this.buttonDown = true;
+						document.addEventListener("mousemove", mouseMove);
+						document.addEventListener("mouseup", mouseUp);
 					}
 					}
-				}, true);
-				element.addEventListener("mousemove", function (ev) {
+				};
+				var mouseMove = function (ev) {
 					if (ev instanceof MouseEvent) {
 					if (ev instanceof MouseEvent) {
 						var rect = element.getBoundingClientRect();
 						var rect = element.getBoundingClientRect();
 						var x = ev.clientX - rect.left;
 						var x = ev.clientX - rect.left;
@@ -6991,8 +6997,8 @@ var spine;
 						_this.lastX = x;
 						_this.lastX = x;
 						_this.lastY = y;
 						_this.lastY = y;
 					}
 					}
-				}, true);
-				element.addEventListener("mouseup", function (ev) {
+				};
+				var mouseUp = function (ev) {
 					if (ev instanceof MouseEvent) {
 					if (ev instanceof MouseEvent) {
 						var rect = element.getBoundingClientRect();
 						var rect = element.getBoundingClientRect();
 						var x = ev.clientX - rect.left;
 						var x = ev.clientX - rect.left;
@@ -7004,8 +7010,13 @@ var spine;
 						_this.lastX = x;
 						_this.lastX = x;
 						_this.lastY = y;
 						_this.lastY = y;
 						_this.buttonDown = false;
 						_this.buttonDown = false;
+						document.removeEventListener("mousemove", mouseMove);
+						document.removeEventListener("mouseup", mouseUp);
 					}
 					}
-				}, true);
+				};
+				element.addEventListener("mousedown", mouseDown, true);
+				element.addEventListener("mousemove", mouseMove, true);
+				element.addEventListener("mouseup", mouseUp, true);
 				element.addEventListener("touchstart", function (ev) {
 				element.addEventListener("touchstart", function (ev) {
 					if (_this.currTouch != null)
 					if (_this.currTouch != null)
 						return;
 						return;
@@ -7167,11 +7178,11 @@ var spine;
 				var renderer = this.renderer;
 				var renderer = this.renderer;
 				var canvas = renderer.canvas;
 				var canvas = renderer.canvas;
 				var gl = renderer.context.gl;
 				var gl = renderer.context.gl;
+				renderer.resize(webgl.ResizeMode.Stretch);
 				var oldX = renderer.camera.position.x, oldY = renderer.camera.position.y;
 				var oldX = renderer.camera.position.x, oldY = renderer.camera.position.y;
 				renderer.camera.position.set(canvas.width / 2, canvas.height / 2, 0);
 				renderer.camera.position.set(canvas.width / 2, canvas.height / 2, 0);
 				renderer.camera.viewportWidth = canvas.width;
 				renderer.camera.viewportWidth = canvas.width;
 				renderer.camera.viewportHeight = canvas.height;
 				renderer.camera.viewportHeight = canvas.height;
-				renderer.resize(webgl.ResizeMode.Stretch);
 				if (!complete) {
 				if (!complete) {
 					gl.clearColor(this.backgroundColor.r, this.backgroundColor.g, this.backgroundColor.b, this.backgroundColor.a);
 					gl.clearColor(this.backgroundColor.r, this.backgroundColor.g, this.backgroundColor.b, this.backgroundColor.a);
 					gl.clear(gl.COLOR_BUFFER_BIT);
 					gl.clear(gl.COLOR_BUFFER_BIT);

文件差異過大導致無法顯示
+ 0 - 0
spine-ts/build/spine-webgl.js.map


+ 75 - 50
spine-ts/build/spine-widget.d.ts

@@ -16,11 +16,11 @@ declare module spine {
         setup = 0,
         setup = 0,
         first = 1,
         first = 1,
         replace = 2,
         replace = 2,
-        add = 3
+        add = 3,
     }
     }
     enum MixDirection {
     enum MixDirection {
         in = 0,
         in = 0,
-        out = 1
+        out = 1,
     }
     }
     enum TimelineType {
     enum TimelineType {
         rotate = 0,
         rotate = 0,
@@ -37,7 +37,7 @@ declare module spine {
         pathConstraintPosition = 11,
         pathConstraintPosition = 11,
         pathConstraintSpacing = 12,
         pathConstraintSpacing = 12,
         pathConstraintMix = 13,
         pathConstraintMix = 13,
-        twoColor = 14
+        twoColor = 14,
     }
     }
     abstract class CurveTimeline implements Timeline {
     abstract class CurveTimeline implements Timeline {
         static LINEAR: number;
         static LINEAR: number;
@@ -341,7 +341,7 @@ declare module spine {
         end = 2,
         end = 2,
         dispose = 3,
         dispose = 3,
         complete = 4,
         complete = 4,
-        event = 5
+        event = 5,
     }
     }
     interface AnimationStateListener2 {
     interface AnimationStateListener2 {
         start(entry: TrackEntry): void;
         start(entry: TrackEntry): void;
@@ -380,8 +380,8 @@ declare module spine {
         private toLoad;
         private toLoad;
         private loaded;
         private loaded;
         constructor(textureLoader: (image: HTMLImageElement) => any, pathPrefix?: string);
         constructor(textureLoader: (image: HTMLImageElement) => any, pathPrefix?: string);
-        private static downloadText;
-        private static downloadBinary;
+        private static downloadText(url, success, error);
+        private static downloadBinary(url, success, error);
         loadText(path: string, success?: (path: string, text: string) => void, error?: (path: string, error: string) => void): void;
         loadText(path: string, success?: (path: string, text: string) => void, error?: (path: string, error: string) => void): void;
         loadTexture(path: string, success?: (path: string, image: HTMLImageElement) => void, error?: (path: string, error: string) => void): void;
         loadTexture(path: string, success?: (path: string, image: HTMLImageElement) => void, error?: (path: string, error: string) => void): void;
         loadTextureData(path: string, data: string, success?: (path: string, image: HTMLImageElement) => void, error?: (path: string, error: string) => void): void;
         loadTextureData(path: string, data: string, success?: (path: string, image: HTMLImageElement) => void, error?: (path: string, error: string) => void): void;
@@ -414,7 +414,7 @@ declare module spine {
         Normal = 0,
         Normal = 0,
         Additive = 1,
         Additive = 1,
         Multiply = 2,
         Multiply = 2,
-        Screen = 3
+        Screen = 3,
     }
     }
 }
 }
 declare module spine {
 declare module spine {
@@ -483,7 +483,7 @@ declare module spine {
         OnlyTranslation = 1,
         OnlyTranslation = 1,
         NoRotationOrReflection = 2,
         NoRotationOrReflection = 2,
         NoScale = 3,
         NoScale = 3,
-        NoScaleOrReflection = 4
+        NoScaleOrReflection = 4,
     }
     }
 }
 }
 declare module spine {
 declare module spine {
@@ -593,17 +593,17 @@ declare module spine {
     }
     }
     enum PositionMode {
     enum PositionMode {
         Fixed = 0,
         Fixed = 0,
-        Percent = 1
+        Percent = 1,
     }
     }
     enum SpacingMode {
     enum SpacingMode {
         Length = 0,
         Length = 0,
         Fixed = 1,
         Fixed = 1,
-        Percent = 2
+        Percent = 2,
     }
     }
     enum RotateMode {
     enum RotateMode {
         Tangent = 0,
         Tangent = 0,
         Chain = 1,
         Chain = 1,
-        ChainScale = 2
+        ChainScale = 2,
     }
     }
 }
 }
 declare module spine {
 declare module spine {
@@ -614,12 +614,12 @@ declare module spine {
         private rawAssets;
         private rawAssets;
         private errors;
         private errors;
         constructor(pathPrefix?: string);
         constructor(pathPrefix?: string);
-        private queueAsset;
+        private queueAsset(clientId, textureLoader, path);
         loadText(clientId: string, path: string): void;
         loadText(clientId: string, path: string): void;
         loadJson(clientId: string, path: string): void;
         loadJson(clientId: string, path: string): void;
         loadTexture(clientId: string, textureLoader: (image: HTMLImageElement) => any, path: string): void;
         loadTexture(clientId: string, textureLoader: (image: HTMLImageElement) => any, path: string): void;
         get(clientId: string, path: string): any;
         get(clientId: string, path: string): any;
-        private updateClientAssets;
+        private updateClientAssets(clientAssets);
         isLoadingComplete(clientId: string): boolean;
         isLoadingComplete(clientId: string): boolean;
         dispose(): void;
         dispose(): void;
         hasErrors(): boolean;
         hasErrors(): boolean;
@@ -823,12 +823,12 @@ declare module spine {
         MipMapNearestNearest = 9984,
         MipMapNearestNearest = 9984,
         MipMapLinearNearest = 9985,
         MipMapLinearNearest = 9985,
         MipMapNearestLinear = 9986,
         MipMapNearestLinear = 9986,
-        MipMapLinearLinear = 9987
+        MipMapLinearLinear = 9987,
     }
     }
     enum TextureWrap {
     enum TextureWrap {
         MirroredRepeat = 33648,
         MirroredRepeat = 33648,
         ClampToEdge = 33071,
         ClampToEdge = 33071,
-        Repeat = 10497
+        Repeat = 10497,
     }
     }
     class TextureRegion {
     class TextureRegion {
         renderObject: any;
         renderObject: any;
@@ -855,7 +855,7 @@ declare module spine {
         pages: TextureAtlasPage[];
         pages: TextureAtlasPage[];
         regions: TextureAtlasRegion[];
         regions: TextureAtlasRegion[];
         constructor(atlasText: string, textureLoader: (path: string) => any);
         constructor(atlasText: string, textureLoader: (path: string) => any);
-        private load;
+        private load(atlasText, textureLoader);
         findRegion(name: string): TextureAtlasRegion;
         findRegion(name: string): TextureAtlasRegion;
         dispose(): void;
         dispose(): void;
     }
     }
@@ -931,9 +931,9 @@ declare module spine {
         private polygonIndicesPool;
         private polygonIndicesPool;
         triangulate(verticesArray: ArrayLike<number>): Array<number>;
         triangulate(verticesArray: ArrayLike<number>): Array<number>;
         decompose(verticesArray: Array<number>, triangles: Array<number>): Array<Array<number>>;
         decompose(verticesArray: Array<number>, triangles: Array<number>): Array<Array<number>>;
-        private static isConcave;
-        private static positiveArea;
-        private static winding;
+        private static isConcave(index, vertexCount, vertices, indices);
+        private static positiveArea(p1x, p1y, p2x, p2y, p3x, p3y);
+        private static winding(p1x, p1y, p2x, p2y, p3x, p3y);
     }
     }
 }
 }
 declare module spine {
 declare module spine {
@@ -1105,7 +1105,7 @@ declare module spine {
         Mesh = 2,
         Mesh = 2,
         LinkedMesh = 3,
         LinkedMesh = 3,
         Path = 4,
         Path = 4,
-        Point = 5
+        Point = 5,
     }
     }
 }
 }
 declare module spine {
 declare module spine {
@@ -1299,7 +1299,7 @@ declare module spine.webgl {
         touchesPool: Pool<Touch>;
         touchesPool: Pool<Touch>;
         private listeners;
         private listeners;
         constructor(element: HTMLElement);
         constructor(element: HTMLElement);
-        private setupCallbacks;
+        private setupCallbacks(element);
         addListener(listener: InputListener): void;
         addListener(listener: InputListener): void;
         removeListener(listener: InputListener): void;
         removeListener(listener: InputListener): void;
     }
     }
@@ -1408,7 +1408,7 @@ declare module spine.webgl {
         drawWithOffset(shader: Shader, primitiveType: number, offset: number, count: number): void;
         drawWithOffset(shader: Shader, primitiveType: number, offset: number, count: number): void;
         bind(shader: Shader): void;
         bind(shader: Shader): void;
         unbind(shader: Shader): void;
         unbind(shader: Shader): void;
-        private update;
+        private update();
         restore(): void;
         restore(): void;
         dispose(): void;
         dispose(): void;
     }
     }
@@ -1434,7 +1434,7 @@ declare module spine.webgl {
         constructor();
         constructor();
     }
     }
     enum VertexAttributeType {
     enum VertexAttributeType {
-        Float = 0
+        Float = 0,
     }
     }
 }
 }
 declare module spine.webgl {
 declare module spine.webgl {
@@ -1453,7 +1453,7 @@ declare module spine.webgl {
         begin(shader: Shader): void;
         begin(shader: Shader): void;
         setBlendMode(srcBlend: number, dstBlend: number): void;
         setBlendMode(srcBlend: number, dstBlend: number): void;
         draw(texture: GLTexture, vertices: ArrayLike<number>, indices: Array<number>): void;
         draw(texture: GLTexture, vertices: ArrayLike<number>, indices: Array<number>): void;
-        private flush;
+        private flush();
         end(): void;
         end(): void;
         getDrawCalls(): number;
         getDrawCalls(): number;
         dispose(): void;
         dispose(): void;
@@ -1493,13 +1493,13 @@ declare module spine.webgl {
         curve(x1: number, y1: number, cx1: number, cy1: number, cx2: number, cy2: number, x2: number, y2: number, segments: number, color?: Color): void;
         curve(x1: number, y1: number, cx1: number, cy1: number, cx2: number, cy2: number, x2: number, y2: number, segments: number, color?: Color): void;
         end(): void;
         end(): void;
         resize(resizeMode: ResizeMode): void;
         resize(resizeMode: ResizeMode): void;
-        private enableRenderer;
+        private enableRenderer(renderer);
         dispose(): void;
         dispose(): void;
     }
     }
     enum ResizeMode {
     enum ResizeMode {
         Stretch = 0,
         Stretch = 0,
         Expand = 1,
         Expand = 1,
-        Fit = 2
+        Fit = 2,
     }
     }
 }
 }
 declare module spine.webgl {
 declare module spine.webgl {
@@ -1527,9 +1527,9 @@ declare module spine.webgl {
         getVertexShaderSource(): string;
         getVertexShaderSource(): string;
         getFragmentSource(): string;
         getFragmentSource(): string;
         constructor(context: ManagedWebGLRenderingContext | WebGLRenderingContext, vertexShader: string, fragmentShader: string);
         constructor(context: ManagedWebGLRenderingContext | WebGLRenderingContext, vertexShader: string, fragmentShader: string);
-        private compile;
-        private compileShader;
-        private compileProgram;
+        private compile();
+        private compileShader(type, source);
+        private compileProgram(vs, fs);
         restore(): void;
         restore(): void;
         bind(): void;
         bind(): void;
         unbind(): void;
         unbind(): void;
@@ -1576,16 +1576,16 @@ declare module spine.webgl {
         polygon(polygonVertices: ArrayLike<number>, offset: number, count: number, color?: Color): void;
         polygon(polygonVertices: ArrayLike<number>, offset: number, count: number, color?: Color): void;
         circle(filled: boolean, x: number, y: number, radius: number, color?: Color, segments?: number): void;
         circle(filled: boolean, x: number, y: number, radius: number, color?: Color, segments?: number): void;
         curve(x1: number, y1: number, cx1: number, cy1: number, cx2: number, cy2: number, x2: number, y2: number, segments: number, color?: Color): void;
         curve(x1: number, y1: number, cx1: number, cy1: number, cx2: number, cy2: number, x2: number, y2: number, segments: number, color?: Color): void;
-        private vertex;
+        private vertex(x, y, color);
         end(): void;
         end(): void;
-        private flush;
-        private check;
+        private flush();
+        private check(shapeType, numVertices);
         dispose(): void;
         dispose(): void;
     }
     }
     enum ShapeType {
     enum ShapeType {
         Point = 0,
         Point = 0,
         Line = 1,
         Line = 1,
-        Filled = 4
+        Filled = 4,
     }
     }
 }
 }
 declare module spine.webgl {
 declare module spine.webgl {
@@ -1687,16 +1687,21 @@ declare module spine {
         jsonUrl: string;
         jsonUrl: string;
         atlasUrl: string;
         atlasUrl: string;
         animation: string;
         animation: string;
+        animations: string[];
         skin: string;
         skin: string;
+        skins: string[];
+        controlBones: string[];
+        premultipliedAlpha: boolean;
+        showControls: boolean;
         debug: {
         debug: {
             bones: boolean;
             bones: boolean;
             regions: boolean;
             regions: boolean;
+            meshes: boolean;
             bounds: boolean;
             bounds: boolean;
             paths: boolean;
             paths: boolean;
-            points: boolean;
             clipping: boolean;
             clipping: boolean;
-            meshHull: boolean;
-            triangles: boolean;
+            points: boolean;
+            hulls: boolean;
         };
         };
         viewport: {
         viewport: {
             x: number;
             x: number;
@@ -1706,19 +1711,33 @@ declare module spine {
         };
         };
         alpha: boolean;
         alpha: boolean;
         backgroundColor: string;
         backgroundColor: string;
-        premultipliedAlpha: boolean;
-        success: (widget: SpineWidget) => void;
-        error: (widget: SpineWidget, msg: string) => void;
+        backgroundImage: {
+            url: string;
+            x: number;
+            y: number;
+            width: number;
+            height: number;
+        };
+        success: (widget: SpinePlayer) => void;
+        error: (widget: SpinePlayer, msg: string) => void;
     }
     }
     class SpinePlayer {
     class SpinePlayer {
         private config;
         private config;
+        static HOVER_COLOR_INNER: Color;
+        static HOVER_COLOR_OUTER: Color;
+        static NON_HOVER_COLOR_INNER: Color;
+        static NON_HOVER_COLOR_OUTER: Color;
         private sceneRenderer;
         private sceneRenderer;
+        private dom;
+        private playerControls;
         private canvas;
         private canvas;
+        private timelineSlider;
+        private playButton;
+        private skinButton;
+        private animationButton;
         private context;
         private context;
         private loadingScreen;
         private loadingScreen;
         private assetManager;
         private assetManager;
-        private timelineSlider;
-        private playButton;
         private loaded;
         private loaded;
         private skeleton;
         private skeleton;
         private animationState;
         private animationState;
@@ -1726,15 +1745,21 @@ declare module spine {
         private paused;
         private paused;
         private playTime;
         private playTime;
         private speed;
         private speed;
+        private selectedBones;
         constructor(parent: HTMLElement, config: SpinePlayerConfig);
         constructor(parent: HTMLElement, config: SpinePlayerConfig);
         validateConfig(config: SpinePlayerConfig): SpinePlayerConfig;
         validateConfig(config: SpinePlayerConfig): SpinePlayerConfig;
-        render(parent: HTMLElement, config: SpinePlayerConfig): void;
+        showError(error: string): void;
+        render(): HTMLElement;
+        showSpeedDialog(): void;
+        showAnimationsDialog(): void;
+        showSkinsDialog(): void;
+        showSettingsDialog(): void;
         drawFrame(requestNextFrame?: boolean): void;
         drawFrame(requestNextFrame?: boolean): void;
         scale(sourceWidth: number, sourceHeight: number, targetWidth: number, targetHeight: number): Vector2;
         scale(sourceWidth: number, sourceHeight: number, targetWidth: number, targetHeight: number): Vector2;
         loadSkeleton(): void;
         loadSkeleton(): void;
-        private play;
-        private pause;
-        private resize;
+        setupInput(): void;
+        private play();
+        private pause();
     }
     }
 }
 }
 declare module spine {
 declare module spine {
@@ -1758,10 +1783,10 @@ declare module spine {
         private loaded;
         private loaded;
         private bounds;
         private bounds;
         constructor(element: HTMLElement | string, config: SpineWidgetConfig);
         constructor(element: HTMLElement | string, config: SpineWidgetConfig);
-        private validateConfig;
-        private load;
-        private render;
-        private resize;
+        private validateConfig(config);
+        private load();
+        private render();
+        private resize();
         pause(): void;
         pause(): void;
         play(): void;
         play(): void;
         isPlaying(): boolean;
         isPlaying(): boolean;
@@ -1769,7 +1794,7 @@ declare module spine {
         static loadWidgets(): void;
         static loadWidgets(): void;
         static loadWidget(widget: HTMLElement): void;
         static loadWidget(widget: HTMLElement): void;
         static pageLoaded: boolean;
         static pageLoaded: boolean;
-        private static ready;
+        private static ready();
         static setupDOMListener(): void;
         static setupDOMListener(): void;
     }
     }
     class SpineWidgetConfig {
     class SpineWidgetConfig {

+ 424 - 152
spine-ts/build/spine-widget.js

@@ -1,10 +1,7 @@
 var __extends = (this && this.__extends) || (function () {
 var __extends = (this && this.__extends) || (function () {
-    var extendStatics = function (d, b) {
-        extendStatics = Object.setPrototypeOf ||
-            ({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||
-            function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; };
-        return extendStatics(d, b);
-    }
+    var extendStatics = Object.setPrototypeOf ||
+        ({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||
+        function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; };
     return function (d, b) {
     return function (d, b) {
         extendStatics(d, b);
         extendStatics(d, b);
         function __() { this.constructor = d; }
         function __() { this.constructor = d; }
@@ -9404,12 +9401,68 @@ var spine;
 })(spine || (spine = {}));
 })(spine || (spine = {}));
 var spine;
 var spine;
 (function (spine) {
 (function (spine) {
+    var Popup = (function () {
+        function Popup(parent, htmlContent) {
+            this.dom = createElement("\n\t\t\t\t<div class=\"spine-player-popup spine-player-hidden\">\n\t\t\t\t</div>\n\t\t\t");
+            this.dom.innerHTML = htmlContent;
+            parent.appendChild(this.dom);
+        }
+        Popup.prototype.show = function () {
+            var _this = this;
+            this.dom.classList.remove("spine-player-hidden");
+            var justClicked = true;
+            var windowClickListener = function (event) {
+                if (justClicked) {
+                    justClicked = false;
+                    return;
+                }
+                if (!isContained(_this.dom, event.target)) {
+                    _this.dom.parentNode.removeChild(_this.dom);
+                    window.removeEventListener("click", windowClickListener);
+                }
+            };
+            window.addEventListener("click", windowClickListener);
+        };
+        return Popup;
+    }());
+    var Switch = (function () {
+        function Switch(text) {
+            this.text = text;
+            this.enabled = false;
+        }
+        Switch.prototype.render = function () {
+            var _this = this;
+            this["switch"] = createElement("\n\t\t\t\t<div class=\"spine-player-switch\">\n\t\t\t\t\t<span class=\"spine-player-switch-text\">" + this.text + "</span>\n\t\t\t\t\t<div class=\"spine-player-switch-knob-area\">\n\t\t\t\t\t\t<div class=\"spine-player-switch-knob\"></div>\n\t\t\t\t\t</div>\n\t\t\t\t</div>\n\t\t\t");
+            this["switch"].addEventListener("click", function () {
+                _this.setEnabled(!_this.enabled);
+                if (_this.change)
+                    _this.change(_this.enabled);
+            });
+            return this["switch"];
+        };
+        Switch.prototype.setEnabled = function (enabled) {
+            if (enabled)
+                this["switch"].classList.add("active");
+            else
+                this["switch"].classList.remove("active");
+            this.enabled = enabled;
+        };
+        Switch.prototype.isEnabled = function () {
+            return this.enabled;
+        };
+        return Switch;
+    }());
     var Slider = (function () {
     var Slider = (function () {
-        function Slider(parent) {
+        function Slider(snaps, snapPercentage) {
+            if (snaps === void 0) { snaps = 0; }
+            if (snapPercentage === void 0) { snapPercentage = 0.1; }
+            this.snaps = snaps;
+            this.snapPercentage = snapPercentage;
+        }
+        Slider.prototype.render = function () {
             var _this = this;
             var _this = this;
-            parent.innerHTML = "\n\t\t\t\t<div class=\"spine-player-slider\">\n\t\t\t\t\t<div class=\"spine-player-slider-value\"></div>\n\t\t\t\t</div>\n\t\t\t";
-            this.slider = findWithClass(parent, "spine-player-slider")[0];
-            this.value = findWithClass(parent, "spine-player-slider-value")[0];
+            this.slider = createElement("\n\t\t\t\t<div class=\"spine-player-slider\">\n\t\t\t\t\t<div class=\"spine-player-slider-value\"></div>\n\t\t\t\t</div>\n\t\t\t");
+            this.value = findWithClass(this.slider, "spine-player-slider-value")[0];
             this.setValue(0);
             this.setValue(0);
             var input = new spine.webgl.Input(this.slider);
             var input = new spine.webgl.Input(this.slider);
             var dragging = false;
             var dragging = false;
@@ -9420,7 +9473,7 @@ var spine;
                 up: function (x, y) {
                 up: function (x, y) {
                     dragging = false;
                     dragging = false;
                     var percentage = x / _this.slider.clientWidth;
                     var percentage = x / _this.slider.clientWidth;
-                    percentage = Math.max(0, Math.min(percentage, 1));
+                    percentage = percentage = Math.max(0, Math.min(percentage, 1));
                     _this.setValue(x / _this.slider.clientWidth);
                     _this.setValue(x / _this.slider.clientWidth);
                     if (_this.change)
                     if (_this.change)
                         _this.change(percentage);
                         _this.change(percentage);
@@ -9429,7 +9482,7 @@ var spine;
                     if (dragging) {
                     if (dragging) {
                         var percentage = x / _this.slider.clientWidth;
                         var percentage = x / _this.slider.clientWidth;
                         percentage = Math.max(0, Math.min(percentage, 1));
                         percentage = Math.max(0, Math.min(percentage, 1));
-                        _this.setValue(x / _this.slider.clientWidth);
+                        percentage = _this.setValue(x / _this.slider.clientWidth);
                         if (_this.change)
                         if (_this.change)
                             _this.change(percentage);
                             _this.change(percentage);
                     }
                     }
@@ -9437,15 +9490,27 @@ var spine;
                 dragged: function (x, y) {
                 dragged: function (x, y) {
                     var percentage = x / _this.slider.clientWidth;
                     var percentage = x / _this.slider.clientWidth;
                     percentage = Math.max(0, Math.min(percentage, 1));
                     percentage = Math.max(0, Math.min(percentage, 1));
-                    _this.setValue(x / _this.slider.clientWidth);
+                    percentage = _this.setValue(x / _this.slider.clientWidth);
                     if (_this.change)
                     if (_this.change)
                         _this.change(percentage);
                         _this.change(percentage);
                 }
                 }
             });
             });
-        }
+            return this.slider;
+        };
         Slider.prototype.setValue = function (percentage) {
         Slider.prototype.setValue = function (percentage) {
             percentage = Math.max(0, Math.min(1, percentage));
             percentage = Math.max(0, Math.min(1, percentage));
+            if (this.snaps > 0) {
+                var modulo = percentage % (1 / this.snaps);
+                if (modulo < (1 / this.snaps) * this.snapPercentage) {
+                    percentage = percentage - modulo;
+                }
+                else if (modulo > (1 / this.snaps) - (1 / this.snaps) * this.snapPercentage) {
+                    percentage = percentage - modulo + (1 / this.snaps);
+                }
+                percentage = Math.max(0, Math.min(1, percentage));
+            }
             this.value.style.width = "" + (percentage * 100) + "%";
             this.value.style.width = "" + (percentage * 100) + "%";
+            return percentage;
         };
         };
         return Slider;
         return Slider;
     }());
     }());
@@ -9456,8 +9521,7 @@ var spine;
             this.paused = true;
             this.paused = true;
             this.playTime = 0;
             this.playTime = 0;
             this.speed = 1;
             this.speed = 1;
-            this.validateConfig(config);
-            this.render(parent, config);
+            parent.appendChild(this.render());
         }
         }
         SpinePlayer.prototype.validateConfig = function (config) {
         SpinePlayer.prototype.validateConfig = function (config) {
             if (!config)
             if (!config)
@@ -9479,13 +9543,13 @@ var spine;
             if (!config.debug)
             if (!config.debug)
                 config.debug = {
                 config.debug = {
                     bones: false,
                     bones: false,
+                    regions: false,
+                    meshes: false,
                     bounds: false,
                     bounds: false,
                     clipping: false,
                     clipping: false,
-                    meshHull: false,
                     paths: false,
                     paths: false,
                     points: false,
                     points: false,
-                    regions: false,
-                    triangles: false
+                    hulls: false
                 };
                 };
             if (!config.debug.bones)
             if (!config.debug.bones)
                 config.debug.bones = false;
                 config.debug.bones = false;
@@ -9493,50 +9557,74 @@ var spine;
                 config.debug.bounds = false;
                 config.debug.bounds = false;
             if (!config.debug.clipping)
             if (!config.debug.clipping)
                 config.debug.clipping = false;
                 config.debug.clipping = false;
-            if (!config.debug.meshHull)
-                config.debug.meshHull = false;
+            if (!config.debug.hulls)
+                config.debug.hulls = false;
             if (!config.debug.paths)
             if (!config.debug.paths)
                 config.debug.paths = false;
                 config.debug.paths = false;
             if (!config.debug.points)
             if (!config.debug.points)
                 config.debug.points = false;
                 config.debug.points = false;
             if (!config.debug.regions)
             if (!config.debug.regions)
                 config.debug.regions = false;
                 config.debug.regions = false;
-            if (!config.debug.triangles)
-                config.debug.triangles = false;
+            if (!config.debug.meshes)
+                config.debug.meshes = false;
+            if (config.animations && config.animation) {
+                if (config.animations.indexOf(config.animation) < 0)
+                    throw new Error("Default animation '" + config.animation + "' is not contained in the list of selectable animations " + escapeHtml(JSON.stringify(this.config.animations)) + ".");
+            }
+            if (config.skins && config.skin) {
+                if (config.skins.indexOf(config.skin) < 0)
+                    throw new Error("Default skin '" + config.skin + "' is not contained in the list of selectable skins " + escapeHtml(JSON.stringify(this.config.skins)) + ".");
+            }
+            if (!config.controlBones)
+                config.controlBones = [];
+            if (!config.showControls)
+                config.showControls = true;
             return config;
             return config;
         };
         };
-        SpinePlayer.prototype.render = function (parent, config) {
+        SpinePlayer.prototype.showError = function (error) {
+            var errorDom = findWithClass(this.dom, "spine-player-error")[0];
+            errorDom.classList.remove("spine-player-hidden");
+            errorDom.innerHTML = "<p style=\"text-align: center; align-self: center;\">" + error + "</p>";
+            this.config.error(this, error);
+        };
+        SpinePlayer.prototype.render = function () {
             var _this = this;
             var _this = this;
-            parent.innerHTML = "\n\t\t\t\t<div class=\"spine-player\">\n\t\t\t\t\t<canvas class=\"spine-player-canvas\"></canvas>\n\t\t\t\t\t<div class=\"spine-player-controls spine-player-dropdown\">\n\t\t\t\t\t\t<div class=\"spine-player-timeline\">\n\t\t\t\t\t\t</div>\n\t\t\t\t\t\t<div class=\"spine-player-buttons\">\n\t\t\t\t\t\t\t<button id=\"spine-player-button-play-pause\" class=\"spine-player-button spine-player-button-icon-pause\"></button>\n\t\t\t\t\t\t\t<div class=\"spine-player-button-spacer\"></div>\n\t\t\t\t\t\t\t<button id=\"spine-player-button-speed\" class=\"spine-player-button spine-player-button-icon-speed\"></button>\n\t\t\t\t\t\t\t<button id=\"spine-player-button-animation\" class=\"spine-player-button spine-player-button-icon-animations\"></button>\n\t\t\t\t\t\t\t<button id=\"spine-player-button-skin\" class=\"spine-player-button spine-player-button-icon-skins\"></button>\n\t\t\t\t\t\t\t<button id=\"spine-player-button-settings\" class=\"spine-player-button spine-player-button-icon-settings\"></button>\n\t\t\t\t\t\t\t<button id=\"spine-player-button-fullscreen\" class=\"spine-player-button spine-player-button-icon-fullscreen\"></button>\n\t\t\t\t\t\t</div>\n\n\t\t\t\t\t\t<div class=\"spine-player-dropdown-content spine-player-hidden\">\n\t\t\t\t\t\t</div>\n\t\t\t\t\t</div>\n\t\t\t\t</div>\n\t\t\t";
-            this.canvas = findWithClass(parent, "spine-player-canvas")[0];
-            var webglConfig = { alpha: config.alpha };
-            this.context = new spine.webgl.ManagedWebGLRenderingContext(this.canvas, webglConfig);
-            this.sceneRenderer = new spine.webgl.SceneRenderer(this.canvas, this.context, true);
-            this.loadingScreen = new spine.webgl.LoadingScreen(this.sceneRenderer);
+            var config = this.config;
+            var dom = this.dom = createElement("\n\t\t\t\t<div class=\"spine-player\">\n\t\t\t\t\t<canvas class=\"spine-player-canvas\"></canvas>\n\t\t\t\t\t<div class=\"spine-player-error spine-player-hidden\"></div>\n\t\t\t\t\t<div class=\"spine-player-controls spine-player-popup-parent hidden\">\n\t\t\t\t\t\t<div class=\"spine-player-timeline\">\n\t\t\t\t\t\t</div>\n\t\t\t\t\t\t<div class=\"spine-player-buttons\">\n\t\t\t\t\t\t\t<button id=\"spine-player-button-play-pause\" class=\"spine-player-button spine-player-button-icon-pause\"></button>\n\t\t\t\t\t\t\t<div class=\"spine-player-button-spacer\"></div>\n\t\t\t\t\t\t\t<button id=\"spine-player-button-speed\" class=\"spine-player-button spine-player-button-icon-speed\"></button>\n\t\t\t\t\t\t\t<button id=\"spine-player-button-animation\" class=\"spine-player-button spine-player-button-icon-animations\"></button>\n\t\t\t\t\t\t\t<button id=\"spine-player-button-skin\" class=\"spine-player-button spine-player-button-icon-skins\"></button>\n\t\t\t\t\t\t\t<button id=\"spine-player-button-settings\" class=\"spine-player-button spine-player-button-icon-settings\"></button>\n\t\t\t\t\t\t\t<button id=\"spine-player-button-fullscreen\" class=\"spine-player-button spine-player-button-icon-fullscreen\"></button>\n\t\t\t\t\t\t</div>\n\t\t\t\t\t</div>\n\t\t\t\t</div>\n\t\t\t");
+            try {
+                this.config = this.validateConfig(config);
+            }
+            catch (e) {
+                this.showError(e);
+                return dom;
+            }
+            try {
+                this.canvas = findWithClass(dom, "spine-player-canvas")[0];
+                var webglConfig = { alpha: config.alpha };
+                this.context = new spine.webgl.ManagedWebGLRenderingContext(this.canvas, webglConfig);
+                this.sceneRenderer = new spine.webgl.SceneRenderer(this.canvas, this.context, true);
+                this.loadingScreen = new spine.webgl.LoadingScreen(this.sceneRenderer);
+            }
+            catch (e) {
+                this.showError("Sorry, your browser does not support WebGL.<br><br>Please use the latest version of Firefox, Chrome, Edge, or Safari.");
+                return dom;
+            }
             this.assetManager = new spine.webgl.AssetManager(this.context);
             this.assetManager = new spine.webgl.AssetManager(this.context);
             this.assetManager.loadText(config.jsonUrl);
             this.assetManager.loadText(config.jsonUrl);
             this.assetManager.loadTextureAtlas(config.atlasUrl);
             this.assetManager.loadTextureAtlas(config.atlasUrl);
+            if (config.backgroundImage && config.backgroundImage.url)
+                this.assetManager.loadTexture(config.backgroundImage.url);
             requestAnimationFrame(function () { return _this.drawFrame(); });
             requestAnimationFrame(function () { return _this.drawFrame(); });
-            var timeline = findWithClass(parent, "spine-player-timeline")[0];
-            this.timelineSlider = new Slider(timeline);
-            this.playButton = findWithId(parent, "spine-player-button-play-pause")[0];
-            var speedButton = findWithId(parent, "spine-player-button-speed")[0];
-            var animationButton = findWithId(parent, "spine-player-button-animation")[0];
-            var skinButton = findWithId(parent, "spine-player-button-skin")[0];
-            var settingsButton = findWithId(parent, "spine-player-button-settings")[0];
-            var fullscreenButton = findWithId(parent, "spine-player-button-fullscreen")[0];
-            var dropdown = findWithClass(parent, "spine-player-dropdown-content")[0];
-            var justClicked = false;
-            var dismissDropdown = function (event) {
-                if (justClicked) {
-                    justClicked = false;
-                    return;
-                }
-                if (!isContained(dropdown, event.target)) {
-                    dropdown.classList.add("spine-player-hidden");
-                    window.onclick = null;
-                }
-            };
+            this.playerControls = findWithClass(dom, "spine-player-controls")[0];
+            var timeline = findWithClass(dom, "spine-player-timeline")[0];
+            this.timelineSlider = new Slider();
+            timeline.appendChild(this.timelineSlider.render());
+            this.playButton = findWithId(dom, "spine-player-button-play-pause")[0];
+            var speedButton = findWithId(dom, "spine-player-button-speed")[0];
+            this.animationButton = findWithId(dom, "spine-player-button-animation")[0];
+            this.skinButton = findWithId(dom, "spine-player-button-skin")[0];
+            var settingsButton = findWithId(dom, "spine-player-button-settings")[0];
+            var fullscreenButton = findWithId(dom, "spine-player-button-fullscreen")[0];
             this.playButton.onclick = function () {
             this.playButton.onclick = function () {
                 if (_this.paused)
                 if (_this.paused)
                     _this.play();
                     _this.play();
@@ -9544,94 +9632,16 @@ var spine;
                     _this.pause();
                     _this.pause();
             };
             };
             speedButton.onclick = function () {
             speedButton.onclick = function () {
-                dropdown.classList.remove("spine-player-hidden");
-                dropdown.innerHTML = "\n\t\t\t\t\t<div class=\"spine-player-row\" style=\"user-select: none; align-items: center;\">\n\t\t\t\t\t\t<div style=\"margin-right: 16px;\">Speed</div>\n\t\t\t\t\t\t<div class=\"spine-player-column\">\n\t\t\t\t\t\t\t<div class=\"spine-player-speed-slider\" style=\"margin-bottom: 4px;\"></div>\n\t\t\t\t\t\t\t<div class=\"spine-player-row\" style=\"justify-content: space-between;\">\n\t\t\t\t\t\t\t\t<div>0.1x</div>\n\t\t\t\t\t\t\t\t<div>1x</div>\n\t\t\t\t\t\t\t\t<div>2x</div>\n\t\t\t\t\t\t\t</div>\n\t\t\t\t\t\t</div>\n\t\t\t\t\t</div>\n\t\t\t\t";
-                var sliderParent = findWithClass(dropdown, "spine-player-speed-slider")[0];
-                var slider = new Slider(sliderParent);
-                slider.setValue(_this.speed / 2);
-                slider.change = function (percentage) {
-                    _this.speed = percentage * 2;
-                };
-                justClicked = true;
-                window.onclick = dismissDropdown;
+                _this.showSpeedDialog();
             };
             };
-            animationButton.onclick = function () {
-                if (!_this.skeleton || _this.skeleton.data.animations.length == 0)
-                    return;
-                dropdown.classList.remove("spine-player-hidden");
-                dropdown.innerHTML = "\n\t\t\t\t\t<div class=\"spine-player-dropdown-title\">Animations</div>\n\t\t\t\t\t<hr>\n\t\t\t\t\t<ul class=\"spine-player-list\">\n\t\t\t\t\t</ul>\n\t\t\t\t";
-                var rows = findWithClass(dropdown, "spine-player-list")[0];
-                _this.skeleton.data.animations.forEach(function (animation) {
-                    var row = document.createElement("li");
-                    row.classList.add("spine-player-list-item");
-                    if (animation.name == _this.config.animation)
-                        row.classList.add("spine-player-list-item-selected");
-                    row.innerText = animation.name;
-                    rows.appendChild(row);
-                    row.onclick = function () {
-                        removeClass(rows.children, "spine-player-list-item-selected");
-                        row.classList.add("spine-player-list-item-selected");
-                        _this.config.animation = animation.name;
-                        _this.playTime = 0;
-                        _this.animationState.setAnimation(0, _this.config.animation, true);
-                    };
-                });
-                justClicked = true;
-                window.onclick = dismissDropdown;
+            this.animationButton.onclick = function () {
+                _this.showAnimationsDialog();
             };
             };
-            skinButton.onclick = function () {
-                if (!_this.skeleton || _this.skeleton.data.animations.length == 0)
-                    return;
-                dropdown.classList.remove("spine-player-hidden");
-                dropdown.innerHTML = "\n\t\t\t\t\t<div class=\"spine-player-dropdown-title\">Skins</div>\n\t\t\t\t\t<hr>\n\t\t\t\t\t<ul class=\"spine-player-list\">\n\t\t\t\t\t</ul>\n\t\t\t\t";
-                var rows = findWithClass(dropdown, "spine-player-list")[0];
-                _this.skeleton.data.skins.forEach(function (skin) {
-                    var row = document.createElement("li");
-                    row.classList.add("spine-player-list-item");
-                    if (skin.name == _this.config.skin)
-                        row.classList.add("spine-player-list-item-selected");
-                    row.innerText = skin.name;
-                    rows.appendChild(row);
-                    row.onclick = function () {
-                        removeClass(rows.children, "spine-player-list-item-selected");
-                        row.classList.add("spine-player-list-item-selected");
-                        _this.config.skin = skin.name;
-                        _this.skeleton.setSkinByName(_this.config.skin);
-                        _this.skeleton.setSlotsToSetupPose();
-                    };
-                });
-                justClicked = true;
-                window.onclick = dismissDropdown;
+            this.skinButton.onclick = function () {
+                _this.showSkinsDialog();
             };
             };
             settingsButton.onclick = function () {
             settingsButton.onclick = function () {
-                if (!_this.skeleton || _this.skeleton.data.animations.length == 0)
-                    return;
-                dropdown.classList.remove("spine-player-hidden");
-                dropdown.innerHTML = "\n\t\t\t\t\t<div class=\"spine-player-dropdown-title\">Debug</div>\n\t\t\t\t\t<hr>\n\t\t\t\t\t<div class=\"spine-player-list\" style=\"user-select: none; align-items: center; max-height: 90px; overflow: auto;\">\n\t\t\t\t\t</div>\n\t\t\t\t";
-                var rows = findWithClass(dropdown, "spine-player-list")[0];
-                var makeItem = function (name) {
-                    var row = document.createElement("div");
-                    row.classList.add("spine-player-list-item");
-                    if (_this.config.debug[name] == true)
-                        row.classList.add("spine-player-list-item-selected");
-                    row.innerText = name;
-                    rows.appendChild(row);
-                    row.onclick = function () {
-                        if (_this.config.debug[name]) {
-                            _this.config.debug[name] = false;
-                            row.classList.remove("spine-player-list-item-selected");
-                        }
-                        else {
-                            _this.config.debug[name] = true;
-                            row.classList.add("spine-player-list-item-selected");
-                        }
-                    };
-                };
-                Object.keys(_this.config.debug).forEach(function (name) {
-                    makeItem(name);
-                });
-                justClicked = true;
-                window.onclick = dismissDropdown;
+                _this.showSettingsDialog();
             };
             };
             fullscreenButton.onclick = function () {
             fullscreenButton.onclick = function () {
                 var doc = document;
                 var doc = document;
@@ -9646,7 +9656,7 @@ var spine;
                         doc.msExitFullscreen();
                         doc.msExitFullscreen();
                 }
                 }
                 else {
                 else {
-                    var player = findWithClass(parent, "spine-player")[0];
+                    var player = dom;
                     if (player.requestFullscreen)
                     if (player.requestFullscreen)
                         player.requestFullscreen();
                         player.requestFullscreen();
                     else if (player.webkitRequestFullScreen)
                     else if (player.webkitRequestFullScreen)
@@ -9660,6 +9670,95 @@ var spine;
             window.onresize = function () {
             window.onresize = function () {
                 _this.drawFrame(false);
                 _this.drawFrame(false);
             };
             };
+            return dom;
+        };
+        SpinePlayer.prototype.showSpeedDialog = function () {
+            var _this = this;
+            var popup = new Popup(this.playerControls, "\n\t\t\t\t<div class=\"spine-player-row\" style=\"user-select: none; align-items: center; padding: 8px;\">\n\t\t\t\t\t<div style=\"margin-right: 16px;\">Speed</div>\n\t\t\t\t\t<div class=\"spine-player-column\">\n\t\t\t\t\t\t<div class=\"spine-player-speed-slider\" style=\"margin-bottom: 4px;\"></div>\n\t\t\t\t\t\t<div class=\"spine-player-row\" style=\"justify-content: space-between;\">\n\t\t\t\t\t\t\t<div>0.1x</div>\n\t\t\t\t\t\t\t<div>1x</div>\n\t\t\t\t\t\t\t<div>2x</div>\n\t\t\t\t\t\t</div>\n\t\t\t\t\t</div>\n\t\t\t\t</div>\n\t\t\t");
+            var sliderParent = findWithClass(popup.dom, "spine-player-speed-slider")[0];
+            var slider = new Slider(2);
+            sliderParent.appendChild(slider.render());
+            slider.setValue(this.speed / 2);
+            slider.change = function (percentage) {
+                _this.speed = percentage * 2;
+            };
+            popup.show();
+        };
+        SpinePlayer.prototype.showAnimationsDialog = function () {
+            var _this = this;
+            if (!this.skeleton || this.skeleton.data.animations.length == 0)
+                return;
+            var popup = new Popup(this.playerControls, "\n\t\t\t\t<div class=\"spine-player-popup-title\">Animations</div>\n\t\t\t\t<hr>\n\t\t\t\t<ul class=\"spine-player-list\"></ul>\n\t\t\t");
+            var rows = findWithClass(popup.dom, "spine-player-list")[0];
+            this.skeleton.data.animations.forEach(function (animation) {
+                if (_this.config.animations && _this.config.animations.indexOf(animation.name) < 0) {
+                    return;
+                }
+                var row = createElement("\n\t\t\t\t\t<li class=\"spine-player-list-item selectable\">\n\t\t\t\t\t\t<div class=\"selectable-circle\">\n\t\t\t\t\t\t</div>\n\t\t\t\t\t\t<div class=\"selectable-text\">\n\t\t\t\t\t\t</div>\n\t\t\t\t\t</li>\n\t\t\t\t");
+                if (animation.name == _this.config.animation)
+                    row.classList.add("selected");
+                findWithClass(row, "selectable-text")[0].innerText = animation.name;
+                rows.appendChild(row);
+                row.onclick = function () {
+                    removeClass(rows.children, "selected");
+                    row.classList.add("selected");
+                    _this.config.animation = animation.name;
+                    _this.playTime = 0;
+                    _this.animationState.setAnimation(0, _this.config.animation, true);
+                };
+            });
+            popup.show();
+        };
+        SpinePlayer.prototype.showSkinsDialog = function () {
+            var _this = this;
+            if (!this.skeleton || this.skeleton.data.animations.length == 0)
+                return;
+            var popup = new Popup(this.playerControls, "\n\t\t\t\t<div class=\"spine-player-popup-title\">Skins</div>\n\t\t\t\t<hr>\n\t\t\t\t<ul class=\"spine-player-list\"></ul>\n\t\t\t");
+            var rows = findWithClass(popup.dom, "spine-player-list")[0];
+            this.skeleton.data.skins.forEach(function (skin) {
+                if (_this.config.skins && _this.config.skins.indexOf(skin.name) < 0) {
+                    return;
+                }
+                var row = createElement("\n\t\t\t\t\t<li class=\"spine-player-list-item selectable\">\n\t\t\t\t\t\t<div class=\"selectable-circle\">\n\t\t\t\t\t\t</div>\n\t\t\t\t\t\t<div class=\"selectable-text\">\n\t\t\t\t\t\t</div>\n\t\t\t\t\t</li>\n\t\t\t\t");
+                if (skin.name == _this.config.skin)
+                    row.classList.add("selected");
+                findWithClass(row, "selectable-text")[0].innerText = skin.name;
+                rows.appendChild(row);
+                row.onclick = function () {
+                    removeClass(rows.children, "selected");
+                    row.classList.add("selected");
+                    _this.config.skin = skin.name;
+                    _this.skeleton.setSkinByName(_this.config.skin);
+                    _this.skeleton.setSlotsToSetupPose();
+                };
+            });
+            popup.show();
+        };
+        SpinePlayer.prototype.showSettingsDialog = function () {
+            var _this = this;
+            if (!this.skeleton || this.skeleton.data.animations.length == 0)
+                return;
+            var popup = new Popup(this.playerControls, "\n\t\t\t\t<div class=\"spine-player-popup-title\">Debug</div>\n\t\t\t\t<hr>\n\t\t\t\t<ul class=\"spine-player-list\">\n\t\t\t\t</li>\n\t\t\t");
+            var rows = findWithClass(popup.dom, "spine-player-list")[0];
+            var makeItem = function (label, name) {
+                var row = createElement("<li class=\"spine-player-list-item\"></li>");
+                var s = new Switch(label);
+                row.appendChild(s.render());
+                s.setEnabled(_this.config.debug[name]);
+                s.change = function (value) {
+                    _this.config.debug[name] = value;
+                };
+                rows.appendChild(row);
+            };
+            makeItem("Bones", "bones");
+            makeItem("Regions", "regions");
+            makeItem("Meshes", "meshes");
+            makeItem("Bounds", "bounds");
+            makeItem("Paths", "paths");
+            makeItem("Clipping", "clipping");
+            makeItem("Points", "points");
+            makeItem("Hulls", "hulls");
+            popup.show();
         };
         };
         SpinePlayer.prototype.drawFrame = function (requestNextFrame) {
         SpinePlayer.prototype.drawFrame = function (requestNextFrame) {
             var _this = this;
             var _this = this;
@@ -9681,29 +9780,52 @@ var spine;
                     var delta = this.time.delta * this.speed;
                     var delta = this.time.delta * this.speed;
                     var animationDuration = this.animationState.getCurrent(0).animation.duration;
                     var animationDuration = this.animationState.getCurrent(0).animation.duration;
                     this.playTime += delta;
                     this.playTime += delta;
-                    while (this.playTime >= animationDuration) {
+                    while (this.playTime >= animationDuration && animationDuration != 0) {
                         this.playTime -= animationDuration;
                         this.playTime -= animationDuration;
                     }
                     }
                     this.playTime = Math.max(0, Math.min(this.playTime, animationDuration));
                     this.playTime = Math.max(0, Math.min(this.playTime, animationDuration));
                     this.timelineSlider.setValue(this.playTime / animationDuration);
                     this.timelineSlider.setValue(this.playTime / animationDuration);
                     this.animationState.update(delta);
                     this.animationState.update(delta);
                     this.animationState.apply(this.skeleton);
                     this.animationState.apply(this.skeleton);
-                    this.skeleton.updateWorldTransform();
                 }
                 }
+                this.skeleton.updateWorldTransform();
                 var viewportSize = this.scale(this.config.viewport.width, this.config.viewport.height, this.canvas.width, this.canvas.height);
                 var viewportSize = this.scale(this.config.viewport.width, this.config.viewport.height, this.canvas.width, this.canvas.height);
                 this.sceneRenderer.camera.zoom = this.config.viewport.width / viewportSize.x;
                 this.sceneRenderer.camera.zoom = this.config.viewport.width / viewportSize.x;
                 this.sceneRenderer.camera.position.x = this.config.viewport.x + this.config.viewport.width / 2;
                 this.sceneRenderer.camera.position.x = this.config.viewport.x + this.config.viewport.width / 2;
                 this.sceneRenderer.camera.position.y = this.config.viewport.y + this.config.viewport.height / 2;
                 this.sceneRenderer.camera.position.y = this.config.viewport.y + this.config.viewport.height / 2;
                 this.sceneRenderer.begin();
                 this.sceneRenderer.begin();
+                if (this.config.backgroundImage && this.config.backgroundImage.url) {
+                    var bgImage = this.assetManager.get(this.config.backgroundImage.url);
+                    if (!this.config.backgroundImage.x) {
+                        this.sceneRenderer.drawTexture(bgImage, this.config.viewport.x, this.config.viewport.y, this.config.viewport.width, this.config.viewport.height);
+                    }
+                    else {
+                        this.sceneRenderer.drawTexture(bgImage, this.config.backgroundImage.x, this.config.backgroundImage.y, this.config.backgroundImage.width, this.config.backgroundImage.height);
+                    }
+                }
                 this.sceneRenderer.drawSkeleton(this.skeleton, this.config.premultipliedAlpha);
                 this.sceneRenderer.drawSkeleton(this.skeleton, this.config.premultipliedAlpha);
                 this.sceneRenderer.skeletonDebugRenderer.drawBones = this.config.debug.bones;
                 this.sceneRenderer.skeletonDebugRenderer.drawBones = this.config.debug.bones;
                 this.sceneRenderer.skeletonDebugRenderer.drawBoundingBoxes = this.config.debug.bounds;
                 this.sceneRenderer.skeletonDebugRenderer.drawBoundingBoxes = this.config.debug.bounds;
                 this.sceneRenderer.skeletonDebugRenderer.drawClipping = this.config.debug.clipping;
                 this.sceneRenderer.skeletonDebugRenderer.drawClipping = this.config.debug.clipping;
-                this.sceneRenderer.skeletonDebugRenderer.drawMeshHull = this.config.debug.meshHull;
+                this.sceneRenderer.skeletonDebugRenderer.drawMeshHull = this.config.debug.hulls;
                 this.sceneRenderer.skeletonDebugRenderer.drawPaths = this.config.debug.paths;
                 this.sceneRenderer.skeletonDebugRenderer.drawPaths = this.config.debug.paths;
                 this.sceneRenderer.skeletonDebugRenderer.drawRegionAttachments = this.config.debug.regions;
                 this.sceneRenderer.skeletonDebugRenderer.drawRegionAttachments = this.config.debug.regions;
-                this.sceneRenderer.skeletonDebugRenderer.drawMeshTriangles = this.config.debug.triangles;
+                this.sceneRenderer.skeletonDebugRenderer.drawMeshTriangles = this.config.debug.meshes;
                 this.sceneRenderer.drawSkeletonDebug(this.skeleton, this.config.premultipliedAlpha);
                 this.sceneRenderer.drawSkeletonDebug(this.skeleton, this.config.premultipliedAlpha);
+                var controlBones = this.config.controlBones;
+                var selectedBones = this.selectedBones;
+                var skeleton = this.skeleton;
+                gl.lineWidth(2);
+                for (var i = 0; i < controlBones.length; i++) {
+                    var bone = skeleton.findBone(controlBones[i]);
+                    if (!bone)
+                        continue;
+                    var colorInner = selectedBones[i] !== null ? SpinePlayer.HOVER_COLOR_INNER : SpinePlayer.NON_HOVER_COLOR_INNER;
+                    var colorOuter = selectedBones[i] !== null ? SpinePlayer.HOVER_COLOR_OUTER : SpinePlayer.NON_HOVER_COLOR_OUTER;
+                    this.sceneRenderer.circle(true, skeleton.x + bone.worldX, skeleton.y + bone.worldY, 20, colorInner);
+                    this.sceneRenderer.circle(false, skeleton.x + bone.worldX, skeleton.y + bone.worldY, 20, colorOuter);
+                }
+                gl.lineWidth(1);
                 this.sceneRenderer.end();
                 this.sceneRenderer.end();
                 this.sceneRenderer.camera.zoom = 0;
                 this.sceneRenderer.camera.zoom = 0;
             }
             }
@@ -9721,20 +9843,50 @@ var spine;
             var _this = this;
             var _this = this;
             if (this.loaded)
             if (this.loaded)
                 return;
                 return;
+            if (this.assetManager.hasErrors()) {
+                this.showError("Error: assets could not be loaded.<br><br>" + escapeHtml(JSON.stringify(this.assetManager.getErrors())));
+                return;
+            }
             var atlas = this.assetManager.get(this.config.atlasUrl);
             var atlas = this.assetManager.get(this.config.atlasUrl);
             var jsonText = this.assetManager.get(this.config.jsonUrl);
             var jsonText = this.assetManager.get(this.config.jsonUrl);
             var json = new spine.SkeletonJson(new spine.AtlasAttachmentLoader(atlas));
             var json = new spine.SkeletonJson(new spine.AtlasAttachmentLoader(atlas));
-            var skeletonData = json.readSkeletonData(jsonText);
+            var skeletonData;
+            try {
+                skeletonData = json.readSkeletonData(jsonText);
+            }
+            catch (e) {
+                this.showError("Error: could not load skeleton .json.<br><br>" + escapeHtml(JSON.stringify(e)));
+                return;
+            }
             this.skeleton = new spine.Skeleton(skeletonData);
             this.skeleton = new spine.Skeleton(skeletonData);
             var stateData = new spine.AnimationStateData(skeletonData);
             var stateData = new spine.AnimationStateData(skeletonData);
             stateData.defaultMix = 0.2;
             stateData.defaultMix = 0.2;
             this.animationState = new spine.AnimationState(stateData);
             this.animationState = new spine.AnimationState(stateData);
+            if (this.config.controlBones) {
+                this.config.controlBones.forEach(function (bone) {
+                    if (!skeletonData.findBone(bone)) {
+                        _this.showError("Error: control bone '" + bone + "' does not exist in skeleton.");
+                    }
+                });
+            }
             if (!this.config.skin) {
             if (!this.config.skin) {
                 if (skeletonData.skins.length > 0) {
                 if (skeletonData.skins.length > 0) {
                     this.config.skin = skeletonData.skins[0].name;
                     this.config.skin = skeletonData.skins[0].name;
                 }
                 }
             }
             }
+            if (this.config.skins && this.config.skin.length > 0) {
+                this.config.skins.forEach(function (skin) {
+                    if (!_this.skeleton.data.findSkin(skin)) {
+                        _this.showError("Error: skin '" + skin + "' in selectable skin list does not exist in skeleton.");
+                        return;
+                    }
+                });
+            }
             if (this.config.skin) {
             if (this.config.skin) {
+                if (!this.skeleton.data.findSkin(this.config.skin)) {
+                    this.showError("Error: skin '" + this.config.skin + "' does not exist in skeleton.");
+                    return;
+                }
                 this.skeleton.setSkinByName(this.config.skin);
                 this.skeleton.setSkinByName(this.config.skin);
                 this.skeleton.setSlotsToSetupPose();
                 this.skeleton.setSlotsToSetupPose();
             }
             }
@@ -9754,12 +9906,27 @@ var spine;
                 this.config.viewport.width = size.x * 1.2;
                 this.config.viewport.width = size.x * 1.2;
                 this.config.viewport.height = size.y * 1.2;
                 this.config.viewport.height = size.y * 1.2;
             }
             }
+            if (this.config.animations && this.config.animations.length > 0) {
+                this.config.animations.forEach(function (animation) {
+                    if (!_this.skeleton.data.findAnimation(animation)) {
+                        _this.showError("Error: animation '" + animation + "' in selectable animation list does not exist in skeleton.");
+                        return;
+                    }
+                });
+                if (!this.config.animation) {
+                    this.config.animation = this.config.animations[0];
+                }
+            }
             if (!this.config.animation) {
             if (!this.config.animation) {
                 if (skeletonData.animations.length > 0) {
                 if (skeletonData.animations.length > 0) {
                     this.config.animation = skeletonData.animations[0].name;
                     this.config.animation = skeletonData.animations[0].name;
                 }
                 }
             }
             }
             if (this.config.animation) {
             if (this.config.animation) {
+                if (!skeletonData.findAnimation(this.config.animation)) {
+                    this.showError("Error: animation '" + this.config.animation + "' does not exist in skeleton.");
+                    return;
+                }
                 this.play();
                 this.play();
                 this.timelineSlider.change = function (percentage) {
                 this.timelineSlider.change = function (percentage) {
                     _this.pause();
                     _this.pause();
@@ -9771,8 +9938,106 @@ var spine;
                     _this.playTime = time;
                     _this.playTime = time;
                 };
                 };
             }
             }
+            this.setupInput();
+            if (skeletonData.skins.length == 1)
+                this.skinButton.classList.add("spine-player-hidden");
+            if (skeletonData.animations.length == 1)
+                this.animationButton.classList.add("spine-player-hidden");
+            this.config.success(this);
             this.loaded = true;
             this.loaded = true;
         };
         };
+        SpinePlayer.prototype.setupInput = function () {
+            var _this = this;
+            var controlBones = this.config.controlBones;
+            var selectedBones = this.selectedBones = new Array(this.config.controlBones.length);
+            var canvas = this.canvas;
+            var input = new spine.webgl.Input(canvas);
+            var target = null;
+            var coords = new spine.webgl.Vector3();
+            var temp = new spine.webgl.Vector3();
+            var temp2 = new spine.Vector2();
+            var skeleton = this.skeleton;
+            var renderer = this.sceneRenderer;
+            input.addListener({
+                down: function (x, y) {
+                    for (var i = 0; i < controlBones.length; i++) {
+                        var bone = skeleton.findBone(controlBones[i]);
+                        if (!bone)
+                            continue;
+                        renderer.camera.screenToWorld(coords.set(x, y, 0), canvas.width, canvas.height);
+                        if (temp.set(skeleton.x + bone.worldX, skeleton.y + bone.worldY, 0).distance(coords) < 30) {
+                            target = bone;
+                        }
+                    }
+                    handleHover();
+                },
+                up: function (x, y) {
+                    target = null;
+                    handleHover();
+                },
+                dragged: function (x, y) {
+                    if (target != null) {
+                        renderer.camera.screenToWorld(coords.set(x, y, 0), canvas.width, canvas.height);
+                        if (target.parent !== null) {
+                            target.parent.worldToLocal(temp2.set(coords.x - skeleton.x, coords.y - skeleton.y));
+                            target.x = temp2.x;
+                            target.y = temp2.y;
+                        }
+                        else {
+                            target.x = coords.x - skeleton.x;
+                            target.y = coords.y - skeleton.y;
+                        }
+                    }
+                    handleHover();
+                },
+                moved: function (x, y) {
+                    for (var i = 0; i < controlBones.length; i++) {
+                        var bone = skeleton.findBone(controlBones[i]);
+                        if (!bone)
+                            continue;
+                        renderer.camera.screenToWorld(coords.set(x, y, 0), canvas.width, canvas.height);
+                        if (temp.set(skeleton.x + bone.worldX, skeleton.y + bone.worldY, 0).distance(coords) < 30) {
+                            selectedBones[i] = bone;
+                        }
+                        else {
+                            selectedBones[i] = null;
+                        }
+                    }
+                    handleHover();
+                }
+            });
+            var mouseOverChildren = false;
+            canvas.onmouseover = function (ev) {
+                mouseOverChildren = false;
+            };
+            canvas.onmouseout = function (ev) {
+                if (ev.relatedTarget == null) {
+                    mouseOverChildren = false;
+                }
+                else {
+                    mouseOverChildren = isContained(_this.dom, ev.relatedTarget);
+                }
+            };
+            var cancelId = 0;
+            var handleHover = function () {
+                if (!_this.config.showControls)
+                    return;
+                clearTimeout(cancelId);
+                _this.playerControls.classList.remove("hidden");
+                _this.playerControls.classList.add("visible");
+                var remove = function () {
+                    var popup = findWithClass(_this.dom, "spine-player-popup");
+                    if (popup.length == 0 && !mouseOverChildren) {
+                        _this.playerControls.classList.remove("visible");
+                        _this.playerControls.classList.add("hidden");
+                    }
+                    else {
+                        cancelId = setTimeout(remove, 1000);
+                    }
+                };
+                cancelId = setTimeout(remove, 1000);
+            };
+        };
         SpinePlayer.prototype.play = function () {
         SpinePlayer.prototype.play = function () {
             this.paused = false;
             this.paused = false;
             this.playButton.classList.remove("spine-player-button-icon-play");
             this.playButton.classList.remove("spine-player-button-icon-play");
@@ -9788,18 +10053,10 @@ var spine;
             this.playButton.classList.remove("spine-player-button-icon-pause");
             this.playButton.classList.remove("spine-player-button-icon-pause");
             this.playButton.classList.add("spine-player-button-icon-play");
             this.playButton.classList.add("spine-player-button-icon-play");
         };
         };
-        SpinePlayer.prototype.resize = function () {
-            var canvas = this.canvas;
-            var w = canvas.clientWidth;
-            var h = canvas.clientHeight;
-            var devicePixelRatio = window.devicePixelRatio || 1;
-            if (canvas.width != Math.floor(w * devicePixelRatio) || canvas.height != Math.floor(h * devicePixelRatio)) {
-                canvas.width = Math.floor(w * devicePixelRatio);
-                canvas.height = Math.floor(h * devicePixelRatio);
-            }
-            this.context.gl.viewport(0, 0, canvas.width, canvas.height);
-            this.sceneRenderer.camera.setViewport(canvas.width, canvas.height);
-        };
+        SpinePlayer.HOVER_COLOR_INNER = new spine.Color(0.478, 0, 0, 0.25);
+        SpinePlayer.HOVER_COLOR_OUTER = new spine.Color(1, 1, 1, 1);
+        SpinePlayer.NON_HOVER_COLOR_INNER = new spine.Color(0.478, 0, 0, 0.5);
+        SpinePlayer.NON_HOVER_COLOR_OUTER = new spine.Color(1, 0, 0, 0.8);
         return SpinePlayer;
         return SpinePlayer;
     }());
     }());
     spine.SpinePlayer = SpinePlayer;
     spine.SpinePlayer = SpinePlayer;
@@ -9844,11 +10101,26 @@ var spine;
         findRecursive(dom, className, found);
         findRecursive(dom, className, found);
         return found;
         return found;
     }
     }
+    function createElement(html) {
+        var dom = document.createElement("div");
+        dom.innerHTML = html;
+        return dom.children[0];
+    }
     function removeClass(elements, clazz) {
     function removeClass(elements, clazz) {
         for (var i = 0; i < elements.length; i++) {
         for (var i = 0; i < elements.length; i++) {
             elements[i].classList.remove(clazz);
             elements[i].classList.remove(clazz);
         }
         }
     }
     }
+    function escapeHtml(str) {
+        if (!str)
+            return "";
+        return str
+            .replace(/&/g, "&amp;")
+            .replace(/</g, "&lt;")
+            .replace(/>/g, "&gt;")
+            .replace(/"/g, "&#34;")
+            .replace(/'/g, "&#39;");
+    }
 })(spine || (spine = {}));
 })(spine || (spine = {}));
 var spine;
 var spine;
 (function (spine) {
 (function (spine) {

文件差異過大導致無法顯示
+ 0 - 0
spine-ts/build/spine-widget.js.map


文件差異過大導致無法顯示
+ 249 - 0
spine-ts/widget/css/spine-player.css


文件差異過大導致無法顯示
+ 8 - 125
spine-ts/widget/example/player-test.html


文件差異過大導致無法顯示
+ 562 - 211
spine-ts/widget/src/Player.ts


+ 1 - 2
spine-unity/Assets/Spine/Runtime/spine-unity/Components/SkeletonAnimation.cs

@@ -34,7 +34,6 @@ namespace Spine.Unity {
 	
 	
 	[ExecuteInEditMode]
 	[ExecuteInEditMode]
 	[AddComponentMenu("Spine/SkeletonAnimation")]
 	[AddComponentMenu("Spine/SkeletonAnimation")]
-	[HelpURL("http://esotericsoftware.com/spine-unity-documentation#Controlling-Animation")]
 	public class SkeletonAnimation : SkeletonRenderer, ISkeletonAnimation, IAnimationStateComponent {
 	public class SkeletonAnimation : SkeletonRenderer, ISkeletonAnimation, IAnimationStateComponent {
 
 
 		#region IAnimationStateComponent
 		#region IAnimationStateComponent
@@ -158,7 +157,7 @@ namespace Spine.Unity {
 					if (Application.isPlaying) {
 					if (Application.isPlaying) {
 					#endif
 					#endif
 
 
-						// Make this block not run in Unity Editor edit mode.
+						// In Unity Editor edit mode, make this block not run.
 						state.SetAnimation(0, animationObject, loop);
 						state.SetAnimation(0, animationObject, loop);
 
 
 					#if UNITY_EDITOR
 					#if UNITY_EDITOR

+ 50 - 14
spine-unity/Assets/Spine/Runtime/spine-unity/Components/SkeletonRenderer.cs

@@ -35,12 +35,16 @@ using System.Collections.Generic;
 using UnityEngine;
 using UnityEngine;
 
 
 namespace Spine.Unity {
 namespace Spine.Unity {
-	/// <summary>Renders a skeleton.</summary>
+	/// <summary>Base class of animated Spine skeleton components. This component manages and renders a skeleton.</summary>
 	[ExecuteInEditMode, RequireComponent(typeof(MeshFilter), typeof(MeshRenderer)), DisallowMultipleComponent]
 	[ExecuteInEditMode, RequireComponent(typeof(MeshFilter), typeof(MeshRenderer)), DisallowMultipleComponent]
-	[HelpURL("http://esotericsoftware.com/spine-unity-documentation#Rendering")]
+	[HelpURL("http://esotericsoftware.com/spine-unity-rendering")]
 	public class SkeletonRenderer : MonoBehaviour, ISkeletonComponent, IHasSkeletonDataAsset {
 	public class SkeletonRenderer : MonoBehaviour, ISkeletonComponent, IHasSkeletonDataAsset {
 
 
+		public bool logErrors = false;
+
 		public delegate void SkeletonRendererDelegate (SkeletonRenderer skeletonRenderer);
 		public delegate void SkeletonRendererDelegate (SkeletonRenderer skeletonRenderer);
+
+		/// <summary>OnRebuild is raised after the Skeleton is successfully initialized.</summary>
 		public event SkeletonRendererDelegate OnRebuild;
 		public event SkeletonRendererDelegate OnRebuild;
 
 
 		/// <summary> Occurs after the vertex data is populated every frame, before the vertices are pushed into the mesh.</summary>
 		/// <summary> Occurs after the vertex data is populated every frame, before the vertices are pushed into the mesh.</summary>
@@ -48,34 +52,59 @@ namespace Spine.Unity {
 
 
 		public SkeletonDataAsset skeletonDataAsset;
 		public SkeletonDataAsset skeletonDataAsset;
 		public SkeletonDataAsset SkeletonDataAsset { get { return skeletonDataAsset; } } // ISkeletonComponent
 		public SkeletonDataAsset SkeletonDataAsset { get { return skeletonDataAsset; } } // ISkeletonComponent
-		[SpineSkin(defaultAsEmptyString:true)]
-		public string initialSkinName;
+
+		#region Initialization settings
+		/// <summary>Skin name to use when the Skeleton is initialized.</summary>
+		[SpineSkin(defaultAsEmptyString:true)] public string initialSkinName;
+
+		/// <summary>Flip X and Y to use when the Skeleton is initialized.</summary>
 		public bool initialFlipX, initialFlipY;
 		public bool initialFlipX, initialFlipY;
+		#endregion
 
 
-		#region Advanced
+		#region Advanced Render Settings
 		// Submesh Separation
 		// Submesh Separation
+		/// <summary>Slot names used to populate separatorSlots list when the Skeleton is initialized. Changing this after initialization does nothing.</summary>
 		[UnityEngine.Serialization.FormerlySerializedAs("submeshSeparators")][SerializeField][SpineSlot] protected string[] separatorSlotNames = new string[0];
 		[UnityEngine.Serialization.FormerlySerializedAs("submeshSeparators")][SerializeField][SpineSlot] protected string[] separatorSlotNames = new string[0];
+
+		/// <summary>Slots that determine where the render is split. This is used by components such as SkeletonRenderSeparator so that the skeleton can be rendered by two separate renderers on different GameObjects.</summary>
 		[System.NonSerialized] public readonly List<Slot> separatorSlots = new List<Slot>();
 		[System.NonSerialized] public readonly List<Slot> separatorSlots = new List<Slot>();
 
 
+		// Render Settings
 		[Range(-0.1f, 0f)] public float zSpacing;
 		[Range(-0.1f, 0f)] public float zSpacing;
+		/// <summary>Use Spine's clipping feature. If false, ClippingAttachments will be ignored.</summary>
 		public bool useClipping = true;
 		public bool useClipping = true;
+
+		/// <summary>If true, triangles will not be updated. Enable this as an optimization if the skeleton does not make use of attachment swapping or hiding, or draw order keys. Otherwise, setting this to false may cause errors in rendering.</summary>
 		public bool immutableTriangles = false;
 		public bool immutableTriangles = false;
+
+		/// <summary>Multiply vertex color RGB with vertex color alpha. Set this to true if the shader used for rendering is a premultiplied alpha shader. Setting this to false disables single-batch additive slots.</summary>
 		public bool pmaVertexColors = true;
 		public bool pmaVertexColors = true;
+
 		/// <summary>Clears the state of the render and skeleton when this component or its GameObject is disabled. This prevents previous state from being retained when it is enabled again. When pooling your skeleton, setting this to true can be helpful.</summary>
 		/// <summary>Clears the state of the render and skeleton when this component or its GameObject is disabled. This prevents previous state from being retained when it is enabled again. When pooling your skeleton, setting this to true can be helpful.</summary>
 		public bool clearStateOnDisable = false;
 		public bool clearStateOnDisable = false;
+
+		/// <summary>If true, second colors on slots will be added to the output Mesh as UV2 and UV3. A special "tint black" shader that interprets UV2 and UV3 as black point colors is required to render this properly.</summary>
 		public bool tintBlack = false;
 		public bool tintBlack = false;
+
+		/// <summary>If true, the renderer assumes the skeleton only requires one Material and one submesh to render. This allows the MeshGenerator to skip checking for changes in Materials. Enable this as an optimization if the skeleton only uses one Material.</summary>
+		/// <remarks>This disables SkeletonRenderSeparator functionality.</remarks>
 		public bool singleSubmesh = false;
 		public bool singleSubmesh = false;
 
 
-		[UnityEngine.Serialization.FormerlySerializedAs("calculateNormals")]
-		public bool addNormals = false;
-		public bool calculateTangents = false;
+		/// <summary>If true, the mesh generator adds normals to the output mesh. For better performance and reduced memory requirements, use a shader that assumes the desired normal.</summary>
+		[UnityEngine.Serialization.FormerlySerializedAs("calculateNormals")] public bool addNormals = false;
 
 
-		public bool logErrors = false;
+		/// <summary>If true, tangents are calculated every frame and added to the Mesh. Enable this when using a shader that uses lighting that requires tangents.</summary>
+		public bool calculateTangents = false;
+		#endregion
 
 
+		#region Overrides
 		#if SPINE_OPTIONAL_RENDEROVERRIDE
 		#if SPINE_OPTIONAL_RENDEROVERRIDE
+		// These are API for anything that wants to take over rendering for a SkeletonRenderer.
 		public bool disableRenderingOnOverride = true;
 		public bool disableRenderingOnOverride = true;
 		public delegate void InstructionDelegate (SkeletonRendererInstruction instruction);
 		public delegate void InstructionDelegate (SkeletonRendererInstruction instruction);
 		event InstructionDelegate generateMeshOverride;
 		event InstructionDelegate generateMeshOverride;
+
+		/// <summary>Allows separate code to take over rendering for this SkeletonRenderer component. The subscriber is passed a SkeletonRendererInstruction argument to determine how to render a skeleton.</summary>
 		public event InstructionDelegate GenerateMeshOverride {
 		public event InstructionDelegate GenerateMeshOverride {
 			add {
 			add {
 				generateMeshOverride += value;
 				generateMeshOverride += value;
@@ -96,17 +125,27 @@ namespace Spine.Unity {
 
 
 		#if SPINE_OPTIONAL_MATERIALOVERRIDE
 		#if SPINE_OPTIONAL_MATERIALOVERRIDE
 		[System.NonSerialized] readonly Dictionary<Material, Material> customMaterialOverride = new Dictionary<Material, Material>();
 		[System.NonSerialized] readonly Dictionary<Material, Material> customMaterialOverride = new Dictionary<Material, Material>();
+		/// <summary>Use this Dictionary to override a Material with a different Material.</summary>
 		public Dictionary<Material, Material> CustomMaterialOverride { get { return customMaterialOverride; } }
 		public Dictionary<Material, Material> CustomMaterialOverride { get { return customMaterialOverride; } }
 		#endif
 		#endif
 
 
-		// Custom Slot Material
 		[System.NonSerialized] readonly Dictionary<Slot, Material> customSlotMaterials = new Dictionary<Slot, Material>();
 		[System.NonSerialized] readonly Dictionary<Slot, Material> customSlotMaterials = new Dictionary<Slot, Material>();
+		/// <summary>Use this Dictionary to use a different Material to render specific Slots.</summary>
 		public Dictionary<Slot, Material> CustomSlotMaterials { get { return customSlotMaterials; } }
 		public Dictionary<Slot, Material> CustomSlotMaterials { get { return customSlotMaterials; } }
 		#endregion
 		#endregion
 
 
+		#region Mesh Generator
+		[System.NonSerialized] readonly SkeletonRendererInstruction currentInstructions = new SkeletonRendererInstruction();
+		readonly MeshGenerator meshGenerator = new MeshGenerator();
+		[System.NonSerialized] readonly MeshRendererBuffers rendererBuffers = new MeshRendererBuffers();
+		#endregion
+
+		#region Cached component references
 		MeshRenderer meshRenderer;
 		MeshRenderer meshRenderer;
 		MeshFilter meshFilter;
 		MeshFilter meshFilter;
+		#endregion
 
 
+		#region Skeleton
 		[System.NonSerialized] public bool valid;
 		[System.NonSerialized] public bool valid;
 		[System.NonSerialized] public Skeleton skeleton;
 		[System.NonSerialized] public Skeleton skeleton;
 		public Skeleton Skeleton {
 		public Skeleton Skeleton {
@@ -115,10 +154,7 @@ namespace Spine.Unity {
 				return skeleton;
 				return skeleton;
 			}
 			}
 		}
 		}
-			
-		[System.NonSerialized] readonly SkeletonRendererInstruction currentInstructions = new SkeletonRendererInstruction();
-		readonly MeshGenerator meshGenerator = new MeshGenerator();
-		[System.NonSerialized] readonly MeshRendererBuffers rendererBuffers = new MeshRendererBuffers();
+		#endregion
 
 
 		#region Runtime Instantiation
 		#region Runtime Instantiation
 		public static T NewSpineGameObject<T> (SkeletonDataAsset skeletonDataAsset) where T : SkeletonRenderer {
 		public static T NewSpineGameObject<T> (SkeletonDataAsset skeletonDataAsset) where T : SkeletonRenderer {

+ 13 - 6
spine-unity/Assets/Spine/Runtime/spine-unity/Mesh Generation/SpineMesh.cs

@@ -84,7 +84,6 @@ namespace Spine.Unity {
 	}
 	}
 
 
 	public delegate void MeshGeneratorDelegate (MeshGeneratorBuffers buffers);
 	public delegate void MeshGeneratorDelegate (MeshGeneratorBuffers buffers);
-
 	public struct MeshGeneratorBuffers {
 	public struct MeshGeneratorBuffers {
 		/// <summary>The vertex count that will actually be used for the mesh. The Lengths of the buffer arrays may be larger than this number.</summary>
 		/// <summary>The vertex count that will actually be used for the mesh. The Lengths of the buffer arrays may be larger than this number.</summary>
 		public int vertexCount;
 		public int vertexCount;
@@ -102,6 +101,7 @@ namespace Spine.Unity {
 		public MeshGenerator meshGenerator;
 		public MeshGenerator meshGenerator;
 	}
 	}
 
 
+	/// <summary>Holds several methods to prepare and generate a UnityEngine mesh based on a skeleton. Contains buffers needed to perform the operation, and serializes settings for mesh generation.</summary>
 	[System.Serializable]
 	[System.Serializable]
 	public class MeshGenerator {
 	public class MeshGenerator {
 		public Settings settings = Settings.Default;
 		public Settings settings = Settings.Default;
@@ -152,6 +152,7 @@ namespace Spine.Unity {
 		[NonSerialized] int[] regionTriangles = { 0, 1, 2, 2, 3, 0 };
 		[NonSerialized] int[] regionTriangles = { 0, 1, 2, 2, 3, 0 };
 
 
 		#region Optional Buffers
 		#region Optional Buffers
+		// These optional buffers are lazy-instantiated when the feature is used.
 		[NonSerialized] Vector3[] normals;
 		[NonSerialized] Vector3[] normals;
 		[NonSerialized] Vector4[] tangents;
 		[NonSerialized] Vector4[] tangents;
 		[NonSerialized] Vector2[] tempTanBuffer;
 		[NonSerialized] Vector2[] tempTanBuffer;
@@ -161,6 +162,7 @@ namespace Spine.Unity {
 
 
 		public int VertexCount { get { return vertexBuffer.Count; } }
 		public int VertexCount { get { return vertexBuffer.Count; } }
 
 
+		/// <summary>A set of mesh arrays whose values are modifiable by the user. Modify these values before they are passed to the UnityEngine mesh object in order to see the effect.</summary>
 		public MeshGeneratorBuffers Buffers {
 		public MeshGeneratorBuffers Buffers {
 			get {
 			get {
 				return new MeshGeneratorBuffers {
 				return new MeshGeneratorBuffers {
@@ -1093,6 +1095,7 @@ namespace Spine.Unity {
 			}
 			}
 		}
 		}
 
 
+		/// <summary>Trims internal buffers to reduce the resulting mesh data stream size.</summary>
 		public void TrimExcess () {
 		public void TrimExcess () {
 			vertexBuffer.TrimExcess();
 			vertexBuffer.TrimExcess();
 			uvBuffer.TrimExcess();
 			uvBuffer.TrimExcess();
@@ -1201,8 +1204,7 @@ namespace Spine.Unity {
 		static List<Color32> AttachmentColors32 = new List<Color32>();
 		static List<Color32> AttachmentColors32 = new List<Color32>();
 		static List<int> AttachmentIndices = new List<int>();
 		static List<int> AttachmentIndices = new List<int>();
 
 
-		/// <summary>
-		/// Fills mesh vertex data to render a RegionAttachment.</summary>
+		/// <summary>Fills mesh vertex data to render a RegionAttachment.</summary>
 		public static void FillMeshLocal (Mesh mesh, RegionAttachment regionAttachment) {
 		public static void FillMeshLocal (Mesh mesh, RegionAttachment regionAttachment) {
 			if (mesh == null) return;
 			if (mesh == null) return;
 			if (regionAttachment == null) return;
 			if (regionAttachment == null) return;
@@ -1308,11 +1310,10 @@ namespace Spine.Unity {
 			AttachmentColors32.Clear();
 			AttachmentColors32.Clear();
 			AttachmentIndices.Clear();
 			AttachmentIndices.Clear();
 		}
 		}
-
-		
 		#endregion
 		#endregion
 	}
 	}
 
 
+	/// <summary>A double-buffered Mesh, and a shared material array, bundled for use by Spine components that need to push a Mesh and materials to a Unity MeshRenderer and MeshFilter.</summary>
 	public class MeshRendererBuffers : IDisposable {
 	public class MeshRendererBuffers : IDisposable {
 		DoubleBuffered<SmartMesh> doubleBufferedMesh;
 		DoubleBuffered<SmartMesh> doubleBufferedMesh;
 		internal readonly ExposedList<Material> submeshMaterials = new ExposedList<Material>();
 		internal readonly ExposedList<Material> submeshMaterials = new ExposedList<Material>();
@@ -1328,6 +1329,8 @@ namespace Spine.Unity {
 			}
 			}
 		}
 		}
 
 
+		/// <summary>Returns a sharedMaterials array for use on a MeshRenderer.</summary>
+		/// <returns></returns>
 		public Material[] GetUpdatedSharedMaterialsArray () {
 		public Material[] GetUpdatedSharedMaterialsArray () {
 			if (submeshMaterials.Count == sharedMaterials.Length)
 			if (submeshMaterials.Count == sharedMaterials.Length)
 				submeshMaterials.CopyTo(sharedMaterials);
 				submeshMaterials.CopyTo(sharedMaterials);
@@ -1337,6 +1340,7 @@ namespace Spine.Unity {
 			return sharedMaterials;
 			return sharedMaterials;
 		}
 		}
 
 
+		/// <summary>Returns true if the materials were modified since the buffers were last updated.</summary>
 		public bool MaterialsChangedInLastUpdate () {
 		public bool MaterialsChangedInLastUpdate () {
 			int newSubmeshMaterials = submeshMaterials.Count;
 			int newSubmeshMaterials = submeshMaterials.Count;
 			var sharedMaterials = this.sharedMaterials;
 			var sharedMaterials = this.sharedMaterials;
@@ -1349,6 +1353,7 @@ namespace Spine.Unity {
 			return false;
 			return false;
 		}
 		}
 
 
+		/// <summary>Updates the internal shared materials array with the given instruction list.</summary>
 		public void UpdateSharedMaterials (ExposedList<SubmeshInstruction> instructions) {
 		public void UpdateSharedMaterials (ExposedList<SubmeshInstruction> instructions) {
 			int newSize = instructions.Count;
 			int newSize = instructions.Count;
 			{ //submeshMaterials.Resize(instructions.Count);
 			{ //submeshMaterials.Resize(instructions.Count);
@@ -1405,10 +1410,11 @@ namespace Spine.Unity {
 		}
 		}
 	}
 	}
 
 
+	/// <summary>Instructions used by a SkeletonRenderer to render a mesh.</summary>
 	public class SkeletonRendererInstruction {
 	public class SkeletonRendererInstruction {
-		public bool immutableTriangles;
 		public readonly ExposedList<SubmeshInstruction> submeshInstructions = new ExposedList<SubmeshInstruction>();
 		public readonly ExposedList<SubmeshInstruction> submeshInstructions = new ExposedList<SubmeshInstruction>();
 
 
+		public bool immutableTriangles;
 		#if SPINE_TRIANGLECHECK
 		#if SPINE_TRIANGLECHECK
 		public bool hasActiveClipping;
 		public bool hasActiveClipping;
 		public int rawVertexCount = -1;
 		public int rawVertexCount = -1;
@@ -1540,4 +1546,5 @@ namespace Spine.Unity {
 		}
 		}
 	}
 	}
 
 
+
 }
 }

+ 5 - 11
spine-unity/Assets/Spine/Runtime/spine-unity/Modules/AttachmentTools/AttachmentTools.cs

@@ -823,18 +823,12 @@ namespace Spine.Unity.Modules.AttachmentTools {
 		public static void SetAttachment (this Skin skin, int slotIndex, string keyName, Attachment attachment) {
 		public static void SetAttachment (this Skin skin, int slotIndex, string keyName, Attachment attachment) {
 			skin.AddAttachment(slotIndex, keyName, attachment);
 			skin.AddAttachment(slotIndex, keyName, attachment);
 		}
 		}
-
-		/// <summary>Removes the attachment. Returns true if the element is successfully found and removed; otherwise, false.</summary>
-		public static bool RemoveAttachment (this Skin skin, string slotName, string keyName, Skeleton skeleton) {
-			int slotIndex = skeleton.FindSlotIndex(slotName);
-			if (skeleton == null) throw new System.ArgumentNullException("skeleton", "skeleton cannot be null.");
+		
+		public static void RemoveAttachment (this Skin skin, string slotName, string keyName, SkeletonData skeletonData) {
+			int slotIndex = skeletonData.FindSlotIndex(slotName);
+			if (skeletonData == null) throw new System.ArgumentNullException("skeletonData", "skeletonData cannot be null.");
 			if (slotIndex == -1) throw new System.ArgumentException(string.Format("Slot '{0}' does not exist in skeleton.", slotName), "slotName");
 			if (slotIndex == -1) throw new System.ArgumentException(string.Format("Slot '{0}' does not exist in skeleton.", slotName), "slotName");
-			return skin.RemoveAttachment(slotIndex, keyName);
-		}
-
-		/// <summary>Removes the attachment. Returns true if the element is successfully found and removed; otherwise, false.</summary>
-		public static bool RemoveAttachment (this Skin skin, int slotIndex, string keyName) {
-			return skin.Attachments.Remove(new Skin.AttachmentKeyTuple(slotIndex, keyName));
+			skin.RemoveAttachment(slotIndex, keyName);
 		}
 		}
 
 
 		public static void Clear (this Skin skin) {
 		public static void Clear (this Skin skin) {

+ 9 - 4
spine-unity/Assets/Spine/Runtime/spine-unity/Modules/SkeletonGraphic/SkeletonGraphic.cs

@@ -106,16 +106,21 @@ namespace Spine.Unity {
 		#endregion
 		#endregion
 
 
 		#region Runtime Instantiation
 		#region Runtime Instantiation
-		public static SkeletonGraphic NewSkeletonGraphicGameObject (SkeletonDataAsset skeletonDataAsset, Transform parent) {
-			SkeletonGraphic sg = SkeletonGraphic.AddSkeletonGraphicComponent(new GameObject("New Spine GameObject"), skeletonDataAsset);
+		/// <summary>Create a new GameObject with a SkeletonGraphic component.</summary>
+		/// <param name="material">Material for the canvas renderer to use. Usually, the default SkeletonGraphic material will work.</param>
+		public static SkeletonGraphic NewSkeletonGraphicGameObject (SkeletonDataAsset skeletonDataAsset, Transform parent, Material material) {
+			var sg = SkeletonGraphic.AddSkeletonGraphicComponent(new GameObject("New Spine GameObject"), skeletonDataAsset, material);
 			if (parent != null) sg.transform.SetParent(parent, false);
 			if (parent != null) sg.transform.SetParent(parent, false);
 			return sg;
 			return sg;
 		}
 		}
 
 
-		public static SkeletonGraphic AddSkeletonGraphicComponent (GameObject gameObject, SkeletonDataAsset skeletonDataAsset) {
+		/// <summary>Add a SkeletonGraphic component to a GameObject.</summary>
+		/// <param name="material">Material for the canvas renderer to use. Usually, the default SkeletonGraphic material will work.</param>
+		public static SkeletonGraphic AddSkeletonGraphicComponent (GameObject gameObject, SkeletonDataAsset skeletonDataAsset, Material material) {
 			var c = gameObject.AddComponent<SkeletonGraphic>();
 			var c = gameObject.AddComponent<SkeletonGraphic>();
 			if (skeletonDataAsset != null) {
 			if (skeletonDataAsset != null) {
-				c.skeletonDataAsset = skeletonDataAsset;				
+				c.material = material;
+				c.skeletonDataAsset = skeletonDataAsset;
 				c.Initialize(false);
 				c.Initialize(false);
 			}
 			}
 			return c;
 			return c;

+ 12 - 5
spine-unity/Assets/Spine/Runtime/spine-unity/Modules/SkeletonRenderSeparator/SkeletonRenderSeparator.cs

@@ -37,7 +37,7 @@ using Spine.Unity;
 namespace Spine.Unity.Modules {
 namespace Spine.Unity.Modules {
 	
 	
 	[ExecuteInEditMode]
 	[ExecuteInEditMode]
-	[HelpURL("https://github.com/pharan/spine-unity-docs/blob/master/SkeletonRenderSeparator.md")]
+	[HelpURL("http://esotericsoftware.com/spine-unity-skeletonrenderseparator")]
 	public class SkeletonRenderSeparator : MonoBehaviour {
 	public class SkeletonRenderSeparator : MonoBehaviour {
 		public const int DefaultSortingOrderIncrement = 5;
 		public const int DefaultSortingOrderIncrement = 5;
 
 
@@ -53,7 +53,8 @@ namespace Spine.Unity.Modules {
 				#endif
 				#endif
 				
 				
 				skeletonRenderer = value;
 				skeletonRenderer = value;
-				this.enabled = false; // Disable if nulled.
+				if (value == null)
+					this.enabled = false;
 			}
 			}
 		}
 		}
 
 
@@ -105,6 +106,15 @@ namespace Spine.Unity.Modules {
 				componentRenderers.Add(spr);
 				componentRenderers.Add(spr);
 			}
 			}
 
 
+			#if UNITY_EDITOR
+			// Make sure editor updates properly in edit mode.
+			if (!Application.isPlaying) {
+				skeletonRenderer.enabled = false;
+				skeletonRenderer.enabled = true;
+				skeletonRenderer.LateUpdate();
+			}
+			#endif
+
 			return srs;
 			return srs;
 		}
 		}
 
 
@@ -167,9 +177,7 @@ namespace Spine.Unity.Modules {
 			skeletonRenderer.GenerateMeshOverride -= HandleRender;
 			skeletonRenderer.GenerateMeshOverride -= HandleRender;
 			#endif
 			#endif
 
 
-			#if UNITY_EDITOR
 			skeletonRenderer.LateUpdate();
 			skeletonRenderer.LateUpdate();
-			#endif
 
 
 			foreach (var s in partsRenderers)
 			foreach (var s in partsRenderers)
 				s.ClearMesh();		
 				s.ClearMesh();		
@@ -189,7 +197,6 @@ namespace Spine.Unity.Modules {
 				calculateTangents = skeletonRenderer.calculateTangents,
 				calculateTangents = skeletonRenderer.calculateTangents,
 				immutableTriangles = false, // parts cannot do immutable triangles.
 				immutableTriangles = false, // parts cannot do immutable triangles.
 				pmaVertexColors = skeletonRenderer.pmaVertexColors,
 				pmaVertexColors = skeletonRenderer.pmaVertexColors,
-				//renderMeshes = skeletonRenderer.renderMeshes,
 				tintBlack = skeletonRenderer.tintBlack,
 				tintBlack = skeletonRenderer.tintBlack,
 				useClipping = true,
 				useClipping = true,
 				zSpacing = skeletonRenderer.zSpacing
 				zSpacing = skeletonRenderer.zSpacing

+ 5 - 0
spine-unity/Assets/Spine/Runtime/spine-unity/SkeletonUtility/SkeletonUtility.cs

@@ -136,6 +136,11 @@ namespace Spine.Unity {
 		bool hasConstraints;
 		bool hasConstraints;
 		bool needToReprocessBones;
 		bool needToReprocessBones;
 
 
+		public void ResubscribeEvents () {
+			OnDisable();
+			OnEnable();
+		}
+		
 		void OnEnable () {
 		void OnEnable () {
 			if (skeletonRenderer == null) {
 			if (skeletonRenderer == null) {
 				skeletonRenderer = GetComponent<SkeletonRenderer>();
 				skeletonRenderer = GetComponent<SkeletonRenderer>();

+ 15 - 14
spine-unity/Assets/Spine/Runtime/spine-unity/SkeletonUtility/SkeletonUtilityBone.cs

@@ -141,23 +141,24 @@ namespace Spine.Unity {
 						// Use Applied transform values (ax, ay, AppliedRotation, ascale) if world values were modified by constraints.
 						// Use Applied transform values (ax, ay, AppliedRotation, ascale) if world values were modified by constraints.
 						if (!bone.appliedValid) {
 						if (!bone.appliedValid) {
 							bone.UpdateAppliedTransform();
 							bone.UpdateAppliedTransform();
-							if (position)
-								thisTransform.localPosition = new Vector3(bone.ax, bone.ay, 0);
-
-							if (rotation) {
-								if (bone.data.transformMode.InheritsRotation()) {
-									thisTransform.localRotation = Quaternion.Euler(0, 0, bone.AppliedRotation);
-								} else {
-									Vector3 euler = skeletonTransform.rotation.eulerAngles;
-									thisTransform.rotation = Quaternion.Euler(euler.x, euler.y, euler.z + (bone.WorldRotationX * skeletonFlipRotation));
-								}
-							}
+						}
+
+						if (position)
+							thisTransform.localPosition = new Vector3(bone.ax, bone.ay, 0);
 
 
-							if (scale) {
-								thisTransform.localScale = new Vector3(bone.ascaleX, bone.ascaleY, 1f);
-								incompatibleTransformMode = BoneTransformModeIncompatible(bone);
+						if (rotation) {
+							if (bone.data.transformMode.InheritsRotation()) {
+								thisTransform.localRotation = Quaternion.Euler(0, 0, bone.AppliedRotation);
+							} else {
+								Vector3 euler = skeletonTransform.rotation.eulerAngles;
+								thisTransform.rotation = Quaternion.Euler(euler.x, euler.y, euler.z + (bone.WorldRotationX * skeletonFlipRotation));
 							}
 							}
 						}
 						}
+
+						if (scale) {
+							thisTransform.localScale = new Vector3(bone.ascaleX, bone.ascaleY, 1f);
+							incompatibleTransformMode = BoneTransformModeIncompatible(bone);
+						}
 						break;
 						break;
 				}
 				}
 				
 				

部分文件因文件數量過多而無法顯示