kettek2/wiki/games/newsboy/Newsboy_0x00/engine/State_EntEdit.c

367 lines
12 KiB
C

#include <stdlib.h>
#include "State_EntEdit.h"
#include "state.h"
#include "globals.h"
#include "Ui.h"
#include "Primitives.h"
#include "render.h"
#include "fifo.h"
#include "EntityData.h"
#include "string.h"
char *ent_text_name[] = {
"Filename: ",
"Name: ",
"Anim: ",
"Set: ",
"Face: ",
"Frame: ",
//////// logic
"type: ",
"behave: ",
//////// movement / collision
"mass: ",
"radius: ",
"speed: ",
"turn: ",
////////
"hp: ",
"sight: ",
//////// attack
"range: ",
"attack: ",
"damage: ",
"spawn: ",
//////// if projectile
"time: "
};
char *ent_button_name[] = {
"Delete",
"Duplicate",
"Save"
};
int openEntEditState() {
report(DEBUG, "EntEditState", "opened");
int i;
int offset_x, offset_y;
offset_x = offset_y = 0;
// window and sub-windows
ent_window = newBox(16, 16, g_v_width-32, g_v_height-32, 0);
ent_window_l = newBox(16, 16, ent_window->w/4, ent_window->h, 0);
ent_window_r = newBox(ent_window_l->x+ent_window_l->w, 16, ent_window->w-ent_window_l->w, ent_window->h, 0);
// list
ent_list = newList(ui_colors);
ent_list->box.x = ent_window_l->x;
ent_list->box.y = ent_window_l->y;
ent_list->box.w = ent_window_l->w;
ent_list->box.h = ent_window_l->h - 32;
ent_item = NULL;
buildEntList();
// text & input
offset_x = ent_window_r->x+2;
offset_y = ent_window_r->y+2;
// first render animation-related stuff
for (i = 0; i < ENT_TEXT_ANIMATION_E; i++) {
ent_text[i] = newTextt(&g_medium_glyphs, ui_colors, ent_text_name[i]);
ent_text[i]->box.x = offset_x;
ent_text[i]->box.y = offset_y;
ent_input[i] = newTextInput(&g_medium_glyphs, button_colors, ent_window_r->w - ent_text[i]->box.w-4);
ent_input[i]->box.x = offset_x + ent_text[i]->box.w+2;
ent_input[i]->box.y = offset_y;
offset_y += ent_text[i]->box.h + 2;
}
offset_y += ent_text[0]->box.h;
// now logic
for (i = ENT_TEXT_ANIMATION_E; i < ENT_TEXT_LOGIC_E; i++) {
ent_text[i] = newTextt(&g_medium_glyphs, ui_colors, ent_text_name[i]);
ent_text[i]->box.x = offset_x;
ent_text[i]->box.y = offset_y;
ent_input[i] = newTextInput(&g_medium_glyphs, button_colors, ent_window_r->w - ent_text[i]->box.w-4);
ent_input[i]->box.x = offset_x + ent_text[i]->box.w+2;
ent_input[i]->box.y = offset_y;
offset_y += ent_text[i]->box.h + 2;
}
offset_y += ent_text[0]->box.h;
// now movement
for (i = ENT_TEXT_LOGIC_E; i < ENT_TEXT_MOVEMENT_E; i++) {
ent_text[i] = newTextt(&g_medium_glyphs, ui_colors, ent_text_name[i]);
ent_text[i]->box.x = offset_x;
ent_text[i]->box.y = offset_y;
ent_input[i] = newTextInput(&g_medium_glyphs, button_colors, ent_window_r->w - ent_text[i]->box.w-4);
ent_input[i]->box.x = offset_x + ent_text[i]->box.w+2;
ent_input[i]->box.y = offset_y;
offset_y += ent_text[i]->box.h + 2;
}
offset_y += ent_text[0]->box.h;
// hp etc.
for (i = ENT_TEXT_MOVEMENT_E; i < ENT_TEXT_ETC_E; i++) {
ent_text[i] = newTextt(&g_medium_glyphs, ui_colors, ent_text_name[i]);
ent_text[i]->box.x = offset_x;
ent_text[i]->box.y = offset_y;
ent_input[i] = newTextInput(&g_medium_glyphs, button_colors, ent_window_r->w - ent_text[i]->box.w-4);
ent_input[i]->box.x = offset_x + ent_text[i]->box.w+2;
ent_input[i]->box.y = offset_y;
offset_y += ent_text[i]->box.h + 2;
}
offset_y += ent_text[0]->box.h;
// combat
for (i = ENT_TEXT_ETC_E; i < ENT_TEXT_COMBAT_E; i++) {
ent_text[i] = newTextt(&g_medium_glyphs, ui_colors, ent_text_name[i]);
ent_text[i]->box.x = offset_x;
ent_text[i]->box.y = offset_y;
ent_input[i] = newTextInput(&g_medium_glyphs, button_colors, ent_window_r->w - ent_text[i]->box.w-4);
ent_input[i]->box.x = offset_x + ent_text[i]->box.w+2;
ent_input[i]->box.y = offset_y;
offset_y += ent_text[i]->box.h + 2;
}
offset_y += ent_text[0]->box.h;
// time-related
for (i = ENT_TEXT_COMBAT_E; i < ENT_TEXT_COUNT; i++) {
ent_text[i] = newTextt(&g_medium_glyphs, ui_colors, ent_text_name[i]);
ent_text[i]->box.x = offset_x;
ent_text[i]->box.y = offset_y;
ent_input[i] = newTextInput(&g_medium_glyphs, button_colors, ent_window_r->w - ent_text[i]->box.w-4);
ent_input[i]->box.x = offset_x + ent_text[i]->box.w+2;
ent_input[i]->box.y = offset_y;
offset_y += ent_text[i]->box.h + 2;
}
offset_y += ent_text[0]->box.h;
ent_input_a = NULL;
// button
offset_y += ent_text[0]->box.h + 8;
for (i = 0; i < ENT_BUTTON_COUNT; i++) {
ent_button[i] = newButton(&g_medium_glyphs, button_colors, ent_button_name[i]);
ent_button[i]->box.x = offset_x;
ent_button[i]->box.y = offset_y - ent_button[i]->box.h;
offset_x += ent_button[i]->box.w + 8;
}
ent_button_a = NULL;
return 0;
}
int closeEntEditState() {
int i;
// window and sub-windows
freeBox(ent_window);
freeBox(ent_window_l);
freeBox(ent_window_r);
// list
freeList(ent_list);
// text & input
for (i = 0; i < ENT_TEXT_COUNT; i++) {
freeTextt(ent_text[i]);
freeTextInput(ent_input[i]);
}
// buttons
for (i = 0; i < ENT_BUTTON_COUNT; i++) {
freeButton(ent_button[i]);
}
report(DEBUG, "EntEditState", "closed");
return 0;
}
int processEntEditState() {
return 1;
}
int renderEntEditState() {
int i;
// window and sub-windows
renderSQuad(ent_window->x, ent_window->y, ent_window->w, ent_window->h, ui_colors->a_bg);
renderSQuad(ent_window_l->x, ent_window_l->y, ent_window_l->w, ent_window_l->h, ui_colors->bg);
renderSQuad(ent_window_r->x, ent_window_r->y, ent_window_r->w, ent_window_r->h, ui_colors->bg);
// list
renderList(ent_list);
// text & input
for (i = 0; i < ENT_TEXT_COUNT; i++) {
renderTextt(ent_text[i]);
renderTextInput(ent_input[i]);
}
for (i = 0; i < ENT_BUTTON_COUNT; i++) {
renderButton(ent_button[i]);
}
return 1;
}
int handleEntEditState(SDL_Event event) {
int i;
switch(event.type) {
case SDL_KEYDOWN:
if (event.key.keysym.sym == SDLK_ESCAPE) {
popState(g_state_manager);
}
if (ent_input_a != NULL) {
if (event.key.keysym.sym == SDLK_LEFT) {
if (ent_input_a->cursor > 0) {
ent_input_a->cursor--;
}
} else if (event.key.keysym.sym == SDLK_RIGHT) {
if (ent_input_a->cursor < strlen(ent_input_a->text)) {
ent_input_a->cursor++;
}
} else if (event.key.keysym.sym == SDLK_BACKSPACE) {
if (ent_input_a->cursor != 0) {
deleteTextInput(ent_input_a, ent_input_a->cursor-1, 1);
ent_input_a->cursor--;
}
}
}
break;
case SDL_TEXTINPUT:
if (ent_input_a != NULL) {
insertTextInput(ent_input_a, event.text.text);
}
break;
case SDL_MOUSEBUTTONDOWN:
if (ent_input_a != NULL) {
ent_input_a->flags &= ~UI_ACTIVE;
ent_input_a = NULL;
SDL_StopTextInput();
}
// check input
for (i = 0; i < ENT_TEXT_COUNT; i++) {
if (inBox(ent_input[i]->box, event.motion.x, event.motion.y)) {
ent_input_a = ent_input[i];
ent_input_a->flags |= UI_ACTIVE;
SDL_Rect rect = { ent_input_a->box.x, ent_input_a->box.y, ent_input_a->box.w, ent_input_a->box.h };
SDL_SetTextInputRect(&rect);
SDL_StartTextInput();
}
}
// check buttons
for (i = 0; i < ENT_BUTTON_COUNT; i++) {
if (inBox(ent_button[i]->box, event.motion.x, event.motion.y)) {
ent_button_a = ent_button[i];
ent_button_a->flags |= UI_ACTIVE;
}
}
// check list
if (inBox(ent_list->box, event.motion.x, event.motion.y)) {
for (i = 0; i < ent_list->count; i++) {
if (inBox(getListItemBoxAbs(ent_list, i), event.motion.x, event.motion.y)) {
if (ent_item != NULL) {
if (ent_item != ent_list->items[i]) {
ent_item->flags &= ~UI_ACTIVE;
} else {
break;
}
}
ent_item = ent_list->items[i];
ent_item->flags |= UI_ACTIVE;
openEntItem();
break;
}
}
}
break;
case SDL_MOUSEBUTTONUP:
if (ent_button_a != NULL) {
if (inBox(ent_button_a->box, event.motion.x, event.motion.y)) {
if (ent_button_a == ent_button[ENT_BUTTON_SAVE]) {
saveEntItem();
} else if (ent_button_a == ent_button[ENT_BUTTON_DELETE]) {
deleteEntItem();
}
buildEntList();
}
ent_button_a->flags &= ~UI_ACTIVE;
ent_button_a = NULL;
}
break;
}
return 1;
}
// ================================================================
void buildEntList() {
freeListItems(ent_list);
int i = 0;
struct Dir *dir = openDir(ENT_DIR, 0);
struct DirEntry *entry;
while ((entry = readDir(dir)) != NULL) {
if (!hasExtension(entry->d_name, ENT_EXT)) continue;
struct Ui_Colors *colors = (++i % 2 == 1 ? ui_colors : button_colors);
addListItem(ent_list, newButton(&g_small_glyphs, colors, entry->d_name));
}
closeDir(dir);
}
void openEntItem() {
char *filename = NULL;
filename = setStringF(filename, "%s%s", ENT_DIR, ent_item->text);
//printf("filename is %s(%d)!\n", filename, strlen(filename));
struct EntityData *entity_data = newEntityData();
loadEntityData(entity_data, filename);
// filename & anim
setTextInputText(ent_input[ENT_TEXT_FILENAME], "%s", ent_item->text);
setTextInputText(ent_input[ENT_TEXT_NAME], "%s", entity_data->name);
setTextInputText(ent_input[ENT_TEXT_ANIM], "%s", entity_data->anim);
setTextInputText(ent_input[ENT_TEXT_SET], "%s", entity_data->set);
setTextInputText(ent_input[ENT_TEXT_FACE], "%s", entity_data->face);
setTextInputText(ent_input[ENT_TEXT_FRAME], "%d", entity_data->frame);
// logic
setTextInputText(ent_input[ENT_TEXT_TYPE], "%d", entity_data->type);
setTextInputText(ent_input[ENT_TEXT_BEHAVE], "%d", entity_data->behave);
// movement
setTextInputText(ent_input[ENT_TEXT_MASS], "%f", entity_data->mass);
setTextInputText(ent_input[ENT_TEXT_RADIUS], "%f", entity_data->radius);
setTextInputText(ent_input[ENT_TEXT_SPEED], "%f", entity_data->speed);
setTextInputText(ent_input[ENT_TEXT_TURN], "%f", entity_data->turn);
// hp etc
setTextInputText(ent_input[ENT_TEXT_HP], "%d", entity_data->hp);
setTextInputText(ent_input[ENT_TEXT_SIGHT], "%f", entity_data->sight);
// combat
setTextInputText(ent_input[ENT_TEXT_RANGE], "%f", entity_data->range);
setTextInputText(ent_input[ENT_TEXT_ATKTYPE], "%d", entity_data->attack);
setTextInputText(ent_input[ENT_TEXT_DAMAGE], "%d", entity_data->damage);
setTextInputText(ent_input[ENT_TEXT_SPAWN], "%s", entity_data->spawn);
// time
setTextInputText(ent_input[ENT_TEXT_TIME], "%d", entity_data->time);
freeEntityData(entity_data);
free(filename);
}
void saveEntItem() {
struct EntityData *entity_data = newEntityData();
char *filename = malloc(1);
// filename & animation
filename = setStringF(filename, "%s%s", ENT_DIR, ent_input[ENT_TEXT_FILENAME]->text);
entity_data->filename = copyString(entity_data->filename, filename);
entity_data->name = copyString(entity_data->name, ent_input[ENT_TEXT_NAME]->text);
entity_data->anim = copyString(entity_data->anim, ent_input[ENT_TEXT_ANIM]->text);
entity_data->set = copyString(entity_data->set, ent_input[ENT_TEXT_SET]->text);
entity_data->face = copyString(entity_data->face, ent_input[ENT_TEXT_FACE]->text);
entity_data->frame = atoi(ent_input[ENT_TEXT_FRAME]->text);
// logic
entity_data->type = atoi(ent_input[ENT_TEXT_TYPE]->text);
entity_data->behave = atoi(ent_input[ENT_TEXT_BEHAVE]->text);
// movement & size
entity_data->mass = atof(ent_input[ENT_TEXT_MASS]->text);
entity_data->radius = atof(ent_input[ENT_TEXT_RADIUS]->text);
entity_data->speed = atof(ent_input[ENT_TEXT_SPEED]->text);
entity_data->turn = atof(ent_input[ENT_TEXT_TURN]->text);
// hp, etc.
entity_data->hp = atoi(ent_input[ENT_TEXT_HP]->text);
entity_data->sight = atof(ent_input[ENT_TEXT_SIGHT]->text);
// combat
entity_data->range = atof(ent_input[ENT_TEXT_RANGE]->text);
entity_data->attack = atoi(ent_input[ENT_TEXT_ATKTYPE]->text);
entity_data->damage = atoi(ent_input[ENT_TEXT_DAMAGE]->text);
entity_data->spawn = copyString(entity_data->spawn, ent_input[ENT_TEXT_SPAWN]->text);
// time
entity_data->time = atoi(ent_input[ENT_TEXT_TIME]->text);
//
saveEntityData(entity_data);
freeEntityData(entity_data);
free(filename);
}
void deleteEntItem() {
if (ent_item != NULL) {
char *filename = malloc(1);
filename[0] = '\0';
filename = catStringF(filename, "%s%s", ENT_DIR, ent_input[ENT_TEXT_FILENAME]->text);
deleteFile(filename);
free(filename);
}
}