This commit is contained in:
Nim XD
2024-08-27 21:01:33 +05:30
parent 99eaf514fd
commit 121a1b7c73
31803 changed files with 623461 additions and 623399 deletions

View File

@@ -1,45 +1,45 @@
/******************************************************************************
* Spine Runtimes License Agreement
* Last updated January 1, 2020. Replaces all prior versions.
*
* Copyright (c) 2013-2020, Esoteric Software LLC
*
* Integration of the Spine Runtimes into software or otherwise creating
* derivative works of the Spine Runtimes is permitted under the terms and
* conditions of Section 2 of the Spine Editor License Agreement:
* http://esotericsoftware.com/spine-editor-license
*
* Otherwise, it is permitted to integrate the Spine Runtimes into software
* or otherwise create derivative works of the Spine Runtimes (collectively,
* "Products"), provided that each user of the Products must obtain their own
* Spine Editor license and redistribution of the Products in any form must
* include this license and copyright notice.
*
* THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY
* EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES,
* BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*****************************************************************************/
namespace Spine.Unity {
public class DoubleBuffered<T> where T : new() {
readonly T a = new T();
readonly T b = new T();
bool usingA;
public T GetCurrent () {
return usingA ? a : b;
}
public T GetNext () {
usingA = !usingA;
return usingA ? a : b;
}
}
}
/******************************************************************************
* Spine Runtimes License Agreement
* Last updated January 1, 2020. Replaces all prior versions.
*
* Copyright (c) 2013-2020, Esoteric Software LLC
*
* Integration of the Spine Runtimes into software or otherwise creating
* derivative works of the Spine Runtimes is permitted under the terms and
* conditions of Section 2 of the Spine Editor License Agreement:
* http://esotericsoftware.com/spine-editor-license
*
* Otherwise, it is permitted to integrate the Spine Runtimes into software
* or otherwise create derivative works of the Spine Runtimes (collectively,
* "Products"), provided that each user of the Products must obtain their own
* Spine Editor license and redistribution of the Products in any form must
* include this license and copyright notice.
*
* THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY
* EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES,
* BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*****************************************************************************/
namespace Spine.Unity {
public class DoubleBuffered<T> where T : new() {
readonly T a = new T();
readonly T b = new T();
bool usingA;
public T GetCurrent () {
return usingA ? a : b;
}
public T GetNext () {
usingA = !usingA;
return usingA ? a : b;
}
}
}

View File

@@ -1,135 +1,135 @@
/******************************************************************************
* Spine Runtimes License Agreement
* Last updated January 1, 2020. Replaces all prior versions.
*
* Copyright (c) 2013-2020, Esoteric Software LLC
*
* Integration of the Spine Runtimes into software or otherwise creating
* derivative works of the Spine Runtimes is permitted under the terms and
* conditions of Section 2 of the Spine Editor License Agreement:
* http://esotericsoftware.com/spine-editor-license
*
* Otherwise, it is permitted to integrate the Spine Runtimes into software
* or otherwise create derivative works of the Spine Runtimes (collectively,
* "Products"), provided that each user of the Products must obtain their own
* Spine Editor license and redistribution of the Products in any form must
* include this license and copyright notice.
*
* THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY
* EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES,
* BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*****************************************************************************/
// Not for optimization. Do not disable.
#define SPINE_TRIANGLECHECK // Avoid calling SetTriangles at the cost of checking for mesh differences (vertex counts, memberwise attachment list compare) every frame.
//#define SPINE_DEBUG
using System;
using System.Collections.Generic;
using UnityEngine;
namespace Spine.Unity {
/// <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 {
DoubleBuffered<SmartMesh> doubleBufferedMesh;
internal readonly ExposedList<Material> submeshMaterials = new ExposedList<Material>();
internal Material[] sharedMaterials = new Material[0];
public void Initialize () {
if (doubleBufferedMesh != null) {
doubleBufferedMesh.GetNext().Clear();
doubleBufferedMesh.GetNext().Clear();
submeshMaterials.Clear();
} else {
doubleBufferedMesh = new DoubleBuffered<SmartMesh>();
}
}
/// <summary>Returns a sharedMaterials array for use on a MeshRenderer.</summary>
/// <returns></returns>
public Material[] GetUpdatedSharedMaterialsArray () {
if (submeshMaterials.Count == sharedMaterials.Length)
submeshMaterials.CopyTo(sharedMaterials);
else
sharedMaterials = submeshMaterials.ToArray();
return sharedMaterials;
}
/// <summary>Returns true if the materials were modified since the buffers were last updated.</summary>
public bool MaterialsChangedInLastUpdate () {
int newSubmeshMaterials = submeshMaterials.Count;
var sharedMaterials = this.sharedMaterials;
if (newSubmeshMaterials != sharedMaterials.Length) return true;
var submeshMaterialsItems = submeshMaterials.Items;
for (int i = 0; i < newSubmeshMaterials; i++)
if (!Material.ReferenceEquals(submeshMaterialsItems[i], sharedMaterials[i])) return true; //if (submeshMaterialsItems[i].GetInstanceID() != sharedMaterials[i].GetInstanceID()) return true;
return false;
}
/// <summary>Updates the internal shared materials array with the given instruction list.</summary>
public void UpdateSharedMaterials (ExposedList<SubmeshInstruction> instructions) {
int newSize = instructions.Count;
{ //submeshMaterials.Resize(instructions.Count);
if (newSize > submeshMaterials.Items.Length)
Array.Resize(ref submeshMaterials.Items, newSize);
submeshMaterials.Count = newSize;
}
var submeshMaterialsItems = submeshMaterials.Items;
var instructionsItems = instructions.Items;
for (int i = 0; i < newSize; i++)
submeshMaterialsItems[i] = instructionsItems[i].material;
}
public SmartMesh GetNextMesh () {
return doubleBufferedMesh.GetNext();
}
public void Clear () {
sharedMaterials = new Material[0];
submeshMaterials.Clear();
}
public void Dispose () {
if (doubleBufferedMesh == null) return;
doubleBufferedMesh.GetNext().Dispose();
doubleBufferedMesh.GetNext().Dispose();
doubleBufferedMesh = null;
}
///<summary>This is a Mesh that also stores the instructions SkeletonRenderer generated for it.</summary>
public class SmartMesh : IDisposable {
public Mesh mesh = SpineMesh.NewSkeletonMesh();
public SkeletonRendererInstruction instructionUsed = new SkeletonRendererInstruction();
public void Clear () {
mesh.Clear();
instructionUsed.Clear();
}
public void Dispose () {
if (mesh != null) {
#if UNITY_EDITOR
if (Application.isEditor && !Application.isPlaying)
UnityEngine.Object.DestroyImmediate(mesh);
else
UnityEngine.Object.Destroy(mesh);
#else
UnityEngine.Object.Destroy(mesh);
#endif
}
mesh = null;
}
}
}
}
/******************************************************************************
* Spine Runtimes License Agreement
* Last updated January 1, 2020. Replaces all prior versions.
*
* Copyright (c) 2013-2020, Esoteric Software LLC
*
* Integration of the Spine Runtimes into software or otherwise creating
* derivative works of the Spine Runtimes is permitted under the terms and
* conditions of Section 2 of the Spine Editor License Agreement:
* http://esotericsoftware.com/spine-editor-license
*
* Otherwise, it is permitted to integrate the Spine Runtimes into software
* or otherwise create derivative works of the Spine Runtimes (collectively,
* "Products"), provided that each user of the Products must obtain their own
* Spine Editor license and redistribution of the Products in any form must
* include this license and copyright notice.
*
* THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY
* EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES,
* BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*****************************************************************************/
// Not for optimization. Do not disable.
#define SPINE_TRIANGLECHECK // Avoid calling SetTriangles at the cost of checking for mesh differences (vertex counts, memberwise attachment list compare) every frame.
//#define SPINE_DEBUG
using System;
using System.Collections.Generic;
using UnityEngine;
namespace Spine.Unity {
/// <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 {
DoubleBuffered<SmartMesh> doubleBufferedMesh;
internal readonly ExposedList<Material> submeshMaterials = new ExposedList<Material>();
internal Material[] sharedMaterials = new Material[0];
public void Initialize () {
if (doubleBufferedMesh != null) {
doubleBufferedMesh.GetNext().Clear();
doubleBufferedMesh.GetNext().Clear();
submeshMaterials.Clear();
} else {
doubleBufferedMesh = new DoubleBuffered<SmartMesh>();
}
}
/// <summary>Returns a sharedMaterials array for use on a MeshRenderer.</summary>
/// <returns></returns>
public Material[] GetUpdatedSharedMaterialsArray () {
if (submeshMaterials.Count == sharedMaterials.Length)
submeshMaterials.CopyTo(sharedMaterials);
else
sharedMaterials = submeshMaterials.ToArray();
return sharedMaterials;
}
/// <summary>Returns true if the materials were modified since the buffers were last updated.</summary>
public bool MaterialsChangedInLastUpdate () {
int newSubmeshMaterials = submeshMaterials.Count;
var sharedMaterials = this.sharedMaterials;
if (newSubmeshMaterials != sharedMaterials.Length) return true;
var submeshMaterialsItems = submeshMaterials.Items;
for (int i = 0; i < newSubmeshMaterials; i++)
if (!Material.ReferenceEquals(submeshMaterialsItems[i], sharedMaterials[i])) return true; //if (submeshMaterialsItems[i].GetInstanceID() != sharedMaterials[i].GetInstanceID()) return true;
return false;
}
/// <summary>Updates the internal shared materials array with the given instruction list.</summary>
public void UpdateSharedMaterials (ExposedList<SubmeshInstruction> instructions) {
int newSize = instructions.Count;
{ //submeshMaterials.Resize(instructions.Count);
if (newSize > submeshMaterials.Items.Length)
Array.Resize(ref submeshMaterials.Items, newSize);
submeshMaterials.Count = newSize;
}
var submeshMaterialsItems = submeshMaterials.Items;
var instructionsItems = instructions.Items;
for (int i = 0; i < newSize; i++)
submeshMaterialsItems[i] = instructionsItems[i].material;
}
public SmartMesh GetNextMesh () {
return doubleBufferedMesh.GetNext();
}
public void Clear () {
sharedMaterials = new Material[0];
submeshMaterials.Clear();
}
public void Dispose () {
if (doubleBufferedMesh == null) return;
doubleBufferedMesh.GetNext().Dispose();
doubleBufferedMesh.GetNext().Dispose();
doubleBufferedMesh = null;
}
///<summary>This is a Mesh that also stores the instructions SkeletonRenderer generated for it.</summary>
public class SmartMesh : IDisposable {
public Mesh mesh = SpineMesh.NewSkeletonMesh();
public SkeletonRendererInstruction instructionUsed = new SkeletonRendererInstruction();
public void Clear () {
mesh.Clear();
instructionUsed.Clear();
}
public void Dispose () {
if (mesh != null) {
#if UNITY_EDITOR
if (Application.isEditor && !Application.isPlaying)
UnityEngine.Object.DestroyImmediate(mesh);
else
UnityEngine.Object.Destroy(mesh);
#else
UnityEngine.Object.Destroy(mesh);
#endif
}
mesh = null;
}
}
}
}

View File

@@ -1,178 +1,178 @@
/******************************************************************************
* Spine Runtimes License Agreement
* Last updated January 1, 2020. Replaces all prior versions.
*
* Copyright (c) 2013-2020, Esoteric Software LLC
*
* Integration of the Spine Runtimes into software or otherwise creating
* derivative works of the Spine Runtimes is permitted under the terms and
* conditions of Section 2 of the Spine Editor License Agreement:
* http://esotericsoftware.com/spine-editor-license
*
* Otherwise, it is permitted to integrate the Spine Runtimes into software
* or otherwise create derivative works of the Spine Runtimes (collectively,
* "Products"), provided that each user of the Products must obtain their own
* Spine Editor license and redistribution of the Products in any form must
* include this license and copyright notice.
*
* THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY
* EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES,
* BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*****************************************************************************/
// Not for optimization. Do not disable.
#define SPINE_TRIANGLECHECK // Avoid calling SetTriangles at the cost of checking for mesh differences (vertex counts, memberwise attachment list compare) every frame.
//#define SPINE_DEBUG
using System;
using System.Collections.Generic;
using UnityEngine;
namespace Spine.Unity {
/// <summary>Instructions used by a SkeletonRenderer to render a mesh.</summary>
public class SkeletonRendererInstruction {
public readonly ExposedList<SubmeshInstruction> submeshInstructions = new ExposedList<SubmeshInstruction>();
public bool immutableTriangles;
#if SPINE_TRIANGLECHECK
public bool hasActiveClipping;
public int rawVertexCount = -1;
public readonly ExposedList<Attachment> attachments = new ExposedList<Attachment>();
#endif
public void Clear () {
#if SPINE_TRIANGLECHECK
this.attachments.Clear(false);
rawVertexCount = -1;
hasActiveClipping = false;
#endif
this.submeshInstructions.Clear(false);
}
public void Dispose () {
attachments.Clear(true);
}
public void SetWithSubset (ExposedList<SubmeshInstruction> instructions, int startSubmesh, int endSubmesh) {
#if SPINE_TRIANGLECHECK
int runningVertexCount = 0;
#endif
var submeshes = this.submeshInstructions;
submeshes.Clear(false);
int submeshCount = endSubmesh - startSubmesh;
submeshes.Resize(submeshCount);
var submeshesItems = submeshes.Items;
var instructionsItems = instructions.Items;
for (int i = 0; i < submeshCount; i++) {
var instruction = instructionsItems[startSubmesh + i];
submeshesItems[i] = instruction;
#if SPINE_TRIANGLECHECK
this.hasActiveClipping |= instruction.hasClipping;
submeshesItems[i].rawFirstVertexIndex = runningVertexCount; // Ensure current instructions have correct cached values.
runningVertexCount += instruction.rawVertexCount; // vertexCount will also be used for the rest of this method.
#endif
}
#if SPINE_TRIANGLECHECK
this.rawVertexCount = runningVertexCount;
// assumption: instructions are contiguous. start and end are valid within instructions.
int startSlot = instructionsItems[startSubmesh].startSlot;
int endSlot = instructionsItems[endSubmesh - 1].endSlot;
attachments.Clear(false);
int attachmentCount = endSlot - startSlot;
attachments.Resize(attachmentCount);
var attachmentsItems = attachments.Items;
var drawOrderItems = instructionsItems[0].skeleton.DrawOrder.Items;
for (int i = 0; i < attachmentCount; i++) {
Slot slot = drawOrderItems[startSlot + i];
if (!slot.Bone.Active) continue;
attachmentsItems[i] = slot.Attachment;
}
#endif
}
public void Set (SkeletonRendererInstruction other) {
this.immutableTriangles = other.immutableTriangles;
#if SPINE_TRIANGLECHECK
this.hasActiveClipping = other.hasActiveClipping;
this.rawVertexCount = other.rawVertexCount;
this.attachments.Clear(false);
this.attachments.EnsureCapacity(other.attachments.Capacity);
this.attachments.Count = other.attachments.Count;
other.attachments.CopyTo(this.attachments.Items);
#endif
this.submeshInstructions.Clear(false);
this.submeshInstructions.EnsureCapacity(other.submeshInstructions.Capacity);
this.submeshInstructions.Count = other.submeshInstructions.Count;
other.submeshInstructions.CopyTo(this.submeshInstructions.Items);
}
public static bool GeometryNotEqual (SkeletonRendererInstruction a, SkeletonRendererInstruction b) {
#if SPINE_TRIANGLECHECK
#if UNITY_EDITOR
if (!Application.isPlaying)
return true;
#endif
if (a.hasActiveClipping || b.hasActiveClipping) return true; // Triangles are unpredictable when clipping is active.
// Everything below assumes the raw vertex and triangle counts were used. (ie, no clipping was done)
if (a.rawVertexCount != b.rawVertexCount) return true;
if (a.immutableTriangles != b.immutableTriangles) return true;
int attachmentCountB = b.attachments.Count;
if (a.attachments.Count != attachmentCountB) return true; // Bounds check for the looped storedAttachments count below.
// Submesh count changed
int submeshCountA = a.submeshInstructions.Count;
int submeshCountB = b.submeshInstructions.Count;
if (submeshCountA != submeshCountB) return true;
// Submesh Instruction mismatch
var submeshInstructionsItemsA = a.submeshInstructions.Items;
var submeshInstructionsItemsB = b.submeshInstructions.Items;
var attachmentsA = a.attachments.Items;
var attachmentsB = b.attachments.Items;
for (int i = 0; i < attachmentCountB; i++)
if (!System.Object.ReferenceEquals(attachmentsA[i], attachmentsB[i])) return true;
for (int i = 0; i < submeshCountB; i++) {
var submeshA = submeshInstructionsItemsA[i];
var submeshB = submeshInstructionsItemsB[i];
if (!(
submeshA.rawVertexCount == submeshB.rawVertexCount &&
submeshA.startSlot == submeshB.startSlot &&
submeshA.endSlot == submeshB.endSlot
&& submeshA.rawTriangleCount == submeshB.rawTriangleCount &&
submeshA.rawFirstVertexIndex == submeshB.rawFirstVertexIndex
))
return true;
}
return false;
#else
// In normal immutable triangle use, immutableTriangles will be initially false, forcing the smartmesh to update the first time but never again after that, unless there was an immutableTriangles flag mismatch..
if (a.immutableTriangles || b.immutableTriangles)
return (a.immutableTriangles != b.immutableTriangles);
return true;
#endif
}
}
}
/******************************************************************************
* Spine Runtimes License Agreement
* Last updated January 1, 2020. Replaces all prior versions.
*
* Copyright (c) 2013-2020, Esoteric Software LLC
*
* Integration of the Spine Runtimes into software or otherwise creating
* derivative works of the Spine Runtimes is permitted under the terms and
* conditions of Section 2 of the Spine Editor License Agreement:
* http://esotericsoftware.com/spine-editor-license
*
* Otherwise, it is permitted to integrate the Spine Runtimes into software
* or otherwise create derivative works of the Spine Runtimes (collectively,
* "Products"), provided that each user of the Products must obtain their own
* Spine Editor license and redistribution of the Products in any form must
* include this license and copyright notice.
*
* THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY
* EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES,
* BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*****************************************************************************/
// Not for optimization. Do not disable.
#define SPINE_TRIANGLECHECK // Avoid calling SetTriangles at the cost of checking for mesh differences (vertex counts, memberwise attachment list compare) every frame.
//#define SPINE_DEBUG
using System;
using System.Collections.Generic;
using UnityEngine;
namespace Spine.Unity {
/// <summary>Instructions used by a SkeletonRenderer to render a mesh.</summary>
public class SkeletonRendererInstruction {
public readonly ExposedList<SubmeshInstruction> submeshInstructions = new ExposedList<SubmeshInstruction>();
public bool immutableTriangles;
#if SPINE_TRIANGLECHECK
public bool hasActiveClipping;
public int rawVertexCount = -1;
public readonly ExposedList<Attachment> attachments = new ExposedList<Attachment>();
#endif
public void Clear () {
#if SPINE_TRIANGLECHECK
this.attachments.Clear(false);
rawVertexCount = -1;
hasActiveClipping = false;
#endif
this.submeshInstructions.Clear(false);
}
public void Dispose () {
attachments.Clear(true);
}
public void SetWithSubset (ExposedList<SubmeshInstruction> instructions, int startSubmesh, int endSubmesh) {
#if SPINE_TRIANGLECHECK
int runningVertexCount = 0;
#endif
var submeshes = this.submeshInstructions;
submeshes.Clear(false);
int submeshCount = endSubmesh - startSubmesh;
submeshes.Resize(submeshCount);
var submeshesItems = submeshes.Items;
var instructionsItems = instructions.Items;
for (int i = 0; i < submeshCount; i++) {
var instruction = instructionsItems[startSubmesh + i];
submeshesItems[i] = instruction;
#if SPINE_TRIANGLECHECK
this.hasActiveClipping |= instruction.hasClipping;
submeshesItems[i].rawFirstVertexIndex = runningVertexCount; // Ensure current instructions have correct cached values.
runningVertexCount += instruction.rawVertexCount; // vertexCount will also be used for the rest of this method.
#endif
}
#if SPINE_TRIANGLECHECK
this.rawVertexCount = runningVertexCount;
// assumption: instructions are contiguous. start and end are valid within instructions.
int startSlot = instructionsItems[startSubmesh].startSlot;
int endSlot = instructionsItems[endSubmesh - 1].endSlot;
attachments.Clear(false);
int attachmentCount = endSlot - startSlot;
attachments.Resize(attachmentCount);
var attachmentsItems = attachments.Items;
var drawOrderItems = instructionsItems[0].skeleton.DrawOrder.Items;
for (int i = 0; i < attachmentCount; i++) {
Slot slot = drawOrderItems[startSlot + i];
if (!slot.Bone.Active) continue;
attachmentsItems[i] = slot.Attachment;
}
#endif
}
public void Set (SkeletonRendererInstruction other) {
this.immutableTriangles = other.immutableTriangles;
#if SPINE_TRIANGLECHECK
this.hasActiveClipping = other.hasActiveClipping;
this.rawVertexCount = other.rawVertexCount;
this.attachments.Clear(false);
this.attachments.EnsureCapacity(other.attachments.Capacity);
this.attachments.Count = other.attachments.Count;
other.attachments.CopyTo(this.attachments.Items);
#endif
this.submeshInstructions.Clear(false);
this.submeshInstructions.EnsureCapacity(other.submeshInstructions.Capacity);
this.submeshInstructions.Count = other.submeshInstructions.Count;
other.submeshInstructions.CopyTo(this.submeshInstructions.Items);
}
public static bool GeometryNotEqual (SkeletonRendererInstruction a, SkeletonRendererInstruction b) {
#if SPINE_TRIANGLECHECK
#if UNITY_EDITOR
if (!Application.isPlaying)
return true;
#endif
if (a.hasActiveClipping || b.hasActiveClipping) return true; // Triangles are unpredictable when clipping is active.
// Everything below assumes the raw vertex and triangle counts were used. (ie, no clipping was done)
if (a.rawVertexCount != b.rawVertexCount) return true;
if (a.immutableTriangles != b.immutableTriangles) return true;
int attachmentCountB = b.attachments.Count;
if (a.attachments.Count != attachmentCountB) return true; // Bounds check for the looped storedAttachments count below.
// Submesh count changed
int submeshCountA = a.submeshInstructions.Count;
int submeshCountB = b.submeshInstructions.Count;
if (submeshCountA != submeshCountB) return true;
// Submesh Instruction mismatch
var submeshInstructionsItemsA = a.submeshInstructions.Items;
var submeshInstructionsItemsB = b.submeshInstructions.Items;
var attachmentsA = a.attachments.Items;
var attachmentsB = b.attachments.Items;
for (int i = 0; i < attachmentCountB; i++)
if (!System.Object.ReferenceEquals(attachmentsA[i], attachmentsB[i])) return true;
for (int i = 0; i < submeshCountB; i++) {
var submeshA = submeshInstructionsItemsA[i];
var submeshB = submeshInstructionsItemsB[i];
if (!(
submeshA.rawVertexCount == submeshB.rawVertexCount &&
submeshA.startSlot == submeshB.startSlot &&
submeshA.endSlot == submeshB.endSlot
&& submeshA.rawTriangleCount == submeshB.rawTriangleCount &&
submeshA.rawFirstVertexIndex == submeshB.rawFirstVertexIndex
))
return true;
}
return false;
#else
// In normal immutable triangle use, immutableTriangles will be initially false, forcing the smartmesh to update the first time but never again after that, unless there was an immutableTriangles flag mismatch..
if (a.immutableTriangles || b.immutableTriangles)
return (a.immutableTriangles != b.immutableTriangles);
return true;
#endif
}
}
}

View File

@@ -1,85 +1,85 @@
/******************************************************************************
* Spine Runtimes License Agreement
* Last updated January 1, 2020. Replaces all prior versions.
*
* Copyright (c) 2013-2020, Esoteric Software LLC
*
* Integration of the Spine Runtimes into software or otherwise creating
* derivative works of the Spine Runtimes is permitted under the terms and
* conditions of Section 2 of the Spine Editor License Agreement:
* http://esotericsoftware.com/spine-editor-license
*
* Otherwise, it is permitted to integrate the Spine Runtimes into software
* or otherwise create derivative works of the Spine Runtimes (collectively,
* "Products"), provided that each user of the Products must obtain their own
* Spine Editor license and redistribution of the Products in any form must
* include this license and copyright notice.
*
* THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY
* EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES,
* BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*****************************************************************************/
// Not for optimization. Do not disable.
#define SPINE_TRIANGLECHECK // Avoid calling SetTriangles at the cost of checking for mesh differences (vertex counts, memberwise attachment list compare) every frame.
//#define SPINE_DEBUG
using System;
using System.Collections.Generic;
using UnityEngine;
namespace Spine.Unity {
public static class SpineMesh {
internal const HideFlags MeshHideflags = HideFlags.DontSaveInBuild | HideFlags.DontSaveInEditor;
/// <summary>Factory method for creating a new mesh for use in Spine components. This can be called in field initializers.</summary>
public static Mesh NewSkeletonMesh () {
var m = new Mesh();
m.MarkDynamic();
m.name = "Skeleton Mesh";
m.hideFlags = SpineMesh.MeshHideflags;
return m;
}
}
/// <summary>Instructions for how to generate a mesh or submesh: "Render this skeleton's slots: start slot, up to but not including endSlot, using this material."</summary>
public struct SubmeshInstruction {
public Skeleton skeleton;
public int startSlot;
public int endSlot;
public Material material;
public bool forceSeparate;
public int preActiveClippingSlotSource;
#if SPINE_TRIANGLECHECK
// Cached values because they are determined in the process of generating instructions,
// but could otherwise be pulled from accessing attachments, checking materials and counting tris and verts.
public int rawTriangleCount;
public int rawVertexCount;
public int rawFirstVertexIndex;
public bool hasClipping;
#endif
public bool hasPMAAdditiveSlot;
/// <summary>The number of slots in this SubmeshInstruction's range. Not necessarily the number of attachments.</summary>
public int SlotCount { get { return endSlot - startSlot; } }
public override string ToString () {
return
string.Format("[SubmeshInstruction: slots {0} to {1}. (Material){2}. preActiveClippingSlotSource:{3}]",
startSlot,
endSlot - 1,
material == null ? "<none>" : material.name,
preActiveClippingSlotSource
);
}
}
}
/******************************************************************************
* Spine Runtimes License Agreement
* Last updated January 1, 2020. Replaces all prior versions.
*
* Copyright (c) 2013-2020, Esoteric Software LLC
*
* Integration of the Spine Runtimes into software or otherwise creating
* derivative works of the Spine Runtimes is permitted under the terms and
* conditions of Section 2 of the Spine Editor License Agreement:
* http://esotericsoftware.com/spine-editor-license
*
* Otherwise, it is permitted to integrate the Spine Runtimes into software
* or otherwise create derivative works of the Spine Runtimes (collectively,
* "Products"), provided that each user of the Products must obtain their own
* Spine Editor license and redistribution of the Products in any form must
* include this license and copyright notice.
*
* THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY
* EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES,
* BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*****************************************************************************/
// Not for optimization. Do not disable.
#define SPINE_TRIANGLECHECK // Avoid calling SetTriangles at the cost of checking for mesh differences (vertex counts, memberwise attachment list compare) every frame.
//#define SPINE_DEBUG
using System;
using System.Collections.Generic;
using UnityEngine;
namespace Spine.Unity {
public static class SpineMesh {
internal const HideFlags MeshHideflags = HideFlags.DontSaveInBuild | HideFlags.DontSaveInEditor;
/// <summary>Factory method for creating a new mesh for use in Spine components. This can be called in field initializers.</summary>
public static Mesh NewSkeletonMesh () {
var m = new Mesh();
m.MarkDynamic();
m.name = "Skeleton Mesh";
m.hideFlags = SpineMesh.MeshHideflags;
return m;
}
}
/// <summary>Instructions for how to generate a mesh or submesh: "Render this skeleton's slots: start slot, up to but not including endSlot, using this material."</summary>
public struct SubmeshInstruction {
public Skeleton skeleton;
public int startSlot;
public int endSlot;
public Material material;
public bool forceSeparate;
public int preActiveClippingSlotSource;
#if SPINE_TRIANGLECHECK
// Cached values because they are determined in the process of generating instructions,
// but could otherwise be pulled from accessing attachments, checking materials and counting tris and verts.
public int rawTriangleCount;
public int rawVertexCount;
public int rawFirstVertexIndex;
public bool hasClipping;
#endif
public bool hasPMAAdditiveSlot;
/// <summary>The number of slots in this SubmeshInstruction's range. Not necessarily the number of attachments.</summary>
public int SlotCount { get { return endSlot - startSlot; } }
public override string ToString () {
return
string.Format("[SubmeshInstruction: slots {0} to {1}. (Material){2}. preActiveClippingSlotSource:{3}]",
startSlot,
endSlot - 1,
material == null ? "<none>" : material.name,
preActiveClippingSlotSource
);
}
}
}