summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--.gitignore5
-rw-r--r--Makefile12
-rw-r--r--framebuffer.c59
-rw-r--r--framebuffer.h71
-rw-r--r--main.c5
5 files changed, 152 insertions, 0 deletions
diff --git a/.gitignore b/.gitignore
new file mode 100644
index 0000000..9050050
--- /dev/null
+++ b/.gitignore
@@ -0,0 +1,5 @@
+# The executable
+wafflestone
+
+# VIM swap files
+.*.swp
diff --git a/Makefile b/Makefile
new file mode 100644
index 0000000..c0492b8
--- /dev/null
+++ b/Makefile
@@ -0,0 +1,12 @@
+CC=clang
+EXECUTABLE=wafflestone
+
+wafflestone: *.c *.h
+ $(CC) -Wall -Wpedantic -Wextra -Werror -O3 -o $(EXECUTABLE) framebuffer.c main.c
+
+debug: *.c *.h
+ $(CC) -Wall -g -o $(EXECUTABLE) framebuffer.c main.c
+
+.PHONY: clean
+clean:
+ rm ./$(EXECUTABLE)
diff --git a/framebuffer.c b/framebuffer.c
new file mode 100644
index 0000000..b6e922e
--- /dev/null
+++ b/framebuffer.c
@@ -0,0 +1,59 @@
+#include <stdlib.h>
+
+#include "framebuffer.h"
+
+Framebuffer fb_new(size_t width, size_t height) {
+ Framebuffer fb;
+
+ /* In case malloc() fails and we return early */
+ fb.width = 0;
+ fb.height = 0;
+
+ fb.fb = malloc(sizeof(Pixel *) * height);
+ if (fb.fb == NULL) return fb;
+
+ for (size_t i = 0; i < height; i++) {
+ fb.fb[i] = malloc(sizeof(Pixel) * width);
+ if (fb.fb[i] == NULL) {
+ /* FIXME: Memory leak; should free all prev. malloced rows */
+ fb.fb = NULL;
+ return fb;
+ }
+ }
+
+ fb.width = width;
+ fb.height = height;
+ return fb;
+}
+
+void fb_free(Framebuffer *fb) {
+ if (fb->fb == NULL) goto ret;
+
+ for (size_t i = 0; i < fb->height; i++) {
+ free(fb->fb[i]);
+ }
+ free(fb->fb);
+
+ret:
+ fb->width = 0;
+ fb->height = 0;
+ return;
+}
+
+void fb_fill(Framebuffer fb, Pixel pixel) {
+ for (size_t row = 0; row < fb.height; row++) {
+ for (size_t col = 0; col < fb.width; col++) {
+ fb_put(fb, row, col, pixel);
+ }
+ }
+}
+
+void inline fb_put(Framebuffer fb, size_t row, size_t col, Pixel pixel) {
+ fb.fb[row][col] = pixel;
+}
+
+void fb_init(void);
+
+void fb_cleanup(void);
+
+void fb_print(Framebuffer fb);
diff --git a/framebuffer.h b/framebuffer.h
new file mode 100644
index 0000000..1b0254f
--- /dev/null
+++ b/framebuffer.h
@@ -0,0 +1,71 @@
+#ifndef FRAMEBUFFER_H_
+#define FRAMEBUFFER_H_
+
+#include <stdint.h> /* uint8_t */
+#include <stddef.h> /* wchar_t */
+#include <sys/types.h> /* ssize_t */
+
+/* Globals for the terminal size, set by fb_init() */
+extern size_t TERM_WIDTH, TERM_HEIGHT;
+
+/* Represents a 24 bit colour, 8 bit per channel */
+typedef struct Colour_s {
+ uint8_t r, g, b;
+} Colour;
+
+/* Basic colours */
+#define C_BLACK (Colour){0, 0, 0}
+#define C_WHITE (Colour){255, 255, 255}
+#define C_RED (Colour){255, 0, 0}
+#define C_GREEN (Colour){0, 255, 0}
+#define C_BLUE (Colour){0, 0, 255}
+#define C_YELLOW (Colour){255, 255, 0}
+#define C_CYAN (Colour){0, 255, 255}
+#define C_MAGENTA (Colour){255, 0, 255}
+
+/* One 'pixel' of the image, AKA one character in the terminal.
+ * For a solid colour pixel, set ch to a space and change the bg colour */
+typedef struct Pixel_s {
+ Colour fg, bg;
+ wchar_t ch; /* the char of the pixel */
+} Pixel;
+
+/* Solid colour pixels */
+#define P_BLACK (Pixel){C_BLACK, C_BLACK, ' '}
+#define P_WHITE (Pixel){C_WHITE, C_WHITE, ' '}
+#define P_RED (Pixel){C_RED, C_RED, ' '}
+#define P_GREEN (Pixel){C_GREEN, C_GREEN, ' '}
+#define P_BLUE (Pixel){C_BLUE, C_BLUE, ' '}
+#define P_YELLOW (Pixel){C_YELLOW, C_YELLOW, ' '}
+#define P_CYAN (Pixel){C_CYAN, C_CYAN, ' '}
+#define P_MAGENTA (Pixel){C_MAGENTA, C_MAGENTA, ' '}
+
+typedef struct Framebuffer_s {
+ Pixel **fb; /* Adressed as fb[row][col] or fb[x][y] */
+ size_t width, height;
+} Framebuffer;
+
+/* Check if fb == NULL in case malloc() fails */
+Framebuffer fb_new(size_t width, size_t height);
+
+void fb_free(Framebuffer *fb);
+
+/* Fills fb with pixel */
+void fb_fill(Framebuffer fb, Pixel pixel);
+
+/* Fills fb with black */
+#define fb_clear(fb) fb_fill(fb, P_BLACK)
+
+/* Puts a pixel onto fb in a specified position */
+void inline fb_put(Framebuffer fb, size_t row, size_t col, Pixel pixel);
+
+/* Initializes the terminal and sets TERM_WIDTH and TERM_HEIGHT */
+void fb_init(void);
+
+/* Undoes everything fb_init() did */
+void fb_cleanup(void);
+
+/* Prints fb to the screen */
+void fb_print(Framebuffer fb);
+
+#endif /* FRAMEBUFFER_H_ */
diff --git a/main.c b/main.c
new file mode 100644
index 0000000..8755687
--- /dev/null
+++ b/main.c
@@ -0,0 +1,5 @@
+#include <stdio.h>
+
+int main(void) {
+ fprintf(stderr, "Not yet implemented\n");
+}