增加线程安全

This commit is contained in:
ww-rm
2025-03-31 01:44:41 +08:00
parent 4654d1d9c2
commit 4b07e02acb
8 changed files with 257 additions and 228 deletions

View File

@@ -92,7 +92,7 @@ namespace SpineViewer.Spine.Implementations.Spine
public override string FileVersion { get => skeletonData.Version; } public override string FileVersion { get => skeletonData.Version; }
public override float Scale protected override float scale
{ {
get get
{ {
@@ -106,11 +106,11 @@ namespace SpineViewer.Spine.Implementations.Spine
set set
{ {
// 保存状态 // 保存状态
var position = Position; var pos = position;
var flipX = FlipX; var fX = flipX;
var flipY = FlipY; var fY = flipY;
var animation = Track0Animation; // TODO: 适配多轨道 var animation = track0Animation; // TODO: 适配多轨道
var skin = Skin; var sk = skin;
var val = Math.Max(value, SCALE_MIN); var val = Math.Max(value, SCALE_MIN);
if (skeletonBinary is not null) if (skeletonBinary is not null)
@@ -130,38 +130,37 @@ namespace SpineViewer.Spine.Implementations.Spine
animationState = new AnimationState(animationStateData); animationState = new AnimationState(animationStateData);
// 恢复状态 // 恢复状态
Position = position; position = pos;
FlipX = flipX; flipX = fX;
FlipY = flipY; flipY = fY;
Track0Animation = animation; // TODO: 适配多轨道 track0Animation = animation; // TODO: 适配多轨道
Skin = skin; skin = sk;
} }
} }
public override PointF Position protected override PointF position
{ {
get => new(skeleton.X, skeleton.Y); get => new(skeleton.X, skeleton.Y);
set set
{ {
skeleton.X = value.X; skeleton.X = value.X;
skeleton.Y = value.Y; skeleton.Y = value.Y;
Update(0); }
}
} }
public override bool FlipX protected override bool flipX
{ {
get => skeleton.FlipX; get => skeleton.FlipX;
set { skeleton.FlipX = value; Update(0); } set => skeleton.FlipX = value;
} }
public override bool FlipY protected override bool flipY
{ {
get => skeleton.FlipY; get => skeleton.FlipY;
set { skeleton.FlipY = value; Update(0); } set => skeleton.FlipY = value;
} }
public override string Skin protected override string skin
{ {
get => skeleton.Skin?.Name ?? "default"; get => skeleton.Skin?.Name ?? "default";
set set
@@ -169,11 +168,10 @@ namespace SpineViewer.Spine.Implementations.Spine
if (!skinNames.Contains(value)) return; if (!skinNames.Contains(value)) return;
skeleton.SetSkin(value); skeleton.SetSkin(value);
skeleton.SetSlotsToSetupPose(); skeleton.SetSlotsToSetupPose();
Update(0);
} }
} }
public override string Track0Animation protected override string track0Animation
{ {
get => animationState.GetCurrent(0)?.Animation.Name ?? EMPTY_ANIMATION; get => animationState.GetCurrent(0)?.Animation.Name ?? EMPTY_ANIMATION;
set set
@@ -182,11 +180,10 @@ namespace SpineViewer.Spine.Implementations.Spine
animationState.SetAnimation(0, EmptyAnimation, false); animationState.SetAnimation(0, EmptyAnimation, false);
else if (animationNames.Contains(value)) else if (animationNames.Contains(value))
animationState.SetAnimation(0, value, true); animationState.SetAnimation(0, value, true);
Update(0);
} }
} }
public override RectangleF Bounds protected override RectangleF bounds
{ {
get get
{ {
@@ -238,7 +235,7 @@ namespace SpineViewer.Spine.Implementations.Spine
public override float GetAnimationDuration(string name) { return skeletonData.FindAnimation(name)?.Duration ?? 0f; } public override float GetAnimationDuration(string name) { return skeletonData.FindAnimation(name)?.Duration ?? 0f; }
public override void Update(float delta) protected override void update(float delta)
{ {
animationState.Update(delta); animationState.Update(delta);
animationState.Apply(skeleton); animationState.Apply(skeleton);
@@ -258,7 +255,7 @@ namespace SpineViewer.Spine.Implementations.Spine
// }; // };
//} //}
public override void Draw(SFML.Graphics.RenderTarget target, SFML.Graphics.RenderStates states) protected override void draw(SFML.Graphics.RenderTarget target, SFML.Graphics.RenderStates states)
{ {
vertexArray.Clear(); vertexArray.Clear();
states.Texture = null; states.Texture = null;
@@ -330,13 +327,13 @@ namespace SpineViewer.Spine.Implementations.Spine
{ {
if (vertexArray.VertexCount > 0) if (vertexArray.VertexCount > 0)
{ {
if (UsePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive)) if (usePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive))
states.Shader = Shader.FragmentShader; states.Shader = Shader.FragmentShader;
else else
states.Shader = null; states.Shader = null;
// 调试纹理 // 调试纹理
if (!IsDebug || DebugTexture) if (!isDebug || debugTexture)
target.Draw(vertexArray, states); target.Draw(vertexArray, states);
vertexArray.Clear(); vertexArray.Clear();
@@ -379,24 +376,24 @@ namespace SpineViewer.Spine.Implementations.Spine
//clipping.ClipEnd(slot); //clipping.ClipEnd(slot);
} }
if (UsePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive)) if (usePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive))
states.Shader = Shader.FragmentShader; states.Shader = Shader.FragmentShader;
else else
states.Shader = null; states.Shader = null;
//clipping.ClipEnd(); //clipping.ClipEnd();
// 调试纹理 // 调试纹理
if (!IsDebug || DebugTexture) if (!isDebug || debugTexture)
target.Draw(vertexArray, states); target.Draw(vertexArray, states);
// 包围盒 // 包围盒
if (IsDebug && IsSelected && DebugBounds) if (isDebug && isSelected && debugBounds)
{ {
var bounds = Bounds; var b = bounds;
boundsVertices[0] = boundsVertices[4] = new(new(bounds.Left, bounds.Top), BoundsColor); boundsVertices[0] = boundsVertices[4] = new(new(b.Left, b.Top), BoundsColor);
boundsVertices[1] = new(new(bounds.Right, bounds.Top), BoundsColor); boundsVertices[1] = new(new(b.Right, b.Top), BoundsColor);
boundsVertices[2] = new(new(bounds.Right, bounds.Bottom), BoundsColor); boundsVertices[2] = new(new(b.Right, b.Bottom), BoundsColor);
boundsVertices[3] = new(new(bounds.Left, bounds.Bottom), BoundsColor); boundsVertices[3] = new(new(b.Left, b.Bottom), BoundsColor);
target.Draw(boundsVertices); target.Draw(boundsVertices);
} }
} }

View File

@@ -91,7 +91,7 @@ namespace SpineViewer.Spine.Implementations.Spine
public override string FileVersion { get => skeletonData.Version; } public override string FileVersion { get => skeletonData.Version; }
public override float Scale protected override float scale
{ {
get get
{ {
@@ -105,11 +105,11 @@ namespace SpineViewer.Spine.Implementations.Spine
set set
{ {
// 保存状态 // 保存状态
var position = Position; var pos = position;
var flipX = FlipX; var fX = flipX;
var flipY = FlipY; var fY = flipY;
var animation = Track0Animation; // TODO: 适配多轨道 var animation = track0Animation; // TODO: 适配多轨道
var skin = Skin; var sk = skin;
var val = Math.Max(value, SCALE_MIN); var val = Math.Max(value, SCALE_MIN);
if (skeletonBinary is not null) if (skeletonBinary is not null)
@@ -129,38 +129,37 @@ namespace SpineViewer.Spine.Implementations.Spine
animationState = new AnimationState(animationStateData); animationState = new AnimationState(animationStateData);
// 恢复状态 // 恢复状态
Position = position; position = pos;
FlipX = flipX; flipX = fX;
FlipY = flipY; flipY = fY;
Track0Animation = animation; // TODO: 适配多轨道 track0Animation = animation; // TODO: 适配多轨道
Skin = skin; skin = sk;
} }
} }
public override PointF Position protected override PointF position
{ {
get => new(skeleton.X, skeleton.Y); get => new(skeleton.X, skeleton.Y);
set set
{ {
skeleton.X = value.X; skeleton.X = value.X;
skeleton.Y = value.Y; skeleton.Y = value.Y;
Update(0);
} }
} }
public override bool FlipX protected override bool flipX
{ {
get => skeleton.FlipX; get => skeleton.FlipX;
set { skeleton.FlipX = value; Update(0); } set => skeleton.FlipX = value;
} }
public override bool FlipY protected override bool flipY
{ {
get => skeleton.FlipY; get => skeleton.FlipY;
set { skeleton.FlipY = value; Update(0); } set => skeleton.FlipY = value;
} }
public override string Skin protected override string skin
{ {
get => skeleton.Skin?.Name ?? "default"; get => skeleton.Skin?.Name ?? "default";
set set
@@ -168,11 +167,10 @@ namespace SpineViewer.Spine.Implementations.Spine
if (!skinNames.Contains(value)) return; if (!skinNames.Contains(value)) return;
skeleton.SetSkin(value); skeleton.SetSkin(value);
skeleton.SetSlotsToSetupPose(); skeleton.SetSlotsToSetupPose();
Update(0);
} }
} }
public override string Track0Animation protected override string track0Animation
{ {
get => animationState.GetCurrent(0)?.Animation.Name ?? EMPTY_ANIMATION; get => animationState.GetCurrent(0)?.Animation.Name ?? EMPTY_ANIMATION;
set set
@@ -181,11 +179,10 @@ namespace SpineViewer.Spine.Implementations.Spine
animationState.SetAnimation(0, EmptyAnimation, false); animationState.SetAnimation(0, EmptyAnimation, false);
else if (animationNames.Contains(value)) else if (animationNames.Contains(value))
animationState.SetAnimation(0, value, true); animationState.SetAnimation(0, value, true);
Update(0);
} }
} }
public override RectangleF Bounds protected override RectangleF bounds
{ {
get get
{ {
@@ -197,7 +194,7 @@ namespace SpineViewer.Spine.Implementations.Spine
public override float GetAnimationDuration(string name) { return skeletonData.FindAnimation(name)?.Duration ?? 0f; } public override float GetAnimationDuration(string name) { return skeletonData.FindAnimation(name)?.Duration ?? 0f; }
public override void Update(float delta) protected override void update(float delta)
{ {
animationState.Update(delta); animationState.Update(delta);
animationState.Apply(skeleton); animationState.Apply(skeleton);
@@ -217,7 +214,7 @@ namespace SpineViewer.Spine.Implementations.Spine
}; };
} }
public override void Draw(SFML.Graphics.RenderTarget target, SFML.Graphics.RenderStates states) protected override void draw(SFML.Graphics.RenderTarget target, SFML.Graphics.RenderStates states)
{ {
vertexArray.Clear(); vertexArray.Clear();
states.Texture = null; states.Texture = null;
@@ -287,13 +284,13 @@ namespace SpineViewer.Spine.Implementations.Spine
{ {
if (vertexArray.VertexCount > 0) if (vertexArray.VertexCount > 0)
{ {
if (UsePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive)) if (usePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive))
states.Shader = Shader.FragmentShader; states.Shader = Shader.FragmentShader;
else else
states.Shader = null; states.Shader = null;
// 调试纹理 // 调试纹理
if (!IsDebug || DebugTexture) if (!isDebug || debugTexture)
target.Draw(vertexArray, states); target.Draw(vertexArray, states);
vertexArray.Clear(); vertexArray.Clear();
@@ -337,23 +334,23 @@ namespace SpineViewer.Spine.Implementations.Spine
} }
clipping.ClipEnd(); clipping.ClipEnd();
if (UsePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive)) if (usePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive))
states.Shader = Shader.FragmentShader; states.Shader = Shader.FragmentShader;
else else
states.Shader = null; states.Shader = null;
// 调试纹理 // 调试纹理
if (!IsDebug || DebugTexture) if (!isDebug || debugTexture)
target.Draw(vertexArray, states); target.Draw(vertexArray, states);
// 包围盒 // 包围盒
if (IsDebug && IsSelected && DebugBounds) if (isDebug && isSelected && debugBounds)
{ {
var bounds = Bounds; var b = bounds;
boundsVertices[0] = boundsVertices[4] = new(new(bounds.Left, bounds.Top), BoundsColor); boundsVertices[0] = boundsVertices[4] = new(new(b.Left, b.Top), BoundsColor);
boundsVertices[1] = new(new(bounds.Right, bounds.Top), BoundsColor); boundsVertices[1] = new(new(b.Right, b.Top), BoundsColor);
boundsVertices[2] = new(new(bounds.Right, bounds.Bottom), BoundsColor); boundsVertices[2] = new(new(b.Right, b.Bottom), BoundsColor);
boundsVertices[3] = new(new(bounds.Left, bounds.Bottom), BoundsColor); boundsVertices[3] = new(new(b.Left, b.Bottom), BoundsColor);
target.Draw(boundsVertices); target.Draw(boundsVertices);
} }
} }

View File

@@ -89,51 +89,47 @@ namespace SpineViewer.Spine.Implementations.Spine
public override string FileVersion { get => skeletonData.Version; } public override string FileVersion { get => skeletonData.Version; }
public override float Scale protected override float scale
{ {
get => Math.Abs(skeleton.ScaleX); get => Math.Abs(skeleton.ScaleX);
set set
{ {
skeleton.ScaleX = Math.Sign(skeleton.ScaleX) * value; skeleton.ScaleX = Math.Sign(skeleton.ScaleX) * value;
skeleton.ScaleY = Math.Sign(skeleton.ScaleY) * value; skeleton.ScaleY = Math.Sign(skeleton.ScaleY) * value;
Update(0);
} }
} }
public override PointF Position protected override PointF position
{ {
get => new(skeleton.X, skeleton.Y); get => new(skeleton.X, skeleton.Y);
set set
{ {
skeleton.X = value.X; skeleton.X = value.X;
skeleton.Y = value.Y; skeleton.Y = value.Y;
Update(0);
} }
} }
public override bool FlipX protected override bool flipX
{ {
get => skeleton.ScaleX < 0; get => skeleton.ScaleX < 0;
set set
{ {
if (skeleton.ScaleX > 0 && value || skeleton.ScaleX < 0 && !value) if (skeleton.ScaleX > 0 && value || skeleton.ScaleX < 0 && !value)
skeleton.ScaleX *= -1; skeleton.ScaleX *= -1;
Update(0);
} }
} }
public override bool FlipY protected override bool flipY
{ {
get => skeleton.ScaleY < 0; get => skeleton.ScaleY < 0;
set set
{ {
if (skeleton.ScaleY > 0 && value || skeleton.ScaleY < 0 && !value) if (skeleton.ScaleY > 0 && value || skeleton.ScaleY < 0 && !value)
skeleton.ScaleY *= -1; skeleton.ScaleY *= -1;
Update(0);
} }
} }
public override string Skin protected override string skin
{ {
get => skeleton.Skin?.Name ?? "default"; get => skeleton.Skin?.Name ?? "default";
set set
@@ -141,11 +137,10 @@ namespace SpineViewer.Spine.Implementations.Spine
if (!skinNames.Contains(value)) return; if (!skinNames.Contains(value)) return;
skeleton.SetSkin(value); skeleton.SetSkin(value);
skeleton.SetSlotsToSetupPose(); skeleton.SetSlotsToSetupPose();
Update(0);
} }
} }
public override string Track0Animation protected override string track0Animation
{ {
get => animationState.GetCurrent(0)?.Animation.Name ?? EMPTY_ANIMATION; get => animationState.GetCurrent(0)?.Animation.Name ?? EMPTY_ANIMATION;
set set
@@ -154,11 +149,10 @@ namespace SpineViewer.Spine.Implementations.Spine
animationState.SetAnimation(0, EmptyAnimation, false); animationState.SetAnimation(0, EmptyAnimation, false);
else if (animationNames.Contains(value)) else if (animationNames.Contains(value))
animationState.SetAnimation(0, value, true); animationState.SetAnimation(0, value, true);
Update(0);
} }
} }
public override RectangleF Bounds protected override RectangleF bounds
{ {
get get
{ {
@@ -170,7 +164,7 @@ namespace SpineViewer.Spine.Implementations.Spine
public override float GetAnimationDuration(string name) { return skeletonData.FindAnimation(name)?.Duration ?? 0f; } public override float GetAnimationDuration(string name) { return skeletonData.FindAnimation(name)?.Duration ?? 0f; }
public override void Update(float delta) protected override void update(float delta)
{ {
animationState.Update(delta); animationState.Update(delta);
animationState.Apply(skeleton); animationState.Apply(skeleton);
@@ -190,7 +184,7 @@ namespace SpineViewer.Spine.Implementations.Spine
}; };
} }
public override void Draw(SFML.Graphics.RenderTarget target, SFML.Graphics.RenderStates states) protected override void draw(SFML.Graphics.RenderTarget target, SFML.Graphics.RenderStates states)
{ {
vertexArray.Clear(); vertexArray.Clear();
states.Texture = null; states.Texture = null;
@@ -261,13 +255,13 @@ namespace SpineViewer.Spine.Implementations.Spine
if (vertexArray.VertexCount > 0) if (vertexArray.VertexCount > 0)
{ {
// XXX: 实测不用设置 sampler2D 的值也正确 // XXX: 实测不用设置 sampler2D 的值也正确
if (UsePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive)) if (usePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive))
states.Shader = Shader.FragmentShader; states.Shader = Shader.FragmentShader;
else else
states.Shader = null; states.Shader = null;
// 调试纹理 // 调试纹理
if (!IsDebug || DebugTexture) if (!isDebug || debugTexture)
target.Draw(vertexArray, states); target.Draw(vertexArray, states);
vertexArray.Clear(); vertexArray.Clear();
@@ -311,23 +305,23 @@ namespace SpineViewer.Spine.Implementations.Spine
} }
clipping.ClipEnd(); clipping.ClipEnd();
if (UsePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive)) if (usePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive))
states.Shader = Shader.FragmentShader; states.Shader = Shader.FragmentShader;
else else
states.Shader = null; states.Shader = null;
// 调试纹理 // 调试纹理
if (!IsDebug || DebugTexture) if (!isDebug || debugTexture)
target.Draw(vertexArray, states); target.Draw(vertexArray, states);
// 包围盒 // 包围盒
if (IsDebug && IsSelected && DebugBounds) if (isDebug && isSelected && debugBounds)
{ {
var bounds = Bounds; var b = bounds;
boundsVertices[0] = boundsVertices[4] = new(new(bounds.Left, bounds.Top), BoundsColor); boundsVertices[0] = boundsVertices[4] = new(new(b.Left, b.Top), BoundsColor);
boundsVertices[1] = new(new(bounds.Right, bounds.Top), BoundsColor); boundsVertices[1] = new(new(b.Right, b.Top), BoundsColor);
boundsVertices[2] = new(new(bounds.Right, bounds.Bottom), BoundsColor); boundsVertices[2] = new(new(b.Right, b.Bottom), BoundsColor);
boundsVertices[3] = new(new(bounds.Left, bounds.Bottom), BoundsColor); boundsVertices[3] = new(new(b.Left, b.Bottom), BoundsColor);
target.Draw(boundsVertices); target.Draw(boundsVertices);
} }
} }

View File

@@ -95,51 +95,47 @@ namespace SpineViewer.Spine.Implementations.Spine
public override string FileVersion { get => skeletonData.Version; } public override string FileVersion { get => skeletonData.Version; }
public override float Scale protected override float scale
{ {
get => Math.Abs(skeleton.ScaleX); get => Math.Abs(skeleton.ScaleX);
set set
{ {
skeleton.ScaleX = Math.Sign(skeleton.ScaleX) * value; skeleton.ScaleX = Math.Sign(skeleton.ScaleX) * value;
skeleton.ScaleY = Math.Sign(skeleton.ScaleY) * value; skeleton.ScaleY = Math.Sign(skeleton.ScaleY) * value;
Update(0);
} }
} }
public override PointF Position protected override PointF position
{ {
get => new(skeleton.X, skeleton.Y); get => new(skeleton.X, skeleton.Y);
set set
{ {
skeleton.X = value.X; skeleton.X = value.X;
skeleton.Y = value.Y; skeleton.Y = value.Y;
Update(0);
} }
} }
public override bool FlipX protected override bool flipX
{ {
get => skeleton.ScaleX < 0; get => skeleton.ScaleX < 0;
set set
{ {
if (skeleton.ScaleX > 0 && value || skeleton.ScaleX < 0 && !value) if (skeleton.ScaleX > 0 && value || skeleton.ScaleX < 0 && !value)
skeleton.ScaleX *= -1; skeleton.ScaleX *= -1;
Update(0);
} }
} }
public override bool FlipY protected override bool flipY
{ {
get => skeleton.ScaleY < 0; get => skeleton.ScaleY < 0;
set set
{ {
if (skeleton.ScaleY > 0 && value || skeleton.ScaleY < 0 && !value) if (skeleton.ScaleY > 0 && value || skeleton.ScaleY < 0 && !value)
skeleton.ScaleY *= -1; skeleton.ScaleY *= -1;
Update(0);
} }
} }
public override string Skin protected override string skin
{ {
get => skeleton.Skin?.Name ?? "default"; get => skeleton.Skin?.Name ?? "default";
set set
@@ -147,11 +143,10 @@ namespace SpineViewer.Spine.Implementations.Spine
if (!skinNames.Contains(value)) return; if (!skinNames.Contains(value)) return;
skeleton.SetSkin(value); skeleton.SetSkin(value);
skeleton.SetSlotsToSetupPose(); skeleton.SetSlotsToSetupPose();
Update(0);
} }
} }
public override string Track0Animation protected override string track0Animation
{ {
get => animationState.GetCurrent(0)?.Animation.Name ?? EMPTY_ANIMATION; get => animationState.GetCurrent(0)?.Animation.Name ?? EMPTY_ANIMATION;
set set
@@ -160,11 +155,10 @@ namespace SpineViewer.Spine.Implementations.Spine
animationState.SetAnimation(0, EmptyAnimation, false); animationState.SetAnimation(0, EmptyAnimation, false);
else if (animationNames.Contains(value)) else if (animationNames.Contains(value))
animationState.SetAnimation(0, value, true); animationState.SetAnimation(0, value, true);
Update(0);
} }
} }
public override RectangleF Bounds protected override RectangleF bounds
{ {
get get
{ {
@@ -176,7 +170,7 @@ namespace SpineViewer.Spine.Implementations.Spine
public override float GetAnimationDuration(string name) { return skeletonData.FindAnimation(name)?.Duration ?? 0f; } public override float GetAnimationDuration(string name) { return skeletonData.FindAnimation(name)?.Duration ?? 0f; }
public override void Update(float delta) protected override void update(float delta)
{ {
animationState.Update(delta); animationState.Update(delta);
animationState.Apply(skeleton); animationState.Apply(skeleton);
@@ -196,7 +190,7 @@ namespace SpineViewer.Spine.Implementations.Spine
}; };
} }
public override void Draw(SFML.Graphics.RenderTarget target, SFML.Graphics.RenderStates states) protected override void draw(SFML.Graphics.RenderTarget target, SFML.Graphics.RenderStates states)
{ {
vertexArray.Clear(); vertexArray.Clear();
states.Texture = null; states.Texture = null;
@@ -267,13 +261,13 @@ namespace SpineViewer.Spine.Implementations.Spine
if (vertexArray.VertexCount > 0) if (vertexArray.VertexCount > 0)
{ {
// XXX: 实测不用设置 sampler2D 的值也正确 // XXX: 实测不用设置 sampler2D 的值也正确
if (UsePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive)) if (usePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive))
states.Shader = Shader.FragmentShader; states.Shader = Shader.FragmentShader;
else else
states.Shader = null; states.Shader = null;
// 调试纹理 // 调试纹理
if (!IsDebug || DebugTexture) if (!isDebug || debugTexture)
target.Draw(vertexArray, states); target.Draw(vertexArray, states);
vertexArray.Clear(); vertexArray.Clear();
@@ -317,23 +311,23 @@ namespace SpineViewer.Spine.Implementations.Spine
} }
clipping.ClipEnd(); clipping.ClipEnd();
if (UsePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive)) if (usePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive))
states.Shader = Shader.FragmentShader; states.Shader = Shader.FragmentShader;
else else
states.Shader = null; states.Shader = null;
// 调试纹理 // 调试纹理
if (!IsDebug || DebugTexture) if (!isDebug || debugTexture)
target.Draw(vertexArray, states); target.Draw(vertexArray, states);
// 调试包围盒 // 调试包围盒
if (IsDebug && IsSelected && DebugBounds) if (isDebug && isSelected && debugBounds)
{ {
var bounds = Bounds; var b = bounds;
boundsVertices[0] = boundsVertices[4] = new(new(bounds.Left, bounds.Top), BoundsColor); boundsVertices[0] = boundsVertices[4] = new(new(b.Left, b.Top), BoundsColor);
boundsVertices[1] = new(new(bounds.Right, bounds.Top), BoundsColor); boundsVertices[1] = new(new(b.Right, b.Top), BoundsColor);
boundsVertices[2] = new(new(bounds.Right, bounds.Bottom), BoundsColor); boundsVertices[2] = new(new(b.Right, b.Bottom), BoundsColor);
boundsVertices[3] = new(new(bounds.Left, bounds.Bottom), BoundsColor); boundsVertices[3] = new(new(b.Left, b.Bottom), BoundsColor);
target.Draw(boundsVertices); target.Draw(boundsVertices);
} }
} }

View File

@@ -91,51 +91,47 @@ namespace SpineViewer.Spine.Implementations.Spine
public override string FileVersion { get => skeletonData.Version; } public override string FileVersion { get => skeletonData.Version; }
public override float Scale protected override float scale
{ {
get => Math.Abs(skeleton.ScaleX); get => Math.Abs(skeleton.ScaleX);
set set
{ {
skeleton.ScaleX = Math.Sign(skeleton.ScaleX) * value; skeleton.ScaleX = Math.Sign(skeleton.ScaleX) * value;
skeleton.ScaleY = Math.Sign(skeleton.ScaleY) * value; skeleton.ScaleY = Math.Sign(skeleton.ScaleY) * value;
Update(0);
} }
} }
public override PointF Position protected override PointF position
{ {
get => new(skeleton.X, skeleton.Y); get => new(skeleton.X, skeleton.Y);
set set
{ {
skeleton.X = value.X; skeleton.X = value.X;
skeleton.Y = value.Y; skeleton.Y = value.Y;
Update(0);
} }
} }
public override bool FlipX protected override bool flipX
{ {
get => skeleton.ScaleX < 0; get => skeleton.ScaleX < 0;
set set
{ {
if (skeleton.ScaleX > 0 && value || skeleton.ScaleX < 0 && !value) if (skeleton.ScaleX > 0 && value || skeleton.ScaleX < 0 && !value)
skeleton.ScaleX *= -1; skeleton.ScaleX *= -1;
Update(0);
} }
} }
public override bool FlipY protected override bool flipY
{ {
get => skeleton.ScaleY < 0; get => skeleton.ScaleY < 0;
set set
{ {
if (skeleton.ScaleY > 0 && value || skeleton.ScaleY < 0 && !value) if (skeleton.ScaleY > 0 && value || skeleton.ScaleY < 0 && !value)
skeleton.ScaleY *= -1; skeleton.ScaleY *= -1;
Update(0);
} }
} }
public override string Skin protected override string skin
{ {
get => skeleton.Skin?.Name ?? "default"; get => skeleton.Skin?.Name ?? "default";
set set
@@ -143,11 +139,10 @@ namespace SpineViewer.Spine.Implementations.Spine
if (!skinNames.Contains(value)) return; if (!skinNames.Contains(value)) return;
skeleton.SetSkin(value); skeleton.SetSkin(value);
skeleton.SetSlotsToSetupPose(); skeleton.SetSlotsToSetupPose();
Update(0);
} }
} }
public override string Track0Animation protected override string track0Animation
{ {
get => animationState.GetCurrent(0)?.Animation.Name ?? EMPTY_ANIMATION; get => animationState.GetCurrent(0)?.Animation.Name ?? EMPTY_ANIMATION;
set set
@@ -156,11 +151,10 @@ namespace SpineViewer.Spine.Implementations.Spine
animationState.SetAnimation(0, EmptyAnimation, false); animationState.SetAnimation(0, EmptyAnimation, false);
else if (animationNames.Contains(value)) else if (animationNames.Contains(value))
animationState.SetAnimation(0, value, true); animationState.SetAnimation(0, value, true);
Update(0);
} }
} }
public override RectangleF Bounds protected override RectangleF bounds
{ {
get get
{ {
@@ -172,7 +166,7 @@ namespace SpineViewer.Spine.Implementations.Spine
public override float GetAnimationDuration(string name) { return skeletonData.FindAnimation(name)?.Duration ?? 0f; } public override float GetAnimationDuration(string name) { return skeletonData.FindAnimation(name)?.Duration ?? 0f; }
public override void Update(float delta) protected override void update(float delta)
{ {
animationState.Update(delta); animationState.Update(delta);
animationState.Apply(skeleton); animationState.Apply(skeleton);
@@ -192,7 +186,7 @@ namespace SpineViewer.Spine.Implementations.Spine
}; };
} }
public override void Draw(SFML.Graphics.RenderTarget target, SFML.Graphics.RenderStates states) protected override void draw(SFML.Graphics.RenderTarget target, SFML.Graphics.RenderStates states)
{ {
vertexArray.Clear(); vertexArray.Clear();
states.Texture = null; states.Texture = null;
@@ -263,13 +257,13 @@ namespace SpineViewer.Spine.Implementations.Spine
if (vertexArray.VertexCount > 0) if (vertexArray.VertexCount > 0)
{ {
// XXX: 实测不用设置 sampler2D 的值也正确 // XXX: 实测不用设置 sampler2D 的值也正确
if (UsePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive)) if (usePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive))
states.Shader = Shader.FragmentShader; states.Shader = Shader.FragmentShader;
else else
states.Shader = null; states.Shader = null;
// 调试纹理 // 调试纹理
if (!IsDebug || DebugTexture) if (!isDebug || debugTexture)
target.Draw(vertexArray, states); target.Draw(vertexArray, states);
vertexArray.Clear(); vertexArray.Clear();
@@ -313,23 +307,23 @@ namespace SpineViewer.Spine.Implementations.Spine
} }
clipping.ClipEnd(); clipping.ClipEnd();
if (UsePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive)) if (usePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive))
states.Shader = Shader.FragmentShader; states.Shader = Shader.FragmentShader;
else else
states.Shader = null; states.Shader = null;
// 调试纹理 // 调试纹理
if (!IsDebug || DebugTexture) if (!isDebug || debugTexture)
target.Draw(vertexArray, states); target.Draw(vertexArray, states);
// 包围盒 // 包围盒
if (IsDebug && IsSelected && DebugBounds) if (isDebug && isSelected && debugBounds)
{ {
var bounds = Bounds; var b = bounds;
boundsVertices[0] = boundsVertices[4] = new(new(bounds.Left, bounds.Top), BoundsColor); boundsVertices[0] = boundsVertices[4] = new(new(b.Left, b.Top), BoundsColor);
boundsVertices[1] = new(new(bounds.Right, bounds.Top), BoundsColor); boundsVertices[1] = new(new(b.Right, b.Top), BoundsColor);
boundsVertices[2] = new(new(bounds.Right, bounds.Bottom), BoundsColor); boundsVertices[2] = new(new(b.Right, b.Bottom), BoundsColor);
boundsVertices[3] = new(new(bounds.Left, bounds.Bottom), BoundsColor); boundsVertices[3] = new(new(b.Left, b.Bottom), BoundsColor);
target.Draw(boundsVertices); target.Draw(boundsVertices);
} }
} }

View File

@@ -91,51 +91,47 @@ namespace SpineViewer.Spine.Implementations.Spine
public override string FileVersion { get => skeletonData.Version; } public override string FileVersion { get => skeletonData.Version; }
public override float Scale protected override float scale
{ {
get => Math.Abs(skeleton.ScaleX); get => Math.Abs(skeleton.ScaleX);
set set
{ {
skeleton.ScaleX = Math.Sign(skeleton.ScaleX) * value; skeleton.ScaleX = Math.Sign(skeleton.ScaleX) * value;
skeleton.ScaleY = Math.Sign(skeleton.ScaleY) * value; skeleton.ScaleY = Math.Sign(skeleton.ScaleY) * value;
Update(0);
} }
} }
public override PointF Position protected override PointF position
{ {
get => new(skeleton.X, skeleton.Y); get => new(skeleton.X, skeleton.Y);
set set
{ {
skeleton.X = value.X; skeleton.X = value.X;
skeleton.Y = value.Y; skeleton.Y = value.Y;
Update(0);
} }
} }
public override bool FlipX protected override bool flipX
{ {
get => skeleton.ScaleX < 0; get => skeleton.ScaleX < 0;
set set
{ {
if (skeleton.ScaleX > 0 && value || skeleton.ScaleX < 0 && !value) if (skeleton.ScaleX > 0 && value || skeleton.ScaleX < 0 && !value)
skeleton.ScaleX *= -1; skeleton.ScaleX *= -1;
Update(0);
} }
} }
public override bool FlipY protected override bool flipY
{ {
get => skeleton.ScaleY < 0; get => skeleton.ScaleY < 0;
set set
{ {
if (skeleton.ScaleY > 0 && value || skeleton.ScaleY < 0 && !value) if (skeleton.ScaleY > 0 && value || skeleton.ScaleY < 0 && !value)
skeleton.ScaleY *= -1; skeleton.ScaleY *= -1;
Update(0);
} }
} }
public override string Skin protected override string skin
{ {
get => skeleton.Skin?.Name ?? "default"; get => skeleton.Skin?.Name ?? "default";
set set
@@ -143,11 +139,10 @@ namespace SpineViewer.Spine.Implementations.Spine
if (!skinNames.Contains(value)) return; if (!skinNames.Contains(value)) return;
skeleton.SetSkin(value); skeleton.SetSkin(value);
skeleton.SetSlotsToSetupPose(); skeleton.SetSlotsToSetupPose();
Update(0);
} }
} }
public override string Track0Animation protected override string track0Animation
{ {
get => animationState.GetCurrent(0)?.Animation.Name ?? EMPTY_ANIMATION; get => animationState.GetCurrent(0)?.Animation.Name ?? EMPTY_ANIMATION;
set set
@@ -156,11 +151,10 @@ namespace SpineViewer.Spine.Implementations.Spine
animationState.SetAnimation(0, EmptyAnimation, false); animationState.SetAnimation(0, EmptyAnimation, false);
else if (animationNames.Contains(value)) else if (animationNames.Contains(value))
animationState.SetAnimation(0, value, true); animationState.SetAnimation(0, value, true);
Update(0);
} }
} }
public override RectangleF Bounds protected override RectangleF bounds
{ {
get get
{ {
@@ -172,7 +166,7 @@ namespace SpineViewer.Spine.Implementations.Spine
public override float GetAnimationDuration(string name) { return skeletonData.FindAnimation(name)?.Duration ?? 0f; } public override float GetAnimationDuration(string name) { return skeletonData.FindAnimation(name)?.Duration ?? 0f; }
public override void Update(float delta) protected override void update(float delta)
{ {
animationState.Update(delta); animationState.Update(delta);
animationState.Apply(skeleton); animationState.Apply(skeleton);
@@ -192,7 +186,7 @@ namespace SpineViewer.Spine.Implementations.Spine
}; };
} }
public override void Draw(SFML.Graphics.RenderTarget target, SFML.Graphics.RenderStates states) protected override void draw(SFML.Graphics.RenderTarget target, SFML.Graphics.RenderStates states)
{ {
vertexArray.Clear(); vertexArray.Clear();
states.Texture = null; states.Texture = null;
@@ -263,13 +257,13 @@ namespace SpineViewer.Spine.Implementations.Spine
if (vertexArray.VertexCount > 0) if (vertexArray.VertexCount > 0)
{ {
// XXX: 实测不用设置 sampler2D 的值也正确 // XXX: 实测不用设置 sampler2D 的值也正确
if (UsePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive)) if (usePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive))
states.Shader = Shader.FragmentShader; states.Shader = Shader.FragmentShader;
else else
states.Shader = null; states.Shader = null;
// 调试纹理 // 调试纹理
if (!IsDebug || DebugTexture) if (!isDebug || debugTexture)
target.Draw(vertexArray, states); target.Draw(vertexArray, states);
vertexArray.Clear(); vertexArray.Clear();
@@ -313,23 +307,23 @@ namespace SpineViewer.Spine.Implementations.Spine
} }
clipping.ClipEnd(); clipping.ClipEnd();
if (UsePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive)) if (usePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive))
states.Shader = Shader.FragmentShader; states.Shader = Shader.FragmentShader;
else else
states.Shader = null; states.Shader = null;
// 调试纹理 // 调试纹理
if (!IsDebug || DebugTexture) if (!isDebug || debugTexture)
target.Draw(vertexArray, states); target.Draw(vertexArray, states);
// 包围盒 // 包围盒
if (IsDebug && IsSelected && DebugBounds) if (isDebug && isSelected && debugBounds)
{ {
var bounds = Bounds; var b = bounds;
boundsVertices[0] = boundsVertices[4] = new(new(bounds.Left, bounds.Top), BoundsColor); boundsVertices[0] = boundsVertices[4] = new(new(b.Left, b.Top), BoundsColor);
boundsVertices[1] = new(new(bounds.Right, bounds.Top), BoundsColor); boundsVertices[1] = new(new(b.Right, b.Top), BoundsColor);
boundsVertices[2] = new(new(bounds.Right, bounds.Bottom), BoundsColor); boundsVertices[2] = new(new(b.Right, b.Bottom), BoundsColor);
boundsVertices[3] = new(new(bounds.Left, bounds.Bottom), BoundsColor); boundsVertices[3] = new(new(b.Left, b.Bottom), BoundsColor);
target.Draw(boundsVertices); target.Draw(boundsVertices);
} }
} }

View File

@@ -91,51 +91,47 @@ namespace SpineViewer.Spine.Implementations.Spine
public override string FileVersion { get => skeletonData.Version; } public override string FileVersion { get => skeletonData.Version; }
public override float Scale protected override float scale
{ {
get => Math.Abs(skeleton.ScaleX); get => Math.Abs(skeleton.ScaleX);
set set
{ {
skeleton.ScaleX = Math.Sign(skeleton.ScaleX) * value; skeleton.ScaleX = Math.Sign(skeleton.ScaleX) * value;
skeleton.ScaleY = Math.Sign(skeleton.ScaleY) * value; skeleton.ScaleY = Math.Sign(skeleton.ScaleY) * value;
Update(0);
} }
} }
public override PointF Position protected override PointF position
{ {
get => new(skeleton.X, skeleton.Y); get => new(skeleton.X, skeleton.Y);
set set
{ {
skeleton.X = value.X; skeleton.X = value.X;
skeleton.Y = value.Y; skeleton.Y = value.Y;
Update(0);
} }
} }
public override bool FlipX protected override bool flipX
{ {
get => skeleton.ScaleX < 0; get => skeleton.ScaleX < 0;
set set
{ {
if (skeleton.ScaleX > 0 && value || skeleton.ScaleX < 0 && !value) if (skeleton.ScaleX > 0 && value || skeleton.ScaleX < 0 && !value)
skeleton.ScaleX *= -1; skeleton.ScaleX *= -1;
Update(0);
} }
} }
public override bool FlipY protected override bool flipY
{ {
get => skeleton.ScaleY < 0; get => skeleton.ScaleY < 0;
set set
{ {
if (skeleton.ScaleY > 0 && value || skeleton.ScaleY < 0 && !value) if (skeleton.ScaleY > 0 && value || skeleton.ScaleY < 0 && !value)
skeleton.ScaleY *= -1; skeleton.ScaleY *= -1;
Update(0);
} }
} }
public override string Skin protected override string skin
{ {
get => skeleton.Skin?.Name ?? "default"; get => skeleton.Skin?.Name ?? "default";
set set
@@ -143,11 +139,10 @@ namespace SpineViewer.Spine.Implementations.Spine
if (!skinNames.Contains(value)) return; if (!skinNames.Contains(value)) return;
skeleton.SetSkin(value); skeleton.SetSkin(value);
skeleton.SetSlotsToSetupPose(); skeleton.SetSlotsToSetupPose();
Update(0);
} }
} }
public override string Track0Animation protected override string track0Animation
{ {
get => animationState.GetCurrent(0)?.Animation.Name ?? EMPTY_ANIMATION; get => animationState.GetCurrent(0)?.Animation.Name ?? EMPTY_ANIMATION;
set set
@@ -156,11 +151,10 @@ namespace SpineViewer.Spine.Implementations.Spine
animationState.SetAnimation(0, EmptyAnimation, false); animationState.SetAnimation(0, EmptyAnimation, false);
else if (animationNames.Contains(value)) else if (animationNames.Contains(value))
animationState.SetAnimation(0, value, true); animationState.SetAnimation(0, value, true);
Update(0);
} }
} }
public override RectangleF Bounds protected override RectangleF bounds
{ {
get get
{ {
@@ -172,7 +166,7 @@ namespace SpineViewer.Spine.Implementations.Spine
public override float GetAnimationDuration(string name) { return skeletonData.FindAnimation(name)?.Duration ?? 0f; } public override float GetAnimationDuration(string name) { return skeletonData.FindAnimation(name)?.Duration ?? 0f; }
public override void Update(float delta) protected override void update(float delta)
{ {
animationState.Update(delta); animationState.Update(delta);
animationState.Apply(skeleton); animationState.Apply(skeleton);
@@ -192,7 +186,7 @@ namespace SpineViewer.Spine.Implementations.Spine
}; };
} }
public override void Draw(SFML.Graphics.RenderTarget target, SFML.Graphics.RenderStates states) protected override void draw(SFML.Graphics.RenderTarget target, SFML.Graphics.RenderStates states)
{ {
vertexArray.Clear(); vertexArray.Clear();
states.Texture = null; states.Texture = null;
@@ -263,13 +257,13 @@ namespace SpineViewer.Spine.Implementations.Spine
if (vertexArray.VertexCount > 0) if (vertexArray.VertexCount > 0)
{ {
// XXX: 实测不用设置 sampler2D 的值也正确 // XXX: 实测不用设置 sampler2D 的值也正确
if (UsePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive)) if (usePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive))
states.Shader = Shader.FragmentShader; states.Shader = Shader.FragmentShader;
else else
states.Shader = null; states.Shader = null;
// 调试纹理 // 调试纹理
if (!IsDebug || DebugTexture) if (!isDebug || debugTexture)
target.Draw(vertexArray, states); target.Draw(vertexArray, states);
vertexArray.Clear(); vertexArray.Clear();
@@ -313,23 +307,23 @@ namespace SpineViewer.Spine.Implementations.Spine
} }
clipping.ClipEnd(); clipping.ClipEnd();
if (UsePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive)) if (usePremultipliedAlpha && (states.BlendMode == BlendModeSFML.Normal || states.BlendMode == BlendModeSFML.Additive))
states.Shader = Shader.FragmentShader; states.Shader = Shader.FragmentShader;
else else
states.Shader = null; states.Shader = null;
// 调试纹理 // 调试纹理
if (!IsDebug || DebugTexture) if (!isDebug || debugTexture)
target.Draw(vertexArray, states); target.Draw(vertexArray, states);
// 包围盒 // 包围盒
if (IsDebug && IsSelected && DebugBounds) if (isDebug && isSelected && debugBounds)
{ {
var bounds = Bounds; var b = bounds;
boundsVertices[0] = boundsVertices[4] = new(new(bounds.Left, bounds.Top), BoundsColor); boundsVertices[0] = boundsVertices[4] = new(new(b.Left, b.Top), BoundsColor);
boundsVertices[1] = new(new(bounds.Right, bounds.Top), BoundsColor); boundsVertices[1] = new(new(b.Right, b.Top), BoundsColor);
boundsVertices[2] = new(new(bounds.Right, bounds.Bottom), BoundsColor); boundsVertices[2] = new(new(b.Right, b.Bottom), BoundsColor);
boundsVertices[3] = new(new(bounds.Left, bounds.Bottom), BoundsColor); boundsVertices[3] = new(new(b.Left, b.Bottom), BoundsColor);
target.Draw(boundsVertices); target.Draw(boundsVertices);
} }
} }

View File

@@ -19,7 +19,7 @@ using SpineViewer.Exporter;
namespace SpineViewer.Spine namespace SpineViewer.Spine
{ {
/// <summary> /// <summary>
/// Spine 基类, 使用静态方法 New 来创建具体版本对象 /// Spine 基类, 使用静态方法 New 来创建具体版本对象, 该类是线程安全的
/// </summary> /// </summary>
public abstract class Spine : ImplementationResolver<Spine, SpineImplementationAttribute, SpineVersion>, SFML.Graphics.Drawable, IDisposable public abstract class Spine : ImplementationResolver<Spine, SpineImplementationAttribute, SpineVersion>, SFML.Graphics.Drawable, IDisposable
{ {
@@ -53,6 +53,11 @@ namespace SpineViewer.Spine
return New(version, [skelPath, atlasPath]).PostInit(); return New(version, [skelPath, atlasPath]).PostInit();
} }
/// <summary>
/// 数据锁
/// </summary>
private readonly object _lock = new();
/// <summary> /// <summary>
/// 构造函数 /// 构造函数
/// </summary> /// </summary>
@@ -74,9 +79,7 @@ namespace SpineViewer.Spine
AnimationNames = animationNames.AsReadOnly(); AnimationNames = animationNames.AsReadOnly();
// 必须 Update 一次否则包围盒还没有值 // 必须 Update 一次否则包围盒还没有值
Update(0); update(0);
InitBounds = Bounds;
// XXX: tex 没办法在这里主动 Dispose // XXX: tex 没办法在这里主动 Dispose
// 批量添加在获取预览图的时候极大概率会和预览线程死锁 // 批量添加在获取预览图的时候极大概率会和预览线程死锁
@@ -84,7 +87,7 @@ namespace SpineViewer.Spine
// 除此之外, 似乎还和 tex 的 Dispose 有关 // 除此之外, 似乎还和 tex 的 Dispose 有关
// 如果不对 tex 进行 Dispose, 那么不管是否 Draw 都正常不会死锁 // 如果不对 tex 进行 Dispose, 那么不管是否 Draw 都正常不会死锁
var tex = new SFML.Graphics.RenderTexture(PREVIEW_WIDTH, PREVIEW_HEIGHT); var tex = new SFML.Graphics.RenderTexture(PREVIEW_WIDTH, PREVIEW_HEIGHT);
tex.SetView(InitBounds.GetView(PREVIEW_WIDTH, PREVIEW_HEIGHT)); tex.SetView(bounds.GetView(PREVIEW_WIDTH, PREVIEW_HEIGHT));
tex.Clear(SFML.Graphics.Color.Transparent); tex.Clear(SFML.Graphics.Color.Transparent);
tex.Draw(this); tex.Draw(this);
tex.Display(); tex.Display();
@@ -101,8 +104,8 @@ namespace SpineViewer.Spine
} }
// 取最后一个作为初始, 尽可能去显示非默认的内容 // 取最后一个作为初始, 尽可能去显示非默认的内容
Skin = SkinNames.Last(); skin = SkinNames.Last();
Track0Animation = AnimationNames.Last(); track0Animation = AnimationNames.Last();
return this; return this;
} }
@@ -158,13 +161,23 @@ namespace SpineViewer.Spine
/// 是否被隐藏, 被隐藏的模型将仅仅在列表显示, 不参与其他行为 /// 是否被隐藏, 被隐藏的模型将仅仅在列表显示, 不参与其他行为
/// </summary> /// </summary>
[Category("[1] "), DisplayName("")] [Category("[1] "), DisplayName("")]
public bool IsHidden { get; set; } = false; public bool IsHidden
{
get { lock (_lock) return isHidden; }
set { lock (_lock) isHidden = value; }
}
protected bool isHidden = false;
/// <summary> /// <summary>
/// 是否使用预乘Alpha /// 是否使用预乘Alpha
/// </summary> /// </summary>
[Category("[1] "), DisplayName("Alpha通道")] [Category("[1] "), DisplayName("Alpha通道")]
public bool UsePremultipliedAlpha { get; set; } = true; public bool UsePremultipliedAlpha
{
get { lock (_lock) return usePremultipliedAlpha; }
set { lock (_lock) usePremultipliedAlpha = value; }
}
protected bool usePremultipliedAlpha = true;
#endregion #endregion
@@ -174,26 +187,46 @@ namespace SpineViewer.Spine
/// 缩放比例 /// 缩放比例
/// </summary> /// </summary>
[Category("[2] "), DisplayName("")] [Category("[2] "), DisplayName("")]
public abstract float Scale { get; set; } public float Scale
{
get { lock (_lock) return scale; }
set { lock (_lock) { scale = value; update(0); } }
}
protected abstract float scale { get; set; }
/// <summary> /// <summary>
/// 位置 /// 位置
/// </summary> /// </summary>
[TypeConverter(typeof(PointFConverter))] [TypeConverter(typeof(PointFConverter))]
[Category("[2] "), DisplayName("")] [Category("[2] "), DisplayName("")]
public abstract PointF Position { get; set; } public PointF Position
{
get { lock (_lock) return position; }
set { lock (_lock) { position = value; update(0); } }
}
protected abstract PointF position { get; set; }
/// <summary> /// <summary>
/// 水平翻转 /// 水平翻转
/// </summary> /// </summary>
[Category("[2] "), DisplayName("")] [Category("[2] "), DisplayName("")]
public abstract bool FlipX { get; set; } public bool FlipX
{
get { lock (_lock) return flipX; }
set { lock (_lock) { flipX = value; update(0); } }
}
protected abstract bool flipX { get; set; }
/// <summary> /// <summary>
/// 垂直翻转 /// 垂直翻转
/// </summary> /// </summary>
[Category("[2] "), DisplayName("")] [Category("[2] "), DisplayName("")]
public abstract bool FlipY { get; set; } public bool FlipY
{
get { lock (_lock) return flipY; }
set { lock (_lock) { flipY = value; update(0); } }
}
protected abstract bool flipY { get; set; }
#endregion #endregion
@@ -211,7 +244,12 @@ namespace SpineViewer.Spine
/// </summary> /// </summary>
[TypeConverter(typeof(SkinConverter))] [TypeConverter(typeof(SkinConverter))]
[Category("[3] "), DisplayName("")] [Category("[3] "), DisplayName("")]
public abstract string Skin { get; set; } public string Skin
{
get { lock (_lock) return skin; }
set { lock (_lock) { skin = value; update(0); } }
}
protected abstract string skin { get; set; }
/// <summary> /// <summary>
/// 包含的所有动画名称 /// 包含的所有动画名称
@@ -225,7 +263,12 @@ namespace SpineViewer.Spine
/// </summary> /// </summary>
[TypeConverter(typeof(AnimationConverter))] [TypeConverter(typeof(AnimationConverter))]
[Category("[3] "), DisplayName("")] [Category("[3] "), DisplayName("")]
public abstract string Track0Animation { get; set; } public string Track0Animation
{
get { lock (_lock) return track0Animation; }
set { lock (_lock) { track0Animation = value; update(0); } }
}
protected abstract string track0Animation { get; set; }
/// <summary> /// <summary>
/// 默认轨道动画时长 /// 默认轨道动画时长
@@ -241,25 +284,45 @@ namespace SpineViewer.Spine
/// 显示调试 /// 显示调试
/// </summary> /// </summary>
[Browsable(false)] [Browsable(false)]
public bool IsDebug { get; set; } = false; public bool IsDebug
{
get { lock (_lock) return isDebug; }
set { lock (_lock) isDebug = value; }
}
protected bool isDebug = false;
/// <summary> /// <summary>
/// 显示纹理 /// 显示纹理
/// </summary> /// </summary>
[Category("[4] "), DisplayName("")] [Category("[4] "), DisplayName("")]
public bool DebugTexture { get; set; } = true; public bool DebugTexture
{
get { lock (_lock) return debugTexture; }
set { lock (_lock) debugTexture = value; }
}
protected bool debugTexture = true;
/// <summary> /// <summary>
/// 显示包围盒 /// 显示包围盒
/// </summary> /// </summary>
[Category("[4] "), DisplayName("")] [Category("[4] "), DisplayName("")]
public bool DebugBounds { get; set; } = true; public bool DebugBounds
{
get { lock (_lock) return debugBounds; }
set { lock (_lock) debugBounds = value; }
}
protected bool debugBounds = true;
/// <summary> /// <summary>
/// 显示骨骼 /// 显示骨骼
/// </summary> /// </summary>
[Category("[4] "), DisplayName("")] [Category("[4] "), DisplayName("")]
public bool DebugBones { get; set; } = false; public bool DebugBones
{
get { lock (_lock) return debugBones; }
set { lock (_lock) debugBones = value; }
}
protected bool debugBones = false;
#endregion #endregion
@@ -272,19 +335,19 @@ namespace SpineViewer.Spine
/// 是否被选中 /// 是否被选中
/// </summary> /// </summary>
[Browsable(false)] [Browsable(false)]
public bool IsSelected { get; set; } = false; public bool IsSelected
{
get { lock (_lock) return isSelected; }
set { lock (_lock) isSelected = value; }
}
protected bool isSelected = false;
/// <summary> /// <summary>
/// 骨骼包围盒 /// 骨骼包围盒
/// </summary> /// </summary>
[Browsable(false)] [Browsable(false)]
public abstract RectangleF Bounds { get; } public RectangleF Bounds { get { lock (_lock) return bounds; } }
protected abstract RectangleF bounds { get; }
/// <summary>
/// 初始状态下的骨骼包围盒
/// </summary>
[Browsable(false)]
public RectangleF InitBounds { get; private set; }
/// <summary> /// <summary>
/// 骨骼预览图 /// 骨骼预览图
@@ -300,7 +363,8 @@ namespace SpineViewer.Spine
/// <summary> /// <summary>
/// 更新内部状态 /// 更新内部状态
/// </summary> /// </summary>
public abstract void Update(float delta); public void Update(float delta) { lock (_lock) update(delta); }
protected abstract void update(float delta);
#region SFML.Graphics.Drawable #region SFML.Graphics.Drawable
@@ -327,7 +391,8 @@ namespace SpineViewer.Spine
/// <summary> /// <summary>
/// SFML.Graphics.Drawable 接口实现 /// SFML.Graphics.Drawable 接口实现
/// </summary> /// </summary>
public abstract void Draw(SFML.Graphics.RenderTarget target, SFML.Graphics.RenderStates states); public void Draw(SFML.Graphics.RenderTarget target, SFML.Graphics.RenderStates states) { lock (_lock) draw(target, states); }
protected abstract void draw(SFML.Graphics.RenderTarget target, SFML.Graphics.RenderStates states);
#endregion #endregion
} }