Changed image_init() to use stb_image and palette functions

This commit is contained in:
rxi
2016-09-22 19:18:50 +01:00
parent 7848c10af9
commit a285efbc3d
3 changed files with 47 additions and 58 deletions

View File

@@ -1,4 +1,4 @@
/** /**
* Copyright (c) 2014 rxi * Copyright (c) 2014 rxi
* *
* This library is free software; you can redistribute it and/or modify it * This library is free software; you can redistribute it and/or modify it
@@ -16,7 +16,7 @@
const char *font_init(font_t *self, const char *filename) { const char *font_init(font_t *self, const char *filename) {
memset(self, 0, sizeof(*self)); memset(self, 0, sizeof(*self));
const char *err = image_init(&self->image, filename, 0x0); const char *err = image_init(&self->image, filename);
if (err) return err; if (err) return err;
return NULL; return NULL;
} }
@@ -70,7 +70,7 @@ void font_blit(font_t *self, pixel_t *buf, int bufw, int bufh,
x = dx; x = dx;
y += chs; y += chs;
} else { } else {
if (*p != ' ') { if (*p != ' ') {
image_blit(&self->image, buf, bufw, bufh, image_blit(&self->image, buf, bufw, bufh,
x, y, cw * (*p % 16), ch * (*p / 16), cw, ch); x, y, cw * (*p % 16), ch * (*p / 16), cw, ch);
} }
@@ -207,4 +207,3 @@ int luaopen_font(lua_State *L) {
luaobj_newclass(L, CLASS_NAME, NULL, l_font_new, reg); luaobj_newclass(L, CLASS_NAME, NULL, l_font_new, reg);
return 1; return 1;
} }

View File

@@ -1,4 +1,4 @@
/** /**
* Copyright (c) 2014 rxi * Copyright (c) 2014 rxi
* *
* This library is free software; you can redistribute it and/or modify it * This library is free software; you can redistribute it and/or modify it
@@ -10,7 +10,9 @@
#include <string.h> #include <string.h>
#include "lib/dmt/dmt.h" #include "lib/dmt/dmt.h"
#include "lib/stb/stb_image.h"
#include "image.h" #include "image.h"
#include "palette.h"
#include "luaobj.h" #include "luaobj.h"
int image_blendMode = IMAGE_NORMAL; int image_blendMode = IMAGE_NORMAL;
@@ -32,65 +34,56 @@ void image_setFlip(int mode) {
const char *image_init(image_t *self, const char *filename, int key) { const char *image_init(image_t *self, const char *filename) {
/* Loads a PCX from the provided filename into the image struct and inits the /* Loads an image file into the struct and inits the mask */
* struct and mask */ const char *errmsg = NULL;
int i, sz;
int rle = 0;
FILE *fp;
memset(self, 0, sizeof(*self)); memset(self, 0, sizeof(*self));
/* Open, read header and error check */ /* Load 32bit image data */
fp = fopen(filename, "rb"); int width, height, n;
if (!fp) return "could not open image file"; unsigned char *data32 = stbi_load(filename, &width, &height, &n, 4);
if (getc(fp) != 10) { fclose(fp); return "invalid pcx file"; } if (!data32) {
fseek(fp, 2, SEEK_SET); errmsg = "could not load image file";
if (getc(fp)) rle = 1; goto fail;
if (getc(fp) != 8) { fclose(fp); return "image file is not 8bit"; } }
/* Get dimensions and allocate space */ /* Set dimensions and allocate memory */
fseek(fp, 8, SEEK_SET); int sz = width * height;
fread(&self->width, 2, 1, fp); self->width = width;
fread(&self->height, 2, 1, fp); self->height = height;
self->width += 1;
self->height += 1;
sz = self->width * self->height;
self->data = dmt_malloc(sz); self->data = dmt_malloc(sz);
/* Load image data */ /* Load pixels into struct, converting 32bit to 8bit paletted */
fseek(fp, 128, SEEK_SET); int i;
/* Load compressed (RLE) data */ for (i = 0; i < width * height; i++) {
if (rle) { unsigned char *p = data32 + i * 4;
unsigned int c; int b = p[0];
i = 0; int g = p[1];
while (i < sz) { int r = p[2];
c = fgetc(fp); int a = p[3];
if ((c & 0xc0) == 0xc0) { int idx = palette_colorIdx(r, g, b);
c &= ~0xc0; if (idx < 0) {
memset(self->data + i, fgetc(fp), c); errmsg = "color palette exhausted: use fewer colors";
i += c; goto fail;
} else {
self->data[i++] = c;
}
} }
/* Load uncompressed data */ self->data[i] = (a >= 127) ? idx : 0;
} else {
fread(self->data, sz, 1, fp);
} }
fclose(fp);
/* Init mask */ /* Init mask */
self->mask = dmt_malloc(sz); self->mask = dmt_malloc(sz);
for (i = 0; i < sz; i++) { for (i = 0; i < sz; i++) {
if (self->data[i] == key) { self->mask[i] = (self->data[i] == 0) ? 0xFF : 0x00;
self->data[i] = 0x00;
self->mask[i] = 0xFF;
} else {
self->mask[i] = 0x0;
}
} }
/* Free 32bit pixel data, return NULL for no error */
free(data32);
data32 = NULL;
return NULL; return NULL;
fail:
free(data32);
return errmsg;
} }
@@ -178,7 +171,7 @@ void image_blit(image_t *self, pixel_t *buf, int bufw, int bufh,
#define BLIT_NORMAL(dst, src, msk)\ #define BLIT_NORMAL(dst, src, msk)\
(dst) &= (msk);\ (dst) &= (msk);\
(dst) |= (src); (dst) |= (src);
#define BLIT_AND(dst, src, msk)\ #define BLIT_AND(dst, src, msk)\
(dst) &= (src); (dst) &= (src);
@@ -207,7 +200,7 @@ void image_blit(image_t *self, pixel_t *buf, int bufw, int bufh,
for (y = 0; y < sh; y++) { for (y = 0; y < sh; y++) {
memcpy(buf + dsti, self->data + srci, sw); memcpy(buf + dsti, self->data + srci, sw);
srci += self->width; srci += self->width;
dsti += bufw; dsti += bufw;
} }
} else { } else {
BLIT(BLIT_LOOP_NORMAL); BLIT(BLIT_LOOP_NORMAL);
@@ -232,10 +225,9 @@ void image_deinit(image_t *self) {
int l_image_new(lua_State *L) { int l_image_new(lua_State *L) {
const char *filename = luaL_checkstring(L, 1); const char *filename = luaL_checkstring(L, 1);
const int key = lua_gettop(L) > 1 ? luaL_checkint(L, 2): 0x0;
image_t *self = luaobj_newudata(L, sizeof(*self)); image_t *self = luaobj_newudata(L, sizeof(*self));
luaobj_setclass(L, CLASS_TYPE, CLASS_NAME); luaobj_setclass(L, CLASS_TYPE, CLASS_NAME);
const char *err = image_init(self, filename, key); const char *err = image_init(self, filename);
if (err) luaL_error(L, err); if (err) luaL_error(L, err);
return 1; return 1;
} }
@@ -343,4 +335,3 @@ int luaopen_image(lua_State *L) {
luaobj_newclass(L, CLASS_NAME, NULL, l_image_new, reg); luaobj_newclass(L, CLASS_NAME, NULL, l_image_new, reg);
return 1; return 1;
} }

View File

@@ -1,4 +1,4 @@
/** /**
* Copyright (c) 2014 rxi * Copyright (c) 2014 rxi
* *
* This library is free software; you can redistribute it and/or modify it * This library is free software; you can redistribute it and/or modify it
@@ -38,11 +38,10 @@ void image_setColor(pixel_t color);
void image_setBlendMode(int mode); void image_setBlendMode(int mode);
void image_setFlip(int mode); void image_setFlip(int mode);
const char *image_init(image_t *self, const char *filename, int key); const char *image_init(image_t *self, const char *filename);
void image_initBlank(image_t*, int, int); void image_initBlank(image_t*, int, int);
void image_blit(image_t *self, pixel_t *buf, int bufw, int bufh, void image_blit(image_t *self, pixel_t *buf, int bufw, int bufh,
int dx, int dy, int sx, int sy, int sw, int sh); int dx, int dy, int sx, int sy, int sw, int sh);
void image_deinit(image_t*); void image_deinit(image_t*);
#endif #endif