[csharp] Code style update.

* `else` on same line as `if` brace.
* `var` only when the type is shown.
* Removed unnecessarily locals, eg `var events = this.events; var eventsItems = events.Items;`.
* Don't indent `case`.
* ExposedList for EventQueue just so iteration can use array indexing.
* EventQueue, inner members (struct/enum) after methods.
* No braces for single line `if/else/for`.
* Removed comments noting ref impl code, eg `// abc.setSize(xyz);`.
* Removed comments that didn't add to what the code shows, eg `// Pooling`.
* Removed comments not in ref impl about implementation details, eg `// nextTrackLast == -1 ...`.
* Removed commented code we are not using.
* Use local with list.Items when iterating.
This commit is contained in:
Nathan Sweet 2021-05-31 01:21:03 -04:00
parent 551f33b2d1
commit 963da7561e
18 changed files with 1001 additions and 1066 deletions

1
.gitignore vendored
View File

@ -48,6 +48,7 @@ xcshareddata/
spine-cocos2d-objc/cocos2d/*
spine-cocos2d-objc/spine-cocos2d-iphone-objc.xcodeproj/project.xcworkspace/xcshareddata/
spine-csharp/.vs/
spine-csharp/bin
spine-csharp/obj
spine-csharp/src/*.meta

File diff suppressed because it is too large Load Diff

View File

@ -134,7 +134,7 @@ namespace Spine {
/// <param name="delta">delta time</param>
public void Update (float delta) {
delta *= timeScale;
var tracksItems = tracks.Items;
TrackEntry[] tracksItems = tracks.Items;
for (int i = 0, n = tracks.Count; i < n; i++) {
TrackEntry current = tracksItems[i];
if (current == null) continue;
@ -225,9 +225,9 @@ namespace Spine {
if (skeleton == null) throw new ArgumentNullException("skeleton", "skeleton cannot be null.");
if (animationsChanged) AnimationsChanged();
var events = this.events;
ExposedList<Event> events = this.events;
bool applied = false;
var tracksItems = tracks.Items;
TrackEntry[] tracksItems = tracks.Items;
for (int i = 0, n = tracks.Count; i < n; i++) {
TrackEntry current = tracksItems[i];
if (current == null || current.delay > 0) continue;
@ -252,25 +252,24 @@ namespace Spine {
}
int timelineCount = current.animation.timelines.Count;
var timelines = current.animation.timelines;
var timelinesItems = timelines.Items;
Timeline[] timelines = current.animation.timelines.Items;
if ((i == 0 && mix == 1) || blend == MixBlend.Add) {
for (int ii = 0; ii < timelineCount; ii++) {
var timeline = timelinesItems[ii];
Timeline timeline = timelines[ii];
if (timeline is AttachmentTimeline)
ApplyAttachmentTimeline((AttachmentTimeline)timeline, skeleton, applyTime, blend, true);
else
timeline.Apply(skeleton, animationLast, applyTime, applyEvents, mix, blend, MixDirection.In);
}
} else {
var timelineMode = current.timelineMode.Items;
int[] timelineMode = current.timelineMode.Items;
bool firstFrame = current.timelinesRotation.Count != timelineCount << 1;
if (firstFrame) current.timelinesRotation.Resize(timelines.Count << 1);
var timelinesRotation = current.timelinesRotation.Items;
if (firstFrame) current.timelinesRotation.Resize(timelineCount << 1);
float[] timelinesRotation = current.timelinesRotation.Items;
for (int ii = 0; ii < timelineCount; ii++) {
Timeline timeline = timelinesItems[ii];
Timeline timeline = timelines[ii];
MixBlend timelineBlend = timelineMode[ii] == AnimationState.Subsequent ? blend : MixBlend.Setup;
var rotateTimeline = timeline as RotateTimeline;
if (rotateTimeline != null)
@ -292,9 +291,9 @@ namespace Spine {
// subsequent timelines see any deform, but the subsequent timelines don't set an attachment (eg they are also mixing out or
// the time is before the first key).
int setupState = unkeyedState + Setup;
var slots = skeleton.slots.Items;
Slot[] slots = skeleton.slots.Items;
for (int i = 0, n = skeleton.slots.Count; i < n; i++) {
Slot slot = (Slot)slots[i];
Slot slot = slots[i];
if (slot.attachmentState == setupState) {
string attachmentName = slot.data.attachmentName;
slot.Attachment = (attachmentName == null ? null : skeleton.GetAttachment(slot.data.index, attachmentName));
@ -311,25 +310,23 @@ namespace Spine {
public bool ApplyEventTimelinesOnly (Skeleton skeleton) {
if (skeleton == null) throw new ArgumentNullException("skeleton", "skeleton cannot be null.");
var events = this.events;
ExposedList<Event> events = this.events;
bool applied = false;
var tracksItems = tracks.Items;
TrackEntry[] tracksItems = tracks.Items;
for (int i = 0, n = tracks.Count; i < n; i++) {
TrackEntry current = tracksItems[i];
if (current == null || current.delay > 0) continue;
applied = true;
// Apply mixing from entries first.
if (current.mixingFrom != null)
ApplyMixingFromEventTimelinesOnly(current, skeleton);
if (current.mixingFrom != null) ApplyMixingFromEventTimelinesOnly(current, skeleton);
// Apply current entry.
float animationLast = current.animationLast, animationTime = current.AnimationTime;
int timelineCount = current.animation.timelines.Count;
var timelines = current.animation.timelines;
var timelinesItems = timelines.Items;
Timeline[] timelines = current.animation.timelines.Items;
for (int ii = 0; ii < timelineCount; ii++) {
Timeline timeline = timelinesItems[ii];
Timeline timeline = timelines[ii];
if (timeline is EventTimeline)
timeline.Apply(skeleton, animationLast, animationTime, events, 1.0f, MixBlend.Setup, MixDirection.In);
}
@ -358,9 +355,8 @@ namespace Spine {
}
bool attachments = mix < from.attachmentThreshold, drawOrder = mix < from.drawOrderThreshold;
var timelines = from.animation.timelines;
int timelineCount = timelines.Count;
var timelinesItems = timelines.Items;
int timelineCount = from.animation.timelines.Count;
Timeline[] timelines = from.animation.timelines.Items;
float alphaHold = from.alpha * to.interruptAlpha, alphaMix = alphaHold * (1 - mix);
float animationLast = from.animationLast, animationTime = from.AnimationTime, applyTime = animationTime;
ExposedList<Event> events = null;
@ -373,44 +369,44 @@ namespace Spine {
if (blend == MixBlend.Add) {
for (int i = 0; i < timelineCount; i++)
timelinesItems[i].Apply(skeleton, animationLast, applyTime, events, alphaMix, blend, MixDirection.Out);
timelines[i].Apply(skeleton, animationLast, applyTime, events, alphaMix, blend, MixDirection.Out);
} else {
var timelineMode = from.timelineMode.Items;
var timelineHoldMix = from.timelineHoldMix.Items;
int[] timelineMode = from.timelineMode.Items;
TrackEntry[] timelineHoldMix = from.timelineHoldMix.Items;
bool firstFrame = from.timelinesRotation.Count != timelineCount << 1;
if (firstFrame) from.timelinesRotation.Resize(timelines.Count << 1); // from.timelinesRotation.setSize
var timelinesRotation = from.timelinesRotation.Items;
if (firstFrame) from.timelinesRotation.Resize(timelineCount << 1);
float[] timelinesRotation = from.timelinesRotation.Items;
from.totalAlpha = 0;
for (int i = 0; i < timelineCount; i++) {
Timeline timeline = timelinesItems[i];
Timeline timeline = timelines[i];
MixDirection direction = MixDirection.Out;
MixBlend timelineBlend;
float alpha;
switch (timelineMode[i]) {
case AnimationState.Subsequent:
if (!drawOrder && timeline is DrawOrderTimeline) continue;
timelineBlend = blend;
alpha = alphaMix;
break;
case AnimationState.First:
timelineBlend = MixBlend.Setup;
alpha = alphaMix;
break;
case AnimationState.HoldSubsequent:
timelineBlend = blend;
alpha = alphaHold;
break;
case AnimationState.HoldFirst:
timelineBlend = MixBlend.Setup;
alpha = alphaHold;
break;
default: // HoldMix
timelineBlend = MixBlend.Setup;
TrackEntry holdMix = timelineHoldMix[i];
alpha = alphaHold * Math.Max(0, 1 - holdMix.mixTime / holdMix.mixDuration);
break;
case AnimationState.Subsequent:
if (!drawOrder && timeline is DrawOrderTimeline) continue;
timelineBlend = blend;
alpha = alphaMix;
break;
case AnimationState.First:
timelineBlend = MixBlend.Setup;
alpha = alphaMix;
break;
case AnimationState.HoldSubsequent:
timelineBlend = blend;
alpha = alphaHold;
break;
case AnimationState.HoldFirst:
timelineBlend = MixBlend.Setup;
alpha = alphaHold;
break;
default: // HoldMix
timelineBlend = MixBlend.Setup;
TrackEntry holdMix = timelineHoldMix[i];
alpha = alphaHold * Math.Max(0, 1 - holdMix.mixTime / holdMix.mixDuration);
break;
}
from.totalAlpha += alpha;
var rotateTimeline = timeline as RotateTimeline;
@ -444,22 +440,19 @@ namespace Spine {
float mix;
if (to.mixDuration == 0) { // Single frame mix to undo mixingFrom changes.
mix = 1;
}
else {
} else {
mix = to.mixTime / to.mixDuration;
if (mix > 1) mix = 1;
}
var eventBuffer = mix < from.eventThreshold ? this.events : null;
if (eventBuffer == null)
return mix;
ExposedList<Event> eventBuffer = mix < from.eventThreshold ? this.events : null;
if (eventBuffer == null) return mix;
float animationLast = from.animationLast, animationTime = from.AnimationTime;
var timelines = from.animation.timelines;
int timelineCount = timelines.Count;
var timelinesItems = timelines.Items;
int timelineCount = from.animation.timelines.Count;
Timeline[] timelines = from.animation.timelines.Items;
for (int i = 0; i < timelineCount; i++) {
var timeline = timelinesItems[i];
Timeline timeline = timelines[i];
if (timeline is EventTimeline)
timeline.Apply(skeleton, animationLast, animationTime, eventBuffer, 0, MixBlend.Setup, MixDirection.Out);
}
@ -486,10 +479,8 @@ namespace Spine {
if (time < frames[0]) { // Time is before first frame.
if (blend == MixBlend.Setup || blend == MixBlend.First)
SetAttachment(skeleton, slot, slot.data.attachmentName, attachments);
}
else {
SetAttachment(skeleton, slot, timeline.AttachmentNames[Animation.Search(frames, time)], attachments);
}
} else
SetAttachment(skeleton, slot, timeline.AttachmentNames[Timeline.Search(frames, time)], attachments);
// If an attachment wasn't set (ie before the first frame or attachments is false), set the setup attachment later.
if (slot.attachmentState <= unkeyedState) slot.attachmentState = unkeyedState + Setup;
@ -570,8 +561,7 @@ namespace Spine {
float trackLastWrapped = entry.trackLast % duration;
// Queue events before complete.
var events = this.events;
var eventsItems = events.Items;
Event[] eventsItems = this.events.Items;
int i = 0, n = events.Count;
for (; i < n; i++) {
Event e = eventsItems[i];
@ -698,9 +688,8 @@ namespace Spine {
DisposeNext(current);
current = current.mixingFrom;
interrupt = false; // mixingFrom is current again, but don't interrupt it twice.
} else {
} else
DisposeNext(current);
}
}
TrackEntry entry = NewTrackEntry(trackIndex, animation, loop, current);
SetCurrent(trackIndex, entry, interrupt);
@ -801,7 +790,7 @@ namespace Spine {
public void SetEmptyAnimations (float mixDuration) {
bool oldDrainDisabled = queue.drainDisabled;
queue.drainDisabled = true;
var tracksItems = tracks.Items;
TrackEntry[] tracksItems = tracks.Items;
for (int i = 0, n = tracks.Count; i < n; i++) {
TrackEntry current = tracksItems[i];
if (current != null) SetEmptyAnimation(current.trackIndex, mixDuration);
@ -819,7 +808,7 @@ namespace Spine {
/// <summary>Object-pooling version of new TrackEntry. Obtain an unused TrackEntry from the pool and clear/initialize its values.</summary>
/// <param name="last">May be null.</param>
private TrackEntry NewTrackEntry (int trackIndex, Animation animation, bool loop, TrackEntry last) {
TrackEntry entry = trackEntryPool.Obtain(); // Pooling
TrackEntry entry = trackEntryPool.Obtain();
entry.trackIndex = trackIndex;
entry.animation = animation;
entry.loop = loop;
@ -837,14 +826,14 @@ namespace Spine {
entry.delay = 0;
entry.trackTime = 0;
entry.trackLast = -1;
entry.nextTrackLast = -1; // nextTrackLast == -1 signifies a TrackEntry that wasn't applied yet.
entry.trackEnd = float.MaxValue; // loop ? float.MaxValue : animation.Duration;
entry.nextTrackLast = -1;
entry.trackEnd = float.MaxValue;
entry.timeScale = 1;
entry.alpha = 1;
entry.interruptAlpha = 1;
entry.mixTime = 0;
entry.mixDuration = (last == null) ? 0 : data.GetMix(last.animation, animation);
entry.mixDuration = last == null ? 0 : data.GetMix(last.animation, animation);
return entry;
}
@ -864,7 +853,7 @@ namespace Spine {
// Process in the order that animations are applied.
propertyIds.Clear();
int n = tracks.Count;
var tracksItems = tracks.Items;
TrackEntry[] tracksItems = tracks.Items;
for (int i = 0; i < n; i++) {
TrackEntry entry = tracksItems[i];
if (entry == null) continue;
@ -882,12 +871,12 @@ namespace Spine {
private void ComputeHold (TrackEntry entry) {
TrackEntry to = entry.mixingTo;
var timelines = entry.animation.timelines.Items;
Timeline[] timelines = entry.animation.timelines.Items;
int timelinesCount = entry.animation.timelines.Count;
var timelineMode = entry.timelineMode.Resize(timelinesCount).Items; //timelineMode.setSize(timelinesCount);
int[] timelineMode = entry.timelineMode.Resize(timelinesCount).Items;
entry.timelineHoldMix.Clear();
var timelineHoldMix = entry.timelineHoldMix.Resize(timelinesCount).Items; //timelineHoldMix.setSize(timelinesCount);
var propertyIds = this.propertyIds;
TrackEntry[] timelineHoldMix = entry.timelineHoldMix.Resize(timelinesCount).Items;
HashSet<string> propertyIds = this.propertyIds;
if (to != null && to.holdPrevious) {
for (int i = 0; i < timelinesCount; i++)
@ -958,7 +947,7 @@ namespace Spine {
override public string ToString () {
var buffer = new System.Text.StringBuilder();
var tracksItems = tracks.Items;
TrackEntry[] tracksItems = tracks.Items;
for (int i = 0, n = tracks.Count; i < n; i++) {
TrackEntry entry = tracksItems[i];
if (entry == null) continue;
@ -1273,7 +1262,7 @@ namespace Spine {
}
class EventQueue {
private readonly List<EventQueueEntry> eventQueueEntries = new List<EventQueueEntry>();
private readonly ExposedList<EventQueueEntry> eventQueueEntries = new ExposedList<EventQueueEntry>();
internal bool drainDisabled;
private readonly AnimationState state;
@ -1286,22 +1275,6 @@ namespace Spine {
this.trackEntryPool = trackEntryPool;
}
struct EventQueueEntry {
public EventType type;
public TrackEntry entry;
public Event e;
public EventQueueEntry (EventType eventType, TrackEntry trackEntry, Event e = null) {
this.type = eventType;
this.entry = trackEntry;
this.e = e;
}
}
enum EventType {
Start, Interrupt, End, Dispose, Complete, Event
}
internal void Start (TrackEntry entry) {
eventQueueEntries.Add(new EventQueueEntry(EventType.Start, entry));
if (AnimationsChanged != null) AnimationsChanged();
@ -1333,12 +1306,12 @@ namespace Spine {
if (drainDisabled) return;
drainDisabled = true;
var entries = this.eventQueueEntries;
EventQueueEntry[] entries = eventQueueEntries.Items;
AnimationState state = this.state;
// Don't cache entries.Count so callbacks can queue their own events (eg, call SetAnimation in AnimationState_Complete).
for (int i = 0; i < entries.Count; i++) {
var queueEntry = entries[i];
// Don't cache eventQueueEntries.Count so callbacks can queue their own events (eg, call SetAnimation in AnimationState_Complete).
for (int i = 0; i < eventQueueEntries.Count; i++) {
EventQueueEntry queueEntry = entries[i];
TrackEntry trackEntry = queueEntry.entry;
switch (queueEntry.type) {
@ -1357,7 +1330,7 @@ namespace Spine {
case EventType.Dispose:
trackEntry.OnDispose();
state.OnDispose(trackEntry);
trackEntryPool.Free(trackEntry); // Pooling
trackEntryPool.Free(trackEntry);
break;
case EventType.Complete:
trackEntry.OnComplete();
@ -1377,9 +1350,25 @@ namespace Spine {
internal void Clear () {
eventQueueEntries.Clear();
}
struct EventQueueEntry {
public EventType type;
public TrackEntry entry;
public Event e;
public EventQueueEntry (EventType eventType, TrackEntry trackEntry, Event e = null) {
this.type = eventType;
this.entry = trackEntry;
this.e = e;
}
}
enum EventType {
Start, Interrupt, End, Dispose, Complete, Event
}
}
public class Pool<T> where T : class, new() {
class Pool<T> where T : class, new() {
public readonly int max;
readonly Stack<T> freeObjects;
@ -1404,19 +1393,6 @@ namespace Spine {
Reset(obj);
}
// protected void FreeAll (List<T> objects) {
// if (objects == null) throw new ArgumentNullException("objects", "objects cannot be null.");
// var freeObjects = this.freeObjects;
// int max = this.max;
// for (int i = 0; i < objects.Count; i++) {
// T obj = objects[i];
// if (obj == null) continue;
// if (freeObjects.Count < max) freeObjects.Push(obj);
// Reset(obj);
// }
// Peak = Math.Max(Peak, freeObjects.Count);
// }
public void Clear () {
freeObjects.Clear();
}
@ -1435,7 +1411,7 @@ namespace Spine {
public static bool AddAll<T> (this HashSet<T> set, T[] addSet) {
bool anyItemAdded = false;
for (int i = 0, n = addSet.Length; i < n; ++i) {
var item = addSet[i];
T item = addSet[i];
anyItemAdded |= set.Add(item);
}
return anyItemAdded;

View File

@ -78,8 +78,7 @@ namespace Spine {
/// <param name="stride">The number of <paramref name="worldVertices"/> entries between the value pairs written.</param>
public void ComputeWorldVertices (Slot slot, int start, int count, float[] worldVertices, int offset, int stride = 2) {
count = offset + (count >> 1) * stride;
Skeleton skeleton = slot.bone.skeleton;
var deformArray = slot.deform;
ExposedList<float> deformArray = slot.deform;
float[] vertices = this.vertices;
int[] bones = this.bones;
if (bones == null) {
@ -100,7 +99,7 @@ namespace Spine {
v += n + 1;
skip += n;
}
var skeletonBones = skeleton.bones.Items;
Bone[] skeletonBones = slot.bone.skeleton.bones.Items;
if (deformArray.Count == 0) {
for (int w = offset, b = skip * 3; w < count; w += stride) {
float wx = 0, wy = 0;
@ -138,15 +137,13 @@ namespace Spine {
if (bones != null) {
attachment.bones = new int[bones.Length];
Array.Copy(bones, 0, attachment.bones, 0, bones.Length);
}
else
} else
attachment.bones = null;
if (vertices != null) {
attachment.vertices = new float[vertices.Length];
Array.Copy(vertices, 0, attachment.vertices, 0, vertices.Length);
}
else
} else
attachment.vertices = null;
attachment.worldVerticesLength = worldVerticesLength;

View File

@ -174,77 +174,77 @@ namespace Spine {
switch (data.transformMode) {
case TransformMode.Normal: {
float rotationY = rotation + 90 + shearY;
float la = MathUtils.CosDeg(rotation + shearX) * scaleX;
float lb = MathUtils.CosDeg(rotationY) * scaleY;
float lc = MathUtils.SinDeg(rotation + shearX) * scaleX;
float ld = MathUtils.SinDeg(rotationY) * scaleY;
a = pa * la + pb * lc;
b = pa * lb + pb * ld;
c = pc * la + pd * lc;
d = pc * lb + pd * ld;
return;
}
float rotationY = rotation + 90 + shearY;
float la = MathUtils.CosDeg(rotation + shearX) * scaleX;
float lb = MathUtils.CosDeg(rotationY) * scaleY;
float lc = MathUtils.SinDeg(rotation + shearX) * scaleX;
float ld = MathUtils.SinDeg(rotationY) * scaleY;
a = pa * la + pb * lc;
b = pa * lb + pb * ld;
c = pc * la + pd * lc;
d = pc * lb + pd * ld;
return;
}
case TransformMode.OnlyTranslation: {
float rotationY = rotation + 90 + shearY;
a = MathUtils.CosDeg(rotation + shearX) * scaleX;
b = MathUtils.CosDeg(rotationY) * scaleY;
c = MathUtils.SinDeg(rotation + shearX) * scaleX;
d = MathUtils.SinDeg(rotationY) * scaleY;
break;
}
float rotationY = rotation + 90 + shearY;
a = MathUtils.CosDeg(rotation + shearX) * scaleX;
b = MathUtils.CosDeg(rotationY) * scaleY;
c = MathUtils.SinDeg(rotation + shearX) * scaleX;
d = MathUtils.SinDeg(rotationY) * scaleY;
break;
}
case TransformMode.NoRotationOrReflection: {
float s = pa * pa + pc * pc, prx;
if (s > 0.0001f) {
s = Math.Abs(pa * pd - pb * pc) / s;
pa /= skeleton.ScaleX;
pc /= skeleton.ScaleY;
pb = pc * s;
pd = pa * s;
prx = MathUtils.Atan2(pc, pa) * MathUtils.RadDeg;
} else {
pa = 0;
pc = 0;
prx = 90 - MathUtils.Atan2(pd, pb) * MathUtils.RadDeg;
}
float rx = rotation + shearX - prx;
float ry = rotation + shearY - prx + 90;
float la = MathUtils.CosDeg(rx) * scaleX;
float lb = MathUtils.CosDeg(ry) * scaleY;
float lc = MathUtils.SinDeg(rx) * scaleX;
float ld = MathUtils.SinDeg(ry) * scaleY;
a = pa * la - pb * lc;
b = pa * lb - pb * ld;
c = pc * la + pd * lc;
d = pc * lb + pd * ld;
break;
float s = pa * pa + pc * pc, prx;
if (s > 0.0001f) {
s = Math.Abs(pa * pd - pb * pc) / s;
pa /= skeleton.ScaleX;
pc /= skeleton.ScaleY;
pb = pc * s;
pd = pa * s;
prx = MathUtils.Atan2(pc, pa) * MathUtils.RadDeg;
} else {
pa = 0;
pc = 0;
prx = 90 - MathUtils.Atan2(pd, pb) * MathUtils.RadDeg;
}
float rx = rotation + shearX - prx;
float ry = rotation + shearY - prx + 90;
float la = MathUtils.CosDeg(rx) * scaleX;
float lb = MathUtils.CosDeg(ry) * scaleY;
float lc = MathUtils.SinDeg(rx) * scaleX;
float ld = MathUtils.SinDeg(ry) * scaleY;
a = pa * la - pb * lc;
b = pa * lb - pb * ld;
c = pc * la + pd * lc;
d = pc * lb + pd * ld;
break;
}
case TransformMode.NoScale:
case TransformMode.NoScaleOrReflection: {
float cos = MathUtils.CosDeg(rotation), sin = MathUtils.SinDeg(rotation);
float za = (pa * cos + pb * sin) / skeleton.ScaleX;
float zc = (pc * cos + pd * sin) / skeleton.ScaleY;
float s = (float)Math.Sqrt(za * za + zc * zc);
if (s > 0.00001f) s = 1 / s;
za *= s;
zc *= s;
s = (float)Math.Sqrt(za * za + zc * zc);
if (data.transformMode == TransformMode.NoScale
&& (pa * pd - pb * pc < 0) != (skeleton.ScaleX < 0 != skeleton.ScaleY < 0)) s = -s;
float cos = MathUtils.CosDeg(rotation), sin = MathUtils.SinDeg(rotation);
float za = (pa * cos + pb * sin) / skeleton.ScaleX;
float zc = (pc * cos + pd * sin) / skeleton.ScaleY;
float s = (float)Math.Sqrt(za * za + zc * zc);
if (s > 0.00001f) s = 1 / s;
za *= s;
zc *= s;
s = (float)Math.Sqrt(za * za + zc * zc);
if (data.transformMode == TransformMode.NoScale
&& (pa * pd - pb * pc < 0) != (skeleton.ScaleX < 0 != skeleton.ScaleY < 0)) s = -s;
float r = MathUtils.PI / 2 + MathUtils.Atan2(zc, za);
float zb = MathUtils.Cos(r) * s;
float zd = MathUtils.Sin(r) * s;
float la = MathUtils.CosDeg(shearX) * scaleX;
float lb = MathUtils.CosDeg(90 + shearY) * scaleY;
float lc = MathUtils.SinDeg(shearX) * scaleX;
float ld = MathUtils.SinDeg(90 + shearY) * scaleY;
a = za * la + zb * lc;
b = za * lb + zb * ld;
c = zc * la + zd * lc;
d = zc * lb + zd * ld;
break;
}
float r = MathUtils.PI / 2 + MathUtils.Atan2(zc, za);
float zb = MathUtils.Cos(r) * s;
float zd = MathUtils.Sin(r) * s;
float la = MathUtils.CosDeg(shearX) * scaleX;
float lb = MathUtils.CosDeg(90 + shearY) * scaleY;
float lc = MathUtils.SinDeg(shearX) * scaleX;
float ld = MathUtils.SinDeg(90 + shearY) * scaleY;
a = za * la + zb * lc;
b = za * lb + zb * ld;
c = zc * la + zd * lc;
d = zc * lb + zd * ld;
break;
}
}
a *= skeleton.ScaleX;

View File

@ -198,10 +198,11 @@ namespace Spine {
if (converter == null)
throw new ArgumentNullException("converter");
ExposedList<TOutput> u = new ExposedList<TOutput>(Count);
for (int i = 0; i < Count; i++)
u.Items[i] = converter(Items[i]);
u.Count = Count;
T[] items = Items;
TOutput[] uItems = u.Items;
for (int i = 0; i < Count; i++)
uItems[i] = converter(items[i]);
return u;
}

View File

@ -293,8 +293,7 @@ namespace Spine {
sx *= a;
if (uniform) sy *= a;
}
}
else
} else
a2 = (float)Math.Acos(cos) * bendDir;
a = l1 + l2 * cos;
b = l2 * (float)Math.Sin(a2);

View File

@ -103,63 +103,62 @@ namespace Spine {
float[] spaces = this.spaces.Resize(spacesCount).Items, lengths = scale ? this.lengths.Resize(boneCount).Items : null;
float spacing = this.spacing;
switch (data.spacingMode) {
case SpacingMode.Percent:
if (scale) {
for (int i = 0, n = spacesCount - 1; i < n; i++) {
Bone bone = bonesItems[i];
float setupLength = bone.data.length;
if (setupLength < PathConstraint.Epsilon)
lengths[i] = 0;
else {
float x = setupLength * bone.a, y = setupLength * bone.c;
lengths[i] = (float)Math.Sqrt(x * x + y * y);
}
}
}
ArraysFill(spaces, 1, spacesCount, spacing);
break;
case SpacingMode.Proportional: {
float sum = 0;
for (int i = 0; i < boneCount;) {
case SpacingMode.Percent:
if (scale) {
for (int i = 0, n = spacesCount - 1; i < n; i++) {
Bone bone = bonesItems[i];
float setupLength = bone.data.length;
if (setupLength < PathConstraint.Epsilon) {
if (scale) lengths[i] = 0;
spaces[++i] = spacing;
} else {
float x = setupLength * bone.a, y = setupLength * bone.c;
float length = (float)Math.Sqrt(x * x + y * y);
if (scale) lengths[i] = length;
spaces[++i] = length;
sum += length;
}
}
if (sum > 0) {
sum = spacesCount / sum * spacing;
for (int i = 1; i < spacesCount; i++)
spaces[i] *= sum;
}
break;
}
default: {
bool lengthSpacing = data.spacingMode == SpacingMode.Length;
for (int i = 0, n = spacesCount - 1; i < n;) {
Bone bone = bonesItems[i];
float setupLength = bone.data.length;
if (setupLength < PathConstraint.Epsilon) {
if (scale) lengths[i] = 0;
spaces[++i] = spacing;
}
if (setupLength < PathConstraint.Epsilon)
lengths[i] = 0;
else {
float x = setupLength * bone.a, y = setupLength * bone.c;
float length = (float)Math.Sqrt(x * x + y * y);
if (scale) lengths[i] = length;
spaces[++i] = (lengthSpacing ? setupLength + spacing : spacing) * length / setupLength;
lengths[i] = (float)Math.Sqrt(x * x + y * y);
}
}
break;
}
ArraysFill(spaces, 1, spacesCount, spacing);
break;
case SpacingMode.Proportional: {
float sum = 0;
for (int i = 0; i < boneCount;) {
Bone bone = bonesItems[i];
float setupLength = bone.data.length;
if (setupLength < PathConstraint.Epsilon) {
if (scale) lengths[i] = 0;
spaces[++i] = spacing;
} else {
float x = setupLength * bone.a, y = setupLength * bone.c;
float length = (float)Math.Sqrt(x * x + y * y);
if (scale) lengths[i] = length;
spaces[++i] = length;
sum += length;
}
}
if (sum > 0) {
sum = spacesCount / sum * spacing;
for (int i = 1; i < spacesCount; i++)
spaces[i] *= sum;
}
break;
}
default: {
bool lengthSpacing = data.spacingMode == SpacingMode.Length;
for (int i = 0, n = spacesCount - 1; i < n;) {
Bone bone = bonesItems[i];
float setupLength = bone.data.length;
if (setupLength < PathConstraint.Epsilon) {
if (scale) lengths[i] = 0;
spaces[++i] = spacing;
} else {
float x = setupLength * bone.a, y = setupLength * bone.c;
float length = (float)Math.Sqrt(x * x + y * y);
if (scale) lengths[i] = length;
spaces[++i] = (lengthSpacing ? setupLength + spacing : spacing) * length / setupLength;
}
}
break;
}
}
float[] positions = ComputeWorldPositions(attachment, spacesCount, tangents);
@ -221,14 +220,13 @@ namespace Spine {
}
float[] ComputeWorldPositions (PathAttachment path, int spacesCount, bool tangents) {
Slot target = this.target;
float position = this.position;
float[] spaces = this.spaces.Items, output = this.positions.Resize(spacesCount * 3 + 2).Items, world;
bool closed = path.Closed;
int verticesLength = path.WorldVerticesLength, curveCount = verticesLength / 6, prevCurve = NONE;
float pathLength;
float multiplier;
float pathLength, multiplier;
if (!path.ConstantSpeed) {
float[] lengths = path.Lengths;
curveCount -= closed ? 1 : 2;
@ -236,17 +234,16 @@ namespace Spine {
if (data.positionMode == PositionMode.Percent) position *= pathLength;
//float multiplier;
switch (data.spacingMode) {
case SpacingMode.Percent:
multiplier = pathLength;
break;
case SpacingMode.Proportional:
multiplier = pathLength / spacesCount;
break;
default:
multiplier = 1;
break;
case SpacingMode.Percent:
multiplier = pathLength;
break;
case SpacingMode.Proportional:
multiplier = pathLength / spacesCount;
break;
default:
multiplier = 1;
break;
}
world = this.world.Resize(8).Items;
@ -355,17 +352,16 @@ namespace Spine {
if (data.positionMode == PositionMode.Percent) position *= pathLength;
//float multiplier;
switch (data.spacingMode) {
case SpacingMode.Percent:
multiplier = pathLength;
break;
case SpacingMode.Proportional:
multiplier = pathLength / spacesCount;
break;
default:
multiplier = 1;
break;
case SpacingMode.Percent:
multiplier = pathLength;
break;
case SpacingMode.Proportional:
multiplier = pathLength / spacesCount;
break;
default:
multiplier = 1;
break;
}
float[] segments = this.segments;

View File

@ -87,7 +87,7 @@ namespace Spine {
this.data = data;
bones = new ExposedList<Bone>(data.bones.Count);
var bonesItems = this.bones.Items;
Bone[] bonesItems = this.bones.Items;
foreach (BoneData boneData in data.bones) {
Bone bone;
if (boneData.parent == null) {
@ -131,17 +131,17 @@ namespace Spine {
var updateCache = this.updateCache;
updateCache.Clear();
int boneCount = this.bones.Items.Length;
var bones = this.bones;
int boneCount = this.bones.Count;
Bone[] bones = this.bones.Items;
for (int i = 0; i < boneCount; i++) {
Bone bone = bones.Items[i];
Bone bone = bones[i];
bone.sorted = bone.data.skinRequired;
bone.active = !bone.sorted;
}
if (skin != null) {
Object[] skinBones = skin.bones.Items;
BoneData[] skinBones = skin.bones.Items;
for (int i = 0, n = skin.bones.Count; i < n; i++) {
Bone bone = (Bone)bones.Items[((BoneData)skinBones[i]).index];
var bone = bones[skinBones[i].index];
do {
bone.sorted = false;
bone.active = true;
@ -151,38 +151,37 @@ namespace Spine {
}
int ikCount = this.ikConstraints.Count, transformCount = this.transformConstraints.Count, pathCount = this.pathConstraints.Count;
var ikConstraints = this.ikConstraints;
var transformConstraints = this.transformConstraints;
var pathConstraints = this.pathConstraints;
IkConstraint[] ikConstraints = this.ikConstraints.Items;
TransformConstraint[] transformConstraints = this.transformConstraints.Items;
PathConstraint[] pathConstraints = this.pathConstraints.Items;
int constraintCount = ikCount + transformCount + pathCount;
//outer:
for (int i = 0; i < constraintCount; i++) {
for (int ii = 0; ii < ikCount; ii++) {
IkConstraint constraint = ikConstraints.Items[ii];
IkConstraint constraint = ikConstraints[ii];
if (constraint.data.order == i) {
SortIkConstraint(constraint);
goto continue_outer; //continue outer;
goto continue_outer;
}
}
for (int ii = 0; ii < transformCount; ii++) {
TransformConstraint constraint = transformConstraints.Items[ii];
TransformConstraint constraint = transformConstraints[ii];
if (constraint.data.order == i) {
SortTransformConstraint(constraint);
goto continue_outer; //continue outer;
goto continue_outer;
}
}
for (int ii = 0; ii < pathCount; ii++) {
PathConstraint constraint = pathConstraints.Items[ii];
PathConstraint constraint = pathConstraints[ii];
if (constraint.data.order == i) {
SortPathConstraint(constraint);
goto continue_outer; //continue outer;
goto continue_outer;
}
}
continue_outer: {}
}
for (int i = 0; i < boneCount; i++)
SortBone(bones.Items[i]);
SortBone(bones[i]);
}
private void SortIkConstraint (IkConstraint constraint) {
@ -200,8 +199,7 @@ namespace Spine {
if (constrained.Count == 1) {
updateCache.Add(constraint);
SortReset(parent.children);
}
else {
} else {
Bone child = constrained.Items[constrained.Count - 1];
SortBone(child);
@ -269,9 +267,8 @@ namespace Spine {
}
private void SortPathConstraintAttachment (Skin skin, int slotIndex, Bone slotBone) {
foreach (var entry in skin.Attachments) {
foreach (var entry in skin.Attachments)
if (entry.SlotIndex == slotIndex) SortPathConstraintAttachment(entry.Attachment, slotBone);
}
}
private void SortPathConstraintAttachment (Attachment attachment, Bone slotBone) {
@ -299,7 +296,7 @@ namespace Spine {
}
private static void SortReset (ExposedList<Bone> bones) {
var bonesItems = bones.Items;
Bone[] bonesItems = bones.Items;
for (int i = 0, n = bones.Count; i < n; i++) {
Bone bone = bonesItems[i];
if (!bone.active) continue;
@ -308,7 +305,6 @@ namespace Spine {
}
}
/// <summary>
/// Updates the world transform for each bone and applies all constraints.
/// <para>
@ -316,9 +312,9 @@ namespace Spine {
/// Runtimes Guide.</para>
/// </summary>
public void UpdateWorldTransform () {
Object[] bones = this.bones.Items;
Bone[] bones = this.bones.Items;
for (int i = 0, n = this.bones.Count; i < n; i++) {
Bone bone = (Bone)bones[i];
Bone bone = bones[i];
bone.ax = bone.x;
bone.ay = bone.y;
bone.arotation = bone.rotation;
@ -360,8 +356,7 @@ namespace Spine {
var updateCache = this.updateCache.Items;
for (int i = 0, n = this.updateCache.Count; i < n; i++) {
var updatable = updateCache[i];
if (updatable != rootBone)
updatable.Update();
if (updatable != rootBone) updatable.Update();
}
}
@ -380,34 +375,35 @@ namespace Spine {
var ikConstraints = this.ikConstraints.Items;
for (int i = 0, n = this.ikConstraints.Count; i < n; i++) {
IkConstraint constraint = ikConstraints[i];
constraint.mix = constraint.data.mix;
constraint.softness = constraint.data.softness;
constraint.bendDirection = constraint.data.bendDirection;
constraint.compress = constraint.data.compress;
constraint.stretch = constraint.data.stretch;
IkConstraintData data = constraint.data;
constraint.mix = data.mix;
constraint.softness = data.softness;
constraint.bendDirection = data.bendDirection;
constraint.compress = data.compress;
constraint.stretch = data.stretch;
}
var transformConstraints = this.transformConstraints.Items;
for (int i = 0, n = this.transformConstraints.Count; i < n; i++) {
TransformConstraint constraint = transformConstraints[i];
TransformConstraintData constraintData = constraint.data;
constraint.mixRotate = constraintData.mixRotate;
constraint.mixX = constraintData.mixX;
constraint.mixY = constraintData.mixY;
constraint.mixScaleX = constraintData.mixScaleX;
constraint.mixScaleY = constraintData.mixScaleY;
constraint.mixShearY = constraintData.mixShearY;
TransformConstraintData data = constraint.data;
constraint.mixRotate = data.mixRotate;
constraint.mixX = data.mixX;
constraint.mixY = data.mixY;
constraint.mixScaleX = data.mixScaleX;
constraint.mixScaleY = data.mixScaleY;
constraint.mixShearY = data.mixShearY;
}
var pathConstraints = this.pathConstraints.Items;
for (int i = 0, n = this.pathConstraints.Count; i < n; i++) {
PathConstraint constraint = pathConstraints[i];
PathConstraintData constraintData = constraint.data;
constraint.position = constraintData.position;
constraint.spacing = constraintData.spacing;
constraint.mixRotate = constraintData.mixRotate;
constraint.mixX = constraintData.mixX;
constraint.mixY = constraintData.mixY;
PathConstraintData data = constraint.data;
constraint.position = data.position;
constraint.spacing = data.spacing;
constraint.mixRotate = data.mixRotate;
constraint.mixX = data.mixX;
constraint.mixY = data.mixY;
}
}
@ -491,9 +487,9 @@ namespace Spine {
if (skin != null)
newSkin.AttachAll(this, skin);
else {
ExposedList<Slot> slots = this.slots;
for (int i = 0, n = slots.Count; i < n; i++) {
Slot slot = slots.Items[i];
Slot[] slots = this.slots.Items;
for (int i = 0, n = this.slots.Count; i < n; i++) {
Slot slot = slots[i];
string name = slot.data.attachmentName;
if (name != null) {
Attachment attachment = newSkin.GetAttachment(i, name);
@ -527,9 +523,9 @@ namespace Spine {
/// <param name="attachmentName">May be null to clear the slot's attachment.</param>
public void SetAttachment (string slotName, string attachmentName) {
if (slotName == null) throw new ArgumentNullException("slotName", "slotName cannot be null.");
ExposedList<Slot> slots = this.slots;
for (int i = 0, n = slots.Count; i < n; i++) {
Slot slot = slots.Items[i];
Slot[] slots = this.slots.Items;
for (int i = 0, n = this.slots.Count; i < n; i++) {
Slot slot = slots[i];
if (slot.data.name == slotName) {
Attachment attachment = null;
if (attachmentName != null) {

View File

@ -376,162 +376,162 @@ namespace Spine {
switch ((AttachmentType)input.ReadByte()) {
case AttachmentType.Region: {
String path = input.ReadStringRef();
float rotation = input.ReadFloat();
float x = input.ReadFloat();
float y = input.ReadFloat();
float scaleX = input.ReadFloat();
float scaleY = input.ReadFloat();
float width = input.ReadFloat();
float height = input.ReadFloat();
int color = input.ReadInt();
String path = input.ReadStringRef();
float rotation = input.ReadFloat();
float x = input.ReadFloat();
float y = input.ReadFloat();
float scaleX = input.ReadFloat();
float scaleY = input.ReadFloat();
float width = input.ReadFloat();
float height = input.ReadFloat();
int color = input.ReadInt();
if (path == null) path = name;
RegionAttachment region = attachmentLoader.NewRegionAttachment(skin, name, path);
if (region == null) return null;
region.Path = path;
region.x = x * scale;
region.y = y * scale;
region.scaleX = scaleX;
region.scaleY = scaleY;
region.rotation = rotation;
region.width = width * scale;
region.height = height * scale;
region.r = ((color & 0xff000000) >> 24) / 255f;
region.g = ((color & 0x00ff0000) >> 16) / 255f;
region.b = ((color & 0x0000ff00) >> 8) / 255f;
region.a = ((color & 0x000000ff)) / 255f;
region.UpdateOffset();
return region;
}
if (path == null) path = name;
RegionAttachment region = attachmentLoader.NewRegionAttachment(skin, name, path);
if (region == null) return null;
region.Path = path;
region.x = x * scale;
region.y = y * scale;
region.scaleX = scaleX;
region.scaleY = scaleY;
region.rotation = rotation;
region.width = width * scale;
region.height = height * scale;
region.r = ((color & 0xff000000) >> 24) / 255f;
region.g = ((color & 0x00ff0000) >> 16) / 255f;
region.b = ((color & 0x0000ff00) >> 8) / 255f;
region.a = ((color & 0x000000ff)) / 255f;
region.UpdateOffset();
return region;
}
case AttachmentType.Boundingbox: {
int vertexCount = input.ReadInt(true);
Vertices vertices = ReadVertices(input, vertexCount);
if (nonessential) input.ReadInt(); //int color = nonessential ? input.ReadInt() : 0; // Avoid unused local warning.
int vertexCount = input.ReadInt(true);
Vertices vertices = ReadVertices(input, vertexCount);
if (nonessential) input.ReadInt(); //int color = nonessential ? input.ReadInt() : 0; // Avoid unused local warning.
BoundingBoxAttachment box = attachmentLoader.NewBoundingBoxAttachment(skin, name);
if (box == null) return null;
box.worldVerticesLength = vertexCount << 1;
box.vertices = vertices.vertices;
box.bones = vertices.bones;
// skipped porting: if (nonessential) Color.rgba8888ToColor(box.getColor(), color);
return box;
}
BoundingBoxAttachment box = attachmentLoader.NewBoundingBoxAttachment(skin, name);
if (box == null) return null;
box.worldVerticesLength = vertexCount << 1;
box.vertices = vertices.vertices;
box.bones = vertices.bones;
// skipped porting: if (nonessential) Color.rgba8888ToColor(box.getColor(), color);
return box;
}
case AttachmentType.Mesh: {
String path = input.ReadStringRef();
int color = input.ReadInt();
int vertexCount = input.ReadInt(true);
float[] uvs = ReadFloatArray(input, vertexCount << 1, 1);
int[] triangles = ReadShortArray(input);
Vertices vertices = ReadVertices(input, vertexCount);
int hullLength = input.ReadInt(true);
int[] edges = null;
float width = 0, height = 0;
if (nonessential) {
edges = ReadShortArray(input);
width = input.ReadFloat();
height = input.ReadFloat();
}
if (path == null) path = name;
MeshAttachment mesh = attachmentLoader.NewMeshAttachment(skin, name, path);
if (mesh == null) return null;
mesh.Path = path;
mesh.r = ((color & 0xff000000) >> 24) / 255f;
mesh.g = ((color & 0x00ff0000) >> 16) / 255f;
mesh.b = ((color & 0x0000ff00) >> 8) / 255f;
mesh.a = ((color & 0x000000ff)) / 255f;
mesh.bones = vertices.bones;
mesh.vertices = vertices.vertices;
mesh.WorldVerticesLength = vertexCount << 1;
mesh.triangles = triangles;
mesh.regionUVs = uvs;
mesh.UpdateUVs();
mesh.HullLength = hullLength << 1;
if (nonessential) {
mesh.Edges = edges;
mesh.Width = width * scale;
mesh.Height = height * scale;
}
return mesh;
String path = input.ReadStringRef();
int color = input.ReadInt();
int vertexCount = input.ReadInt(true);
float[] uvs = ReadFloatArray(input, vertexCount << 1, 1);
int[] triangles = ReadShortArray(input);
Vertices vertices = ReadVertices(input, vertexCount);
int hullLength = input.ReadInt(true);
int[] edges = null;
float width = 0, height = 0;
if (nonessential) {
edges = ReadShortArray(input);
width = input.ReadFloat();
height = input.ReadFloat();
}
if (path == null) path = name;
MeshAttachment mesh = attachmentLoader.NewMeshAttachment(skin, name, path);
if (mesh == null) return null;
mesh.Path = path;
mesh.r = ((color & 0xff000000) >> 24) / 255f;
mesh.g = ((color & 0x00ff0000) >> 16) / 255f;
mesh.b = ((color & 0x0000ff00) >> 8) / 255f;
mesh.a = ((color & 0x000000ff)) / 255f;
mesh.bones = vertices.bones;
mesh.vertices = vertices.vertices;
mesh.WorldVerticesLength = vertexCount << 1;
mesh.triangles = triangles;
mesh.regionUVs = uvs;
mesh.UpdateUVs();
mesh.HullLength = hullLength << 1;
if (nonessential) {
mesh.Edges = edges;
mesh.Width = width * scale;
mesh.Height = height * scale;
}
return mesh;
}
case AttachmentType.Linkedmesh: {
String path = input.ReadStringRef();
int color = input.ReadInt();
String skinName = input.ReadStringRef();
String parent = input.ReadStringRef();
bool inheritDeform = input.ReadBoolean();
float width = 0, height = 0;
if (nonessential) {
width = input.ReadFloat();
height = input.ReadFloat();
}
if (path == null) path = name;
MeshAttachment mesh = attachmentLoader.NewMeshAttachment(skin, name, path);
if (mesh == null) return null;
mesh.Path = path;
mesh.r = ((color & 0xff000000) >> 24) / 255f;
mesh.g = ((color & 0x00ff0000) >> 16) / 255f;
mesh.b = ((color & 0x0000ff00) >> 8) / 255f;
mesh.a = ((color & 0x000000ff)) / 255f;
if (nonessential) {
mesh.Width = width * scale;
mesh.Height = height * scale;
}
linkedMeshes.Add(new SkeletonJson.LinkedMesh(mesh, skinName, slotIndex, parent, inheritDeform));
return mesh;
String path = input.ReadStringRef();
int color = input.ReadInt();
String skinName = input.ReadStringRef();
String parent = input.ReadStringRef();
bool inheritDeform = input.ReadBoolean();
float width = 0, height = 0;
if (nonessential) {
width = input.ReadFloat();
height = input.ReadFloat();
}
if (path == null) path = name;
MeshAttachment mesh = attachmentLoader.NewMeshAttachment(skin, name, path);
if (mesh == null) return null;
mesh.Path = path;
mesh.r = ((color & 0xff000000) >> 24) / 255f;
mesh.g = ((color & 0x00ff0000) >> 16) / 255f;
mesh.b = ((color & 0x0000ff00) >> 8) / 255f;
mesh.a = ((color & 0x000000ff)) / 255f;
if (nonessential) {
mesh.Width = width * scale;
mesh.Height = height * scale;
}
linkedMeshes.Add(new SkeletonJson.LinkedMesh(mesh, skinName, slotIndex, parent, inheritDeform));
return mesh;
}
case AttachmentType.Path: {
bool closed = input.ReadBoolean();
bool constantSpeed = input.ReadBoolean();
int vertexCount = input.ReadInt(true);
Vertices vertices = ReadVertices(input, vertexCount);
float[] lengths = new float[vertexCount / 3];
for (int i = 0, n = lengths.Length; i < n; i++)
lengths[i] = input.ReadFloat() * scale;
if (nonessential) input.ReadInt(); //int color = nonessential ? input.ReadInt() : 0;
bool closed = input.ReadBoolean();
bool constantSpeed = input.ReadBoolean();
int vertexCount = input.ReadInt(true);
Vertices vertices = ReadVertices(input, vertexCount);
float[] lengths = new float[vertexCount / 3];
for (int i = 0, n = lengths.Length; i < n; i++)
lengths[i] = input.ReadFloat() * scale;
if (nonessential) input.ReadInt(); //int color = nonessential ? input.ReadInt() : 0;
PathAttachment path = attachmentLoader.NewPathAttachment(skin, name);
if (path == null) return null;
path.closed = closed;
path.constantSpeed = constantSpeed;
path.worldVerticesLength = vertexCount << 1;
path.vertices = vertices.vertices;
path.bones = vertices.bones;
path.lengths = lengths;
// skipped porting: if (nonessential) Color.rgba8888ToColor(path.getColor(), color);
return path;
}
PathAttachment path = attachmentLoader.NewPathAttachment(skin, name);
if (path == null) return null;
path.closed = closed;
path.constantSpeed = constantSpeed;
path.worldVerticesLength = vertexCount << 1;
path.vertices = vertices.vertices;
path.bones = vertices.bones;
path.lengths = lengths;
// skipped porting: if (nonessential) Color.rgba8888ToColor(path.getColor(), color);
return path;
}
case AttachmentType.Point: {
float rotation = input.ReadFloat();
float x = input.ReadFloat();
float y = input.ReadFloat();
if (nonessential) input.ReadInt(); //int color = nonessential ? input.ReadInt() : 0;
float rotation = input.ReadFloat();
float x = input.ReadFloat();
float y = input.ReadFloat();
if (nonessential) input.ReadInt(); //int color = nonessential ? input.ReadInt() : 0;
PointAttachment point = attachmentLoader.NewPointAttachment(skin, name);
if (point == null) return null;
point.x = x * scale;
point.y = y * scale;
point.rotation = rotation;
// skipped porting: if (nonessential) point.color = color;
return point;
}
PointAttachment point = attachmentLoader.NewPointAttachment(skin, name);
if (point == null) return null;
point.x = x * scale;
point.y = y * scale;
point.rotation = rotation;
// skipped porting: if (nonessential) point.color = color;
return point;
}
case AttachmentType.Clipping: {
int endSlotIndex = input.ReadInt(true);
int vertexCount = input.ReadInt(true);
Vertices vertices = ReadVertices(input, vertexCount);
if (nonessential) input.ReadInt();
int endSlotIndex = input.ReadInt(true);
int vertexCount = input.ReadInt(true);
Vertices vertices = ReadVertices(input, vertexCount);
if (nonessential) input.ReadInt();
ClippingAttachment clip = attachmentLoader.NewClippingAttachment(skin, name);
if (clip == null) return null;
clip.EndSlot = skeletonData.slots.Items[endSlotIndex];
clip.worldVerticesLength = vertexCount << 1;
clip.vertices = vertices.vertices;
clip.bones = vertices.bones;
// skipped porting: if (nonessential) Color.rgba8888ToColor(clip.getColor(), color);
return clip;
}
ClippingAttachment clip = attachmentLoader.NewClippingAttachment(skin, name);
if (clip == null) return null;
clip.EndSlot = skeletonData.slots.Items[endSlotIndex];
clip.worldVerticesLength = vertexCount << 1;
clip.vertices = vertices.vertices;
clip.bones = vertices.bones;
// skipped porting: if (nonessential) Color.rgba8888ToColor(clip.getColor(), color);
return clip;
}
}
return null;
}
@ -865,42 +865,42 @@ namespace Spine {
PathConstraintData data = skeletonData.pathConstraints.Items[index];
for (int ii = 0, nn = input.ReadInt(true); ii < nn; ii++) {
switch (input.ReadByte()) {
case PATH_POSITION:
timelines
.Add(ReadTimeline(input, new PathConstraintPositionTimeline(input.ReadInt(true), input.ReadInt(true), index),
data.positionMode == PositionMode.Fixed ? scale : 1));
break;
case PATH_SPACING:
timelines
.Add(ReadTimeline(input, new PathConstraintSpacingTimeline(input.ReadInt(true), input.ReadInt(true), index),
data.spacingMode == SpacingMode.Length || data.spacingMode == SpacingMode.Fixed ? scale : 1));
break;
case PATH_MIX:
PathConstraintMixTimeline timeline = new PathConstraintMixTimeline(input.ReadInt(true), input.ReadInt(true),
index);
float time = input.ReadFloat(), mixRotate = input.ReadFloat(), mixX = input.ReadFloat(), mixY = input.ReadFloat();
for (int frame = 0, bezier = 0, frameLast = timeline.FrameCount - 1; ; frame++) {
timeline.SetFrame(frame, time, mixRotate, mixX, mixY);
if (frame == frameLast) break;
float time2 = input.ReadFloat(), mixRotate2 = input.ReadFloat(), mixX2 = input.ReadFloat(),
mixY2 = input.ReadFloat();
switch (input.ReadByte()) {
case CURVE_STEPPED:
timeline.SetStepped(frame);
break;
case CURVE_BEZIER:
SetBezier(input, timeline, bezier++, frame, 0, time, time2, mixRotate, mixRotate2, 1);
SetBezier(input, timeline, bezier++, frame, 1, time, time2, mixX, mixX2, 1);
SetBezier(input, timeline, bezier++, frame, 2, time, time2, mixY, mixY2, 1);
break;
}
time = time2;
mixRotate = mixRotate2;
mixX = mixX2;
mixY = mixY2;
case PATH_POSITION:
timelines
.Add(ReadTimeline(input, new PathConstraintPositionTimeline(input.ReadInt(true), input.ReadInt(true), index),
data.positionMode == PositionMode.Fixed ? scale : 1));
break;
case PATH_SPACING:
timelines
.Add(ReadTimeline(input, new PathConstraintSpacingTimeline(input.ReadInt(true), input.ReadInt(true), index),
data.spacingMode == SpacingMode.Length || data.spacingMode == SpacingMode.Fixed ? scale : 1));
break;
case PATH_MIX:
PathConstraintMixTimeline timeline = new PathConstraintMixTimeline(input.ReadInt(true), input.ReadInt(true),
index);
float time = input.ReadFloat(), mixRotate = input.ReadFloat(), mixX = input.ReadFloat(), mixY = input.ReadFloat();
for (int frame = 0, bezier = 0, frameLast = timeline.FrameCount - 1; ; frame++) {
timeline.SetFrame(frame, time, mixRotate, mixX, mixY);
if (frame == frameLast) break;
float time2 = input.ReadFloat(), mixRotate2 = input.ReadFloat(), mixX2 = input.ReadFloat(),
mixY2 = input.ReadFloat();
switch (input.ReadByte()) {
case CURVE_STEPPED:
timeline.SetStepped(frame);
break;
case CURVE_BEZIER:
SetBezier(input, timeline, bezier++, frame, 0, time, time2, mixRotate, mixRotate2, 1);
SetBezier(input, timeline, bezier++, frame, 1, time, time2, mixX, mixX2, 1);
SetBezier(input, timeline, bezier++, frame, 2, time, time2, mixY, mixY2, 1);
break;
}
timelines.Add(timeline);
break;
time = time2;
mixRotate = mixRotate2;
mixX = mixX2;
mixY = mixY2;
}
timelines.Add(timeline);
break;
}
}
}
@ -934,8 +934,7 @@ namespace Spine {
if (scale == 1) {
for (int v = start; v < end; v++)
deform[v] = input.ReadFloat();
}
else {
} else {
for (int v = start; v < end; v++)
deform[v] = input.ReadFloat() * scale;
}
@ -948,12 +947,12 @@ namespace Spine {
if (frame == frameLast) break;
float time2 = input.ReadFloat();
switch (input.ReadByte()) {
case CURVE_STEPPED:
timeline.SetStepped(frame);
break;
case CURVE_BEZIER:
SetBezier(input, timeline, bezier++, frame, 0, time, time2, 0, 1, 1);
break;
case CURVE_STEPPED:
timeline.SetStepped(frame);
break;
case CURVE_BEZIER:
SetBezier(input, timeline, bezier++, frame, 0, time, time2, 0, 1, 1);
break;
}
time = time2;
}

View File

@ -64,8 +64,8 @@ namespace Spine {
public void Update (Skeleton skeleton, bool updateAabb) {
ExposedList<BoundingBoxAttachment> boundingBoxes = BoundingBoxes;
ExposedList<Polygon> polygons = Polygons;
ExposedList<Slot> slots = skeleton.slots;
int slotCount = slots.Count;
Slot[] slots = skeleton.slots.Items;
int slotCount = skeleton.slots.Count;
boundingBoxes.Clear();
for (int i = 0, n = polygons.Count; i < n; i++)
@ -73,7 +73,7 @@ namespace Spine {
polygons.Clear();
for (int i = 0; i < slotCount; i++) {
Slot slot = slots.Items[i];
Slot slot = slots[i];
if (!slot.bone.active) continue;
BoundingBoxAttachment boundingBox = slot.attachment as BoundingBoxAttachment;
if (boundingBox == null) continue;
@ -106,9 +106,9 @@ namespace Spine {
private void AabbCompute () {
float minX = int.MaxValue, minY = int.MaxValue, maxX = int.MinValue, maxY = int.MinValue;
ExposedList<Polygon> polygons = Polygons;
for (int i = 0, n = polygons.Count; i < n; i++) {
Polygon polygon = polygons.Items[i];
Polygon[] polygons = Polygons.Items;
for (int i = 0, n = Polygons.Count; i < n; i++) {
Polygon polygon = polygons[i];
float[] vertices = polygon.Vertices;
for (int ii = 0, nn = polygon.Count; ii < nn; ii += 2) {
float x = vertices[ii];
@ -178,18 +178,18 @@ namespace Spine {
/// <summary>Returns the first bounding box attachment that contains the point, or null. When doing many checks, it is usually more
/// efficient to only call this method if <see cref="AabbContainsPoint(float, float)"/> returns true.</summary>
public BoundingBoxAttachment ContainsPoint (float x, float y) {
ExposedList<Polygon> polygons = Polygons;
for (int i = 0, n = polygons.Count; i < n; i++)
if (ContainsPoint(polygons.Items[i], x, y)) return BoundingBoxes.Items[i];
Polygon[] polygons = Polygons.Items;
for (int i = 0, n = Polygons.Count; i < n; i++)
if (ContainsPoint(polygons[i], x, y)) return BoundingBoxes.Items[i];
return null;
}
/// <summary>Returns the first bounding box attachment that contains the line segment, or null. When doing many checks, it is usually
/// more efficient to only call this method if <see cref="aabbIntersectsSegment(float, float, float, float)"/> returns true.</summary>
public BoundingBoxAttachment IntersectsSegment (float x1, float y1, float x2, float y2) {
ExposedList<Polygon> polygons = Polygons;
for (int i = 0, n = polygons.Count; i < n; i++)
if (IntersectsSegment(polygons.Items[i], x1, y1, x2, y2)) return BoundingBoxes.Items[i];
Polygon[] polygons = Polygons.Items;
for (int i = 0, n = Polygons.Count; i < n; i++)
if (IntersectsSegment(polygons[i], x1, y1, x2, y2)) return BoundingBoxes.Items[i];
return null;
}

View File

@ -137,8 +137,7 @@ namespace Spine {
s += 3;
}
index += clipOutputCount + 1;
}
else {
} else {
float[] clippedVerticesItems = clippedVertices.Resize(s + 3 * 2).Items;
float[] clippedUVsItems = clippedUVs.Resize(s + 3 * 2).Items;
clippedVerticesItems[s] = x1;
@ -224,8 +223,7 @@ namespace Spine {
output.Add(edgeX);
output.Add(edgeY);
}
}
else if (side2) { // v1 outside, v2 inside
} else if (side2) { // v1 outside, v2 inside
float c0 = inputY2 - inputY, c2 = inputX2 - inputX;
float s = c0 * (edgeX2 - edgeX) - c2 * (edgeY2 - edgeY);
if (Math.Abs(s) > 0.000001f) {
@ -259,12 +257,10 @@ namespace Spine {
if (originalOutput != output) {
originalOutput.Clear();
for (int i = 0, n = output.Count - 2; i < n; i++) {
for (int i = 0, n = output.Count - 2; i < n; i++)
originalOutput.Add(output.Items[i]);
}
} else {
} else
originalOutput.Resize(originalOutput.Count - 2);
}
return clipped;
}

View File

@ -136,9 +136,9 @@ namespace Spine {
/// <returns>-1 if the slot was not found.</returns>
public int FindSlotIndex (string slotName) {
if (slotName == null) throw new ArgumentNullException("slotName", "slotName cannot be null.");
ExposedList<SlotData> slots = this.slots;
for (int i = 0, n = slots.Count; i < n; i++)
if (slots.Items[i].name == slotName) return i;
SlotData[] slots = this.slots.Items;
for (int i = 0, n = this.slots.Count; i < n; i++)
if (slots[i].name == slotName) return i;
return -1;
}
@ -217,9 +217,9 @@ namespace Spine {
/// <returns>-1 if the path constraint was not found.</returns>
public int FindPathConstraintIndex (string pathConstraintName) {
if (pathConstraintName == null) throw new ArgumentNullException("pathConstraintName", "pathConstraintName cannot be null.");
ExposedList<PathConstraintData> pathConstraints = this.pathConstraints;
for (int i = 0, n = pathConstraints.Count; i < n; i++)
if (pathConstraints.Items[i].name.Equals(pathConstraintName)) return i;
PathConstraintData[] pathConstraints = this.pathConstraints.Items;
for (int i = 0, n = this.pathConstraints.Count; i < n; i++)
if (pathConstraints[i].name.Equals(pathConstraintName)) return i;
return -1;
}

View File

@ -590,8 +590,7 @@ namespace Spine {
}
timelines.Add(timeline);
}
else if (timelineName == "rgb") {
} else if (timelineName == "rgb") {
var timeline = new RGBTimeline(values.Count, values.Count * 3, slotIndex);
var keyMapEnumerator = values.GetEnumerator();
@ -772,28 +771,23 @@ namespace Spine {
else if (timelineName == "translate") {
TranslateTimeline timeline = new TranslateTimeline(values.Count, values.Count << 1, boneIndex);
timelines.Add(ReadTimeline(ref keyMapEnumerator, timeline, "x", "y", 0, scale));
}
else if (timelineName == "translatex") {
} else if (timelineName == "translatex") {
timelines
.Add(ReadTimeline(ref keyMapEnumerator, new TranslateXTimeline(values.Count, values.Count, boneIndex), 0, scale));
}
else if (timelineName == "translatey") {
} else if (timelineName == "translatey") {
timelines
.Add(ReadTimeline(ref keyMapEnumerator, new TranslateYTimeline(values.Count, values.Count, boneIndex), 0, scale));
}
else if (timelineName == "scale") {
} else if (timelineName == "scale") {
ScaleTimeline timeline = new ScaleTimeline(values.Count, values.Count << 1, boneIndex);
timelines.Add(ReadTimeline(ref keyMapEnumerator, timeline, "x", "y", 1, 1));
}
else if (timelineName == "scalex")
} else if (timelineName == "scalex")
timelines.Add(ReadTimeline(ref keyMapEnumerator, new ScaleXTimeline(values.Count, values.Count, boneIndex), 1, 1));
else if (timelineName == "scaley")
timelines.Add(ReadTimeline(ref keyMapEnumerator, new ScaleYTimeline(values.Count, values.Count, boneIndex), 1, 1));
else if (timelineName == "shear") {
ShearTimeline timeline = new ShearTimeline(values.Count, values.Count << 1, boneIndex);
timelines.Add(ReadTimeline(ref keyMapEnumerator, timeline, "x", "y", 0, 1));
}
else if (timelineName == "shearx")
} else if (timelineName == "shearx")
timelines.Add(ReadTimeline(ref keyMapEnumerator, new ShearXTimeline(values.Count, values.Count, boneIndex), 0, 1));
else if (timelineName == "sheary")
timelines.Add(ReadTimeline(ref keyMapEnumerator, new ShearYTimeline(values.Count, values.Count, boneIndex), 0, 1));
@ -906,13 +900,11 @@ namespace Spine {
if (timelineName == "position") {
CurveTimeline1 timeline = new PathConstraintPositionTimeline(values.Count, values.Count, index);
timelines.Add(ReadTimeline(ref keyMapEnumerator, timeline, 0, data.positionMode == PositionMode.Fixed ? scale : 1));
}
else if (timelineName == "spacing") {
} else if (timelineName == "spacing") {
CurveTimeline1 timeline = new PathConstraintSpacingTimeline(values.Count, values.Count, index);
timelines.Add(ReadTimeline(ref keyMapEnumerator, timeline, 0,
data.spacingMode == SpacingMode.Length || data.spacingMode == SpacingMode.Fixed ? scale : 1));
}
else if (timelineName == "mix") {
} else if (timelineName == "mix") {
PathConstraintMixTimeline timeline = new PathConstraintMixTimeline(values.Count, values.Count * 3, index);
var keyMap = (Dictionary<string, Object>)keyMapEnumerator.Current;
float time = GetFloat(keyMap, "time", 0);
@ -1135,8 +1127,7 @@ namespace Spine {
if (curve is string) {
if (value != 0) timeline.SetStepped(frame);
}
else {
} else {
var curveValues = (List<object>)curve;
int index = value << 2;
float cx1 = (float)curveValues[index];

View File

@ -132,10 +132,11 @@ namespace Spine {
/// <summary>Attach all attachments from this skin if the corresponding attachment from the old skin is currently attached.</summary>
internal void AttachAll (Skeleton skeleton, Skin oldSkin) {
Slot[] slots = skeleton.slots.Items;
foreach (var item in oldSkin.attachments) {
SkinEntry entry = item.Value;
int slotIndex = entry.slotIndex;
Slot slot = skeleton.slots.Items[slotIndex];
Slot slot = slots[slotIndex];
if (slot.Attachment == entry.attachment) {
Attachment attachment = GetAttachment(slotIndex, entry.name);
if (attachment != null) slot.Attachment = attachment;

View File

@ -124,15 +124,13 @@ namespace Spine {
public ExposedList<ExposedList<float>> Decompose (ExposedList<float> verticesArray, ExposedList<int> triangles) {
var vertices = verticesArray.Items;
var convexPolygons = this.convexPolygons;
for (int i = 0, n = convexPolygons.Count; i < n; i++) {
for (int i = 0, n = convexPolygons.Count; i < n; i++)
polygonPool.Free(convexPolygons.Items[i]);
}
convexPolygons.Clear();
var convexPolygonsIndices = this.convexPolygonsIndices;
for (int i = 0, n = convexPolygonsIndices.Count; i < n; i++) {
for (int i = 0, n = convexPolygonsIndices.Count; i < n; i++)
polygonIndicesPool.Free(convexPolygonsIndices.Items[i]);
}
convexPolygonsIndices.Clear();
var polygonIndices = polygonIndicesPool.Obtain();

View File

@ -1994,22 +1994,23 @@ public class Animation {
public void apply (Skeleton skeleton, float lastTime, float time, @Null Array<Event> events, float alpha, MixBlend blend,
MixDirection direction) {
Object[] drawOrder = skeleton.drawOrder.items;
if (direction == out) {
if (blend == setup) arraycopy(skeleton.slots.items, 0, drawOrder, 0, skeleton.slots.size);
if (blend == setup) arraycopy(skeleton.slots.items, 0, skeleton.drawOrder.items, 0, skeleton.slots.size);
return;
}
if (time < frames[0]) { // Time is before first frame.
if (blend == setup || blend == first) arraycopy(skeleton.slots.items, 0, drawOrder, 0, skeleton.slots.size);
if (blend == setup || blend == first)
arraycopy(skeleton.slots.items, 0, skeleton.drawOrder.items, 0, skeleton.slots.size);
return;
}
int[] drawOrderToSetupIndex = drawOrders[search(frames, time)];
if (drawOrderToSetupIndex == null)
arraycopy(skeleton.slots.items, 0, drawOrder, 0, skeleton.slots.size);
arraycopy(skeleton.slots.items, 0, skeleton.drawOrder.items, 0, skeleton.slots.size);
else {
Object[] slots = skeleton.slots.items;
Object[] drawOrder = skeleton.drawOrder.items;
for (int i = 0, n = drawOrderToSetupIndex.length; i < n; i++)
drawOrder[i] = slots[drawOrderToSetupIndex[i]];
}

View File

@ -66,7 +66,6 @@ abstract public class VertexAttachment extends Attachment {
* @param stride The number of <code>worldVertices</code> entries between the value pairs written. */
public void computeWorldVertices (Slot slot, int start, int count, float[] worldVertices, int offset, int stride) {
count = offset + (count >> 1) * stride;
Skeleton skeleton = slot.getSkeleton();
FloatArray deformArray = slot.getDeform();
float[] vertices = this.vertices;
int[] bones = this.bones;
@ -88,7 +87,7 @@ abstract public class VertexAttachment extends Attachment {
v += n + 1;
skip += n;
}
Object[] skeletonBones = skeleton.getBones().items;
Object[] skeletonBones = slot.getSkeleton().getBones().items;
if (deformArray.size == 0) {
for (int w = offset, b = skip * 3; w < count; w += stride) {
float wx = 0, wy = 0;