diff --git a/Artifact Tracker.esp b/Artifact Tracker.esp index 56bfd25..bab97f8 100644 Binary files a/Artifact Tracker.esp and b/Artifact Tracker.esp differ diff --git a/SKSE/Plugins/ArtifactTracker.dll b/SKSE/Plugins/ArtifactTracker.dll index 1a57616..63ae374 100644 Binary files a/SKSE/Plugins/ArtifactTracker.dll and b/SKSE/Plugins/ArtifactTracker.dll differ diff --git a/Source/ArtifactTrackerDLL/src/ArtifactTracker.cpp b/Source/ArtifactTrackerDLL/src/ArtifactTracker.cpp index afc7ee8..aa1c7e9 100644 --- a/Source/ArtifactTrackerDLL/src/ArtifactTracker.cpp +++ b/Source/ArtifactTrackerDLL/src/ArtifactTracker.cpp @@ -12,8 +12,10 @@ namespace ArtifactTracker RE::BGSListForm* g_listStored; RE::BGSListForm* g_listFound; RE::BGSListForm* g_persistentStorage; + RE::BGSKeyword* g_extraArtifactKeyword; RE::BGSKeyword* g_homeKeyword; std::unordered_map g_artifactMap; + std::unordered_set g_artifactFormTypes; std::unordered_map g_persistentMap; RE::TESObjectREFR* g_cellStorage; @@ -34,13 +36,14 @@ namespace ArtifactTracker g_listStored = dataHandler->LookupForm(0x805, "Artifact Tracker.esp"); // ETR_ItemsStored g_listFound = dataHandler->LookupForm(0x806, "Artifact Tracker.esp"); // ETR_ItemsFound g_persistentStorage = dataHandler->LookupForm(0x807, "Artifact Tracker.esp"); // ETR_PersistentStorageList + g_extraArtifactKeyword = dataHandler->LookupForm(0x80B, "Artifact Tracker.esp"); // ETR_ExtraArtifact g_homeKeyword = dataHandler->LookupForm(0xFC1A3, "Skyrim.esm"); // LocTypePlayerHouse const auto recipeKeyword = dataHandler->LookupForm(0xF5CB0, "Skyrim.esm"); // VendorItemRecipe const auto excludeKeywords = dataHandler->LookupForm(0x801, "Artifact Tracker.esp"); // ETR_ExcludeMiscKeywords - if (!g_cellContainer || !g_listNew || !g_listStored || !g_listFound || !g_persistentStorage || !g_homeKeyword || !recipeKeyword || !excludeKeywords) { + if (!g_cellContainer || !g_listNew || !g_listStored || !g_listFound || !g_persistentStorage || !g_homeKeyword || !g_extraArtifactKeyword || !recipeKeyword || !excludeKeywords) { SKSE::log::warn("Failed to load data from Artifact Tracker.esp"); RE::DebugMessageBox("Failed to load data from Artifact Tracker.esp, the mod is disabled."); return; @@ -48,52 +51,84 @@ namespace ArtifactTracker // Preloading item lists + g_artifactFormTypes.insert(RE::FormType::Weapon); + for (const auto& form : dataHandler->GetFormArray(RE::FormType::Weapon)) { + if (form->GetPlayable()) { + g_artifactMap[form->formID] = form; + } + } + g_artifactMap.erase(0x1F4); // Unarmed + + g_artifactFormTypes.insert(RE::FormType::Armor); + for (const auto& form : dataHandler->GetFormArray(RE::FormType::Armor)) { + if (form->GetPlayable()) { + g_artifactMap[form->formID] = form; + } + } + + g_artifactFormTypes.insert(RE::FormType::Book); for (const auto& form : dataHandler->GetFormArray()) { if (form && !form->TeachesSpell() && (form->HasKeyword(recipeKeyword) || BookCheck::IsBook(form))) { g_artifactMap[form->formID] = form; } } - for (const auto& form : dataHandler->GetFormArray(RE::FormType::Misc)) { - if (form->GetPlayable() && !form->HasKeywordInList(excludeKeywords, false)) { + OnGameLoad(); + EventListener::Install(); + } + + void PreloadArtifactList() + { + if (g_bLoaded) { + return; + } + + const auto dataHandler = RE::TESDataHandler::GetSingleton(); + const auto recipeKeyword = dataHandler->LookupForm(0xF5CB0, "Skyrim.esm"); // VendorItemRecipe + const auto excludeKeywords = dataHandler->LookupForm(0x801, "Artifact Tracker.esp"); // ETR_ExcludeMiscKeywords + + for (const auto& form : dataHandler->GetFormArray()) { + if (form->HasKeyword(g_extraArtifactKeyword)) { + g_artifactMap[form->formID] = form; + } + } + + g_artifactFormTypes.insert(RE::FormType::Misc); + for (const auto& form : dataHandler->GetFormArray()) { + if (form->GetPlayable() && (form->HasKeyword(g_extraArtifactKeyword) || !form->HasKeywordInList(excludeKeywords, false))) { g_artifactMap[form->formID] = form; } } g_artifactMap.erase(0xA); // Lockpick g_artifactMap.erase(0xF); // Gold - - for (const auto& form : dataHandler->GetFormArray(RE::FormType::Weapon)) { - if (form->GetPlayable()) { + + for (const auto& form : dataHandler->GetFormArray()) { + if (form->HasKeyword(g_extraArtifactKeyword)) { g_artifactMap[form->formID] = form; + g_artifactFormTypes.insert(RE::FormType::AlchemyItem); } } - g_artifactMap.erase(0x1F4); // Unarmed - - for (const auto& form : dataHandler->GetFormArray(RE::FormType::Armor)) { - if (form->GetPlayable()) { + + for (const auto& form : dataHandler->GetFormArray()) { + if (form->HasKeyword(g_extraArtifactKeyword)) { g_artifactMap[form->formID] = form; + g_artifactFormTypes.insert(RE::FormType::Ingredient); } } - OnGameLoad(); - EventListener::Install(); + for (const auto& form : dataHandler->GetFormArray()) { + if (form->HasKeyword(g_extraArtifactKeyword)) { + g_artifactMap[form->formID] = form; + g_artifactFormTypes.insert(RE::FormType::SoulGem); + } + } g_bLoaded = true; } bool IsArtifact(RE::TESForm* a_form) { - if (!a_form) { - return false; - } - - const auto formType = a_form->GetFormType(); - - if (formType == RE::FormType::Armor || formType == RE::FormType::Weapon || formType == RE::FormType::Book || formType == RE::FormType::Misc) { - return g_artifactMap.contains(a_form->formID); - } - - return false; + return a_form && g_artifactFormTypes.contains(a_form->GetFormType()) && g_artifactMap.contains(a_form->formID); } RE::TESForm* GetArtifactByID(RE::FormID a_formID) diff --git a/Source/ArtifactTrackerDLL/src/ArtifactTracker.h b/Source/ArtifactTrackerDLL/src/ArtifactTracker.h index c1b92c6..25b9cc5 100644 --- a/Source/ArtifactTrackerDLL/src/ArtifactTracker.h +++ b/Source/ArtifactTrackerDLL/src/ArtifactTracker.h @@ -9,13 +9,17 @@ namespace ArtifactTracker extern RE::BGSListForm* g_listStored; extern RE::BGSListForm* g_listFound; extern RE::BGSListForm* g_persistentStorage; + extern RE::BGSKeyword* g_extraArtifactKeyword; extern RE::BGSKeyword* g_homeKeyword; extern std::unordered_map g_artifactMap; + extern std::unordered_set g_artifactFormTypes; extern std::unordered_map g_persistentMap; extern RE::TESObjectREFR* g_cellStorage; void Init(); + void PreloadArtifactList(); + bool IsArtifact(RE::TESForm* a_item); RE::TESForm* GetArtifactByID(RE::FormID a_formID); diff --git a/Source/ArtifactTrackerDLL/src/Main.cpp b/Source/ArtifactTrackerDLL/src/Main.cpp index 0f27fb0..6208df6 100644 --- a/Source/ArtifactTrackerDLL/src/Main.cpp +++ b/Source/ArtifactTrackerDLL/src/Main.cpp @@ -32,6 +32,8 @@ namespace { ArtifactTracker::Init(); } else if (message->type == MessagingInterface::kPostLoadGame) { ArtifactTracker::OnGameLoad(); + } else if (message->type == MessagingInterface::kNewGame || message->type == MessagingInterface::kPreLoadGame) { + ArtifactTracker::PreloadArtifactList(); } }); }