123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266 |
- -------------------------------------------------------------------------------
- -- Spine Runtimes Software License v2.5
- --
- -- Copyright (c) 2013-2016, Esoteric Software
- -- All rights reserved.
- --
- -- You are granted a perpetual, non-exclusive, non-sublicensable, and
- -- non-transferable license to use, install, execute, and perform the Spine
- -- Runtimes software and derivative works solely for personal or internal
- -- use. Without the written permission of Esoteric Software (see Section 2 of
- -- the Spine Software License Agreement), you may not (a) modify, translate,
- -- adapt, or develop new applications using the Spine Runtimes or otherwise
- -- create derivative works or improvements of the Spine Runtimes or (b) remove,
- -- delete, alter, or obscure any trademarks or any copyright, trademark, patent,
- -- or other intellectual property or proprietary rights notices on or in the
- -- Software, including any copy thereof. Redistributions in binary or source
- -- form must include this license and terms.
- --
- -- THIS SOFTWARE IS PROVIDED BY ESOTERIC SOFTWARE "AS IS" AND ANY EXPRESS OR
- -- IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
- -- MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO
- -- EVENT SHALL ESOTERIC SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- -- SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
- -- PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, BUSINESS INTERRUPTION, OR LOSS OF
- -- USE, DATA, OR PROFITS) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
- -- IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
- -- ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
- -- POSSIBILITY OF SUCH DAMAGE.
- -------------------------------------------------------------------------------
- spine = {}
- spine.utils = require "spine-lua.utils"
- spine.SkeletonJson = require "spine-lua.SkeletonJson"
- spine.SkeletonData = require "spine-lua.SkeletonData"
- spine.BoneData = require "spine-lua.BoneData"
- spine.SlotData = require "spine-lua.SlotData"
- spine.IkConstraintData = require "spine-lua.IkConstraintData"
- spine.Skin = require "spine-lua.Skin"
- spine.Attachment = require "spine-lua.attachments.Attachment"
- spine.BoundingBoxAttachment = require "spine-lua.attachments.BoundingBoxAttachment"
- spine.RegionAttachment = require "spine-lua.attachments.RegionAttachment"
- spine.MeshAttachment = require "spine-lua.attachments.MeshAttachment"
- spine.VertexAttachment = require "spine-lua.attachments.VertexAttachment"
- spine.PathAttachment = require "spine-lua.attachments.PathAttachment"
- spine.PointAttachment = require "spine-lua.attachments.PointAttachment"
- spine.ClippingAttachment = require "spine-lua.attachments.ClippingAttachment"
- spine.Skeleton = require "spine-lua.Skeleton"
- spine.Bone = require "spine-lua.Bone"
- spine.Slot = require "spine-lua.Slot"
- spine.IkConstraint = require "spine-lua.IkConstraint"
- spine.AttachmentType = require "spine-lua.attachments.AttachmentType"
- spine.AttachmentLoader = require "spine-lua.AttachmentLoader"
- spine.Animation = require "spine-lua.Animation"
- spine.AnimationStateData = require "spine-lua.AnimationStateData"
- spine.AnimationState = require "spine-lua.AnimationState"
- spine.EventData = require "spine-lua.EventData"
- spine.Event = require "spine-lua.Event"
- spine.SkeletonBounds = require "spine-lua.SkeletonBounds"
- spine.BlendMode = require "spine-lua.BlendMode"
- spine.TextureAtlas = require "spine-lua.TextureAtlas"
- spine.TextureRegion = require "spine-lua.TextureRegion"
- spine.TextureAtlasRegion = require "spine-lua.TextureAtlasRegion"
- spine.AtlasAttachmentLoader = require "spine-lua.AtlasAttachmentLoader"
- spine.Color = require "spine-lua.Color"
- spine.Triangulator = require "spine-lua.Triangulator"
- spine.SkeletonClipping = require "spine-lua.SkeletonClipping"
- spine.utils.readFile = function (fileName, base)
- if not base then base = system.ResourceDirectory end
- local path = system.pathForFile(fileName, base)
- local file = io.open(path, "r")
- if not file then return nil end
- local contents = file:read("*a")
- io.close(file)
- return contents
- end
- local json = require "json"
- spine.utils.readJSON = function (text)
- return json.decode(text)
- end
- local QUAD_TRIANGLES = { 1, 2, 3, 3, 4, 1 }
- spine.Skeleton.new_super = spine.Skeleton.new
- spine.Skeleton.updateWorldTransform_super = spine.Skeleton.updateWorldTransform
- spine.Skeleton.new = function(skeletonData, group)
- self = spine.Skeleton.new_super(skeletonData)
- self.group = group or display.newGroup()
- self.drawingGroup = nil
- self.premultipliedAlpha = false
- self.batches = 0
- self.tempColor = spine.Color.newWith(1, 1, 1, 1)
- self.tempColor2 = spine.Color.newWith(-1, 1, 1, 1)
- self.clipper = spine.SkeletonClipping.new()
- return self
- end
- local function colorEquals(color1, color2)
- if not color1 and not color2 then return true end
- if not color1 and color2 then return false end
- if color1 and not color2 then return false end
- return color1[1] == color2[1] and color1[2] == color2[2] and color1[3] == color2[3] and color1[4] == color2[4]
- end
- local function toCoronaBlendMode(blendMode)
- if blendMode == spine.BlendMode.normal then
- return "normal"
- elseif blendMode == spine.BlendMode.additive then
- return "add"
- elseif blendMode == spine.BlendMode.multiply then
- return "multiply"
- elseif blendMode == spine.BlendMode.screen then
- return "screen"
- end
- end
- local worldVertices = spine.utils.newNumberArray(10000 * 8)
- function spine.Skeleton:updateWorldTransform()
- spine.Skeleton.updateWorldTransform_super(self)
- local premultipliedAlpha = self.premultipliedAlpha
- self.batches = 0
- -- Remove old drawing group, we will start anew
- if self.drawingGroup then self.drawingGroup:removeSelf() end
- local drawingGroup = display.newGroup()
- self.drawingGroup = drawingGroup
- self.group:insert(drawingGroup)
- local drawOrder = self.drawOrder
- local currentGroup = nil
- local groupVertices = {}
- local groupIndices = {}
- local groupUvs = {}
- local color = self.tempColor
- local lastColor = self.tempColor2
- lastColor.r = -1
- local texture = nil
- local lastTexture = nil
- local blendMode = nil
- local lastBlendMode = nil
- local renderable = {
- vertices = nil,
- uvs = nil
- }
-
- for i,slot in ipairs(drawOrder) do
- local attachment = slot.attachment
- local vertices = nil
- local uvs = nil
- local numVertices = 0
- local indices = nil
- if attachment then
- if attachment.type == spine.AttachmentType.region then
- numVertices = 4
- vertices = worldVertices
- attachment:computeWorldVertices(slot.bone, vertices, 0, 2)
- uvs = attachment.uvs
- indices = QUAD_TRIANGLES
- texture = attachment.region.renderObject.texture
- blendMode = toCoronaBlendMode(slot.data.blendMode)
- elseif attachment.type == spine.AttachmentType.mesh then
- numVertices = attachment.worldVerticesLength / 2
- vertices = worldVertices
- attachment:computeWorldVertices(slot, 0, attachment.worldVerticesLength, vertices, 0, 2)
- uvs = attachment.uvs
- indices = attachment.triangles
- texture = attachment.region.renderObject.texture
- blendMode = toCoronaBlendMode(slot.data.blendMode)
- elseif attachment.type == spine.AttachmentType.clipping then
- self.clipper:clipStart(slot, attachment)
- end
-
- local skeleton = slot.bone.skeleton
- local skeletonColor = skeleton.color
- local slotColor = slot.color
- local attachmentColor = attachment.color
- local alpha = skeletonColor.a * slotColor.a * attachmentColor.a
- local multiplier = alpha
- if premultipliedAlpha then multiplier = 1 end
- color:set(skeletonColor.r * slotColor.r * attachmentColor.r * multiplier,
- skeletonColor.g * slotColor.g * attachmentColor.g * multiplier,
- skeletonColor.b * slotColor.b * attachmentColor.b * multiplier,
- alpha)
- if texture and vertices and indices then
- if not lastTexture then lastTexture = texture end
- if lastColor.r == -1 then lastColor:setFrom(color) end
- if not lastBlendMode then lastBlendMode = blendMode end
- if (texture ~= lastTexture or not colorEquals(color, lastColor) or blendMode ~= lastBlendMode) then
- self:flush(groupVertices, groupUvs, groupIndices, lastTexture, lastColor, lastBlendMode, drawingGroup)
- lastTexture = texture
- lastColor = color
- lastBlendMode = blendMode
- groupVertices = {}
- groupUvs = {}
- groupIndices = {}
- end
-
- if self.clipper:isClipping() then
- self.clipper:clipTriangles(vertices, uvs, indices, #indices)
- vertices = self.clipper.clippedVertices
- numVertices = #vertices / 2
- uvs = self.clipper.clippedUVs
- indices = self.clipper.clippedTriangles
- end
- self:batch(vertices, uvs, numVertices, indices, groupVertices, groupUvs, groupIndices)
- end
-
- self.clipper:clipEnd(slot)
- end
- end
- if #groupVertices > 0 then
- self:flush(groupVertices, groupUvs, groupIndices, texture, color, blendMode, drawingGroup)
- end
-
- self.clipper:clipEnd2()
- end
- function spine.Skeleton:flush(groupVertices, groupUvs, groupIndices, texture, color, blendMode, drawingGroup)
- local mesh = display.newMesh(drawingGroup, 0, 0, {
- mode = "indexed",
- vertices = groupVertices,
- uvs = groupUvs,
- indices = groupIndices
- })
- mesh.fill = texture
- mesh:setFillColor(color.r, color.g, color.b)
- mesh.alpha = color.a
- mesh.blendMode = blendMode
- mesh:translate(mesh.path:getVertexOffset())
- self.batches = self.batches + 1
- end
- function spine.Skeleton:batch(vertices, uvs, numVertices, indices, groupVertices, groupUvs, groupIndices)
- local numIndices = #indices
- local i = 1
- local indexStart = #groupIndices + 1
- local offset = #groupVertices / 2
- local indexEnd = indexStart + numIndices
- while indexStart < indexEnd do
- groupIndices[indexStart] = indices[i] + offset
- indexStart = indexStart + 1
- i = i + 1
- end
- i = 1
- local vertexStart = #groupVertices + 1
- local vertexEnd = vertexStart + numVertices * 2
- while vertexStart < vertexEnd do
- groupVertices[vertexStart] = vertices[i]
- groupVertices[vertexStart+1] = vertices[i+1]
- groupUvs[vertexStart] = uvs[i]
- groupUvs[vertexStart+1] = uvs[i+1]
- vertexStart = vertexStart + 2
- i = i + 2
- end
- end
- return spine
|