#ifndef __DRAW_H__
#define __DRAW_H__

#define WIDTH 480
#define HEIGHT 240

typedef unsigned char u8;
typedef signed char i8;
typedef unsigned short u16;
typedef signed short i16;
typedef unsigned int u32;
typedef signed int i32;
typedef u16 Color;

extern Color framebuffer[WIDTH * HEIGHT];

#define rgb565(r, g, b) ((((u16)r & 0b11111000) << 8) | (((u16)g & 0b11111100) << 3) | (((u16)b & 0xff) >> 3))
#define rgb(r, g, b) (((u32)(r & 0xff) << 24) | ((u32)(g & 0xff) << 16) | ((u32)(b & 0xff) << 8) | 0xff)

void from_hsv(u8 h, u8 s, u8 v, u8* r, u8* g, u8* b);
void to_hsv(u8 r, u8 g, u8 b, u8* h, u8* s, u8* v);
void clear_screen();
void draw_point(i32 x, i32 y, Color color);
void fill_rect(i32 x, i32 y, i32 width, i32 height, Color color);
void draw_rect(i32 x, i32 y, i32 width, i32 height, Color color);
void draw_line(i32 x0, i32 y0, i32 x1, i32 y1, Color color);
void draw_circle(i32 xm, i32 ym, i32 r, Color color);
void horizontal_line(i32 x1, i32 x2, i32 y, Color color);
void fill_circle(i32 xm, i32 ym, i32 r, Color color);
void copy(int n, float *points, float* result);
void scale(int n, float* points, float factorX, float factorY);
void translate(int n, float* points, float x, float y);
void rotate(int n, float* points, float angle);
void draw(int n, float* points, int close, Color color);
void fill(int n, float* points, int wrap, Color color);
int point_in_polygon(int n, float* points, float x, float y);
int line_intersect(float* l1, float* l2);
int polygon_intersect(int n, float* a, int m, float* b);

#define MIRROR_V 1
#define MIRROR_H 2
#define ROTATE_L 4
void blit(i32 x, i32 y, i32 source_x, i32 source_y, i32 width, i32 height, Color* source, i32 source_width, i32 source_height);
void blit_masked(i32 x, i32 y, i32 source_x, i32 source_y, i32 width, i32 height, Color mask, Color* source, i32 source_width, i32 source_height);

typedef struct {
  char text[4];
  u8 width, height;
  u16 offset;
} glyph_t;

typedef struct {
  u8* pixels;
  glyph_t* glyphs;
  int num_glyphs;
  int line_height;
} font_t;

font_t* load_font(char* font_data, int font_data_size);
void draw_text(font_t* font, i32 x, i32 y, Color color, char* text);
void draw_printf(font_t* font, i32 x, i32 y, Color color, char* format, ...);

#endif
