import sys
import array
import unittest
import Image
import time
import compress

import gameduino.remote
import gameduino.prep as gdprep

gd = gameduino.remote.Gameduino(sys.argv.pop(), 115200)

def desert():
    def lerp(t, a, b):
        return a + t * (b - a)

    def clerp(t, ta, tb):
        return tuple([int(lerp(t, a, b)) for (a, b) in zip(ta, tb)])

    sky = (0,169,255)
    sand = (249,214,114)
    white = (255,255,255)
    return array.array('H', [gdprep.rgb555(*clerp(i / 31., sky, white)) for i in range(32)] + [gdprep.rgb555(*clerp(i / 31., white, sand)) for i in range(32)])

def main():
    hh = open("../../bg.h", "w")

    ir = gdprep.ImageRAM(hh)
    (walk,pogo) = gdprep.palettize([Image.open("walk.png"), Image.open("pogo.png")], 16)
    ir.addsprites("walk", (32, 32), walk, gdprep.PALETTE16A, center = (8,32))
    ir.addsprites("pogo", (16, 48), pogo, gdprep.PALETTE16A, center = (8,48))

    (fruit,) = gdprep.palettize([Image.open("fruit.png")], 16)
    ir.addsprites("fruit", (16, 16), fruit, gdprep.PALETTE16B, center = (8,8))

    gdprep.dump(hh, "desert", desert())

    open("dump", "w").write(ir.used().tostring())
    cc = compress.Codec(b_off = 9, b_len = 3)
    compressed = cc.toarray(ir.used().tostring())
    gdprep.dump(hh, "sprimg_cc", compressed)

    gdprep.dump(hh, "palette16a", gdprep.getpal(walk))
    gdprep.dump(hh, "palette16b", gdprep.getpal(fruit))

    chars = Image.open("chr.png")
    charset = [chars.crop((x, y, x+8, y+8)) for y in range(0, 128, 8) for x in range(0, 128, 8)]
    dchr = array.array('B', [0] * 4096)
    dpal = array.array('H', [0] * 1024)
    for i,ci in enumerate(charset):
        dc,dp = gdprep.encodech(ci.tostring())
        dchr[16 * i:16 * i + 16] = array.array('B', dc)
        dpal[4 * i:4 * i + 4] = dp
    gdprep.dump(hh, "dchr", cc.toarray(dchr.tostring()))
    gdprep.dump(hh, "dpal", cc.toarray(dpal.tostring()))
    gdprep.dump(hh, "tiles", array.array('B', open("tiles").read()))
    gdprep.dump(hh, "level", array.array('B', open("map").read()))

    gd.wrstr(gameduino.RAM_SPRIMG, ir.used())
    print "sprites use", len(ir.used()), "bytes.", "compressed", len(compressed)
    gd.wrstr(gameduino.PALETTE16A, gdprep.getpal(walk))
    gd.wrstr(gameduino.PALETTE16B, gdprep.getpal(fruit))

    for i in range(128):
        gd.sprite(i, 200 + 20 * (i & 7), 20 * (i / 8), i / 2, gdprep.PALETTE16A[i&1], 0)

    def jb(x, y, f):
        frame = 4 * f
        gd.sprite(200, x, y, frame / 2, gdprep.PALETTE16A[frame&1], 0)
        gd.sprite(201, x + 16, y, (frame+1) / 2, gdprep.PALETTE16A[(frame+1)&1], 0)
        gd.sprite(202, x, y+16, (frame+2) / 2, gdprep.PALETTE16A[(frame+2)&1], 0)
        gd.sprite(203, x + 16, y+16, (frame+3) / 2, gdprep.PALETTE16A[(frame+3)&1], 0)

    while True:
        x = 0
        while x < 300:
            for i in range(1,9):
                jb(x, 100, i)
                time.sleep(6/72.)
                x += 5
        jb(x, 100, 0)
        time.sleep(4)

if __name__ == '__main__':
    main()
