Load shop keywords and gold, update shop gold

Gold is loaded into merchant chest after merchandise is loaded now. Gold is not saved to the merchandise list, but if owner takes or stores gold the change is saved to the shop separately. Gold refreshes after any transaction.
This commit is contained in:
Tyler Hallada 2021-02-13 17:50:19 -05:00
parent 289ec598d4
commit 17d428d385
5 changed files with 250 additions and 24 deletions

View File

@ -286,9 +286,6 @@ void LoadRefsTask(FFIResult<RawInteriorRefData> result, RE::TESObjectREFR* targe
RE::BGSKeyword* toggle_keyword = data_handler->LookupForm<RE::BGSKeyword>(KEYWORD_TOGGLE, MOD_NAME);
RE::BGSKeyword* next_keyword = data_handler->LookupForm<RE::BGSKeyword>(KEYWORD_NEXT, MOD_NAME);
RE::BGSKeyword* prev_keyword = data_handler->LookupForm<RE::BGSKeyword>(KEYWORD_PREV, MOD_NAME);
RE::BGSKeyword* vendor_item_armor_keyword = RE::TESForm::LookupByID<RE::BGSKeyword>(KEYWORD_VENDOR_ITEM_ARMOR);
RE::BGSListForm* vendor_items = data_handler->LookupForm<RE::BGSListForm>(FORM_LIST_VENDOR_ITEMS, MOD_NAME);
RE::TESFaction* vendor_services_faction = data_handler->LookupForm<RE::TESFaction>(FACTION_SERVICES_VENDOR, MOD_NAME);
SKSE::RegistrationMap<bool, std::vector<RE::TESObjectREFR*>> successReg = SKSE::RegistrationMap<bool, std::vector<RE::TESObjectREFR*>>();
successReg.Register(quest, RE::BSFixedString("OnLoadInteriorRefListSuccess"));
@ -462,11 +459,6 @@ void LoadRefsTask(FFIResult<RawInteriorRefData> result, RE::TESObjectREFR* targe
}
// TODO: load shop vendor(s)
// TODO: load these values from shop config data
vendor_items->ClearData();
vendor_items->AddForm(vendor_item_armor_keyword);
vendor_services_faction->vendorData.vendorValues.notBuySell = false;
} else {
const char * error = result.AsErr();
logger::error(FMT_STRING("LoadInteriorRefList get_interior_ref_list error: {}"), error);

View File

@ -307,7 +307,6 @@ void FillShelf(
std::tuple modifiers = CalculatePriceModifiers();
float price_factor = std::get<0>(modifiers);
float buy_price_modifier = std::get<1>(modifiers);
float sell_price_modifier = std::get<2>(modifiers);
RE::NiPoint3 shelf_position = merchant_shelf->data.location;
RE::NiPoint3 shelf_angle = merchant_shelf->data.angle;
@ -981,7 +980,6 @@ void CreateMerchandiseListImpl(
RE::TESObjectREFR* merchant_chest
) {
logger::info("Entered CreateMerchandiseListImpl");
RE::TESDataHandler* data_handler = RE::TESDataHandler::GetSingleton();
std::vector<RawMerchandise> merch_records;
std::vector<std::vector<const char*>> keyword_strings;
@ -1015,6 +1013,10 @@ void CreateMerchandiseListImpl(
uint32_t form_type = (uint32_t)base->GetFormType();
uint32_t quantity = entry_data->countDelta;
RE::FormID form_id = base->GetFormID();
if (form_id == 15) { // gold
logger::info("CreateMerchandiseList ignoring gold in merchant chest");
continue;
}
logger::info(FMT_STRING("CreateMerchandiseList quantity: {:d}"), quantity);
logger::info(FMT_STRING("CreateMerchandiseList base form_id: {:x}, name: {}, type: {:x}"), (uint32_t)form_id, name, (uint32_t)form_type);

View File

@ -1,4 +1,5 @@
#include "bindings.h"
#include "FormIds.h"
void CreateShopImpl(RE::BSFixedString api_url, RE::BSFixedString api_key, RE::BSFixedString name, RE::BSFixedString description, RE::TESQuest* quest) {
logger::info("Entered CreateShopImpl");
@ -7,7 +8,8 @@ void CreateShopImpl(RE::BSFixedString api_url, RE::BSFixedString api_key, RE::BS
return;
}
SKSE::RegistrationMap<int, RE::BSFixedString, RE::BSFixedString> successReg = SKSE::RegistrationMap<int, RE::BSFixedString, RE::BSFixedString>();
SKSE::RegistrationMap<int, RE::BSFixedString, RE::BSFixedString, int, RE::BSFixedString, std::vector<RE::BGSKeyword*>, bool> successReg =
SKSE::RegistrationMap<int, RE::BSFixedString, RE::BSFixedString, int, RE::BSFixedString, std::vector<RE::BGSKeyword*>, bool>();
successReg.Register(quest, RE::BSFixedString("OnCreateShopSuccess"));
SKSE::RegistrationMap<RE::BSFixedString> failReg = SKSE::RegistrationMap<RE::BSFixedString>();
failReg.Register(quest, RE::BSFixedString("OnCreateShopFail"));
@ -17,7 +19,24 @@ void CreateShopImpl(RE::BSFixedString api_url, RE::BSFixedString api_key, RE::BS
if (result.IsOk()) {
RawShop shop = result.AsOk();
logger::info(FMT_STRING("CreateShop success: {}"), shop.id);
successReg.SendEvent(shop.id, RE::BSFixedString(shop.name), RE::BSFixedString(shop.description));
std::vector<RE::BGSKeyword*> keyword_forms;
for (int i = 0; i < shop.vendor_keywords_len; i++) {
RE::BSFixedString keyword = shop.vendor_keywords[i];
logger::info(FMT_STRING("GetShop keyword {:d}: {}"), i, keyword);
RE::TESForm* form = RE::TESForm::LookupByEditorID(keyword);
if (!form) { // form is not found, might be in an uninstalled mod
logger::warn(FMT_STRING("GetShop could not find keyword form for: {}"), keyword);
continue;
}
RE::BGSKeyword* keyword_form = static_cast<RE::BGSKeyword*>(form);
if (!keyword_form) {
logger::warn(FMT_STRING("GetShop could cast form to keyword with id {:x} for: {}"), (uint32_t)form->GetFormID(), keyword);
continue;
}
keyword_forms.push_back(keyword_form);
}
successReg.SendEvent(shop.id, RE::BSFixedString(shop.name), RE::BSFixedString(shop.description), shop.gold, RE::BSFixedString(shop.shop_type), keyword_forms, shop.vendor_keywords_exclude);
} else {
const char* error = result.AsErr();
logger::error(FMT_STRING("CreateShop failure: {}"), error);
@ -39,24 +58,58 @@ bool CreateShop(RE::StaticFunctionTag*, RE::BSFixedString api_url, RE::BSFixedSt
return true;
}
void UpdateShopImpl(RE::BSFixedString api_url, RE::BSFixedString api_key, int32_t id, RE::BSFixedString name, RE::BSFixedString description, RE::TESQuest* quest) {
void UpdateShopImpl(
RE::BSFixedString api_url,
RE::BSFixedString api_key,
int32_t id,
RE::BSFixedString name,
RE::BSFixedString description,
int gold,
RE::BSFixedString shop_type,
std::vector<RE::BGSKeyword*> keywords,
bool keywords_exclude,
RE::TESQuest* quest
) {
logger::info("Entered UpdateShopImpl");
if (!quest) {
logger::error("UpdateShopImpl quest is null!");
return;
}
SKSE::RegistrationMap<int, RE::BSFixedString, RE::BSFixedString> successReg = SKSE::RegistrationMap<int, RE::BSFixedString, RE::BSFixedString>();
SKSE::RegistrationMap<int, RE::BSFixedString, RE::BSFixedString, int, RE::BSFixedString, std::vector<RE::BGSKeyword*>, bool> successReg =
SKSE::RegistrationMap<int, RE::BSFixedString, RE::BSFixedString, int, RE::BSFixedString, std::vector<RE::BGSKeyword*>, bool>();
successReg.Register(quest, RE::BSFixedString("OnUpdateShopSuccess"));
SKSE::RegistrationMap<RE::BSFixedString> failReg = SKSE::RegistrationMap<RE::BSFixedString>();
failReg.Register(quest, RE::BSFixedString("OnUpdateShopFail"));
logger::info(FMT_STRING("UpdateShop api_url: {}, api_key: {}, name: {}, description: {}"), api_url, api_key, name, description);
FFIResult<RawShop> result = update_shop(api_url.c_str(), api_key.c_str(), id, name.c_str(), description.c_str());
std::vector<const char*> keyword_strings;
for (auto keyword = keywords.begin(); keyword != keywords.end(); ++keyword) {
keyword_strings.push_back((*keyword)->GetFormEditorID());
}
logger::info(FMT_STRING("UpdateShop api_url: {}, api_key: {}, name: {}, description: {}, gold: {}, shop_type: {}, keywords.size(): {}, keywords_exclude: {}"), api_url, api_key, name, description, gold, shop_type, keywords.size(), keywords_exclude);
FFIResult<RawShop> result = update_shop(api_url.c_str(), api_key.c_str(), id, name.c_str(), description.c_str(), gold, shop_type.c_str(), &keyword_strings[0], keyword_strings.size(), keywords_exclude);
if (result.IsOk()) {
RawShop shop = result.AsOk();
logger::info(FMT_STRING("UpdateShop success: {}"), shop.id);
successReg.SendEvent(shop.id, RE::BSFixedString(shop.name), RE::BSFixedString(shop.description));
std::vector<RE::BGSKeyword*> keyword_forms;
for (int i = 0; i < shop.vendor_keywords_len; i++) {
RE::BSFixedString keyword = shop.vendor_keywords[i];
logger::info(FMT_STRING("GetShop keyword {:d}: {}"), i, keyword);
RE::TESForm* form = RE::TESForm::LookupByEditorID(keyword);
if (!form) { // form is not found, might be in an uninstalled mod
logger::warn(FMT_STRING("GetShop could not find keyword form for: {}"), keyword);
continue;
}
RE::BGSKeyword* keyword_form = static_cast<RE::BGSKeyword*>(form);
if (!keyword_form) {
logger::warn(FMT_STRING("GetShop could cast form to keyword with id {:x} for: {}"), (uint32_t)form->GetFormID(), keyword);
continue;
}
keyword_forms.push_back(keyword_form);
}
successReg.SendEvent(shop.id, RE::BSFixedString(shop.name), RE::BSFixedString(shop.description), shop.gold, RE::BSFixedString(shop.shop_type), keyword_forms, shop.vendor_keywords_exclude);
} else {
const char* error = result.AsErr();
logger::error(FMT_STRING("UpdateShop failure: {}"), error);
@ -66,14 +119,26 @@ void UpdateShopImpl(RE::BSFixedString api_url, RE::BSFixedString api_key, int32_
failReg.Unregister(quest);
}
bool UpdateShop(RE::StaticFunctionTag*, RE::BSFixedString api_url, RE::BSFixedString api_key, int32_t id, RE::BSFixedString name, RE::BSFixedString description, RE::TESQuest* quest) {
bool UpdateShop(
RE::StaticFunctionTag*,
RE::BSFixedString api_url,
RE::BSFixedString api_key,
int32_t id,
RE::BSFixedString name,
RE::BSFixedString description,
int gold,
RE::BSFixedString shop_type,
std::vector<RE::BGSKeyword*> keywords,
bool keywords_exclude,
RE::TESQuest* quest
) {
logger::info("Entered UpdateShop");
if (!quest) {
logger::error("UpdateShop quest is null!");
return false;
}
std::thread thread(UpdateShopImpl, api_url, api_key, id, name, description, quest);
std::thread thread(UpdateShopImpl, api_url, api_key, id, name, description, gold, shop_type, keywords, keywords_exclude, quest);
thread.detach();
return true;
}
@ -85,7 +150,8 @@ void GetShopImpl(RE::BSFixedString api_url, RE::BSFixedString api_key, int32_t i
return;
}
SKSE::RegistrationMap<int, RE::BSFixedString, RE::BSFixedString> successReg = SKSE::RegistrationMap<int, RE::BSFixedString, RE::BSFixedString>();
SKSE::RegistrationMap<int, RE::BSFixedString, RE::BSFixedString, int, RE::BSFixedString, std::vector<RE::BGSKeyword*>, bool> successReg =
SKSE::RegistrationMap<int, RE::BSFixedString, RE::BSFixedString, int, RE::BSFixedString, std::vector<RE::BGSKeyword*>, bool>();
successReg.Register(quest, RE::BSFixedString("OnGetShopSuccess"));
SKSE::RegistrationMap<RE::BSFixedString> failReg = SKSE::RegistrationMap<RE::BSFixedString>();
failReg.Register(quest, RE::BSFixedString("OnGetShopFail"));
@ -95,7 +161,24 @@ void GetShopImpl(RE::BSFixedString api_url, RE::BSFixedString api_key, int32_t i
if (result.IsOk()) {
RawShop shop = result.AsOk();
logger::info(FMT_STRING("GetShop success: {}"), shop.id);
successReg.SendEvent(shop.id, RE::BSFixedString(shop.name), RE::BSFixedString(shop.description));
std::vector<RE::BGSKeyword*> keyword_forms;
for (int i = 0; i < shop.vendor_keywords_len; i++) {
RE::BSFixedString keyword = shop.vendor_keywords[i];
logger::info(FMT_STRING("GetShop keyword {:d}: {}"), i, keyword);
RE::TESForm* form = RE::TESForm::LookupByEditorID(keyword);
if (!form) { // form is not found, might be in an uninstalled mod
logger::warn(FMT_STRING("GetShop could not find keyword form for: {}"), keyword);
continue;
}
RE::BGSKeyword* keyword_form = static_cast<RE::BGSKeyword*>(form);
if (!keyword_form) {
logger::warn(FMT_STRING("GetShop could cast form to keyword with id {:x} for: {}"), (uint32_t)form->GetFormID(), keyword);
continue;
}
keyword_forms.push_back(keyword_form);
}
successReg.SendEvent(shop.id, RE::BSFixedString(shop.name), RE::BSFixedString(shop.description), shop.gold, RE::BSFixedString(shop.shop_type), keyword_forms, shop.vendor_keywords_exclude);
} else {
const char* error = result.AsErr();
logger::error(FMT_STRING("GetShop failure: {}"), error);
@ -125,7 +208,8 @@ void ListShopsImpl(RE::BSFixedString api_url, RE::BSFixedString api_key, RE::TES
}
// Since Papyrus arrays are single-type, the array of shops from the API needs to be decomposed into multiple arrays for each shop field
SKSE::RegistrationMap<std::vector<int>, std::vector<RE::BSFixedString>, std::vector<RE::BSFixedString>> successReg = SKSE::RegistrationMap<std::vector<int>, std::vector<RE::BSFixedString>, std::vector<RE::BSFixedString>>();
SKSE::RegistrationMap<std::vector<int>, std::vector<RE::BSFixedString>, std::vector<RE::BSFixedString>, std::vector<int>, std::vector<RE::BSFixedString>, std::vector<RE::BGSKeyword*>, std::vector<bool>> successReg =
SKSE::RegistrationMap<std::vector<int>, std::vector<RE::BSFixedString>, std::vector<RE::BSFixedString>, std::vector<int>, std::vector<RE::BSFixedString>, std::vector<RE::BGSKeyword*>, std::vector<bool>>();
successReg.Register(quest, RE::BSFixedString("OnListShopsSuccess"));
SKSE::RegistrationMap<RE::BSFixedString> failReg = SKSE::RegistrationMap<RE::BSFixedString>();
failReg.Register(quest, RE::BSFixedString("OnListShopsFail"));
@ -139,13 +223,41 @@ void ListShopsImpl(RE::BSFixedString api_url, RE::BSFixedString api_key, RE::TES
std::vector<int> id_vec = std::vector<int>();
std::vector<RE::BSFixedString> name_vec = std::vector<RE::BSFixedString>();
std::vector<RE::BSFixedString> description_vec = std::vector<RE::BSFixedString>();
std::vector<int> gold_vec = std::vector<int>();
std::vector<RE::BSFixedString> shop_type_vec = std::vector<RE::BSFixedString>();
std::vector<RE::BGSKeyword*> keywords_vec = std::vector<RE::BGSKeyword*>();
std::vector<bool> keywords_exclude_vec = std::vector<bool>();
for (int i = 0; i < vec.len; i++) {
RawShop shop = vec.ptr[i];
id_vec.push_back(shop.id);
name_vec.push_back(RE::BSFixedString(shop.name));
description_vec.push_back(RE::BSFixedString(shop.description));
gold_vec.push_back(shop.gold);
shop_type_vec.push_back(RE::BSFixedString(shop.shop_type));
std::vector<RE::BGSKeyword*> keyword_forms;
for (int j = 0; j < shop.vendor_keywords_len; j++) {
RE::BSFixedString keyword = shop.vendor_keywords[j];
logger::info(FMT_STRING("ListShop keyword {:d}: {}"), j, keyword);
RE::TESForm* form = RE::TESForm::LookupByEditorID(keyword);
if (!form) { // form is not found, might be in an uninstalled mod
logger::warn(FMT_STRING("ListShop could not find keyword form for: {}"), keyword);
continue;
}
successReg.SendEvent(id_vec, name_vec, description_vec);
RE::BGSKeyword* keyword_form = static_cast<RE::BGSKeyword*>(form);
if (!keyword_form) {
logger::warn(FMT_STRING("ListShop could cast form to keyword with id {:x} for: {}"), (uint32_t)form->GetFormID(), keyword);
continue;
}
keyword_forms.push_back(keyword_form);
}
// Since papyrus doesn't have multi-dimensional arrays, I have to fake it with one flat array with each keyword list separated by a nullptr
keywords_vec.insert(keywords_vec.end(), keyword_forms.begin(), keyword_forms.end());
keywords_vec.push_back(nullptr);
keywords_exclude_vec.push_back(shop.vendor_keywords_exclude);
}
successReg.SendEvent(id_vec, name_vec, description_vec, gold_vec, shop_type_vec, keywords_vec, keywords_exclude_vec);
} else {
const char* error = result.AsErr();
logger::error(FMT_STRING("ListShops failure: {}"), error);
@ -155,6 +267,27 @@ void ListShopsImpl(RE::BSFixedString api_url, RE::BSFixedString api_key, RE::TES
failReg.Unregister(quest);
}
std::vector<RE::BGSKeyword*> GetKeywordsSubArray(RE::StaticFunctionTag*, std::vector<RE::BGSKeyword*> flat_keywords_array, int sub_array_index) {
int i = 0;
int current_sub_array = 0;
while (current_sub_array < sub_array_index) {
if (flat_keywords_array[i] == nullptr) {
current_sub_array += 1;
}
i += 1;
}
std::vector<RE::BGSKeyword*> sub_array = std::vector<RE::BGSKeyword*>();
while (true) {
if (flat_keywords_array[i] == nullptr) {
break;
} else {
sub_array.push_back(flat_keywords_array[i]);
}
i += 1;
}
return sub_array;
}
bool ListShops(RE::StaticFunctionTag*, RE::BSFixedString api_url, RE::BSFixedString api_key, RE::TESQuest* quest) {
logger::info("Entered ListShops");
if (!quest) {
@ -166,3 +299,84 @@ bool ListShops(RE::StaticFunctionTag*, RE::BSFixedString api_url, RE::BSFixedStr
thread.detach();
return true;
}
bool SetVendorKeywords(RE::StaticFunctionTag*, std::vector<RE::BGSKeyword*> keywords, bool keywords_exclude) {
logger::info("Entered SetVendorKeywords");
RE::TESDataHandler * data_handler = RE::TESDataHandler::GetSingleton();
RE::BGSListForm* vendor_items = data_handler->LookupForm<RE::BGSListForm>(FORM_LIST_VENDOR_ITEMS, MOD_NAME);
RE::TESFaction* vendor_services_faction = data_handler->LookupForm<RE::TESFaction>(FACTION_SERVICES_VENDOR, MOD_NAME);
if (!vendor_items) {
logger::error("SetVendorKeywords vendor_items could not be loaded!");
return false;
}
if (!vendor_services_faction) {
logger::error("SetVendorKeywords vendor_services_faction could not be loaded!");
return false;
}
vendor_items->ClearData();
for (auto keyword = keywords.begin(); keyword != keywords.end(); ++keyword) {
vendor_items->AddForm(*keyword);
}
vendor_services_faction->vendorData.vendorValues.notBuySell = keywords_exclude;
return true;
}
void RefreshShopGoldImpl(RE::BSFixedString api_url, RE::BSFixedString api_key, int32_t id, RE::TESObjectREFR* merchant_chest) {
logger::info("Entered RefreshShopGoldImpl");
if (!merchant_chest) {
logger::error("RefreshShopGoldImpl merch_chest is null!");
return;
}
SKSE::RegistrationMap<int> successReg = SKSE::RegistrationMap<int>();
successReg.Register(merchant_chest, RE::BSFixedString("OnRefreshShopGoldSuccess"));
SKSE::RegistrationMap<RE::BSFixedString> failReg = SKSE::RegistrationMap<RE::BSFixedString>();
failReg.Register(merchant_chest, RE::BSFixedString("OnRefreshShopGoldFail"));
RE::TESForm* gold_form = RE::TESForm::LookupByID(15);
if (!gold_form) {
logger::error("RefreshShopGoldImpl failed to lookup gold form");
failReg.SendEvent(RE::BSFixedString("Failed to lookup gold form"));
successReg.Unregister(merchant_chest);
failReg.Unregister(merchant_chest);
return;
}
RE::TESBoundObject* gold = static_cast<RE::TESBoundObject*>(gold_form);
if (!gold) {
logger::error("RefreshShopGoldImpl failed to cast gold form to gold bound object");
failReg.SendEvent(RE::BSFixedString("Failed to cast gold form to gold bound object"));
successReg.Unregister(merchant_chest);
failReg.Unregister(merchant_chest);
return;
}
logger::info(FMT_STRING("RefreshShopGold api_url: {}, api_key: {}, id: {}"), api_url, api_key, id);
FFIResult<RawShop> result = get_shop(api_url.c_str(), api_key.c_str(), id);
if (result.IsOk()) {
RawShop shop = result.AsOk();
logger::info(FMT_STRING("RefreshShopGold success id: {} gold: {}"), shop.id, shop.gold);
if (shop.gold > 0) {
merchant_chest->AddObjectToContainer(gold, nullptr, shop.gold, merchant_chest);
}
successReg.SendEvent(shop.gold);
} else {
const char* error = result.AsErr();
logger::error(FMT_STRING("RefreshShopGold failure: {}"), error);
failReg.SendEvent(RE::BSFixedString(error));
}
successReg.Unregister(merchant_chest);
failReg.Unregister(merchant_chest);
}
bool RefreshShopGold(RE::StaticFunctionTag*, RE::BSFixedString api_url, RE::BSFixedString api_key, int32_t id, RE::TESObjectREFR* merchant_chest) {
logger::info("Entered RefreshShopGold");
if (!merchant_chest) {
logger::error("RefreshShopGold merch_chest is null!");
return false;
}
std::thread thread(RefreshShopGoldImpl, api_url, api_key, id, merchant_chest);
thread.detach();
return true;
}

View File

@ -1,6 +1,21 @@
#pragma once
bool CreateShop(RE::StaticFunctionTag*, RE::BSFixedString api_url, RE::BSFixedString api_key, RE::BSFixedString name, RE::BSFixedString description, RE::TESQuest* quest);
bool UpdateShop(RE::StaticFunctionTag*, RE::BSFixedString api_url, RE::BSFixedString api_key, int32_t id, RE::BSFixedString name, RE::BSFixedString description, RE::TESQuest* quest);
bool UpdateShop(
RE::StaticFunctionTag*,
RE::BSFixedString api_url,
RE::BSFixedString api_key,
int32_t id,
RE::BSFixedString name,
RE::BSFixedString description,
int gold,
RE::BSFixedString shop_type,
std::vector<RE::BGSKeyword*> keywords,
bool keywords_exclude,
RE::TESQuest* quest
);
bool GetShop(RE::StaticFunctionTag*, RE::BSFixedString api_url, RE::BSFixedString api_key, int32_t id, RE::TESQuest* quest);
bool ListShops(RE::StaticFunctionTag*, RE::BSFixedString api_url, RE::BSFixedString api_key, RE::TESQuest* quest);
std::vector<RE::BGSKeyword*> GetKeywordsSubArray(RE::StaticFunctionTag*, std::vector<RE::BGSKeyword*> flat_keywords_array, int sub_array_index);
bool SetVendorKeywords(RE::StaticFunctionTag*, std::vector<RE::BGSKeyword*> keywords, bool keywords_exclude);
bool RefreshShopGold(RE::StaticFunctionTag*, RE::BSFixedString api_url, RE::BSFixedString api_key, int32_t id, RE::TESObjectREFR* merchant_chest);

View File

@ -19,6 +19,9 @@ bool RegisterFuncs(RE::BSScript::IVirtualMachine* a_vm)
a_vm->RegisterFunction("Update", "BRShop", UpdateShop);
a_vm->RegisterFunction("Get", "BRShop", GetShop);
a_vm->RegisterFunction("List", "BRShop", ListShops);
a_vm->RegisterFunction("GetKeywordsSubArray", "BRShop", GetKeywordsSubArray);
a_vm->RegisterFunction("SetVendorKeywords", "BRShop", SetVendorKeywords);
a_vm->RegisterFunction("RefreshGold", "BRShop", RefreshShopGold);
a_vm->RegisterFunction("Create", "BRInteriorRefList", CreateInteriorRefList);
a_vm->RegisterFunction("ClearCell", "BRInteriorRefList", ClearCell);
a_vm->RegisterFunction("Load", "BRInteriorRefList", LoadInteriorRefList);