diff --git a/common/ruletypes.h b/common/ruletypes.h index 159335f50..0f8c3eb2c 100644 --- a/common/ruletypes.h +++ b/common/ruletypes.h @@ -909,6 +909,7 @@ RULE_BOOL(Inventory, AllowAnyWeaponTransformation, false, "Weapons can use any w RULE_BOOL(Inventory, TransformSummonedBags, false, "Transforms summoned bags into disenchanted ones instead of deleting") RULE_BOOL(Inventory, AllowMultipleOfSameAugment, false, "Allows multiple of the same augment to be placed in an item via #augmentitem or MQ2, set to true to allow") RULE_INT(Inventory, AlternateAugmentationSealer, 53, "Allows RoF+ clients to augment items from a special container type") +RULE_BOOL(Inventory, LazyLoadBank, true, "Don't load bank during zoning, only when in proximinity to a banker. May increase zone speed and stability") RULE_CATEGORY_END() RULE_CATEGORY(Client) diff --git a/zone/client.cpp b/zone/client.cpp index 4b705e24e..d272c5a26 100644 --- a/zone/client.cpp +++ b/zone/client.cpp @@ -185,7 +185,8 @@ Client::Client(EQStreamInterface *ieqs) : Mob( position_update_timer(10000), consent_throttle_timer(2000), tmSitting(0), - parcel_timer(RuleI(Parcel, ParcelDeliveryDelay)) + parcel_timer(RuleI(Parcel, ParcelDeliveryDelay)), + lazy_load_bank_check_timer(1000) { for (auto client_filter = FilterNone; client_filter < _FilterCount; client_filter = eqFilterType(client_filter + 1)) { SetFilter(client_filter, FilterShow); @@ -391,7 +392,6 @@ Client::Client(EQStreamInterface *ieqs) : Mob( SetBotPrecombat(false); AI_Init(); - } Client::~Client() { diff --git a/zone/client.h b/zone/client.h index 1eefb3737..0336798ba 100644 --- a/zone/client.h +++ b/zone/client.h @@ -2056,6 +2056,10 @@ private: Timer task_request_timer; Timer pick_lock_timer; Timer parcel_timer; //Used to limit the number of parcels to one every 30 seconds (default). Changable via rule. + Timer lazy_load_bank_check_timer; + + bool m_lazy_load_bank = false; + int m_lazy_load_sent_bank_slots = 0; glm::vec3 m_Proximity; glm::vec4 last_position_before_bulk_update; @@ -2175,7 +2179,6 @@ private: bool m_has_quest_compass = false; std::vector m_dynamic_zone_ids; - public: enum BotOwnerOption : size_t { booDeathMarquee, diff --git a/zone/client_process.cpp b/zone/client_process.cpp index 532669476..87bf39626 100644 --- a/zone/client_process.cpp +++ b/zone/client_process.cpp @@ -289,6 +289,37 @@ bool Client::Process() { entity_list.ScanCloseMobs(close_mobs, this, IsMoving()); } + if (RuleB(Inventory, LazyLoadBank)) { + // poll once a second to see if we are close to a banker and we haven't loaded the bank yet + if (!m_lazy_load_bank && lazy_load_bank_check_timer.Check()) { + if (m_lazy_load_sent_bank_slots <= EQ::invslot::SHARED_BANK_END && IsCloseToBanker()) { + m_lazy_load_bank = true; + lazy_load_bank_check_timer.Disable(); + } + } + + if (m_lazy_load_bank && m_lazy_load_sent_bank_slots <= EQ::invslot::SHARED_BANK_END) { + const EQ::ItemInstance *inst = nullptr; + + // Jump the gaps + if (m_lazy_load_sent_bank_slots < EQ::invslot::BANK_BEGIN) { + m_lazy_load_sent_bank_slots = EQ::invslot::BANK_BEGIN; + } + else if (m_lazy_load_sent_bank_slots > EQ::invslot::BANK_END && + m_lazy_load_sent_bank_slots < EQ::invslot::SHARED_BANK_BEGIN) { + m_lazy_load_sent_bank_slots = EQ::invslot::SHARED_BANK_BEGIN; + } + else { + m_lazy_load_sent_bank_slots++; + } + + inst = m_inv[m_lazy_load_sent_bank_slots]; + if (inst) { + SendItemPacket(m_lazy_load_sent_bank_slots, inst, ItemPacketType::ItemPacketTrade); + } + } + } + bool may_use_attacks = false; /* Things which prevent us from attacking: @@ -780,39 +811,41 @@ void Client::BulkSendInventoryItems() last_pos = ob.tellp(); } - // Bank items - for (int16 slot_id = EQ::invslot::BANK_BEGIN; slot_id <= EQ::invslot::BANK_END; slot_id++) { - const EQ::ItemInstance* inst = m_inv[slot_id]; - if (!inst) - continue; + if (!RuleB(Inventory, LazyLoadBank)) { + // Bank items + for (int16 slot_id = EQ::invslot::BANK_BEGIN; slot_id <= EQ::invslot::BANK_END; slot_id++) { + const EQ::ItemInstance* inst = m_inv[slot_id]; + if (!inst) + continue; - inst->Serialize(ob, slot_id); + inst->Serialize(ob, slot_id); - if (ob.tellp() == last_pos) - LogInventory("Serialization failed on item slot [{}] during BulkSendInventoryItems. Item skipped", slot_id); + if (ob.tellp() == last_pos) + LogInventory("Serialization failed on item slot [{}] during BulkSendInventoryItems. Item skipped", slot_id); - last_pos = ob.tellp(); - } + last_pos = ob.tellp(); + } - // SharedBank items - for (int16 slot_id = EQ::invslot::SHARED_BANK_BEGIN; slot_id <= EQ::invslot::SHARED_BANK_END; slot_id++) { - const EQ::ItemInstance* inst = m_inv[slot_id]; - if (!inst) - continue; + // SharedBank items + for (int16 slot_id = EQ::invslot::SHARED_BANK_BEGIN; slot_id <= EQ::invslot::SHARED_BANK_END; slot_id++) { + const EQ::ItemInstance* inst = m_inv[slot_id]; + if (!inst) + continue; - inst->Serialize(ob, slot_id); + inst->Serialize(ob, slot_id); - if (ob.tellp() == last_pos) - LogInventory("Serialization failed on item slot [{}] during BulkSendInventoryItems. Item skipped", slot_id); + if (ob.tellp() == last_pos) + LogInventory("Serialization failed on item slot [{}] during BulkSendInventoryItems. Item skipped", slot_id); - last_pos = ob.tellp(); - } + last_pos = ob.tellp(); + } + } - auto outapp = new EQApplicationPacket(OP_CharInventory); - outapp->size = ob.size(); - outapp->pBuffer = ob.detach(); - QueuePacket(outapp); - safe_delete(outapp); + auto outapp = new EQApplicationPacket(OP_CharInventory); + outapp->size = ob.size(); + outapp->pBuffer = ob.detach(); + QueuePacket(outapp); + safe_delete(outapp); } void Client::BulkSendMerchantInventory(int merchant_id, int npcid) {