diff --git a/common/Item.cpp b/common/Item.cpp index 82e3b5112..2b62be089 100644 --- a/common/Item.cpp +++ b/common/Item.cpp @@ -24,6 +24,7 @@ #include "races.h" #include "shareddb.h" #include "classes.h" +#include "../common/rulesys.h" #include @@ -400,6 +401,35 @@ void ItemInst::PutAugment(SharedDatabase *db, uint8 slot, uint32 item_id) } } +bool ItemInst::HasOrnamentation() const +{ + if(!RuleB(Inventory,UseAugOrnamentations)) return false; + const ItemInst *item; + for (int i = 0; i < MAX_AUGMENT_SLOTS; ++i) + { + uint32 id = 0; + if ((item = GetItem(i)) != nullptr) + { + if (item->GetItem()->AugType == RuleI(Inventory,AugOrnamentationType))return true; + } + } + return false; +} + +ItemInst* ItemInst::GetOrnamentation() const +{ + if(!RuleB(Inventory,UseAugOrnamentations)) return nullptr; + if (m_item->ItemClass == ItemClassCommon) + { + ItemInst *item; + for (int i = 0; i < MAX_AUGMENT_SLOTS; ++i) + { + if ((item = GetItem(i)) != nullptr && item->GetItem()->AugType == RuleI(Inventory,AugOrnamentationType)) return item; + } + } + return nullptr; +} + // Retrieve item inside container ItemInst* ItemInst::GetItem(uint8 index) const { diff --git a/common/Item.h b/common/Item.h index d62d92bda..a0081e31e 100644 --- a/common/Item.h +++ b/common/Item.h @@ -304,7 +304,8 @@ public: bool AvailableWearSlot(uint32 aug_wear_slots) const; int8 AvailableAugmentSlot(int32 augtype) const; inline int32 GetAugmentType() const { return m_item->AugType; } - + bool HasOrnamentation() const; + ItemInst* GetOrnamentation() const; inline bool IsExpendable() const { return ((m_item->Click.Type == ET_Expendable ) || (m_item->ItemType == ItemTypePotion)); } // diff --git a/common/patches/RoF.cpp b/common/patches/RoF.cpp index cbe228c92..7b65d301d 100644 --- a/common/patches/RoF.cpp +++ b/common/patches/RoF.cpp @@ -4926,13 +4926,25 @@ char* SerializeItem(const ItemInst *inst, int16 slot_id_in, uint32 *length, uint ss.write((const char*)&null_term, sizeof(uint8)); } - if(strlen(item->IDFile) > 0) + if (RuleB(Inventory,UseAugOrnamentations) && inst && inst->HasOrnamentation()) { - ss.write(item->IDFile, strlen(item->IDFile)); + ItemInst* ornamentation = inst->GetOrnamentation(); + if (ornamentation) //paranoid! + { + ss.write(ornamentation->GetItem()->IDFile, strlen(ornamentation->GetItem()->IDFile)); + } + else if (strlen(item->IDFile) > 0) + { + ss.write(item->IDFile, strlen(item->IDFile)); + } ss.write((const char*)&null_term, sizeof(uint8)); } - else + else //original code although I shortened it { + if (strlen(item->IDFile) > 0) + { + ss.write(item->IDFile, strlen(item->IDFile)); + } ss.write((const char*)&null_term, sizeof(uint8)); } diff --git a/common/patches/SoD.cpp b/common/patches/SoD.cpp index 08a3401ad..460be1e1f 100644 --- a/common/patches/SoD.cpp +++ b/common/patches/SoD.cpp @@ -3119,13 +3119,25 @@ char* SerializeItem(const ItemInst *inst, int16 slot_id_in, uint32 *length, uint ss.write((const char*)&null_term, sizeof(uint8)); } - if(strlen(item->IDFile) > 0) + if (RuleB(Inventory,UseAugOrnamentations) && inst && inst->HasOrnamentation()) { - ss.write(item->IDFile, strlen(item->IDFile)); + ItemInst* ornamentation = inst->GetOrnamentation(); + if (ornamentation) //paranoid! + { + ss.write(ornamentation->GetItem()->IDFile, strlen(ornamentation->GetItem()->IDFile)); + } + else if (strlen(item->IDFile) > 0) + { + ss.write(item->IDFile, strlen(item->IDFile)); + } ss.write((const char*)&null_term, sizeof(uint8)); } - else + else //original code although I shortened it { + if (strlen(item->IDFile) > 0) + { + ss.write(item->IDFile, strlen(item->IDFile)); + } ss.write((const char*)&null_term, sizeof(uint8)); } diff --git a/common/patches/SoF.cpp b/common/patches/SoF.cpp index 96b1f223e..6bfd22538 100644 --- a/common/patches/SoF.cpp +++ b/common/patches/SoF.cpp @@ -2437,13 +2437,25 @@ char* SerializeItem(const ItemInst *inst, int16 slot_id_in, uint32 *length, uint ss.write((const char*)&null_term, sizeof(uint8)); } - if(strlen(item->IDFile) > 0) + if (RuleB(Inventory,UseAugOrnamentations) && inst && inst->HasOrnamentation()) { - ss.write(item->IDFile, strlen(item->IDFile)); + ItemInst* ornamentation = inst->GetOrnamentation(); + if (ornamentation) //paranoid! + { + ss.write(ornamentation->GetItem()->IDFile, strlen(ornamentation->GetItem()->IDFile)); + } + else if (strlen(item->IDFile) > 0) + { + ss.write(item->IDFile, strlen(item->IDFile)); + } ss.write((const char*)&null_term, sizeof(uint8)); } - else + else //original code although I shortened it { + if (strlen(item->IDFile) > 0) + { + ss.write(item->IDFile, strlen(item->IDFile)); + } ss.write((const char*)&null_term, sizeof(uint8)); } diff --git a/common/patches/Underfoot.cpp b/common/patches/Underfoot.cpp index f15a94bde..0c51c4823 100644 --- a/common/patches/Underfoot.cpp +++ b/common/patches/Underfoot.cpp @@ -3530,13 +3530,25 @@ char* SerializeItem(const ItemInst *inst, int16 slot_id_in, uint32 *length, uint ss.write((const char*)&null_term, sizeof(uint8)); } - if(strlen(item->IDFile) > 0) + if (RuleB(Inventory,UseAugOrnamentations) && inst && inst->HasOrnamentation()) { - ss.write(item->IDFile, strlen(item->IDFile)); + ItemInst* ornamentation = inst->GetOrnamentation(); + if (ornamentation) //paranoid! + { + ss.write(ornamentation->GetItem()->IDFile, strlen(ornamentation->GetItem()->IDFile)); + } + else if (strlen(item->IDFile) > 0) + { + ss.write(item->IDFile, strlen(item->IDFile)); + } ss.write((const char*)&null_term, sizeof(uint8)); } - else + else //original code although I shortened it { + if (strlen(item->IDFile) > 0) + { + ss.write(item->IDFile, strlen(item->IDFile)); + } ss.write((const char*)&null_term, sizeof(uint8)); } diff --git a/common/ruletypes.h b/common/ruletypes.h index 70e4ba0d2..79b714fd8 100644 --- a/common/ruletypes.h +++ b/common/ruletypes.h @@ -553,6 +553,8 @@ RULE_CATEGORY( Inventory ) RULE_BOOL ( Inventory, EnforceAugmentRestriction, true) // Forces augment slot restrictions RULE_BOOL ( Inventory, EnforceAugmentUsability, true) // Forces augmented item usability RULE_BOOL ( Inventory, EnforceAugmentWear, true) // Forces augment wear slot validation +RULE_BOOL ( Inventory, UseAugOrnamentations, true) // Allows use of augment ornamentations +RULE_INT(Inventory,AugOrnamentationType,524288) // Custom servers can override default value (slot 20/524288) RULE_CATEGORY_END() #undef RULE_CATEGORY diff --git a/world/worlddb.cpp b/world/worlddb.cpp index ab8f6099a..1d9f170f8 100644 --- a/world/worlddb.cpp +++ b/world/worlddb.cpp @@ -197,14 +197,27 @@ void WorldDatabase::GetCharSelectInfo(uint32 account_id, CharacterSelect_Struct* cs->cs_colors[char_num][material].color = color; // the weapons are kept elsewhere - if ((material==MaterialPrimary) || (material==MaterialSecondary)) + if ((material == MaterialPrimary) || (material == MaterialSecondary)) { - if(strlen(item->GetItem()->IDFile) > 2) { - uint32 idfile=atoi(&item->GetItem()->IDFile[2]); - if (material==MaterialPrimary) - cs->primary[char_num]=idfile; + if (strlen(item->GetItem()->IDFile) > 2) + { + uint32 idfile = 0; + if (RuleB(Inventory,UseAugOrnamentations) && item->HasOrnamentation()) + { + ItemInst* ornament = item->GetOrnamentation(); + if (strlen(ornament->GetItem()->IDFile) > 2) + { + idfile = atoi(&ornament->GetItem()->IDFile[2]); + } + } else - cs->secondary[char_num]=idfile; + { + idfile = atoi(&item->GetItem()->IDFile[2]); + } + if (material == MaterialPrimary) + cs->primary[char_num] = idfile; + else + cs->secondary[char_num] = idfile; } } } diff --git a/zone/bot.cpp b/zone/bot.cpp index 1526beddc..1ba12ec4b 100644 --- a/zone/bot.cpp +++ b/zone/bot.cpp @@ -4565,6 +4565,49 @@ void Bot::SetLevel(uint8 in_level, bool command) { } } +int32 Bot::GetEquipmentMaterial(uint8 material_slot) const +{ + if // for primary and secondary we need the model, not the material + ( + material_slot == MaterialPrimary || + material_slot == MaterialSecondary + ) + { + uint8 inventorySlot = Inventory::CalcSlotFromMaterial(material_slot); + const ItemInst* inst = m_inv.GetItem(inventorySlot); + if (inst != nullptr) + { + if (RuleB(Inventory,UseAugOrnamentations) && inst->HasOrnamentation()) + { + const ItemInst* ornament = inst->GetOrnamentation(); + if (strlen(ornament->GetItem()->IDFile) > 2) + { + return atoi(&ornament->GetItem()->IDFile[2]); + } + } + else + { + if (strlen(inst->GetItem()->IDFile) > 2) + { + return atoi(&inst->GetItem()->IDFile[2]); + } + else //may as well try this, since were going to 0 anyways + { + return inst->GetItem()->Material; + } + } + } + } + else + { + const Item_Struct *item = database.GetItem(GetEquipment(material_slot)); + if (item!=nullptr) return item->Material; + } + + + return 0; +} + void Bot::FillSpawnStruct(NewSpawn_Struct* ns, Mob* ForWho) { if(ns) { Mob::FillSpawnStruct(ns, ForWho); @@ -4665,24 +4708,51 @@ void Bot::FillSpawnStruct(NewSpawn_Struct* ns, Mob* ForWho) { ns->spawn.colors[MaterialFeet].color = GetEquipmentColor(MaterialFeet); } } - inst = GetBotItem(SLOT_PRIMARY); if(inst) { item = inst->GetItem(); - if(item) { - if(strlen(item->IDFile) > 2) + if(item) + { + if (RuleB(Inventory,UseAugOrnamentations) && inst->HasOrnamentation()) + { + const ItemInst* ornament = inst->GetOrnamentation(); + if (strlen(ornament->GetItem()->IDFile) > 2) + { + ns->spawn.equipment[MaterialPrimary]= atoi(&ornament->GetItem()->IDFile[2]); + ns->spawn.colors[MaterialPrimary].color = GetEquipmentColor(MaterialPrimary); + } + } + else + { + item = inst->GetItem(); + if (strlen(item->IDFile) > 2) ns->spawn.equipment[MaterialPrimary] = atoi(&item->IDFile[2]); ns->spawn.colors[MaterialPrimary].color = GetEquipmentColor(MaterialPrimary); + } } } inst = GetBotItem(SLOT_SECONDARY); if(inst) { item = inst->GetItem(); - if(item) { - if(strlen(item->IDFile) > 2) + if(item) + { + if (RuleB(Inventory,UseAugOrnamentations) && inst->HasOrnamentation()) + { + const ItemInst* ornament = inst->GetOrnamentation(); + if (strlen(ornament->GetItem()->IDFile) > 2) + { + ns->spawn.equipment[MaterialSecondary]= atoi(&ornament->GetItem()->IDFile[2]); + ns->spawn.colors[MaterialSecondary].color = GetEquipmentColor(MaterialSecondary); + } + } + else + { + item = inst->GetItem(); + if (strlen(item->IDFile) > 2) ns->spawn.equipment[MaterialSecondary] = atoi(&item->IDFile[2]); ns->spawn.colors[MaterialSecondary].color = GetEquipmentColor(MaterialSecondary); + } } } } diff --git a/zone/bot.h b/zone/bot.h index 485d37377..41b591b11 100644 --- a/zone/bot.h +++ b/zone/bot.h @@ -332,6 +332,7 @@ public: void EquipBot(std::string* errorMessage); bool CheckLoreConflict(const Item_Struct* item); uint32 GetEquipmentColor(uint8 material_slot) const; + int32 GetEquipmentMaterial(uint8 material_slot) const; // Static Class Methods static void SaveBotGroup(Group* botGroup, std::string botGroupName, std::string* errorMessage); diff --git a/zone/client.cpp b/zone/client.cpp index 7aa7bd748..8775af1f1 100644 --- a/zone/client.cpp +++ b/zone/client.cpp @@ -1908,14 +1908,36 @@ void Client::FillSpawnStruct(NewSpawn_Struct* ns, Mob* ForWho) ns->spawn.colors[MaterialFeet].color = GetEquipmentColor(MaterialFeet); } if ((inst = m_inv[SLOT_PRIMARY]) && inst->IsType(ItemClassCommon)) { - item = inst->GetItem(); - if (strlen(item->IDFile) > 2) - ns->spawn.equipment[MaterialPrimary] = atoi(&item->IDFile[2]); + if (RuleB(Inventory,UseAugOrnamentations) && inst->HasOrnamentation()) + { + const ItemInst* ornament = inst->GetOrnamentation(); + if (strlen(ornament->GetItem()->IDFile) > 2) + { + ns->spawn.equipment[MaterialPrimary]= atoi(&ornament->GetItem()->IDFile[2]); + } + } + else + { + item = inst->GetItem(); + if (strlen(item->IDFile) > 2) + ns->spawn.equipment[MaterialPrimary] = atoi(&item->IDFile[2]); + } } if ((inst = m_inv[SLOT_SECONDARY]) && inst->IsType(ItemClassCommon)) { - item = inst->GetItem(); - if (strlen(item->IDFile) > 2) + if (RuleB(Inventory,UseAugOrnamentations) && inst->HasOrnamentation()) + { + const ItemInst* ornament = inst->GetOrnamentation(); + if (strlen(ornament->GetItem()->IDFile) > 2) + { + ns->spawn.equipment[MaterialPrimary]= atoi(&ornament->GetItem()->IDFile[2]); + } + } + else + { + item = inst->GetItem(); + if (strlen(item->IDFile) > 2) ns->spawn.equipment[MaterialSecondary] = atoi(&item->IDFile[2]); + } } //these two may be related to ns->spawn.texture diff --git a/zone/client.h b/zone/client.h index a97671c20..1f666e857 100644 --- a/zone/client.h +++ b/zone/client.h @@ -806,6 +806,7 @@ public: void SendItemPacket(int16 slot_id, const ItemInst* inst, ItemPacketType packet_type); bool IsValidSlot(uint32 slot); bool IsBankSlot(uint32 slot); + int32 GetEquipmentMaterial(uint8 material_slot) const; inline bool IsTrader() const { return(Trader); } inline bool IsBuyer() const { return(Buyer); } diff --git a/zone/command.cpp b/zone/command.cpp index eb1b94e89..af0f290a9 100644 --- a/zone/command.cpp +++ b/zone/command.cpp @@ -4707,7 +4707,15 @@ void command_iteminfo(Client *c, const Seperator *sep) const Item_Struct* item = inst->GetItem(); c->Message(0, "ID: %i Name: %s", item->ID, item->Name); c->Message(0, " Lore: %s ND: %i NS: %i Type: %i", (item->LoreFlag) ? "true":"false", item->NoDrop, item->NoRent, item->ItemClass); - c->Message(0, " IDF: %s Size: %i Weight: %i icon_id: %i Price: %i", item->IDFile, item->Size, item->Weight, item->Icon, item->Price); + if(RuleB(Inventory,UseAugOrnamentations) && inst->HasOrnamentation()) + { + c->Message(0, " IDF: %s Size: %i Weight: %i icon_id: %i Price: %i", inst->GetOrnamentation()->GetItem()->IDFile, item->Size, item->Weight, item->Icon, item->Price); + } + else + { + c->Message(0, " IDF: %s Size: %i Weight: %i icon_id: %i Price: %i", item->IDFile, item->Size, item->Weight, item->Icon, item->Price); + } + if (c->Admin() >= 200) c->Message(0, "MinStatus: %i", item->MinStatus); if (item->ItemClass==ItemClassBook) diff --git a/zone/inventory.cpp b/zone/inventory.cpp index 5292dd1c0..dbc3fca04 100644 --- a/zone/inventory.cpp +++ b/zone/inventory.cpp @@ -1886,6 +1886,50 @@ void Client::DyeArmor(DyeStruct* dye){ Save(); } + +int32 Client::GetEquipmentMaterial(uint8 material_slot) const +{ + if // for primary and secondary we need the model, not the material + ( + material_slot == MaterialPrimary || + material_slot == MaterialSecondary + ) + { + uint8 inventorySlot = Inventory::CalcSlotFromMaterial(material_slot); + const ItemInst* inst = m_inv.GetItem(inventorySlot); + if (inst != nullptr) + { + if (inst->HasOrnamentation()) + { + const ItemInst* ornament = inst->GetOrnamentation(); + if (strlen(ornament->GetItem()->IDFile) > 2) + { + return atoi(&ornament->GetItem()->IDFile[2]); + } + } + else + { + if (strlen(inst->GetItem()->IDFile) > 2) + { + return atoi(&inst->GetItem()->IDFile[2]); + } + else //may as well try this, since were going to 0 anyways + { + return inst->GetItem()->Material; + } + } + } + } + else + { + const Item_Struct *item = database.GetItem(GetEquipment(material_slot)); + if (item!=nullptr) return item->Material; + } + + + return 0; +} + /*bool Client::DecreaseByItemType(uint32 type, uint8 amt) { const Item_Struct* TempItem = 0; ItemInst* ins; diff --git a/zone/mob.cpp b/zone/mob.cpp index c2cf34650..50fa81717 100644 --- a/zone/mob.cpp +++ b/zone/mob.cpp @@ -2577,9 +2577,7 @@ void Mob::WearChange(uint8 material_slot, uint16 texture, uint32 color) int32 Mob::GetEquipmentMaterial(uint8 material_slot) const { - const Item_Struct *item; - - item = database.GetItem(GetEquipment(material_slot)); + const Item_Struct *item = database.GetItem(GetEquipment(material_slot)); if(item != 0) { if // for primary and secondary we need the model, not the material