TexturePacker exporters for Codea (Easy sprite sheet import and use!)

I’ve created a couple of custom exporters for the marvelous TexturePacker (http://www.codeandweb.com/texturepacker) for Codea. You can find them here: https://github.com/apendley/TPCodea (please read the readme for exporter installation instructions and for some important details about generating Codea-friendly retina-ready sprite sheets and data).

Also, I’ve created a class (SpriteBatch) that makes it easy to batch render sprites using the data and sprite sheets generated from TexturePacker. It’s basic right now, but I plan on adding more to it if I have time over the next few days. An example project including the class can be found here: https://github.com/apendley/TPCodeaExamples

Thanks a lot. It’s very very interesting. Do you have a small example ?
Here it’s morning :slight_smile:

EDIT: updated original post with link to example project. Mods, you can delete this post if you want.

Update: I’ve finished the SpriteBatch class for batch rendering sprites using exported sprite sheets from Codea. It’s super simple to use. Once you’ve got your sprite sheet imported into your project, you can use it like so:

function setup()
    -- assumes texture is in "Documents" sprite pack, though
    -- you can specify a different sprite pack name as an
    -- optional second parameter.
    batch = SpriteBatch(tp["SmallWorldSprites"])
end

function draw()
    background(0)
    
    -- submit a "Beam" sprite from the sprite sheet to the batch renderer.
    batch:sprite("Beam", WIDTH/2, HEIGHT/2)

    -- submit all sprites in batch to Codea's renderer
    batch:draw()
end

```



The SpriteBatch:sprite() interface is identical to Codea's sprite() function, with the exception that the first parameter specifies the name of a sprite in the sprite sheet, rather than a sprite in a sprite pack. SpriteBatch:sprite() will add your sprite to the batch using the current model matrix and sprite style settings, so you can even transform a sprite submitted with SpriteBatch:sprite() using translate(), rotate(), scale(), applyMatrix(), and you can change the color and mode using tint() and spriteMode(), just like Codea's sprite() function.

I've updated the example projects with the latest version of SpriteBatch.

Very nice, @toadkick. I’m thinking perhaps something like this should be built into Codea in the future.

Nice! I’ve used TexturePacker in Moai, and reused the resulting exported file in Codea. But this is much nicer!

.@Simeon: That would be great! I think I’ve optimized the SpriteBatch:sprite() function as much as I can, but a native version of SpriteBatch (perhaps with a better name :smiley: ) would be much more optimal. Feel free to use the SpriteBatch class as a reference, the logic should pretty much be identical in Objective-C.

.@tnlogy: Thanks! The Moai exporter was actually an inspiration, but there were several things about it that made it cumbersome and inefficient to use for Codea (like the fact that it stores the frames in an array instead of using key/value pairs, and the fact that I needed to write a function in Codea to process the UV coordinate data into a format that works with Codea’s mesh() class). Initially I was planning on contacting Andreas Lowe to see if he could add Codea exporters to TexturePacker, until I realized that version 3 provides facilities to create your own custom exporters :slight_smile:

As a bonus, Andreas has informed me that he will include the Codea exporters into the next version of TexturePacker, so soon it will not be necessary to add the exporters manually :slight_smile: There is a bug with version 3.0.1 of TexturePacker (the lastest version) where normalized UV coordinates are output incorrectly. Once that’s fixed, I can modify the exporters to not have to calculate the normalized UV coordinates at run-time, and I imagine at that point the exporters will be in a final state. To that end, I will accept any feedback about the format of the exported data and make any changes that would be helpful.

Another point of potential interest: I am thinking about creating a tile map editor project in Codea, with the ability to create tile maps that can be used by other Codea projects easily. I’ve got a stressful move to another state coming up, and I’m busy with my “real” job, but I hope to find time to start working on it soon.

Some performance stats: Using Codea’s sprite() function to render sprites, I was able to get around ~45 sprites displaying and animating using the tween library before performance started to degrade. By using SpriteBatch instead to do the same thing, I was able to get ~360 sprites displaying and animating before performance started to degrade below 60fps. That’s an 8x as many sprites! If you aren’t sold yet on the benefits of using mesh() (and by extension TexturePacker/SpriteBatch) to render your sprites, that might persuade you :slight_smile:

A small update:

  • renamed tpBatch to SpriteBatch

  • allow using individual sprites (e.g. batch = SpriteBatch(“Small World:Church”).
    This provides some of the benefits of the SpriteBatch class to “normal” sprites (e.g. you can render lots of the same sprite more cheaply).

  • modified the SpriteBatch:sprite() interface to allow specifying texture coordinates (based on a comment by @Simeon in this discussion: http://twolivesleft.com/Codea/Talk/discussion/comment/10690#Comment_10690).

An example:

-- load the sprite "Church" from the "SmallWorld" sprite pack
batch = SpriteBatch("Small World:Church")

-- draw only the bottom half of the "Church" sprite
local w, h = batch:spriteSize("Church")
batch:sprite("Church", WIDTH/2, HEIGHT/2, 0, 0, 1, 0.5, w, h/2)

```


This enables some neat tricks, for example texture coordinate scrolling (I'll try to come up with an example soon).

Did the latest release of texturepacker ever release the Codea stuff? Their site doesn’t mention it, and it was 3 updates ago.

Oh dang, Andreas emailed me right before the holidays saying the he couldn’t repro the issue I was having with the normalized coordinates, so I’m assuming he hasn’t added the Codea exporters yet. I’ve been super busy with work so I haven’t had a chance to look at this yet…when I get some time I’ll try to narrow down the bug and see if he can reproduce it. If not, the exporters in their current state will still work, so I’ll see if he can just add them as they are. In the meantime you’ll need to add the exporters manually as per the instructions in the readme on the github repo for TPCodea.

@toadkick thanks for your brilliant class! I was able to replace my sprites in no time!
There is only one problem: is there a way to use blendMode(ADDITIVE) with meshes?

.@derhannes: Thank you!

The answer to your question is yes, but it probably won’t work with SpriteBatch in the way you expect. Blend mode does affect meshes, however a limitation of rendering batched sprites using meshes is that you cannot set the blend mode separately on the individual sprites within the mesh, only on the actual mesh itself. In other words, all sprites rendered in the same batch will have the same blend mode. Setting the blend mode before calling SpriteBatch:sprite() will not have the desired effect, because the sprites are not actually drawn until the mesh is drawn.

If that limitation is not a problem for you, then what you can do is set the blend mode before calling SpriteBatch:draw().

Here’s a quick and dirty example:

function setup()
    batch = SpriteBatch("Small World:Church")
end

function draw(dt)
    background(0)

    batch:sprite("Church", WIDTH/2, HEIGHT/2)
    
    -- 1) you can set the tint on individual batch sprites:
    tint(255, 255, 255, 128)
    batch:sprite("Church", WIDTH/2 + 40, HEIGHT/2)    
    
    -- 2) reset the opacity before drawing sprite batch
    tint(255)
    
    -- 3) set the blend mode on the sprite batch
    blendMode(ADDITIVE)
    batch:draw()
end

```

Just clarifying the above: blendMode is a feature coming in 1.5.

@toadkick thanks for your quick answer!
Unfortunately that is a problem, but I’ll think of a workaround…

This is pretty interesting, any idea if texturepacker has hadded codea support yet? I couldnt find it. This would be so much more usful then the eaqually spaced spritesheets i’m using.

It’s been awhile since I’ve contacted Andreas, but last I heard he was not able to reproduce the exporter bug I was running into. At any rate, you can still add the plugin with the workaround manually to TP and it will be available for use as an exporter in TP (I’ve been using it for some time now, it works great), just follow the link in the first post to din the instructions (it’s actually not too bad).

Thanks @toadkick really cool. Just wish i could use texturepacker from my ipad :slight_smile: I’ve been avoiding my pc for a long while.

Thanks @toadkick Its really great!! … I faced a problem accidentally when I tried to paste your examples into Lua Jump example after running I can see all sprites are shifted the right side of the screen although the boundary box is in the correct position(i.e. the center), it seems for me its a problem with the translate action, Any hint?

Try removing the part of your draw where you tell the sprite to be in a certain place. If you use translate to set your sprite, you then need to tell your sprite to draw at (the now translated spot) at 0,0.

like this

  translate(120,610)
  rotate(180)
  sprite("Cargo Bot:Command Grab", 0,0)