mirror of
https://github.com/aimrebirth/tools.git
synced 2026-04-15 01:43:25 +00:00
[mod] Initial copy_from_aim2().
This commit is contained in:
parent
98d9cd36e1
commit
466aa747f4
2 changed files with 92 additions and 23 deletions
|
|
@ -37,6 +37,9 @@ deps: pub.lzwdgc.Polygon4.Tools.aim1.mod_maker-master
|
||||||
// patch note: You should start new game after applying this mod. This is necessary for map changes
|
// patch note: You should start new game after applying this mod. This is necessary for map changes
|
||||||
// patch note: to became visible.
|
// patch note: to became visible.
|
||||||
// patch note:
|
// patch note:
|
||||||
|
// patch note: Changes from 0.0.4
|
||||||
|
// patch note: fix Finder-2 textures
|
||||||
|
// patch note:
|
||||||
// patch note: Changes from 0.0.3
|
// patch note: Changes from 0.0.3
|
||||||
// patch note: add locale suffix to all quest databases (localized strings). Example: quest_ru_RU.*
|
// patch note: add locale suffix to all quest databases (localized strings). Example: quest_ru_RU.*
|
||||||
// patch note: add en_US localization (quest database, quest_en_US.*)
|
// patch note: add en_US localization (quest database, quest_en_US.*)
|
||||||
|
|
@ -104,13 +107,7 @@ int main(int argc, char *argv[]) {
|
||||||
#endif
|
#endif
|
||||||
));
|
));
|
||||||
// patch note: add Finder-2 model and textures from aim2 game (lz)
|
// patch note: add Finder-2 model and textures from aim2 game (lz)
|
||||||
// TODO: auto take models from aim2
|
mod.copy_from_aim2("MOD_GL_S3_PS_FINDER2");
|
||||||
// TODO: auto fix models with mod_converter2
|
|
||||||
mod.add_resource("MOD_GL_S3_PS_FINDER2");
|
|
||||||
// TODO: copy data from aim2 db
|
|
||||||
mod.add_resource("TEX_GL_S3_PS_FINDER_2.TM");
|
|
||||||
mod.add_resource("TEX_GL_S3_PS_FINDER_2_SPEC.TM");
|
|
||||||
mod.add_resource("TEX_GL_S3_PS_FINDER_2_SPEC_1.TM");
|
|
||||||
// patch note: set correct model for a plant (Streef)
|
// patch note: set correct model for a plant (Streef)
|
||||||
mod.patch<uint8_t>("location6.mmo", 0x0005775D, 'R', 'F');
|
mod.patch<uint8_t>("location6.mmo", 0x0005775D, 'R', 'F');
|
||||||
// patch note: fix 'TOV_POLYMER_PLATE' spawn (Streef)
|
// patch note: fix 'TOV_POLYMER_PLATE' spawn (Streef)
|
||||||
|
|
@ -139,14 +136,10 @@ int main(int argc, char *argv[]) {
|
||||||
// patch note: DB
|
// patch note: DB
|
||||||
auto db = mod.db();
|
auto db = mod.db();
|
||||||
// patch note: set glider GL_S3_PS_FINDER2 model to MOD_GL_S3_PS_FINDER2 (lz)
|
// patch note: set glider GL_S3_PS_FINDER2 model to MOD_GL_S3_PS_FINDER2 (lz)
|
||||||
db[u8"Ãëàéäåðû"]["GL_S3_PS_FINDER2"]["MODEL"] = "MOD_GL_S3_PS_FINDER2";
|
|
||||||
// patch note - maybe copy from finder1?: change MOD_GL_S3_PS_FINDER2 model radius to MOD_GL_S3_PS_FINDER1 radius (lz)
|
// patch note - maybe copy from finder1?: change MOD_GL_S3_PS_FINDER2 model radius to MOD_GL_S3_PS_FINDER1 radius (lz)
|
||||||
// patch note: copy MOD_GL_S3_PS_FINDER2 model radius from aim2 (lz)
|
db[u8"Ãëàéäåðû"]["GL_S3_PS_FINDER2"]["MODEL"] = "MOD_GL_S3_PS_FINDER2";
|
||||||
db.copy_from_aim2(u8"Ìîäåëè", "MOD_GL_S3_PS_FINDER2", "RADIUS");
|
// patch note: copy MOD_GL_S3_PS_FINDER2 model from aim2 (lz)
|
||||||
// patch note: copy MOD_GL_S3_PS_FINDER2 textures from aim2 (lz)
|
// patch note: copy MOD_GL_S3_PS_FINDER2 textures data from aim2 (lz)
|
||||||
db.copy_from_aim2(u8"Òåêñòóðû", "TEX_GL_S3_PS_FINDER_2");
|
|
||||||
db.copy_from_aim2(u8"Òåêñòóðû", "TEX_GL_S3_PS_FINDER_2_SPEC");
|
|
||||||
db.copy_from_aim2(u8"Òåêñòóðû", "TEX_GL_S3_PS_FINDER_2_SPEC_1");
|
|
||||||
// patch note: double gun for config CFG_NARGOON (double electro discharge) (lz)
|
// patch note: double gun for config CFG_NARGOON (double electro discharge) (lz)
|
||||||
auto &tblcfg = db[u8"Êîíôèãóðàöèè"];
|
auto &tblcfg = db[u8"Êîíôèãóðàöèè"];
|
||||||
tblcfg["CFG_NARGOON"]["HEAVYGUN1"] = "GUN_ELECTRO_DISCHARGER";
|
tblcfg["CFG_NARGOON"]["HEAVYGUN1"] = "GUN_ELECTRO_DISCHARGER";
|
||||||
|
|
|
||||||
|
|
@ -74,7 +74,7 @@ struct aim_exe_v1_06_constants {
|
||||||
struct mod_maker {
|
struct mod_maker {
|
||||||
struct db_wrapper {
|
struct db_wrapper {
|
||||||
db2::files::db2_internal m;
|
db2::files::db2_internal m;
|
||||||
db2::files::db2_internal m2;
|
db2::files::db2_internal *m2_{};
|
||||||
path fn;
|
path fn;
|
||||||
int codepage{1251};
|
int codepage{1251};
|
||||||
bool written{};
|
bool written{};
|
||||||
|
|
@ -94,16 +94,19 @@ struct mod_maker {
|
||||||
auto &operator[](this auto &&d, const std::u8string &s) {
|
auto &operator[](this auto &&d, const std::u8string &s) {
|
||||||
return d.m[(const char *)s.c_str()];
|
return d.m[(const char *)s.c_str()];
|
||||||
}
|
}
|
||||||
|
auto &m2() {
|
||||||
|
return *m2_;
|
||||||
|
}
|
||||||
void copy_from_aim2(auto &&table_name, auto &&value_name, auto &&field_name) {
|
void copy_from_aim2(auto &&table_name, auto &&value_name, auto &&field_name) {
|
||||||
auto check_val = [](auto &&m, const std::string &key, auto &&err) {
|
auto check_val = [](auto &&m, const std::string &key, auto &&err) {
|
||||||
if (auto it = m.find(key); it == m.end()) {
|
if (auto it = m.find(key); it == m.end()) {
|
||||||
throw std::runtime_error{err};
|
throw std::runtime_error{err};
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
check_val(m2.m, (const char *)table_name, "aim2: no such table");
|
check_val(m2().m, (const char *)table_name, "aim2: no such table");
|
||||||
check_val(m2[table_name], value_name, "aim2: no such value");
|
check_val(m2()[table_name], value_name, "aim2: no such value");
|
||||||
check_val(m2[table_name][value_name], field_name, "aim2: no such field");
|
check_val(m2()[table_name][value_name], field_name, "aim2: no such field");
|
||||||
m[table_name][value_name][field_name] = m2[table_name][value_name][field_name];
|
m[table_name][value_name][field_name] = m2()[table_name][value_name][field_name];
|
||||||
}
|
}
|
||||||
void copy_from_aim2(auto &&table_name, auto &&value_name) {
|
void copy_from_aim2(auto &&table_name, auto &&value_name) {
|
||||||
auto check_val = [](auto &&m, const std::string &key, auto &&err) {
|
auto check_val = [](auto &&m, const std::string &key, auto &&err) {
|
||||||
|
|
@ -111,9 +114,9 @@ struct mod_maker {
|
||||||
throw std::runtime_error{err};
|
throw std::runtime_error{err};
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
check_val(m2.m, (const char *)table_name, "aim2: no such table");
|
check_val(m2().m, (const char *)table_name, "aim2: no such table");
|
||||||
check_val(m2[table_name], value_name, "aim2: no such value");
|
check_val(m2()[table_name], value_name, "aim2: no such value");
|
||||||
m[table_name][value_name] = m2[table_name][value_name];
|
m[table_name][value_name] = m2()[table_name][value_name];
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
enum class file_type {
|
enum class file_type {
|
||||||
|
|
@ -363,7 +366,7 @@ struct mod_maker {
|
||||||
auto db() {
|
auto db() {
|
||||||
auto w = open_db("db", 1251); // always 1251 probably
|
auto w = open_db("db", 1251); // always 1251 probably
|
||||||
if (aim2_available()) {
|
if (aim2_available()) {
|
||||||
w.m2 = db2{aim2_game_dir / "data" / "db", 1251}.open().to_map();
|
w.m2_ = &open_aim2_db();
|
||||||
}
|
}
|
||||||
return w;
|
return w;
|
||||||
}
|
}
|
||||||
|
|
@ -398,7 +401,78 @@ struct mod_maker {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void copy_from_aim2(auto &&object) {
|
||||||
|
log("copying from aim2: {}", path{object}.filename().string());
|
||||||
|
|
||||||
|
auto ft = detect_file_type(object);
|
||||||
|
switch (ft) {
|
||||||
|
case file_type::model: {
|
||||||
|
auto p = aim2_game_dir / "data" / "aimmod.pak";
|
||||||
|
unpak(p);
|
||||||
|
p = make_unpak_dir(p);
|
||||||
|
if (fs::exists(p / object)) {
|
||||||
|
p /= object;
|
||||||
|
} else {
|
||||||
|
p /= "data";
|
||||||
|
p /= "models";
|
||||||
|
p /= object;
|
||||||
|
if (!fs::exists(p)) {
|
||||||
|
throw std::runtime_error{std::format("aim2: model is not found: {}", p.string())};
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// TODO: this - fix add_resource()/find_real_filename()
|
||||||
|
//auto copied_fn = get_mod_dir() / object;
|
||||||
|
auto copied_fn = get_data_dir() / object;
|
||||||
|
fs::copy_file(p, copied_fn, fs::copy_options::overwrite_existing);
|
||||||
|
run_p4_tool("mod_converter2", copied_fn);
|
||||||
|
add_resource(object);
|
||||||
|
db().copy_from_aim2(u8"Ìîäåëè", path{object}.stem().string());
|
||||||
|
auto textures = read_lines(path{copied_fn} += ".textures.txt");
|
||||||
|
auto &m2 = open_aim2_db();
|
||||||
|
for (auto &&t : textures) {
|
||||||
|
path fn = std::get<std::string>(m2[u8"Òåêñòóðû"][t]["FILENAME"]);
|
||||||
|
if (fn.empty()) {
|
||||||
|
throw std::runtime_error{"Can't find texture: "s + t};
|
||||||
|
}
|
||||||
|
copy_from_aim2(fn);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
case file_type::tm: {
|
||||||
|
auto p = aim2_game_dir / "data" / "aimtex.pak";
|
||||||
|
unpak(p);
|
||||||
|
p = make_unpak_dir(p);
|
||||||
|
if (fs::exists(p / object)) {
|
||||||
|
p /= object;
|
||||||
|
} else {
|
||||||
|
p /= "data";
|
||||||
|
p /= "tm";
|
||||||
|
p /= object;
|
||||||
|
if (!fs::exists(p)) {
|
||||||
|
throw std::runtime_error{std::format("aim2: model is not found: {}", p.string())};
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// TODO: this - fix add_resource()/find_real_filename()
|
||||||
|
// auto copied_fn = get_mod_dir() / object;
|
||||||
|
auto copied_fn = get_data_dir() / path{object}.filename().string();
|
||||||
|
fs::copy_file(p, copied_fn, fs::copy_options::overwrite_existing);
|
||||||
|
add_resource(path{object}.filename());
|
||||||
|
db().copy_from_aim2(u8"Òåêñòóðû", path{object}.stem().string());
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
default:
|
||||||
|
SW_UNIMPLEMENTED;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
db2::files::db2_internal &open_aim2_db() {
|
||||||
|
if (!aim2_available()) {
|
||||||
|
throw std::runtime_error{"aim2 is not available, setup it first"};
|
||||||
|
}
|
||||||
|
static auto m2 = db2{aim2_game_dir / "data" / "db", 1251}.open().to_map();
|
||||||
|
return m2;
|
||||||
|
}
|
||||||
bool aim2_available() const {
|
bool aim2_available() const {
|
||||||
return !aim2_game_dir.empty();
|
return !aim2_game_dir.empty();
|
||||||
}
|
}
|
||||||
|
|
@ -757,8 +831,10 @@ FF D7 ; call edi
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (fn.empty()) {
|
if (fn.empty()) {
|
||||||
|
log("unpacking {}", p.string());
|
||||||
run_p4_tool("unpaker", p);
|
run_p4_tool("unpaker", p);
|
||||||
} else {
|
} else {
|
||||||
|
log("unpacking {} from {}", fn.string(), p.string());
|
||||||
run_p4_tool("unpaker", p, fn);
|
run_p4_tool("unpaker", p, fn);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue