Flip timelines for spine-lua, spine-corona, spine-love.

This commit is contained in:
NathanSweet 2014-11-16 00:04:53 +01:00
parent 631add64fb
commit 59204db7f8
32 changed files with 286 additions and 331 deletions

View File

@ -38,4 +38,3 @@ Runtime:addEventListener("enterFrame", function (event)
state:apply(skeleton) state:apply(skeleton)
skeleton:updateWorldTransform() skeleton:updateWorldTransform()
end) end)

View File

@ -1,290 +0,0 @@
dragon.png
format: RGBA4444
filter: Nearest,Nearest
repeat: none
L_rear_thigh
rotate: false
xy: 895, 20
size: 91, 148
orig: 91, 149
offset: 0, 0
index: -1
L_wing01
rotate: false
xy: 814, 672
size: 191, 256
orig: 191, 256
offset: 0, 0
index: -1
L_wing02
rotate: false
xy: 714, 189
size: 179, 269
orig: 179, 269
offset: 0, 0
index: -1
L_wing03
rotate: false
xy: 785, 463
size: 186, 207
orig: 186, 207
offset: 0, 0
index: -1
L_wing05
rotate: true
xy: 2, 9
size: 218, 213
orig: 218, 213
offset: 0, 0
index: -1
L_wing06
rotate: false
xy: 2, 229
size: 192, 331
orig: 192, 331
offset: 0, 0
index: -1
R_wing01
rotate: true
xy: 502, 709
size: 219, 310
orig: 219, 310
offset: 0, 0
index: -1
R_wing02
rotate: true
xy: 204, 463
size: 203, 305
orig: 203, 305
offset: 0, 0
index: -1
R_wing03
rotate: false
xy: 511, 460
size: 272, 247
orig: 272, 247
offset: 0, 0
index: -1
R_wing05
rotate: false
xy: 196, 232
size: 251, 229
orig: 251, 229
offset: 0, 0
index: -1
R_wing06
rotate: false
xy: 2, 562
size: 200, 366
orig: 200, 366
offset: 0, 0
index: -1
R_wing07
rotate: true
xy: 449, 258
size: 200, 263
orig: 200, 263
offset: 0, 0
index: -1
R_wing08
rotate: false
xy: 467, 2
size: 234, 254
orig: 234, 254
offset: 0, 0
index: -1
R_wing09
rotate: false
xy: 217, 26
size: 248, 204
orig: 248, 204
offset: 0, 0
index: -1
back
rotate: false
xy: 703, 2
size: 190, 185
orig: 190, 185
offset: 0, 0
index: -1
chest
rotate: true
xy: 895, 170
size: 136, 122
orig: 136, 122
offset: 0, 0
index: -1
front_toeA
rotate: false
xy: 976, 972
size: 29, 50
orig: 29, 50
offset: 0, 0
index: -1
head
rotate: false
xy: 204, 668
size: 296, 260
orig: 296, 260
offset: 0, 0
index: -1
logo
rotate: false
xy: 2, 930
size: 897, 92
orig: 897, 92
offset: 0, 0
index: -1
tail01
rotate: false
xy: 895, 308
size: 120, 153
orig: 120, 153
offset: 0, 0
index: -1
tail03
rotate: false
xy: 901, 930
size: 73, 92
orig: 73, 92
offset: 0, 0
index: -1
dragon2.png
format: RGBA4444
filter: Nearest,Nearest
repeat: none
L_front_leg
rotate: true
xy: 391, 141
size: 84, 57
orig: 84, 57
offset: 0, 0
index: -1
L_front_thigh
rotate: false
xy: 446, 269
size: 84, 72
orig: 84, 72
offset: 0, 0
index: -1
L_rear_leg
rotate: true
xy: 888, 342
size: 168, 132
orig: 206, 177
offset: 19, 20
index: -1
L_wing04
rotate: false
xy: 256, 227
size: 188, 135
orig: 188, 135
offset: 0, 0
index: -1
L_wing07
rotate: false
xy: 2, 109
size: 159, 255
orig: 159, 255
offset: 0, 0
index: -1
L_wing08
rotate: true
xy: 705, 346
size: 164, 181
orig: 164, 181
offset: 0, 0
index: -1
L_wing09
rotate: false
xy: 499, 343
size: 204, 167
orig: 204, 167
offset: 0, 0
index: -1
R_front_leg
rotate: false
xy: 273, 34
size: 101, 89
orig: 101, 89
offset: 0, 0
index: -1
R_front_thigh
rotate: false
xy: 163, 106
size: 108, 108
orig: 108, 108
offset: 0, 0
index: -1
R_rear_leg
rotate: false
xy: 273, 125
size: 116, 100
orig: 116, 100
offset: 0, 0
index: -1
R_rear_thigh
rotate: false
xy: 163, 216
size: 91, 148
orig: 91, 149
offset: 0, 0
index: -1
R_wing04
rotate: false
xy: 2, 366
size: 279, 144
orig: 279, 144
offset: 0, 0
index: -1
chin
rotate: false
xy: 283, 364
size: 214, 146
orig: 214, 146
offset: 0, 0
index: -1
front_toeB
rotate: false
xy: 590, 284
size: 56, 57
orig: 56, 57
offset: 0, 0
index: -1
rear-toe
rotate: true
xy: 2, 2
size: 105, 77
orig: 109, 77
offset: 0, 0
index: -1
tail02
rotate: true
xy: 151, 9
size: 95, 120
orig: 95, 120
offset: 0, 0
index: -1
tail04
rotate: false
xy: 532, 270
size: 56, 71
orig: 56, 71
offset: 0, 0
index: -1
tail05
rotate: false
xy: 648, 282
size: 52, 59
orig: 52, 59
offset: 0, 0
index: -1
tail06
rotate: true
xy: 81, 12
size: 95, 68
orig: 95, 68
offset: 0, 0
index: -1

View File

@ -0,0 +1,39 @@
-- This skeleton uses IK for the feet.
local spine = require "spine-corona.spine"
local json = spine.SkeletonJson.new()
local skeletonData = json:readSkeletonDataFile("examples/hero/hero.json")
local skeleton = spine.Skeleton.new(skeletonData)
function skeleton:createImage (attachment)
return display.newImage("examples/hero/images/" .. attachment.name .. ".png")
end
skeleton.group.x = 195
skeleton.group.y = 385
skeleton.flipX = false
skeleton.flipY = false
skeleton.debug = true -- Omit or set to false to not draw debug lines on top of the images.
skeleton:setToSetupPose()
-- AnimationStateData defines crossfade durations between animations.
local stateData = spine.AnimationStateData.new(skeletonData)
-- AnimationState has a queue of animations and can apply them with crossfading.
local state = spine.AnimationState.new(stateData)
--state:setAnimationByName(0, "Idle", true, 0)
state:setAnimationByName(0, "Walk", true, 0)
local lastTime = 0
local animationTime = 0
Runtime:addEventListener("enterFrame", function (event)
-- Compute time in seconds since last frame.
local currentTime = event.time / 1000
local delta = currentTime - lastTime
lastTime = currentTime
-- Update the state with the delta time, apply it, and update the world transforms.
state:update(delta)
state:apply(skeleton)
skeleton:updateWorldTransform()
end)

File diff suppressed because one or more lines are too long

Binary file not shown.

After

Width:  |  Height:  |  Size: 15 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 18 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 13 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.8 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 11 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 11 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 9.7 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 7.2 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 28 KiB

View File

@ -0,0 +1,5 @@
Copyright (c) 2014, XDTech
The project file and images in this "Hero" project are provided for
demonstration purposes only and may not be redistributed for any reason nor
used as the basis for derivative work.

Binary file not shown.

After

Width:  |  Height:  |  Size: 14 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.8 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 7.9 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 7.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 15 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 7.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 7.0 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.2 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.7 KiB

View File

@ -1,4 +1,5 @@
require "examples.spineboy" -- require "examples.spineboy"
-- require "examples.goblins" -- require "examples.goblins"
-- require "examples.dragon" -- require "examples.dragon"
require "examples.hero"

View File

@ -128,10 +128,11 @@ function spine.Skeleton.new (skeletonData, group)
end end
-- Position image based on attachment and bone. -- Position image based on attachment and bone.
if image ~= spine.Skeleton.failed then if image ~= spine.Skeleton.failed then
local flipX, flipY = ((self.flipX and -1) or 1), ((self.flipY and -1) or 1) local bone = slot.bone
local flipX, flipY = ((bone.worldFlipX and -1) or 1), ((bone.worldFlipY and -1) or 1)
local x = slot.bone.worldX + attachment.x * slot.bone.m00 + attachment.y * slot.bone.m01 local x = bone.worldX + attachment.x * bone.m00 + attachment.y * bone.m01
local y = -(slot.bone.worldY + attachment.x * slot.bone.m10 + attachment.y * slot.bone.m11) local y = -(bone.worldY + attachment.x * bone.m10 + attachment.y * bone.m11)
if not image.lastX then if not image.lastX then
image.x, image.y = x, y image.x, image.y = x, y
image.lastX, image.lastY = x, y image.lastX, image.lastY = x, y
@ -145,16 +146,16 @@ function spine.Skeleton.new (skeletonData, group)
-- Fix scaling when attachment is rotated 90 or -90. -- Fix scaling when attachment is rotated 90 or -90.
local rotation = math.abs(attachment.rotation) % 180 local rotation = math.abs(attachment.rotation) % 180
if (rotation == 90) then if (rotation == 90) then
xScale = xScale * slot.bone.worldScaleY xScale = xScale * bone.worldScaleY
yScale = yScale * slot.bone.worldScaleX yScale = yScale * bone.worldScaleX
else else
xScale = xScale * slot.bone.worldScaleX xScale = xScale * bone.worldScaleX
yScale = yScale * slot.bone.worldScaleY yScale = yScale * bone.worldScaleY
if rotation ~= 0 and xScale ~= yScale and not image.rotationWarning then if rotation ~= 0 and xScale ~= yScale and not image.rotationWarning then
image.rotationWarning = true image.rotationWarning = true
print("WARNING: Non-uniform bone scaling with attachments not rotated to\n" print("WARNING: Non-uniform bone scaling with attachments not rotated to\n"
.." cardinal angles will not work as expected with Corona.\n" .." cardinal angles will not work as expected with Corona.\n"
.." Bone: "..slot.bone.data.name..", slot: "..slot.data.name..", attachment: "..attachment.name) .." Bone: "..bone.data.name..", slot: "..slot.data.name..", attachment: "..attachment.name)
end end
end end
if not image.lastScaleX then if not image.lastScaleX then
@ -165,7 +166,7 @@ function spine.Skeleton.new (skeletonData, group)
image.lastScaleX, image.lastScaleY = xScale, yScale image.lastScaleX, image.lastScaleY = xScale, yScale
end end
rotation = -(slot.bone.worldRotation + attachment.rotation) * flipX * flipY rotation = -(bone.worldRotation + attachment.rotation) * flipX * flipY
if not image.lastRotation then if not image.lastRotation then
image.rotation = rotation image.rotation = rotation
image.lastRotation = rotation image.lastRotation = rotation
@ -199,13 +200,13 @@ function spine.Skeleton.new (skeletonData, group)
bone.line.x = bone.worldX bone.line.x = bone.worldX
bone.line.y = -bone.worldY bone.line.y = -bone.worldY
bone.line.rotation = -bone.worldRotation bone.line.rotation = -bone.worldRotation
if self.flipX then if bone.worldFlipX then
bone.line.xScale = -1 bone.line.xScale = -1
bone.line.rotation = -bone.line.rotation bone.line.rotation = -bone.line.rotation
else else
bone.line.xScale = 1 bone.line.xScale = 1
end end
if self.flipY then if bone.worldFlipY then
bone.line.yScale = -1 bone.line.yScale = -1
bone.line.rotation = -bone.line.rotation bone.line.rotation = -bone.line.rotation
else else

View File

@ -83,6 +83,22 @@ local function binarySearch (values, target, step)
end end
end end
local function binarySearch1 (values, target)
local low = 0
local high = math.floor(#values - 1)
if high == 0 then return 1 end
local current = math.floor(high / 2)
while true do
if values[current + 1] <= target then
low = current + 1
else
high = current
end
if low == high then return low + 1 end
current = math.floor((low + high) / 2)
end
end
local function linearSearch (values, target, step) local function linearSearch (values, target, step)
for i = 0, #values, step do for i = 0, #values, step do
if (values[i] > target) then return i end if (values[i] > target) then return i end
@ -419,7 +435,7 @@ function Animation.AttachmentTimeline.new ()
if time >= frames[#frames] then -- Time is after last frame. if time >= frames[#frames] then -- Time is after last frame.
frameIndex = #frames frameIndex = #frames
else else
frameIndex = binarySearch(frames, time, 1) - 1 frameIndex = binarySearch1(frames, time) - 1
end end
local attachmentName = self.attachmentNames[frameIndex] local attachmentName = self.attachmentNames[frameIndex]
@ -477,7 +493,7 @@ function Animation.EventTimeline.new ()
if lastTime < frames[0] then if lastTime < frames[0] then
frameIndex = 0 frameIndex = 0
else else
frameIndex = binarySearch(frames, lastTime, 1) frameIndex = binarySearch1(frames, lastTime)
local frame = frames[frameIndex] local frame = frames[frameIndex]
while frameIndex > 0 do -- Fire multiple events with the same frame. while frameIndex > 0 do -- Fire multiple events with the same frame.
if frames[frameIndex - 1] ~= frame then break end if frames[frameIndex - 1] ~= frame then break end
@ -522,7 +538,7 @@ function Animation.DrawOrderTimeline.new ()
if time >= frames[#frames] then -- Time is after last frame. if time >= frames[#frames] then -- Time is after last frame.
frameIndex = #frames frameIndex = #frames
else else
frameIndex = binarySearch(frames, time, 1) - 1 frameIndex = binarySearch1(frames, time) - 1
end end
local drawOrder = skeleton.drawOrder local drawOrder = skeleton.drawOrder
@ -542,4 +558,147 @@ function Animation.DrawOrderTimeline.new ()
return self return self
end end
Animation.FfdTimeline = {}
function Animation.FfdTimeline.new ()
local self = Animation.CurveTimeline.new()
self.frames = {}
self.frameVertices = {}
self.slotIndex = -1
function self:getDuration ()
return self.frames[#self.frames]
end
function self:getFrameCount ()
return #self.frames + 1
end
function self:setFrame (frameIndex, time, vertices)
self.frames[frameIndex] = time
self.frameVertices[frameIndex] = vertices
end
function self:apply (skeleton, lastTime, time, firedEvents, alpha)
local slot = skeleton.slots[self.slotIndex]
if slot.attachment ~= attachment then return end
local frames = self.frames
if time < frames[0] then -- Time is before first frame.
slot.attachmentVerticesCount = 0
return
end
local frameVertices = self.frameVertices
local vertexCount = #frameVertices[0]
local vertices = slot.attachmentVertices
if #vertices < vertexCount then
vertices = {}
vertices[vertexCount] = 0
slot.attachmentVertices = vertices
elseif #vertices < vertexCount then
alpha = 1 -- Don't mix from uninitialized slot vertices.
end
slot.attachmentVerticesCount = vertexCount
if time >= frames[#frames] then -- Time is after last frame.
local lastVertices = frameVertices[#frames.Length]
if alpha < 1 then
for i = 0, vertexCount do
local vertex = vertices[i]
vertices[i] = vertex + (lastVertices[i] - vertex) * alpha
end
else
for i = 0, vertexCount do
vertices[i] = lastVertices[i]
end
end
return
end
-- Interpolate between the previous frame and the current frame.
local frameIndex = binarySearch1(frames, time)
local frameTime = frames[frameIndex]
local percent = 1 - (time - frameTime) / (frames[frameIndex - 1] - frameTime)
if percent < 0 then percent = 0 elseif percent > 1 then percent = 1 end
percent = self:getCurvePercent(frameIndex - 1, percent)
local prevVertices = frameVertices[frameIndex - 1]
local nextVertices = frameVertices[frameIndex]
if alpha < 1 then
for i = 0, vertexCount do
local prev = prevVertices[i]
local vertices = vertices[i]
vertices[i] = vertices + (prev + (nextVertices[i] - prev) * percent - vertices) * alpha
end
else
for i = 0, vertexCount do
local prev = prevVertices[i]
vertices[i] = prev + (nextVertices[i] - prev) * percent
end
end
end
return self
end
Animation.FlipXTimeline = {}
function Animation.FlipXTimeline.new ()
local self = {
frames = {}, -- time, flip, ...
boneIndex = -1
}
function self:getDuration ()
return self.frames[#self.frames - 1]
end
function self:getFrameCount ()
return (#self.frames + 1) / 2
end
function self:setFrame (frameIndex, time, flip)
frameIndex = frameIndex * 2
self.frames[frameIndex] = time
self.frames[frameIndex + 1] = flip
end
function self:apply (skeleton, lastTime, time, firedEvents, alpha)
local frames = self.frames
if time < frames[0] then
if lastTime > time then self:apply(skeleton, lastTime, 999999, null, 0) end
return
elseif lastTime > time then
lastTime = -1
end
local frameIndex
if time >= frames[#frames - 1] then
frameIndex = #frames - 1
else
frameIndex = binarySearch(frames, time, 2) - 2
end
if frames[frameIndex] < lastTime then return end
self:setFlip(skeleton.bones[self.boneIndex], frames[frameIndex + 1])
end
function self:setFlip (bone, flip)
bone.flipX = flip
end
return self
end
Animation.FlipYTimeline = {}
function Animation.FlipYTimeline.new ()
local self = Animation.FlipXTimeline.new()
function self:setFlip (bone, flip)
bone.flipY = flip
end
return self
end
return Animation return Animation

View File

@ -30,19 +30,23 @@
local Bone = {} local Bone = {}
function Bone.new (data, parent) function Bone.new (data, skeleton, parent)
if not data then error("data cannot be nil", 2) end if not data then error("data cannot be nil", 2) end
if not skeleton then error("skeleton cannot be nil", 2) end
local self = { local self = {
data = data, data = data,
skeleton = skeleton,
parent = parent, parent = parent,
x = 0, y = 0, x = 0, y = 0,
rotation = 0, rotation = 0,
scaleX = 1, scaleY = 1, scaleX = 1, scaleY = 1,
flipX = false, flipY = false,
m00 = 0, m01 = 0, worldX = 0, -- a b x m00 = 0, m01 = 0, worldX = 0, -- a b x
m10 = 0, m11 = 0, worldY = 0, -- c d y m10 = 0, m11 = 0, worldY = 0, -- c d y
worldRotation = 0, worldRotation = 0,
worldScaleX = 1, worldScaleY = 1, worldScaleX = 1, worldScaleY = 1,
worldFlipX = false, worldFlipY = false,
} }
function self:updateWorldTransform (flipX, flipY) function self:updateWorldTransform (flipX, flipY)
@ -62,13 +66,16 @@ function Bone.new (data, parent)
else else
self.worldRotation = self.rotation self.worldRotation = self.rotation
end end
self.worldFlipX = parent.worldFlipX ~= self.flipX
self.worldFlipY = parent.worldFlipY ~= self.flipY
else else
if flipX then local skeletonFlipX, skeletonFlipY = self.skeleton.flipX, self.skeleton.flipY
if skeletonFlipX then
self.worldX = -self.x self.worldX = -self.x
else else
self.worldX = self.x self.worldX = self.x
end end
if flipY then if skeletonFlipY then
self.worldY = -self.y self.worldY = -self.y
else else
self.worldY = self.y self.worldY = self.y
@ -76,21 +83,25 @@ function Bone.new (data, parent)
self.worldScaleX = self.scaleX self.worldScaleX = self.scaleX
self.worldScaleY = self.scaleY self.worldScaleY = self.scaleY
self.worldRotation = self.rotation self.worldRotation = self.rotation
self.worldFlipX = skeletonFlipX ~= self.flipX
self.worldFlipY = skeletonFlipY ~= self.flipY
end end
local radians = math.rad(self.worldRotation) local radians = math.rad(self.worldRotation)
local cos = math.cos(radians) local cos = math.cos(radians)
local sin = math.sin(radians) local sin = math.sin(radians)
self.m00 = cos * self.worldScaleX if self.worldFlipX then
self.m10 = sin * self.worldScaleX self.m00 = -cos * self.worldScaleX
self.m01 = -sin * self.worldScaleY self.m01 = sin * self.worldScaleY
self.m11 = cos * self.worldScaleY else
if flipX then self.m00 = cos * self.worldScaleX
self.m00 = -self.m00 self.m01 = -sin * self.worldScaleY
self.m01 = -self.m01
end end
if flipY then if self.worldFlipY then
self.m10 = -self.m10 self.m10 = -sin * self.worldScaleX
self.m11 = -self.m11 self.m11 = -cos * self.worldScaleY
else
self.m10 = sin * self.worldScaleX
self.m11 = cos * self.worldScaleY
end end
end end
@ -101,6 +112,8 @@ function Bone.new (data, parent)
self.rotation = data.rotation self.rotation = data.rotation
self.scaleX = data.scaleX self.scaleX = data.scaleX
self.scaleY = data.scaleY self.scaleY = data.scaleY
self.flipX = data.flipX
self.flipY = data.flipY
end end
self:setToSetupPose() self:setToSetupPose()

View File

@ -51,7 +51,7 @@ function Skeleton.new (skeletonData)
function self:updateWorldTransform () function self:updateWorldTransform ()
for i,bone in ipairs(self.bones) do for i,bone in ipairs(self.bones) do
bone:updateWorldTransform(self.flipX, self.flipY) bone:updateWorldTransform()
end end
end end
@ -165,12 +165,12 @@ function Skeleton.new (skeletonData)
for i,boneData in ipairs(skeletonData.bones) do for i,boneData in ipairs(skeletonData.bones) do
local parent local parent
if boneData.parent then parent = self.bones[spine.utils.indexOf(skeletonData.bones, boneData.parent)] end if boneData.parent then parent = self.bones[spine.utils.indexOf(skeletonData.bones, boneData.parent)] end
table.insert(self.bones, Bone.new(boneData, parent)) table.insert(self.bones, Bone.new(boneData, self, parent))
end end
for i,slotData in ipairs(skeletonData.slots) do for i,slotData in ipairs(skeletonData.slots) do
local bone = self.bones[spine.utils.indexOf(skeletonData.bones, slotData.boneData)] local bone = self.bones[spine.utils.indexOf(skeletonData.bones, slotData.boneData)]
local slot = Slot.new(slotData, self, bone) local slot = Slot.new(slotData, bone)
table.insert(self.slots, slot) table.insert(self.slots, slot)
self.slotsByName[slot.data.name] = slot self.slotsByName[slot.data.name] = slot
table.insert(self.drawOrder, slot) table.insert(self.drawOrder, slot)

View File

@ -86,6 +86,8 @@ function SkeletonJson.new (attachmentLoader)
else else
boneData.scaleY = 1 boneData.scaleY = 1
end end
boneData.flipX = boneMap["flipX"] or false
boneData.flipY = boneMap["flipY"] or false
if boneMap["inheritScale"] == false then if boneMap["inheritScale"] == false then
boneData.inheritScale = false boneData.inheritScale = false
else else
@ -375,6 +377,27 @@ function SkeletonJson.new (attachmentLoader)
table.insert(timelines, timeline) table.insert(timelines, timeline)
duration = math.max(duration, timeline:getDuration()) duration = math.max(duration, timeline:getDuration())
elseif timelineName == "flipX" or timelineName == "flipY" then
local x = timelineName == "flipX"
local timeline, field
if x then
timeline = Animation.FlipXTimeline.new()
field = "x"
else
timeline = Animation.FlipYTimeline.new();
field = "y"
end
timeline.boneIndex = boneIndex
local frameIndex = 0
for i,valueMap in ipairs(values) do
local flip
timeline:setFrame(frameIndex, valueMap["time"], valueMap[field] or false)
frameIndex = frameIndex + 1
end
table.insert(timelines, timeline)
duration = math.max(duration, timeline:getDuration())
else else
error("Invalid timeline type for a bone: " .. timelineName .. " (" .. boneName .. ")") error("Invalid timeline type for a bone: " .. timelineName .. " (" .. boneName .. ")")
end end

View File

@ -29,19 +29,18 @@
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
local Slot = {} local Slot = {}
function Slot.new (slotData, skeleton, bone) function Slot.new (slotData, bone)
if not slotData then error("slotData cannot be nil", 2) end if not slotData then error("slotData cannot be nil", 2) end
if not skeleton then error("skeleton cannot be nil", 2) end
if not bone then error("bone cannot be nil", 2) end if not bone then error("bone cannot be nil", 2) end
local self = { local self = {
data = slotData, data = slotData,
skeleton = skeleton,
bone = bone, bone = bone,
r = 1, g = 1, b = 1, a = 1, r = 1, g = 1, b = 1, a = 1,
attachment = nil, attachment = nil,
attachmentTime = 0, attachmentTime = 0,
attachmentVertices = nil attachmentVertices = nil,
attachmentVerticesCount = 0
} }
function self:setColor (r, g, b, a) function self:setColor (r, g, b, a)
@ -53,15 +52,16 @@ function Slot.new (slotData, skeleton, bone)
function self:setAttachment (attachment) function self:setAttachment (attachment)
self.attachment = attachment self.attachment = attachment
self.attachmentTime = self.skeleton.time self.attachmentTime = self.bone.skeleton.time
self.attachmentVerticesCount = 0
end end
function self:setAttachmentTime (time) function self:setAttachmentTime (time)
self.attachmentTime = self.skeleton.time - time self.attachmentTime = self.bone.skeleton.time - time
end end
function self:getAttachmentTime () function self:getAttachmentTime ()
return self.skeleton.time - self.attachmentTime return self.bone.skeleton.time - self.attachmentTime
end end
function self:setToSetupPose () function self:setToSetupPose ()
@ -71,7 +71,7 @@ function Slot.new (slotData, skeleton, bone)
local attachment local attachment
if data.attachmentName then if data.attachmentName then
attachment = self.skeleton:getAttachment(data.name, data.attachmentName) attachment = self.bone.skeleton:getAttachment(data.name, data.attachmentName)
end end
self:setAttachment(attachment) self:setAttachment(attachment)
end end