Bitmap demo for the Gameduino

Dependencies:   Gameduino mbed

Revision:
0:abda4161bf6e
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/main.cpp	Thu Dec 20 20:55:38 2012 +0000
@@ -0,0 +1,167 @@
+#include "mbed.h"
+#include "GD.h"
+#include "shield.h"
+GDClass GD(ARD_MOSI, ARD_MISO, ARD_SCK, ARD_D9, USBTX, USBRX) ;
+
+
+// replicate a 2-bit color across the whole byte.  Optimization for setpixel
+byte replicate(byte color)
+{
+    return (color << 6) | (color << 4) | (color << 2) | color;
+}
+
+// Set pixel at (x,y) to color.  (note that color is replicated).
+void setpixel(byte x, byte y, byte color)
+{
+  /*
+   Because of the way the sprites are laid out in setup(), it's not too
+   hard to translate the pixel (x,y) to an address and mask.  Taking the
+   two byte values as x7-x0 and y7-y0, the address of the pixel is:
+
+      x5 x4 y7 y6 y5 y4 y3 y2 y1 y0 x3 x2 x1 x0
+
+  (x6, x7) gives the value of the mask.
+  */
+    unsigned int addr = RAM_SPRIMG | (x & 0xf) | (y << 4) | ((x & 0x30) << 8);
+    byte mask = 0xc0 >> ((x >> 5) & 6);
+    GD.wr(addr, (GD.rd(addr) & ~mask) | (color & mask));
+}
+
+// Draw color line from (x0,y0) to (x1,y1).
+void line(byte x0, byte y0, byte x1, byte y1, byte color)
+{
+    byte swap;
+#define SWAP(a, b) (swap = (a), (a) = (b), (b) = swap)
+
+    color = replicate(color);
+    byte steep = abs(y1 - y0) > abs(x1 - x0);
+    if (steep) {
+        SWAP(x0, y0);
+        SWAP(x1, y1);
+    }
+    if (x0 > x1) {
+        SWAP(x0, x1);
+        SWAP(y0, y1);
+    }
+    int deltax = x1 - x0;
+    int deltay = abs(y1 - y0);
+    int error = deltax / 2;
+    signed char ystep;
+    if (y0 < y1)  
+    {
+        ystep = 1;
+    }
+    else
+    {
+        ystep = -1;
+    }
+    byte x;
+    byte y = y0;
+    for (x = x0; x < x1; x++) 
+    {
+        if (steep)
+        {
+            setpixel(y, x, color);
+        }
+        else
+        {
+            setpixel(x, y, color);
+        }
+        error -= deltay;
+        if (error < 0) 
+        {
+            y += ystep;
+            error += deltax;
+        }
+    }
+}
+
+struct point {
+  int x, y;
+  signed char xv, yv;
+};
+static struct point triangle[3];
+
+#define RANDOM_RGB() RGB(rand()%256,rand()%256,rand()%256)
+
+// Restart the drawing
+static void restart()
+{
+    // Clear the screen
+    GD.fill(RAM_SPRIMG, 0, 16384);
+
+    // Position triangle at random
+    byte i;
+    for (i = 0; i < 3; i++) {
+        triangle[i].x = 3 + rand()%250;
+        triangle[i].y = 3 + rand()%250;
+    }
+    triangle[0].xv = 1;
+    triangle[0].yv = 1;
+    triangle[1].xv = -1;
+    triangle[1].yv = 1;
+    triangle[2].xv = 1;
+    triangle[2].yv = -1;
+
+    // Choose a random palette
+    GD.wr16(PALETTE4A, RGB(0,0,0));
+    GD.wr16(PALETTE4A + 2, RANDOM_RGB());
+    GD.wr16(PALETTE4A + 4, RANDOM_RGB());
+    GD.wr16(PALETTE4A + 6, RANDOM_RGB());
+}
+
+void setup()
+{
+    int i;
+
+    GD.begin();
+    GD.ascii();
+    GD.putstr(0, 0,"Bitmap demonstration");
+
+    // Draw 256 sprites left to right, top to bottom, all in 4-color
+    // palette mode.  By doing them in column-wise order, the address
+    // calculation in setpixel is made simpler.
+    // First 64 use bits 0-1, next 64 use bits 2-4, etc.
+    // This gives a 256 x 256 4-color bitmap.
+
+   for (i = 0; i < 256; i++) {
+       int x =     72 + 16 * ((i >> 4) & 15);
+       int y =     22 + 16 * (i & 15);
+       int image = i & 63;     /* image 0-63 */
+       int pal =   3 - (i >> 6);   /* palettes bits in columns 3,2,1,0 */
+       GD.sprite(i, x, y, image, 0x8 | (pal << 1), 0);
+    }
+    restart();
+}
+
+int main()
+{
+    setup();
+    while(1)
+    {
+        static byte color;
+
+        if (rand()%1000 == 0)
+        {
+            restart();
+        }
+        line(triangle[0].x, triangle[0].y, triangle[1].x, triangle[1].y, color);
+        line(triangle[1].x, triangle[1].y, triangle[2].x, triangle[2].y, color);
+        line(triangle[2].x, triangle[2].y, triangle[0].x, triangle[0].y, color);
+        color = (color + 1) & 3;
+        byte i;
+        for (i = 0; i < 3; i++) 
+        {
+            triangle[i].x += triangle[i].xv;
+            triangle[i].y += triangle[i].yv;
+            if (triangle[i].x == 0 || triangle[i].x == 255)
+            {
+                triangle[i].xv = -triangle[i].xv;
+            }
+            if (triangle[i].y == 0 || triangle[i].y == 255)
+            {
+                triangle[i].yv = -triangle[i].yv;
+            }
+        }
+    }
+}
\ No newline at end of file