Import blues from 8bc7cf4e
This commit is contained in:
parent
ec71a464eb
commit
627fa13e25
21
decode.c
21
decode.c
|
@ -28,3 +28,24 @@ void decode_ega_spr(const uint8_t *src, int src_pitch, int w, int h, uint8_t *ds
|
||||||
src += src_pitch - w;
|
src += src_pitch - w;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void decode_amiga_planar8(const uint8_t *src, int w, int h, int depth, uint8_t *dst, int dst_pitch, int dst_x, int dst_y) {
|
||||||
|
dst += dst_y * dst_pitch + dst_x;
|
||||||
|
const int plane_size = w * h;
|
||||||
|
for (int y = 0; y < h; ++y) {
|
||||||
|
for (int x = 0; x < w; ++x) {
|
||||||
|
for (int i = 0; i < 8; ++i) {
|
||||||
|
int color = 0;
|
||||||
|
const int mask = 1 << (7 - i);
|
||||||
|
for (int bit = 0; bit < depth; ++bit) {
|
||||||
|
if (src[bit * plane_size] & mask) {
|
||||||
|
color |= 1 << bit;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
dst[x * 8 + i] = color;
|
||||||
|
}
|
||||||
|
++src;
|
||||||
|
}
|
||||||
|
dst += dst_pitch;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
1
decode.h
1
decode.h
|
@ -5,5 +5,6 @@
|
||||||
#include "intern.h"
|
#include "intern.h"
|
||||||
|
|
||||||
extern void decode_ega_spr(const uint8_t *src, int src_pitch, int w, int h, uint8_t *dst, int dst_pitch, int dst_x, int dst_y);
|
extern void decode_ega_spr(const uint8_t *src, int src_pitch, int w, int h, uint8_t *dst, int dst_pitch, int dst_x, int dst_y);
|
||||||
|
extern void decode_amiga_planar8(const uint8_t *src, int w, int h, int depth, uint8_t *dst, int dst_pitch, int dst_x, int dst_y);
|
||||||
|
|
||||||
#endif /* DECODE_H__ */
|
#endif /* DECODE_H__ */
|
||||||
|
|
7
game.c
7
game.c
|
@ -17,7 +17,7 @@ void update_input() {
|
||||||
|
|
||||||
void do_title_screen() {
|
void do_title_screen() {
|
||||||
const uint32_t timestamp = g_sys.get_timestamp() + 20 * 1000;
|
const uint32_t timestamp = g_sys.get_timestamp() + 20 * 1000;
|
||||||
load_img("pres.sqz");
|
load_img(g_options.amiga_lbms ? "blues.lbm" : "pres.sqz");
|
||||||
fade_in_palette();
|
fade_in_palette();
|
||||||
do {
|
do {
|
||||||
update_input();
|
update_input();
|
||||||
|
@ -28,7 +28,6 @@ void do_title_screen() {
|
||||||
play_sound(SOUND_0);
|
play_sound(SOUND_0);
|
||||||
fade_out_palette();
|
fade_out_palette();
|
||||||
g_sys.input.space = 0;
|
g_sys.input.space = 0;
|
||||||
read_file("avtmag.sqv", g_res.avt_sqv);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void check_cheat_code() {
|
static void check_cheat_code() {
|
||||||
|
@ -53,7 +52,7 @@ void do_select_player() {
|
||||||
int frame2 = 1;
|
int frame2 = 1;
|
||||||
const int color_rgb = 2;
|
const int color_rgb = 2;
|
||||||
const int colors_count = 25;
|
const int colors_count = 25;
|
||||||
load_img("choix.sqz");
|
load_img(g_options.amiga_lbms ? "choix.lbm" : "choix.sqz");
|
||||||
screen_load_graphics();
|
screen_load_graphics();
|
||||||
screen_clear_sprites();
|
screen_clear_sprites();
|
||||||
do {
|
do {
|
||||||
|
@ -239,7 +238,7 @@ static void do_inter_screen_helper(int xpos, int ypos, int c) {
|
||||||
static void do_inter_screen() {
|
static void do_inter_screen() {
|
||||||
static const uint8_t xpos[] = { 0xFA, 0x50, 0xF0, 0xC8, 0x50, 0x50 };
|
static const uint8_t xpos[] = { 0xFA, 0x50, 0xF0, 0xC8, 0x50, 0x50 };
|
||||||
static const uint8_t ypos[] = { 0xAA, 0x37, 0x28, 0x5F, 0xA5, 0xAA };
|
static const uint8_t ypos[] = { 0xAA, 0x37, 0x28, 0x5F, 0xA5, 0xAA };
|
||||||
load_img("inter.sqz");
|
load_img(g_options.amiga_lbms ? "inter.lbm" : "inter.sqz");
|
||||||
g_vars.screen_h = 199;
|
g_vars.screen_h = 199;
|
||||||
screen_clear_sprites();
|
screen_clear_sprites();
|
||||||
if (g_vars.level > 1) {
|
if (g_vars.level > 1) {
|
||||||
|
|
3
game.h
3
game.h
|
@ -42,6 +42,9 @@ struct options_t {
|
||||||
int start_ypos16;
|
int start_ypos16;
|
||||||
bool amiga_copper_bars;
|
bool amiga_copper_bars;
|
||||||
bool amiga_colors;
|
bool amiga_colors;
|
||||||
|
bool amiga_sprites;
|
||||||
|
bool amiga_lbms;
|
||||||
|
bool amiga_data;
|
||||||
};
|
};
|
||||||
|
|
||||||
extern struct options_t g_options;
|
extern struct options_t g_options;
|
||||||
|
|
24
level.c
24
level.c
|
@ -29,7 +29,7 @@ static const uint16_t _colors_data[16 * MAX_LEVELS] = {
|
||||||
0x000,0x30b,0x747,0x446,0x006,0xfda,0x400,0xf87,0x37a,0x600,0xd63,0x000,0x000,0x800,0xdd0,0x98d
|
0x000,0x30b,0x747,0x446,0x006,0xfda,0x400,0xf87,0x37a,0x600,0xd63,0x000,0x000,0x800,0xdd0,0x98d
|
||||||
};
|
};
|
||||||
|
|
||||||
static const struct level_data_t {
|
static const struct {
|
||||||
const char *ck1;
|
const char *ck1;
|
||||||
const char *ck2;
|
const char *ck2;
|
||||||
const char *sql;
|
const char *sql;
|
||||||
|
@ -48,6 +48,18 @@ static const struct level_data_t {
|
||||||
{ "concert.ck1", "concert.ck2", "concert.sql", "concert.bin", "", "enemi6.sqv", level_xpos_concert, level_ypos_concert, 3 },
|
{ "concert.ck1", "concert.ck2", "concert.sql", "concert.bin", "", "enemi6.sqv", level_xpos_concert, level_ypos_concert, 3 },
|
||||||
};
|
};
|
||||||
|
|
||||||
|
static const struct {
|
||||||
|
const char *m;
|
||||||
|
const char *bin;
|
||||||
|
} _levels_amiga[MAX_LEVELS] = {
|
||||||
|
{ "mag.m", "magasin.bin" },
|
||||||
|
{ "ent.m", "entrepo.bin" },
|
||||||
|
{ "pris.m", "prison.bin" },
|
||||||
|
{ "egou.m", "egout.bin" },
|
||||||
|
{ "ville.m", "ville.bin" },
|
||||||
|
{ 0, "concert.bin" },
|
||||||
|
};
|
||||||
|
|
||||||
static const char *_demo_filenames[] = {
|
static const char *_demo_filenames[] = {
|
||||||
"demomag.ck1", "demomag.ck2", "demomag.sql"
|
"demomag.ck1", "demomag.ck2", "demomag.sql"
|
||||||
};
|
};
|
||||||
|
@ -63,9 +75,19 @@ void load_level_data(int num) {
|
||||||
load_ck(_levels[num].ck2, 0x8000);
|
load_ck(_levels[num].ck2, 0x8000);
|
||||||
load_sql(_levels[num].sql);
|
load_sql(_levels[num].sql);
|
||||||
}
|
}
|
||||||
|
if (g_options.amiga_data) {
|
||||||
|
load_bin(_levels_amiga[num].bin);
|
||||||
|
} else {
|
||||||
load_bin(_levels[num].bin);
|
load_bin(_levels[num].bin);
|
||||||
|
}
|
||||||
load_avt(_levels[num].avt, g_res.avt_sqv, 0);
|
load_avt(_levels[num].avt, g_res.avt_sqv, 0);
|
||||||
|
if (g_options.amiga_sprites) {
|
||||||
|
char name[16];
|
||||||
|
snprintf(name, sizeof(name), "ennemi%d", 1 + num);
|
||||||
|
load_spr(name, g_res.tmp, SPRITES_COUNT);
|
||||||
|
} else {
|
||||||
load_sqv(_levels[num].sqv, g_res.tmp, SPRITES_COUNT);
|
load_sqv(_levels[num].sqv, g_res.tmp, SPRITES_COUNT);
|
||||||
|
}
|
||||||
memcpy(g_vars.level_xpos, _levels[num].xpos, MAX_OBJECTS * sizeof(int16_t));
|
memcpy(g_vars.level_xpos, _levels[num].xpos, MAX_OBJECTS * sizeof(int16_t));
|
||||||
memcpy(g_vars.level_ypos, _levels[num].ypos, MAX_OBJECTS * sizeof(int16_t));
|
memcpy(g_vars.level_ypos, _levels[num].ypos, MAX_OBJECTS * sizeof(int16_t));
|
||||||
if (g_vars.music_num != _levels[num].music) {
|
if (g_vars.music_num != _levels[num].music) {
|
||||||
|
|
3
main.c
3
main.c
|
@ -23,6 +23,9 @@ int main(int argc, char *argv[]) {
|
||||||
g_options.start_ypos16 = -1;
|
g_options.start_ypos16 = -1;
|
||||||
g_options.amiga_copper_bars = true;
|
g_options.amiga_copper_bars = true;
|
||||||
g_options.amiga_colors = true;
|
g_options.amiga_colors = true;
|
||||||
|
// g_options.amiga_sprites = true;
|
||||||
|
// g_options.amiga_lbms = true;
|
||||||
|
// g_options.amiga_data = true;
|
||||||
const char *data_path = DEFAULT_DATA_PATH;
|
const char *data_path = DEFAULT_DATA_PATH;
|
||||||
if (argc == 2) {
|
if (argc == 2) {
|
||||||
struct stat st;
|
struct stat st;
|
||||||
|
|
63
resource.c
63
resource.c
|
@ -44,14 +44,7 @@ void res_init() {
|
||||||
if (!g_res.snd) {
|
if (!g_res.snd) {
|
||||||
print_warning("Failed to allocate sound buffer, %d bytes", SOUND_SIZE);
|
print_warning("Failed to allocate sound buffer, %d bytes", SOUND_SIZE);
|
||||||
} else {
|
} else {
|
||||||
int f = fio_open(filename, 1);
|
read_file(filename, g_res.snd, SOUND_SIZE);
|
||||||
const int filesize = fio_size(f);
|
|
||||||
if (filesize != SOUND_SIZE) {
|
|
||||||
print_warning("Unexpected '%s' file size %d", filename, filesize);
|
|
||||||
} else if (fio_read(f, g_res.snd, SOUND_SIZE) != SOUND_SIZE) {
|
|
||||||
print_error("Failed to read %d bytes from file '%s'", filesize, filename);
|
|
||||||
}
|
|
||||||
fio_close(f);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (fio_exists("demomag.sql")) {
|
if (fio_exists("demomag.sql")) {
|
||||||
|
@ -69,10 +62,12 @@ void res_fini() {
|
||||||
free(g_res.snd);
|
free(g_res.snd);
|
||||||
}
|
}
|
||||||
|
|
||||||
int read_file(const char *filename, uint8_t *dst) {
|
int read_file(const char *filename, uint8_t *dst, int size) {
|
||||||
const int f = fio_open(filename, 1);
|
const int f = fio_open(filename, 1);
|
||||||
const int filesize = fio_size(f);
|
const int filesize = fio_size(f);
|
||||||
if (fio_read(f, dst, filesize) != filesize) {
|
if (size > 0 && size != filesize) {
|
||||||
|
print_error("Unexpected '%s' file size %d (%d)", filename, filesize, size);
|
||||||
|
} else if (fio_read(f, dst, filesize) != filesize) {
|
||||||
print_error("Failed to read %d bytes from file '%s'", filesize, filename);
|
print_error("Failed to read %d bytes from file '%s'", filesize, filename);
|
||||||
}
|
}
|
||||||
fio_close(f);
|
fio_close(f);
|
||||||
|
@ -210,8 +205,7 @@ static const uint8_t *trigger_lookup_table3(uint8_t num) {
|
||||||
|
|
||||||
void load_bin(const char *filename) {
|
void load_bin(const char *filename) {
|
||||||
uint8_t bin[MAX_TRIGGERS * 10];
|
uint8_t bin[MAX_TRIGGERS * 10];
|
||||||
const int size = read_file(filename, bin);
|
read_file(filename, bin, MAX_TRIGGERS * 10);
|
||||||
assert(size == MAX_TRIGGERS * 10);
|
|
||||||
const uint8_t *p = bin;
|
const uint8_t *p = bin;
|
||||||
for (int i = 0; i < MAX_TRIGGERS; ++i) {
|
for (int i = 0; i < MAX_TRIGGERS; ++i) {
|
||||||
struct trigger_t *t = &g_res.triggers[i];
|
struct trigger_t *t = &g_res.triggers[i];
|
||||||
|
@ -247,7 +241,13 @@ void load_ck(const char *filename, uint16_t offset) {
|
||||||
}
|
}
|
||||||
|
|
||||||
void load_img(const char *filename) {
|
void load_img(const char *filename) {
|
||||||
const int size = read_compressed_file(filename, g_res.tmp);
|
int size;
|
||||||
|
const char *ext = strrchr(filename, '.');
|
||||||
|
if (ext && strcmp(ext + 1, "lbm") == 0) {
|
||||||
|
size = read_file(filename, g_res.tmp, 0);
|
||||||
|
} else {
|
||||||
|
size = read_compressed_file(filename, g_res.tmp);
|
||||||
|
}
|
||||||
assert(size <= 32000);
|
assert(size <= 32000);
|
||||||
load_iff(g_res.tmp, size, g_res.tmp + 32000, 320);
|
load_iff(g_res.tmp, size, g_res.tmp + 32000, 320);
|
||||||
g_sys.set_screen_palette(g_res.palette, 16);
|
g_sys.set_screen_palette(g_res.palette, 16);
|
||||||
|
@ -255,21 +255,44 @@ void load_img(const char *filename) {
|
||||||
memcpy(g_res.vga, g_res.tmp + 32000, 64000);
|
memcpy(g_res.vga, g_res.tmp + 32000, 64000);
|
||||||
}
|
}
|
||||||
|
|
||||||
void load_sqv(const char *filename, uint8_t *dst, int offset) {
|
static int load_spr_helper(int offset, const uint8_t *ptr, uint16_t (*read16)(const uint8_t *)) {
|
||||||
read_compressed_file(filename, dst);
|
const int count = read16(ptr); ptr += 6;
|
||||||
const uint8_t *ptr = dst;
|
print_debug(DBG_RESOURCE, "spr count %d", count);
|
||||||
const int count = READ_LE_UINT16(ptr); ptr += 6;
|
|
||||||
print_debug(DBG_RESOURCE, "sqv count %d", count);
|
|
||||||
assert(offset + count <= MAX_SPR_FRAMES);
|
assert(offset + count <= MAX_SPR_FRAMES);
|
||||||
for (int i = 0; i < count; ++i) {
|
for (int i = 0; i < count; ++i) {
|
||||||
g_res.spr_frames[offset + i] = ptr;
|
g_res.spr_frames[offset + i] = ptr;
|
||||||
const int h = READ_LE_UINT16(ptr - 4);
|
const int h = read16(ptr - 4);
|
||||||
const int w = READ_LE_UINT16(ptr - 2);
|
const int w = read16(ptr - 2);
|
||||||
assert((w & 3) == 0);
|
assert((w & 3) == 0);
|
||||||
const int size = (w >> 1) * h + 4;
|
const int size = (w >> 1) * h + 4;
|
||||||
print_debug(DBG_RESOURCE, "sprite %d, dim %d,%d size %d", i, w, h, size);
|
print_debug(DBG_RESOURCE, "sprite %d, dim %d,%d size %d", i, w, h, size);
|
||||||
ptr += size;
|
ptr += size;
|
||||||
}
|
}
|
||||||
|
return count;
|
||||||
|
}
|
||||||
|
|
||||||
|
void load_spr(const char *filename, uint8_t *dst, int offset) {
|
||||||
|
read_file(filename, dst, 0);
|
||||||
|
const int count = load_spr_helper(offset, dst, READ_BE_UINT16);
|
||||||
|
g_res.spr_count = offset + count;
|
||||||
|
// convert to little endian
|
||||||
|
uint8_t *ptr = dst;
|
||||||
|
for (int i = 0; i < count; ++i) {
|
||||||
|
const int h = READ_BE_UINT16(ptr + 2);
|
||||||
|
ptr[2] = h;
|
||||||
|
ptr[3] = 0;
|
||||||
|
const int w = READ_BE_UINT16(ptr + 4);
|
||||||
|
ptr[4] = w;
|
||||||
|
ptr[5] = 0;
|
||||||
|
assert((w & 3) == 0);
|
||||||
|
const int size = (w >> 1) * h + 4;
|
||||||
|
ptr += size;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void load_sqv(const char *filename, uint8_t *dst, int offset) {
|
||||||
|
read_compressed_file(filename, dst);
|
||||||
|
const int count = load_spr_helper(offset, dst, READ_LE_UINT16);
|
||||||
g_res.spr_count = offset + count;
|
g_res.spr_count = offset + count;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -50,13 +50,14 @@ extern struct resource_data_t g_res;
|
||||||
|
|
||||||
extern void res_init();
|
extern void res_init();
|
||||||
extern void res_fini();
|
extern void res_fini();
|
||||||
extern int read_file(const char *filename, uint8_t *dst);
|
extern int read_file(const char *filename, uint8_t *dst, int size);
|
||||||
extern int read_compressed_file(const char *filename, uint8_t *dst);
|
extern int read_compressed_file(const char *filename, uint8_t *dst);
|
||||||
extern void load_avt(const char *filename, uint8_t *dst, int offset);
|
extern void load_avt(const char *filename, uint8_t *dst, int offset);
|
||||||
extern void load_bin(const char *filename);
|
extern void load_bin(const char *filename);
|
||||||
extern void load_ck(const char *filename, uint16_t offset);
|
extern void load_ck(const char *filename, uint16_t offset);
|
||||||
extern void load_img(const char *filename);
|
extern void load_img(const char *filename);
|
||||||
extern void load_sqv(const char *filename, uint8_t *dst, int size);
|
extern void load_spr(const char *filename, uint8_t *dst, int offset);
|
||||||
|
extern void load_sqv(const char *filename, uint8_t *dst, int offset);
|
||||||
extern void load_sql(const char *filename);
|
extern void load_sql(const char *filename);
|
||||||
extern uint8_t * lookup_sql(int x, int y);
|
extern uint8_t * lookup_sql(int x, int y);
|
||||||
|
|
||||||
|
|
9
screen.c
9
screen.c
|
@ -160,6 +160,7 @@ void screen_add_game_sprite4(int x, int y, int frame, int blinking_counter) {
|
||||||
}
|
}
|
||||||
|
|
||||||
static void decode_graphics(int spr_type, int start, int end) {
|
static void decode_graphics(int spr_type, int start, int end) {
|
||||||
|
const bool amiga = g_options.amiga_sprites && start != 0;
|
||||||
struct sys_rect_t r[MAX_SPR_FRAMES];
|
struct sys_rect_t r[MAX_SPR_FRAMES];
|
||||||
uint8_t *data = (uint8_t *)calloc(MAX_SPRITESHEET_W * MAX_SPRITESHEET_H, 1);
|
uint8_t *data = (uint8_t *)calloc(MAX_SPRITESHEET_W * MAX_SPRITESHEET_H, 1);
|
||||||
if (data) {
|
if (data) {
|
||||||
|
@ -179,11 +180,19 @@ static void decode_graphics(int spr_type, int start, int end) {
|
||||||
}
|
}
|
||||||
current_x = 0;
|
current_x = 0;
|
||||||
max_h = h;
|
max_h = h;
|
||||||
|
if (amiga) {
|
||||||
|
decode_amiga_planar8(ptr, w / 8, h, 4, data, MAX_SPRITESHEET_W, current_x, current_y);
|
||||||
|
} else {
|
||||||
decode_ega_spr(ptr, w, w, h, data, MAX_SPRITESHEET_W, current_x, current_y);
|
decode_ega_spr(ptr, w, w, h, data, MAX_SPRITESHEET_W, current_x, current_y);
|
||||||
|
}
|
||||||
r[j].x = current_x;
|
r[j].x = current_x;
|
||||||
r[j].y = current_y;
|
r[j].y = current_y;
|
||||||
|
} else {
|
||||||
|
if (amiga) {
|
||||||
|
decode_amiga_planar8(ptr, w / 8, h, 4, data, MAX_SPRITESHEET_W, current_x, current_y);
|
||||||
} else {
|
} else {
|
||||||
decode_ega_spr(ptr, w, w, h, data, MAX_SPRITESHEET_W, current_x, current_y);
|
decode_ega_spr(ptr, w, w, h, data, MAX_SPRITESHEET_W, current_x, current_y);
|
||||||
|
}
|
||||||
r[j].x = current_x;
|
r[j].x = current_x;
|
||||||
r[j].y = current_y;
|
r[j].y = current_y;
|
||||||
current_x += w;
|
current_x += w;
|
||||||
|
|
Loading…
Reference in New Issue