For those who are new to this game, a sprite is a 2D rectangular bitmap that is rendered to the screen. For 2D games, sprites are the most essential graphical abstraction. They are used for drawing maps, players, NPCs, items, particles, text, etc.
In Chickadee, the (chickadee render sprite)
module provides the
interface for working with sprites. Bitmaps are stored in textures
(see Textures) and can be used to draw sprites via the
draw-sprite
procedure.
Draw texture at position.
Optionally, other transformations may be applied to the sprite. rotation specifies the angle to rotate the sprite, in radians. scale specifies the scaling factor as a 2D vector. All transformations are applied relative to origin, a 2D vector, which defaults to the lower-left corner.
tint specifies the color to multiply against all the sprite’s pixels. By default white is used, which does no tinting at all.
Alpha blending is used by default but the blending method can be changed by specifying blend-mode.
The area drawn to is as big as the texture, by default. To draw to an arbitrary section of the screen, specify rect.
It’s not uncommon to need to draw hundreds or thousands of sprites
each frame. However, GPUs (graphics processing units) are tricky
beasts that prefer to be sent few, large chunks of data to render
rather than many, small chunks. Using draw-sprite
on its own
will involve at least one GPU call per sprite. This is fine
for rendering a few dozen sprites, but will become a serious
bottleneck when rendering hundreds or thousands of sprites. To deal
with this, a technique known as “sprite batching” is used. Instead
of drawing each sprite immediately, the sprite batch will build up a
large of buffer of sprites to draw and send them to the GPU all at
once. There is one caveat, however. Batching only works if the
sprites being drawn share a common texture. A good strategy for
reducing the number of different textures is to stuff many bitmaps
into a single image file and create a “texture atlas”
(see Textures) to access the sub-images within.
Create a new sprite batch for texture with initial space for capacity sprites. Sprite batches automatically resize when they are full to accomodate as many sprites as necessary.
Return #t
if obj is a sprite batch.
Return the texture for batch.
Set texture for batch to texture.
white
] [#:texture-region]Add sprite located at position to batch.
To render a subsection of the batch’s texture, a texture object whose parent is the batch texture may be specified as texture-region.
See draw-sprite
for information about the other arguments.
Reset size of batch to 0.
alpha
]Render batch using blend-mode. Alpha blending is used by default.
With a basic sprite abstraction in place, it’s possible to build other abstractions on top of it. One such example is the “nine patch”. A nine patch is a sprite that can be rendered at various sizes without becoming distorted. This is achieved by dividing up the sprite into nine regions:
The one caveat is that the bitmap regions must be designed in such a way so that they are not distorted when stretched along the affected axes. For example, that means that the top and bottom sides could have varying colored pixels vertically, but not horizontally.
The most common application of this technique is for graphical user interface widgets like buttons and dialog boxes. By using a nine patch, they can be rendered at any size without unappealing scaling artifacts.
Draw a nine patch sprite. A nine patch sprite renders texture as a width x height rectangle whose stretchable areas are defined by the given margin measurements top-margin, bottom-margin, left-margin, and right-margin. The margin argument may be used to configure all four margins at once.
Refer to draw-sprite
(see Sprites) for information about
the other arguments.