--- /dev/null
+#include <string.h>
+#include "sprite.h"
+
+#define MAX_SPRITES 32
+
+static int scount;
+static sprite *spr[MAX_SPRITES];
+static sprite *hwspr[4]; /* 4 channels because we support only attached sprites */
+
+void begin_sprites(void)
+{
+ scount = 0;
+ memset(hwspr_used, 0, sizeof hwspr_used);
+}
+
+void end_sprites(void)
+{
+ int i, j;
+
+ /* sort sprites by increasing start position */
+ for(i=0; i<scount; i++) {
+ for(j=i+1; j<scount; j++) {
+ if(spr[j]->y < spr[i]->y) {
+ struct sprite *tmp = spr[i];
+ spr[i] = spr[j];
+ spr[j] = tmp;
+ }
+ }
+ }
+
+ /* set sprite positions and populate copperlist to draw
+ * hardware sprites
+ */
+ for(i=0; i<scount; i++) {
+ struct sprite *s = spr[i];
+ uint16_t sx = 0x80 + s->x;
+ uint16_t sy = 0x2c + s->y;
+ uint16_t vstop = sy + s->height;
+
+ int chan = -1;
+ for(j=0; j<4; j++) {
+ if(!hwspr[j] || hwspr[j]->y + hwspr[j]->height < s->y) {
+ chan = j;
+ hwspr[j] = s;
+ }
+ }
+ if(chan == -1) continue;
+
+ for(j=0; j<s->hwslices; j++) {
+ s->hwspr[idx][0] = s->hwspr[idx + 1][0] = (sx >> 1) | (sy << 8);
+ s->hwspr[idx][1] = s->hwspr[idx + 1][1] = (vstop << 8) |
+ ((vstop >> 7) & 2) | (sx & 1) | 0x80;
+ }
+ }
+}
+
+void draw_sprite(struct sprite *s, int x, int y)
+{
+ if(s->img) {
+ /* blitter sprite */
+ } else {
+ /* hw sprites */
+ spr[scount++] = s;
+ s->x = x - origx;
+ s->y = y - origy;
+ }
+}