mirror of
https://github.com/EsotericSoftware/spine-runtimes.git
synced 2026-03-26 22:49:01 +08:00
[unity] Added option for unsafe data loading avoiding some allocations on skel.bytes data. Closes #2851.
This commit is contained in:
parent
430b54de5e
commit
fb8bc402e7
@ -175,6 +175,7 @@
|
|||||||
2. Add a `RenderExistingMeshGraphic` component.
|
2. Add a `RenderExistingMeshGraphic` component.
|
||||||
3. In the `RenderExistingMeshGraphic` component Inspector at `Reference Skeleton Graphic` assign the original `SkeletonGraphic` object.
|
3. In the `RenderExistingMeshGraphic` component Inspector at `Reference Skeleton Graphic` assign the original `SkeletonGraphic` object.
|
||||||
4. At `Replacement Material` assign e.g. the included _SkeletonGraphicDefaultOutline_ material to replace all materials with this material. Alternatively, if `Multiple CanvasRenderers` is enabled at the reference SkeletonGraphic, you can add entries to the `Replacement Materials` list and at each entry assign the original SkeletonGraphic material (e.g. _SkeletonGraphicDefault_) to be replaced and the respective `Replacement Material` (e.g. _SkeletonGraphicDefaultOutline_).
|
4. At `Replacement Material` assign e.g. the included _SkeletonGraphicDefaultOutline_ material to replace all materials with this material. Alternatively, if `Multiple CanvasRenderers` is enabled at the reference SkeletonGraphic, you can add entries to the `Replacement Materials` list and at each entry assign the original SkeletonGraphic material (e.g. _SkeletonGraphicDefault_) to be replaced and the respective `Replacement Material` (e.g. _SkeletonGraphicDefaultOutline_).
|
||||||
|
- Added option for unsafe direct data loading when loading skeleton binary data to avoid some allocations, enabled via build define `SPINE_ALLOW_UNSAFE`. This define can be set via Spine Preferences, setting `Unsafe Build Defines - Direct data access`. The define is disabled by default to maintain existing behaviour. Changed asmdef setting for spine-unity assembly to allow unsafe code, has no effect other than allowing setting the `SPINE_ALLOW_UNSAFE` define.
|
||||||
|
|
||||||
- **Breaking changes**
|
- **Breaking changes**
|
||||||
|
|
||||||
|
|||||||
@ -83,6 +83,8 @@ namespace Spine.Unity.Editor {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static class SpineBuildEnvUtility {
|
public static class SpineBuildEnvUtility {
|
||||||
|
public const string SPINE_ALLOW_UNSAFE_CODE = "SPINE_ALLOW_UNSAFE";
|
||||||
|
|
||||||
static bool IsInvalidGroup (BuildTargetGroup group) {
|
static bool IsInvalidGroup (BuildTargetGroup group) {
|
||||||
int gi = (int)group;
|
int gi = (int)group;
|
||||||
return
|
return
|
||||||
@ -99,15 +101,18 @@ namespace Spine.Unity.Editor {
|
|||||||
if (IsInvalidGroup(group))
|
if (IsInvalidGroup(group))
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
string defines = PlayerSettings.GetScriptingDefineSymbolsForGroup(group);
|
try {
|
||||||
if (!defines.Contains(define)) {
|
string defines = PlayerSettings.GetScriptingDefineSymbolsForGroup(group);
|
||||||
wasDefineAdded = true;
|
if (!defines.Contains(define)) {
|
||||||
if (defines.EndsWith(";", System.StringComparison.Ordinal))
|
wasDefineAdded = true;
|
||||||
defines += define;
|
if (defines.EndsWith(";", System.StringComparison.Ordinal))
|
||||||
else
|
defines += define;
|
||||||
defines += ";" + define;
|
else
|
||||||
|
defines += ";" + define;
|
||||||
|
|
||||||
PlayerSettings.SetScriptingDefineSymbolsForGroup(group, defines);
|
PlayerSettings.SetScriptingDefineSymbolsForGroup(group, defines);
|
||||||
|
}
|
||||||
|
} catch (System.Exception) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Debug.LogWarning("Please ignore errors \"PlayerSettings Validation: Requested build target group doesn't exist\" above");
|
Debug.LogWarning("Please ignore errors \"PlayerSettings Validation: Requested build target group doesn't exist\" above");
|
||||||
@ -127,15 +132,18 @@ namespace Spine.Unity.Editor {
|
|||||||
if (IsInvalidGroup(group))
|
if (IsInvalidGroup(group))
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
string defines = PlayerSettings.GetScriptingDefineSymbolsForGroup(group);
|
try {
|
||||||
if (defines.Contains(define)) {
|
string defines = PlayerSettings.GetScriptingDefineSymbolsForGroup(group);
|
||||||
wasDefineRemoved = true;
|
if (defines.Contains(define)) {
|
||||||
if (defines.Contains(define + ";"))
|
wasDefineRemoved = true;
|
||||||
defines = defines.Replace(define + ";", "");
|
if (defines.Contains(define + ";"))
|
||||||
else
|
defines = defines.Replace(define + ";", "");
|
||||||
defines = defines.Replace(define, "");
|
else
|
||||||
|
defines = defines.Replace(define, "");
|
||||||
|
|
||||||
PlayerSettings.SetScriptingDefineSymbolsForGroup(group, defines);
|
PlayerSettings.SetScriptingDefineSymbolsForGroup(group, defines);
|
||||||
|
}
|
||||||
|
} catch (System.Exception) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -39,6 +39,14 @@
|
|||||||
#define HAS_ON_POSTPROCESS_PREFAB
|
#define HAS_ON_POSTPROCESS_PREFAB
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#if UNITY_2021_2_OR_NEWER
|
||||||
|
#define TEXT_ASSET_HAS_GET_DATA_BYTES
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if TEXT_ASSET_HAS_GET_DATA_BYTES
|
||||||
|
#define HAS_ANY_UNSAFE_OPTIONS
|
||||||
|
#endif
|
||||||
|
|
||||||
using System.Threading;
|
using System.Threading;
|
||||||
using UnityEditor;
|
using UnityEditor;
|
||||||
using UnityEngine;
|
using UnityEngine;
|
||||||
@ -356,6 +364,18 @@ namespace Spine.Unity.Editor {
|
|||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#if HAS_ANY_UNSAFE_OPTIONS
|
||||||
|
GUILayout.Space(20);
|
||||||
|
EditorGUILayout.LabelField("Unsafe Build Defines", EditorStyles.boldLabel);
|
||||||
|
using (new GUILayout.HorizontalScope()) {
|
||||||
|
EditorGUILayout.PrefixLabel(new GUIContent("Direct data access", "Allow unsafe direct data access. Currently affects reading .skel.bytes files, reading with fewer allocations."));
|
||||||
|
if (GUILayout.Button("Enable", GUILayout.Width(64)))
|
||||||
|
SpineBuildEnvUtility.EnableBuildDefine(SpineBuildEnvUtility.SPINE_ALLOW_UNSAFE_CODE);
|
||||||
|
if (GUILayout.Button("Disable", GUILayout.Width(64)))
|
||||||
|
SpineBuildEnvUtility.DisableBuildDefine(SpineBuildEnvUtility.SPINE_ALLOW_UNSAFE_CODE);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
#if SPINE_TK2D_DEFINE
|
#if SPINE_TK2D_DEFINE
|
||||||
bool isTK2DDefineSet = true;
|
bool isTK2DDefineSet = true;
|
||||||
#else
|
#else
|
||||||
|
|||||||
@ -1,4 +1,5 @@
|
|||||||
{
|
{
|
||||||
"name": "spine-unity",
|
"name": "spine-unity",
|
||||||
"references": [ "spine-csharp" ]
|
"references": [ "spine-csharp" ],
|
||||||
|
"allowUnsafeCode": true
|
||||||
}
|
}
|
||||||
|
|||||||
@ -27,14 +27,37 @@
|
|||||||
* SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
* SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
*****************************************************************************/
|
*****************************************************************************/
|
||||||
|
|
||||||
|
//#define SPINE_ALLOW_UNSAFE // note: this define can be set via Edit - Preferences - Spine.
|
||||||
|
|
||||||
|
#if UNITY_2021_2_OR_NEWER
|
||||||
|
#define TEXT_ASSET_HAS_GET_DATA_BYTES
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if SPINE_ALLOW_UNSAFE && TEXT_ASSET_HAS_GET_DATA_BYTES
|
||||||
|
#define UNSAFE_DIRECT_ACCESS_TEXT_ASSET_DATA
|
||||||
|
#endif
|
||||||
|
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
|
using Unity.Collections;
|
||||||
using UnityEngine;
|
using UnityEngine;
|
||||||
|
|
||||||
using CompatibilityProblemInfo = Spine.Unity.SkeletonDataCompatibility.CompatibilityProblemInfo;
|
using CompatibilityProblemInfo = Spine.Unity.SkeletonDataCompatibility.CompatibilityProblemInfo;
|
||||||
|
|
||||||
namespace Spine.Unity {
|
namespace Spine.Unity {
|
||||||
|
#if UNSAFE_DIRECT_ACCESS_TEXT_ASSET_DATA
|
||||||
|
public static class TextAssetExtensions {
|
||||||
|
public static Stream GetStreamUnsafe (this TextAsset textAsset) {
|
||||||
|
NativeArray<byte> dataNativeArray = textAsset.GetData<byte>();
|
||||||
|
return dataNativeArray.GetUnmanagedMemoryStream();
|
||||||
|
}
|
||||||
|
|
||||||
|
public static unsafe UnmanagedMemoryStream GetUnmanagedMemoryStream<T> (this NativeArray<T> nativeArray) where T : struct {
|
||||||
|
return new UnmanagedMemoryStream((byte*)global::Unity.Collections.LowLevel.Unsafe.
|
||||||
|
NativeArrayUnsafeUtility.GetUnsafeReadOnlyPtr(nativeArray), nativeArray.Length);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
[CreateAssetMenu(fileName = "New SkeletonDataAsset", menuName = "Spine/SkeletonData Asset")]
|
[CreateAssetMenu(fileName = "New SkeletonDataAsset", menuName = "Spine/SkeletonData Asset")]
|
||||||
public class SkeletonDataAsset : ScriptableObject {
|
public class SkeletonDataAsset : ScriptableObject {
|
||||||
@ -188,9 +211,13 @@ namespace Spine.Unity {
|
|||||||
SkeletonData loadedSkeletonData = null;
|
SkeletonData loadedSkeletonData = null;
|
||||||
|
|
||||||
try {
|
try {
|
||||||
if (hasBinaryExtension)
|
if (hasBinaryExtension) {
|
||||||
|
#if UNSAFE_DIRECT_ACCESS_TEXT_ASSET_DATA
|
||||||
|
loadedSkeletonData = SkeletonDataAsset.ReadSkeletonData(skeletonJSON.GetStreamUnsafe(), attachmentLoader, skeletonDataScale);
|
||||||
|
#else
|
||||||
loadedSkeletonData = SkeletonDataAsset.ReadSkeletonData(skeletonJSON.bytes, attachmentLoader, skeletonDataScale);
|
loadedSkeletonData = SkeletonDataAsset.ReadSkeletonData(skeletonJSON.bytes, attachmentLoader, skeletonDataScale);
|
||||||
else
|
#endif
|
||||||
|
} else
|
||||||
loadedSkeletonData = SkeletonDataAsset.ReadSkeletonData(skeletonJSON.text, attachmentLoader, skeletonDataScale);
|
loadedSkeletonData = SkeletonDataAsset.ReadSkeletonData(skeletonJSON.text, attachmentLoader, skeletonDataScale);
|
||||||
} catch (Exception ex) {
|
} catch (Exception ex) {
|
||||||
if (!quiet)
|
if (!quiet)
|
||||||
@ -287,6 +314,13 @@ namespace Spine.Unity {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
internal static SkeletonData ReadSkeletonData (Stream assetStream, AttachmentLoader attachmentLoader, float scale) {
|
||||||
|
SkeletonBinary binary = new SkeletonBinary(attachmentLoader) {
|
||||||
|
Scale = scale
|
||||||
|
};
|
||||||
|
return binary.ReadSkeletonData(assetStream);
|
||||||
|
}
|
||||||
|
|
||||||
internal static SkeletonData ReadSkeletonData (string text, AttachmentLoader attachmentLoader, float scale) {
|
internal static SkeletonData ReadSkeletonData (string text, AttachmentLoader attachmentLoader, float scale) {
|
||||||
StringReader input = new StringReader(text);
|
StringReader input = new StringReader(text);
|
||||||
SkeletonJson json = new SkeletonJson(attachmentLoader) {
|
SkeletonJson json = new SkeletonJson(attachmentLoader) {
|
||||||
|
|||||||
@ -2,7 +2,7 @@
|
|||||||
"name": "com.esotericsoftware.spine.spine-unity",
|
"name": "com.esotericsoftware.spine.spine-unity",
|
||||||
"displayName": "spine-unity Runtime",
|
"displayName": "spine-unity Runtime",
|
||||||
"description": "This plugin provides the spine-unity runtime core.",
|
"description": "This plugin provides the spine-unity runtime core.",
|
||||||
"version": "4.2.104",
|
"version": "4.2.105",
|
||||||
"unity": "2018.3",
|
"unity": "2018.3",
|
||||||
"author": {
|
"author": {
|
||||||
"name": "Esoteric Software",
|
"name": "Esoteric Software",
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user