diff options
| author | KonAki <konaki@anokonaki.org> | 2026-10-16 15:38:03 +0800 |
|---|---|---|
| committer | KonAki <konaki@anokonaki.org> | 2026-10-16 15:38:03 +0800 |
| commit | 84ce07075a8fbebef8d3472bf608b11ce6b2265b (patch) | |
| tree | 4f96b895a3d7b7416d06afc182c000f00dc4bf57 | |
| parent | eb07fabdea8f3ebec3c1774e9a1aef09f6152bf1 (diff) | |
mzdata: classes, actors, items, weapons and armor
| -rw-r--r-- | tools/mzdata.c | 208 |
1 files changed, 185 insertions, 23 deletions
diff --git a/tools/mzdata.c b/tools/mzdata.c index 637b06d..2bf4e52 100644 --- a/tools/mzdata.c +++ b/tools/mzdata.c @@ -47,7 +47,9 @@ #define STRING_PIECE 100 static int warnings, droppedStatements, badFormulas, droppedEffects, otherEffects; -static int stateCount, skillCount, itemCount, enemyCount, troopCount; +static int stateCount, skillCount, itemCount, enemyCount, troopCount, classCount, actorCount, gearCount, droppedLearnings, droppedGear; + +#define CLASS_LEVELS 100 /*** output ***/ @@ -191,7 +193,7 @@ static void writeStates(FILE *f, const char *name, const kon_json_t *list) memset(idSeen, 0, sizeof idSeen); - fprintf(f, "const kon_state_t %s_states[%d] = {\n", name, high + 1); + fprintf(f, "const kon_state_t %s_states[%d] = {\n\t[0] = {0},\n", name, high + 1); for (i = 1; i < kon_jsonCount(list); i++) { const kon_json_t *s = kon_jsonAt(list, i); const kon_json_t *traits; @@ -248,7 +250,7 @@ static void formulaOf(const char *in, char *out, size_t size) snprintf(out, size, "%s", *start ? start : "0"); } -static void writeSkill(FILE *f, const kon_json_t *s, int id, const char *kind) +static void writeSkill(FILE *f, const kon_json_t *s, int id, const char *kind, int offset) { const kon_json_t *damage = kon_jsonGet(s, "damage"), *effects = kon_jsonGet(s, "effects"); char formula[512], extra[160]; @@ -305,7 +307,7 @@ static void writeSkill(FILE *f, const kon_json_t *s, int id, const char *kind) warn(kind, id, nm, extra); } - fprintf(f, "\t[%d] = {.name = ", id); + fprintf(f, "\t[%d] = {.name = ", id + offset); cstring(f, nm); fprintf(f, ", .mpCost = %d, .tpCost = %d, .tpGain = %d, .scope = %s, .randomCount = %d, .speed = %d, .successRate = %d, .repeats = %d, .hitType = %s, .damageType = %s, .element = %d, .formulaText = ", number(kon_jsonGet(s, "mpCost"), 0, 100000, 0), number(kon_jsonGet(s, "tpCost"), 0, 100000, 0), number(kon_jsonGet(s, "tpGain"), 0, 100000, 0), scopeNames[rscope], random, @@ -326,13 +328,12 @@ static void writeSkill(FILE *f, const kon_json_t *s, int id, const char *kind) fputs("},\n", f); } -static int writeSkills(FILE *f, const char *name, const char *table, const kon_json_t *list, const char *kind) +/* the entries of the table of skills. the items follow the skills in the same table, so the game has one place to look */ +static int writeSkills(FILE *f, const kon_json_t *list, const char *kind, int offset) { - int i, high = highestId(list), n = 0; + int i, n = 0; memset(idSeen, 0, sizeof idSeen); - - fprintf(f, "kon_skill_t %s_%s[%d] = {\n", name, table, high + 1); for (i = 1; i < kon_jsonCount(list); i++) { const kon_json_t *s = kon_jsonAt(list, i); int id; @@ -340,10 +341,9 @@ static int writeSkills(FILE *f, const char *name, const char *table, const kon_j if (!s || s->type != KON_JSON_OBJECT) continue; id = tableId(s, i); if (id < 1) continue; - writeSkill(f, s, id, kind); + writeSkill(f, s, id, kind, offset); n++; } - fputs("};\n\n", f); return n; } @@ -392,7 +392,7 @@ static void writeEnemies(FILE *f, const char *name, const kon_json_t *list) } memset(idSeen, 0, sizeof idSeen); - fprintf(f, "const kon_rmEnemy_t %s_enemies[%d] = {\n", name, high + 1); + fprintf(f, "const kon_rmEnemy_t %s_enemies[%d] = {\n\t[0] = {0},\n", name, high + 1); for (i = 1; i < kon_jsonCount(list); i++) { const kon_json_t *e = kon_jsonAt(list, i); const kon_json_t *traits, *params; @@ -487,7 +487,7 @@ static void writeTroops(FILE *f, const char *name, const kon_json_t *list) } memset(idSeen, 0, sizeof idSeen); - fprintf(f, "const kon_rmTroop_t %s_troops[%d] = {\n", name, high + 1); + fprintf(f, "const kon_rmTroop_t %s_troops[%d] = {\n\t[0] = {0},\n", name, high + 1); for (i = 1; i < kon_jsonCount(list); i++) { const kon_json_t *t = kon_jsonAt(list, i); int id, nm, np; @@ -508,14 +508,141 @@ static void writeTroops(FILE *f, const char *name, const kon_json_t *list) fputs("};\n\n", f); } +/*** classes, items and actors ***/ + +static int classTraits; + +static void writeClasses(FILE *f, const char *name, const kon_json_t *list) +{ + int i, k, p, high = highestId(list); + + memset(idSeen, 0, sizeof idSeen); + for (i = 1; i < kon_jsonCount(list); i++) { + const kon_json_t *c = kon_jsonAt(list, i); + const kon_json_t *params = kon_jsonGet(c, "params"); + int id; + + if (!c || c->type != KON_JSON_OBJECT) continue; + id = tableId(c, i); + if (id < 1) continue; + for (p = 0; p < KON_PARAMS; p++) { + const kon_json_t *row = kon_jsonAt(params, p); + + fprintf(f, "static const short %s_class%d_p%d[%d] = {", name, id, p, CLASS_LEVELS); + for (k = 0; k < CLASS_LEVELS; k++) fprintf(f, "%s%d", k ? ", " : "", number(kon_jsonAt(row, k), 0, 32767, 0)); + fputs("};\n", f); + } + fputs("\n", f); + classTraits += kon_jsonCount(kon_jsonGet(c, "traits")); + } + + fprintf(f, "const kon_class_t %s_classes[%d] = {\n\t[0] = {0},\n", name, high + 1); + memset(idSeen, 0, sizeof idSeen); + for (i = 1; i < kon_jsonCount(list); i++) { + const kon_json_t *c = kon_jsonAt(list, i); + const kon_json_t *exp = kon_jsonGet(c, "expParams"), *learn = kon_jsonGet(c, "learnings"); + int id, n; + + if (!c || c->type != KON_JSON_OBJECT) continue; + id = tableId(c, i); + if (id < 1) continue; + fprintf(f, "\t[%d] = {", id); + cstring(f, text(kon_jsonGet(c, "name"))); + fprintf(f, ", %d, {", CLASS_LEVELS - 1); + for (p = 0; p < KON_PARAMS; p++) fprintf(f, "%s%s_class%d_p%d", p ? ", " : "", name, id, p); + fprintf(f, "}, %d, %d, %d, %d, {", number(kon_jsonAt(exp, 0), 0, 100000, 30), number(kon_jsonAt(exp, 1), 0, 100000, 20), number(kon_jsonAt(exp, 2), 0, 100000, 30), number(kon_jsonAt(exp, 3), 0, 100000, 30)); + n = 0; + for (k = 0; k < kon_jsonCount(learn); k++) { + const kon_json_t *l = kon_jsonAt(learn, k); + + if (n >= KON_CLASS_LEARNINGS) { + droppedLearnings++; + continue; + } + fprintf(f, "%s{%d, %d}", n ? ", " : "", number(kon_jsonGet(l, "level"), 1, 99, 1), number(kon_jsonGet(l, "skillId"), 0, MAX_ID, 0)); + n++; + } + if (n == 0) fputs("{0, 0}", f); + fprintf(f, "}, %d},\n", n); + classCount++; + } + fputs("};\n\n", f); +} + +/* items, weapons and armor in one table: the items by their id, the weapons after them, then the armor */ +static int writeGear(FILE *f, const kon_json_t *list, int kind, int base, int skillBase) +{ + int i, k, n = 0; + + memset(idSeen, 0, sizeof idSeen); + for (i = 1; i < kon_jsonCount(list); i++) { + const kon_json_t *it = kon_jsonAt(list, i); + const kon_json_t *params = kon_jsonGet(it, "params"); + int id, slot = 0, usable = 0; + + if (!it || it->type != KON_JSON_OBJECT) continue; + id = tableId(it, i); + if (id < 1) continue; + if (kind == 0) { + usable = number(kon_jsonGet(it, "scope"), 0, 100, 0) != 0 || kon_jsonCount(kon_jsonGet(it, "effects")) > 0; + } else { + slot = number(kon_jsonGet(it, "etypeId"), 1, 100, 1) - 1; + if (slot >= KON_EQUIP_SLOTS) { + droppedGear++; + continue; + } + } + fprintf(f, "\t[%d] = {", base + id); + cstring(f, text(kon_jsonGet(it, "name"))); + fprintf(f, ", %s, %d, %d, %d, %d, {", kind == 0 ? (kon_jsonInt(kon_jsonGet(it, "itypeId"), 1) == 2 ? "KON_ITEM_KEY" : "KON_ITEM_ITEM") : kind == 1 ? "KON_ITEM_WEAPON" : "KON_ITEM_ARMOR", + number(kon_jsonGet(it, "price"), 0, 99999999, 0), kind == 0 && kon_jsonBool(kon_jsonGet(it, "consumable"), 0) ? 1 : 0, kind == 0 ? within(kon_jsonGet(it, "occasion"), 0, 3, 0) : 3, slot); + for (k = 0; k < KON_PARAMS; k++) fprintf(f, "%s%d", k ? ", " : "", kind == 0 ? 0 : number(kon_jsonAt(params, k), -99999, 99999, 0)); + fprintf(f, "}, %d},\n", usable ? skillBase + id : -1); + n++; + } + return n; +} + +static void writeActors(FILE *f, const char *name, const kon_json_t *list) +{ + int i, k, high = highestId(list); + + fprintf(f, "const kon_rmActor_t %s_actors[%d] = {\n\t[0] = {0},\n", name, high + 1); + memset(idSeen, 0, sizeof idSeen); + for (i = 1; i < kon_jsonCount(list); i++) { + const kon_json_t *a = kon_jsonAt(list, i); + const kon_json_t *equips = kon_jsonGet(a, "equips"); + int id; + + if (!a || a->type != KON_JSON_OBJECT) continue; + id = tableId(a, i); + if (id < 1) continue; + fprintf(f, "\t[%d] = {", id); + cstring(f, text(kon_jsonGet(a, "name"))); + fputs(", ", f); + cstring(f, text(kon_jsonGet(a, "nickname"))); + fputs(", ", f); + cstring(f, text(kon_jsonGet(a, "characterName"))); + fputs(", ", f); + cstring(f, text(kon_jsonGet(a, "faceName"))); + fputs(", ", f); + cstring(f, text(kon_jsonGet(a, "battlerName"))); + fprintf(f, ", %d, %d, %d, %d, %d, {", number(kon_jsonGet(a, "characterIndex"), 0, 7, 0), number(kon_jsonGet(a, "faceIndex"), 0, 7, 0), number(kon_jsonGet(a, "classId"), 0, MAX_ID, 0), number(kon_jsonGet(a, "initialLevel"), 1, 99, 1), number(kon_jsonGet(a, "maxLevel"), 1, 99, 99)); + for (k = 0; k < KON_EQUIP_SLOTS; k++) fprintf(f, "%s%d", k ? ", " : "", number(kon_jsonAt(equips, k), 0, MAX_ID, 0)); + fputs("}},\n", f); + actorCount++; + } + fputs("};\n\n", f); +} + /*** main ***/ int main(int argc, char **argv) { char name[64] = "game", path[1100], upper[64], dataPath[1100]; const char *folder = NULL, *outFolder = NULL; - kon_json_t *states, *skills, *items, *enemies, *troops; - int a, i, hs = 0, hk = 0, hi = 0, he = 0, ht = 0; + kon_json_t *states, *skills, *items, *weapons, *armors, *enemies, *troops, *classes, *actors; + int a, i, hs, hk, hi, hw, ha, he, ht, hc, hr, skillTotal, gearTotal; FILE *f; for (a = 1; a < argc; a++) { @@ -537,17 +664,27 @@ int main(int argc, char **argv) states = load(folder, "States.json"); skills = load(folder, "Skills.json"); items = load(folder, "Items.json"); + weapons = load(folder, "Weapons.json"); + armors = load(folder, "Armors.json"); enemies = load(folder, "Enemies.json"); troops = load(folder, "Troops.json"); - if (!states && !skills && !items && !enemies && !troops) { + classes = load(folder, "Classes.json"); + actors = load(folder, "Actors.json"); + if (!states && !skills && !items && !enemies && !troops && !classes && !actors) { fprintf(stderr, "none of the database files were found in %s\n", folder); return 1; } hs = highestId(states); hk = highestId(skills); hi = highestId(items); + hw = highestId(weapons); + ha = highestId(armors); he = highestId(enemies); ht = highestId(troops); + hc = highestId(classes); + hr = highestId(actors); + skillTotal = hk + hi + 1; /* the skills by their id, then the items, hk + their id */ + gearTotal = hi + hw + ha + 1; /* the items, then the weapons, then the armor */ for (i = 0; name[i] && i < 63; i++) upper[i] = (char)toupper((unsigned char)name[i]); upper[i] = '\0'; @@ -559,8 +696,11 @@ int main(int argc, char **argv) return 1; } fprintf(f, "/* written by mzdata, the database of the game */\n\n#ifndef %s_DATA_H\n#define %s_DATA_H\n\n#include \"konrmdata.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n", upper, upper); - fprintf(f, "#define %s_STATE_IDS %d\n#define %s_SKILL_IDS %d\n#define %s_ITEM_IDS %d\n#define %s_ENEMY_IDS %d\n#define %s_TROOP_IDS %d\n\n", upper, hs + 1, upper, hk + 1, upper, hi + 1, upper, he + 1, upper, ht + 1); - fprintf(f, "extern const kon_state_t %s_states[%d];\nextern kon_skill_t %s_skills[%d];\nextern kon_skill_t %s_items[%d];\nextern const kon_rmEnemy_t %s_enemies[%d];\nextern const kon_rmTroop_t %s_troops[%d];\n\n", name, hs + 1, name, hk + 1, name, hi + 1, name, he + 1, name, ht + 1); + fprintf(f, "#define %s_STATE_IDS %d\n#define %s_SKILL_IDS %d /* the skills, then the items as skills */\n#define %s_ITEM_SKILL_BASE %d /* an item's skill is its id and this */\n", upper, hs + 1, upper, skillTotal, upper, hk); + fprintf(f, "#define %s_ITEM_IDS %d /* the items, the weapons, then the armor */\n#define %s_WEAPON_BASE %d /* a weapon's number is its id and this */\n#define %s_ARMOR_BASE %d\n", upper, gearTotal, upper, hi, upper, hi + hw); + fprintf(f, "#define %s_CLASS_IDS %d\n#define %s_ACTOR_IDS %d\n#define %s_ENEMY_IDS %d\n#define %s_TROOP_IDS %d\n\n", upper, hc + 1, upper, hr + 1, upper, he + 1, upper, ht + 1); + fprintf(f, "extern const kon_state_t %s_states[%d];\nextern kon_skill_t %s_skills[%d];\nextern const kon_item_t %s_items[%d];\nextern const kon_class_t %s_classes[%d];\nextern const kon_rmActor_t %s_actors[%d];\n", name, hs + 1, name, skillTotal, name, gearTotal, name, hc + 1, name, hr + 1); + fprintf(f, "extern const kon_rmEnemy_t %s_enemies[%d];\nextern const kon_rmTroop_t %s_troops[%d];\n\n/* what the party module wants */\nextern const kon_database_t %s_database;\n\n", name, he + 1, name, ht + 1, name); fprintf(f, "/* compiles the formulas of the skills and items, once before they are used */\nvoid %s_dataInit(void);\n\n#ifdef __cplusplus\n}\n#endif\n#endif\n", name); fclose(f); @@ -573,27 +713,49 @@ int main(int argc, char **argv) fprintf(f, "/* written by mzdata, the database of the game */\n\n#include \"%s_data.h\"\n\n#include <stddef.h>\n\n", name); if (states) writeStates(f, name, states); else fprintf(f, "const kon_state_t %s_states[1];\n\n", name); - if (skills) skillCount = writeSkills(f, name, "skills", skills, "skill"); - else fprintf(f, "kon_skill_t %s_skills[1];\n\n", name); - if (items) itemCount = writeSkills(f, name, "items", items, "item"); - else fprintf(f, "kon_skill_t %s_items[1];\n\n", name); + + fprintf(f, "kon_skill_t %s_skills[%d] = {\n\t[0] = {0},\n", name, skillTotal); + if (skills) skillCount = writeSkills(f, skills, "skill", 0); + if (items) itemCount = writeSkills(f, items, "item", hk); + fputs("};\n\n", f); + if (enemies) writeEnemies(f, name, enemies); else fprintf(f, "const kon_rmEnemy_t %s_enemies[1];\n\n", name); if (troops) writeTroops(f, name, troops); else fprintf(f, "const kon_rmTroop_t %s_troops[1];\n\n", name); - fprintf(f, "void %s_dataInit(void)\n{\n\tint i;\n\n\tfor (i = 0; i < %s_SKILL_IDS; i++) kon_skillCompile(&%s_skills[i]);\n\tfor (i = 0; i < %s_ITEM_IDS; i++) kon_skillCompile(&%s_items[i]);\n}\n", name, upper, name, upper, name); + if (classes) writeClasses(f, name, classes); + else fprintf(f, "const kon_class_t %s_classes[1];\n\n", name); + + fprintf(f, "const kon_item_t %s_items[%d] = {\n\t[0] = {0},\n", name, gearTotal); + if (items) gearCount += writeGear(f, items, 0, 0, hk); + if (weapons) gearCount += writeGear(f, weapons, 1, hi, hk); + if (armors) gearCount += writeGear(f, armors, 2, hi + hw, hk); + fputs("};\n\n", f); + + if (actors) writeActors(f, name, actors); + else fprintf(f, "const kon_rmActor_t %s_actors[1];\n\n", name); + + fprintf(f, "const kon_database_t %s_database = {%s_items, %d, %s_classes, %d, %s_skills, %d, %s_states, %d};\n\n", name, name, gearTotal, name, hc + 1, name, skillTotal, name, hs + 1); + fprintf(f, "void %s_dataInit(void)\n{\n\tint i;\n\n\tfor (i = 0; i < %s_SKILL_IDS; i++) kon_skillCompile(&%s_skills[i]);\n}\n", name, upper, name); fclose(f); - printf("%d states, %d skills, %d items, %d enemies, %d troops\n", stateCount, skillCount, itemCount, enemyCount, troopCount); + printf("%d states, %d skills, %d items, %d enemies, %d troops, %d classes, %d actors, %d items, weapons and armor\n", stateCount, skillCount, itemCount, enemyCount, troopCount, classCount, actorCount, gearCount); if (droppedStatements) printf("%d formulas had something before the damage, which was dropped\n", droppedStatements); if (badFormulas) printf("%d formulas the damage parser cannot read, those skills do nothing\n", badFormulas); if (droppedEffects) printf("%d state effects did not fit (4 for each skill)\n", droppedEffects); if (otherEffects) printf("%d other item and skill effects are not converted (growth, learning, common events and so on)\n", otherEffects); + if (classTraits) printf("%d traits of classes are not converted (hit and evasion, equipment allowed, element and state rates)\n", classTraits); + if (droppedLearnings) printf("%d learned skills did not fit (%d for each class)\n", droppedLearnings, KON_CLASS_LEARNINGS); + if (droppedGear) printf("%d weapons and armor are for an equipment slot there is no room for\n", droppedGear); if (warnings > 25) printf("%d warnings, the first ones were printed\n", warnings); kon_jsonFree(states); kon_jsonFree(skills); kon_jsonFree(items); + kon_jsonFree(weapons); + kon_jsonFree(armors); kon_jsonFree(enemies); kon_jsonFree(troops); + kon_jsonFree(classes); + kon_jsonFree(actors); return 0; } |
