commit 8184b6442df94646fac162fab217abff111cf7b0
parent 27962884cc72f5136c74fb125d8c97e8c9e04ebc
Author: amin <dev@aminmesbah.com>
Date: Sat, 6 Jul 2019 00:35:03 +0000
Move image code to separate files
FossilOrigin-Name: a8bcff94c7abec8b72ae58607c4423c38d5283288a2a56fea3512ad813a2df5e
Diffstat:
M | src/game.c | | | 142 | +------------------------------------------------------------------------------ |
M | src/game.h | | | 2 | ++ |
A | src/image.c | | | 120 | +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
A | src/image.h | | | 19 | +++++++++++++++++++ |
4 files changed, 142 insertions(+), 141 deletions(-)
diff --git a/src/game.c b/src/game.c
@@ -10,147 +10,7 @@
#include "render.c"
#include "world.c"
#include "input.c"
-
-#pragma pack(push, 1)
-struct ImgTgaHeader
-{
- // http://paulbourke.net/dataformats/tga/
- u8 id_length;
- u8 color_map_type;
- u8 data_type_code;
- u16 color_map_origin;
- u16 color_map_length;
- u8 color_map_depth;
- u16 x_origin;
- u16 y_origin;
- u16 width;
- u16 height;
- u8 bits_per_pixel;
- u8 image_descriptor;
-};
-#pragma pack(pop)
-static_assert(sizeof(struct ImgTgaHeader) == 18, "");
-
-internal void img_tga_header_print(struct ImgTgaHeader h)
-{
- printf("id_length: %u\n", h.id_length);
- printf("color_map_type: %u\n", h.color_map_type);
- printf("data_type_code: %u\n", h.data_type_code);
- printf("color_map_origin: %u\n", h.color_map_origin);
- printf("color_map_length: %u\n", h.color_map_length);
- printf("color_map_depth: %u\n", h.color_map_depth);
- printf("x_origin: %u\n", h.x_origin);
- printf("y_origin: %u\n", h.y_origin);
- printf("width: %u\n", h.width);
- printf("height: %u\n", h.height);
- printf("bits_per_pixel: %u\n", h.bits_per_pixel);
- printf("image_descriptor: %u\n", h.image_descriptor);
-}
-
-internal u8 img_consume_byte(u8 **buffer, uintptr_t end_address)
-{
- u8 byte = 0;
- if ((uintptr_t)*buffer < end_address)
- {
- byte = **buffer;
- (*buffer)++;
- }
- return byte;
-}
-
-internal u8 *img_load_from_memory(u8 *buffer, size_t len, i32 *out_width, i32 *out_height, struct StackAllocator *allocator)
-{
- assert(buffer);
- uintptr_t buf_end = (uintptr_t)buffer + (len * sizeof(u8));
-
- assert(len >= sizeof(struct ImgTgaHeader));
- struct ImgTgaHeader h = *(struct ImgTgaHeader *)buffer;
- buffer += sizeof(struct ImgTgaHeader);
- img_tga_header_print(h);
-
- // Image descriptor not currently accounted for
- assert(h.id_length == 0);
- // Color maps not currently supported
- assert(h.color_map_type == 0);
- // Only RGB is supported
- assert(h.data_type_code == 2 || h.data_type_code == 10);
- assert(h.bits_per_pixel <= 32);
-
- if (out_width)
- {
- *out_width = h.width;
- }
- if (out_height)
- {
- *out_height = h.height;
- }
-
- u8 bytes_per_pixel = h.bits_per_pixel / 8;
- size_t bytes_per_row = h.width * bytes_per_pixel;
- size_t img_data_buf_len = h.height * bytes_per_row;
- u8 *img_data = mem_st_alloc_buffer(allocator, u8, img_data_buf_len);
- assert(img_data);
-
- if (h.data_type_code == 2)
- {
- // uncompressed RGB
- for (size_t b = 0; b < img_data_buf_len; b++)
- {
- img_data[b] = img_consume_byte(&buffer, buf_end);
- }
- }
- else if (h.data_type_code == 10)
- {
- // Run Length Encoded RGB
- size_t img_bytes_read = 0;
- while (img_bytes_read < img_data_buf_len)
- {
- u8 packet_header = img_consume_byte(&buffer, buf_end);
- u8 run_length_header_bit = packet_header >> 7;
- u32 run_count = (packet_header & (~(1 << 7))) + 1;
- assert(run_count <= 128);
- u32 run_length_in_bytes = run_count * bytes_per_pixel;
-
- if (run_length_header_bit)
- {
- u8 pixel[4] = {0};
- for (u32 b = 0; b < bytes_per_pixel; b++)
- {
- pixel[b] = img_consume_byte(&buffer, buf_end);
- }
- for (u32 b = 0; b < run_length_in_bytes; b++)
- {
- img_data[img_bytes_read + b] = pixel[b % bytes_per_pixel];
- }
- img_bytes_read += run_length_in_bytes;
- }
- else
- {
- for (u32 b = 0; b < run_length_in_bytes; b++)
- {
- img_data[img_bytes_read + b] = img_consume_byte(&buffer, buf_end);
- }
- img_bytes_read += run_length_in_bytes;
- }
- }
- }
-
- // NOTE(amin): Intentional truncating division. If height is odd, we want
- // our last row offset to be 1 less than the middle row.
- u32 half_height = h.height / 2;
- for (size_t row_offset = 0; row_offset < half_height; row_offset++)
- {
- u8 *top_row = &img_data[row_offset * bytes_per_row];
- u8 *bot_row = &img_data[(h.height - row_offset - 1) * bytes_per_row];
- for (size_t b = 0; b < bytes_per_row; b++)
- {
- u8 temp = top_row[b];
- top_row[b] = bot_row[b];
- bot_row[b] = temp;
- }
- }
- return img_data;
-}
+#include "image.c"
internal void move_mode_print(enum MoveMode s)
{
diff --git a/src/game.h b/src/game.h
@@ -81,6 +81,8 @@ void *memmove(void *dst, const void *src, size_t n)
#include "render.h"
#include "world.h"
#include "input.h"
+#include "image.h"
+
#include "platform.h"
static_assert(-1 == ~0, "Implementation doesn't use two's complement");
diff --git a/src/image.c b/src/image.c
@@ -0,0 +1,120 @@
+internal void img_tga_header_print(struct ImgTgaHeader h)
+{
+ printf("id_length: %u\n", h.id_length);
+ printf("color_map_type: %u\n", h.color_map_type);
+ printf("data_type_code: %u\n", h.data_type_code);
+ printf("color_map_origin: %u\n", h.color_map_origin);
+ printf("color_map_length: %u\n", h.color_map_length);
+ printf("color_map_depth: %u\n", h.color_map_depth);
+ printf("x_origin: %u\n", h.x_origin);
+ printf("y_origin: %u\n", h.y_origin);
+ printf("width: %u\n", h.width);
+ printf("height: %u\n", h.height);
+ printf("bits_per_pixel: %u\n", h.bits_per_pixel);
+ printf("image_descriptor: %u\n", h.image_descriptor);
+}
+
+internal u8 img_consume_byte(u8 **buffer, uintptr_t end_address)
+{
+ u8 byte = 0;
+ if ((uintptr_t)*buffer < end_address)
+ {
+ byte = **buffer;
+ (*buffer)++;
+ }
+ return byte;
+}
+
+internal u8 *img_load_from_memory(u8 *buffer, size_t len, i32 *out_width, i32 *out_height, struct StackAllocator *allocator)
+{
+ assert(buffer);
+ uintptr_t buf_end = (uintptr_t)buffer + (len * sizeof(u8));
+
+ assert(len >= sizeof(struct ImgTgaHeader));
+ struct ImgTgaHeader h = *(struct ImgTgaHeader *)buffer;
+ buffer += sizeof(struct ImgTgaHeader);
+ img_tga_header_print(h);
+
+ // Image descriptor not currently accounted for
+ assert(h.id_length == 0);
+ // Color maps not currently supported
+ assert(h.color_map_type == 0);
+ // Only RGB is supported
+ assert(h.data_type_code == 2 || h.data_type_code == 10);
+ assert(h.bits_per_pixel <= 32);
+
+ if (out_width)
+ {
+ *out_width = h.width;
+ }
+ if (out_height)
+ {
+ *out_height = h.height;
+ }
+
+ u8 bytes_per_pixel = h.bits_per_pixel / 8;
+ size_t bytes_per_row = h.width * bytes_per_pixel;
+ size_t img_data_buf_len = h.height * bytes_per_row;
+ u8 *img_data = mem_st_alloc_buffer(allocator, u8, img_data_buf_len);
+ assert(img_data);
+
+ if (h.data_type_code == 2)
+ {
+ // uncompressed RGB
+ for (size_t b = 0; b < img_data_buf_len; b++)
+ {
+ img_data[b] = img_consume_byte(&buffer, buf_end);
+ }
+ }
+ else if (h.data_type_code == 10)
+ {
+ // Run Length Encoded RGB
+ size_t img_bytes_read = 0;
+ while (img_bytes_read < img_data_buf_len)
+ {
+ u8 packet_header = img_consume_byte(&buffer, buf_end);
+ u8 run_length_header_bit = packet_header >> 7;
+ u32 run_count = (packet_header & (~(1 << 7))) + 1;
+ assert(run_count <= 128);
+ u32 run_length_in_bytes = run_count * bytes_per_pixel;
+
+ if (run_length_header_bit)
+ {
+ u8 pixel[4] = {0};
+ for (u32 b = 0; b < bytes_per_pixel; b++)
+ {
+ pixel[b] = img_consume_byte(&buffer, buf_end);
+ }
+ for (u32 b = 0; b < run_length_in_bytes; b++)
+ {
+ img_data[img_bytes_read + b] = pixel[b % bytes_per_pixel];
+ }
+ img_bytes_read += run_length_in_bytes;
+ }
+ else
+ {
+ for (u32 b = 0; b < run_length_in_bytes; b++)
+ {
+ img_data[img_bytes_read + b] = img_consume_byte(&buffer, buf_end);
+ }
+ img_bytes_read += run_length_in_bytes;
+ }
+ }
+ }
+
+ // NOTE(amin): Intentional truncating division. If height is odd, we want
+ // our last row offset to be 1 less than the middle row.
+ u32 half_height = h.height / 2;
+ for (size_t row_offset = 0; row_offset < half_height; row_offset++)
+ {
+ u8 *top_row = &img_data[row_offset * bytes_per_row];
+ u8 *bot_row = &img_data[(h.height - row_offset - 1) * bytes_per_row];
+ for (size_t b = 0; b < bytes_per_row; b++)
+ {
+ u8 temp = top_row[b];
+ top_row[b] = bot_row[b];
+ bot_row[b] = temp;
+ }
+ }
+ return img_data;
+}
diff --git a/src/image.h b/src/image.h
@@ -0,0 +1,19 @@
+#pragma pack(push, 1)
+struct ImgTgaHeader
+{
+ // http://paulbourke.net/dataformats/tga/
+ u8 id_length;
+ u8 color_map_type;
+ u8 data_type_code;
+ u16 color_map_origin;
+ u16 color_map_length;
+ u8 color_map_depth;
+ u16 x_origin;
+ u16 y_origin;
+ u16 width;
+ u16 height;
+ u8 bits_per_pixel;
+ u8 image_descriptor;
+};
+#pragma pack(pop)
+static_assert(sizeof(struct ImgTgaHeader) == 18, "");