Expose function for getting the details for currently opened mods

This commit is contained in:
Mr-Wiseguy 2024-09-03 00:03:41 -04:00
parent 3718758cd5
commit 986881e4e1
3 changed files with 42 additions and 0 deletions

View file

@ -148,6 +148,7 @@ namespace recomp {
void scan_mods(); void scan_mods();
void enable_mod(const std::string& mod_id, bool enabled); void enable_mod(const std::string& mod_id, bool enabled);
bool is_mod_enabled(const std::string& mod_id); bool is_mod_enabled(const std::string& mod_id);
std::vector<ModDetails> get_mod_details(const std::string& mod_game_id);
// Internal functions, TODO move to an internal header. // Internal functions, TODO move to an internal header.
struct PatchData { struct PatchData {
@ -170,6 +171,7 @@ namespace recomp {
size_t num_opened_mods(); size_t num_opened_mods();
std::vector<ModLoadErrorDetails> load_mods(const std::string& mod_game_id, uint8_t* rdram, int32_t load_address, uint32_t& ram_used); std::vector<ModLoadErrorDetails> load_mods(const std::string& mod_game_id, uint8_t* rdram, int32_t load_address, uint32_t& ram_used);
void unload_mods(); void unload_mods();
std::vector<ModDetails> get_mod_details(const std::string& mod_game_id);
private: private:
ModOpenError open_mod(const std::filesystem::path& mod_path, std::string& error_param); ModOpenError open_mod(const std::filesystem::path& mod_path, std::string& error_param);
ModLoadError load_mod(uint8_t* rdram, const std::unordered_map<uint32_t, uint16_t>& section_map, recomp::mods::ModHandle& handle, int32_t load_address, uint32_t& ram_used, std::string& error_param); ModLoadError load_mod(uint8_t* rdram, const std::unordered_map<uint32_t, uint16_t>& section_map, recomp::mods::ModHandle& handle, int32_t load_address, uint32_t& ram_used, std::string& error_param);

View file

@ -414,6 +414,41 @@ size_t recomp::mods::ModContext::num_opened_mods() {
return opened_mods.size(); return opened_mods.size();
} }
std::vector<recomp::mods::ModDetails> recomp::mods::ModContext::get_mod_details(const std::string& mod_game_id) {
std::vector<ModDetails> ret{};
bool all_games = mod_game_id.empty();
size_t game_index = (size_t)-1;
auto find_game_it = mod_game_ids.find(mod_game_id);
if (find_game_it != mod_game_ids.end()) {
game_index = find_game_it->second;
}
for (const ModHandle& mod : opened_mods) {
if (all_games || mod.is_for_game(game_index)) {
std::vector<DependencyDetails> cur_dependencies{};
// TODO the recompiler context isn't available at this point, since it's parsed on mod load.
// Move that parsing to mod opening so it can be used here.
// for (const auto& cur_dep : mod.recompiler_context->dependencies) {
// cur_dependencies.emplace_back(DependencyDetails{
// .mod_id = cur_dep.mod_id,
// .version = Version{.major = cur_dep.major_version, .minor = cur_dep.minor_version, .patch = cur_dep.patch_version}
// });
// }
ret.emplace_back(ModDetails{
.mod_id = mod.manifest.mod_id,
.version = mod.manifest.version,
.authors = {}, // TODO add mod authors to the manifest and copy them here
.dependencies = std::move(cur_dependencies)
});
}
}
return ret;
}
std::vector<recomp::mods::ModLoadErrorDetails> recomp::mods::ModContext::load_mods(const std::string& mod_game_id, uint8_t* rdram, int32_t load_address, uint32_t& ram_used) { std::vector<recomp::mods::ModLoadErrorDetails> recomp::mods::ModContext::load_mods(const std::string& mod_game_id, uint8_t* rdram, int32_t load_address, uint32_t& ram_used) {
std::vector<recomp::mods::ModLoadErrorDetails> ret{}; std::vector<recomp::mods::ModLoadErrorDetails> ret{};
ram_used = 0; ram_used = 0;

View file

@ -482,6 +482,11 @@ bool recomp::mods::is_mod_enabled(const std::string& mod_id) {
return mod_context->is_mod_enabled(mod_id); return mod_context->is_mod_enabled(mod_id);
} }
std::vector<recomp::mods::ModDetails> recomp::mods::get_mod_details(const std::string& mod_game_id) {
std::lock_guard lock { mod_context_mutex };
return mod_context->get_mod_details(mod_game_id);
}
bool wait_for_game_started(uint8_t* rdram, recomp_context* context) { bool wait_for_game_started(uint8_t* rdram, recomp_context* context) {
game_status.wait(GameStatus::None); game_status.wait(GameStatus::None);