mirror of
https://github.com/EQEmu/Server.git
synced 2025-12-22 07:01:29 +00:00
Early stages of swapping requirements in, should check for basic validity and equipable status
This commit is contained in:
parent
568938d003
commit
18b4d068ea
@ -38,8 +38,8 @@ T ClampUpper(const T& value, const T& upper) {
|
||||
return std::min(value, upper);
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
bool ValueWithin(const T& value, const T& lower, const T& upper) {
|
||||
template <typename T, typename U, typename V>
|
||||
bool ValueWithin(const T& value, const U& lower, const V& upper) {
|
||||
return value >= lower && value <= upper;
|
||||
}
|
||||
|
||||
|
||||
@ -19,8 +19,82 @@
|
||||
#include "inventory.h"
|
||||
#include "data_verification.h"
|
||||
#include "item_container_personal_serialization.h"
|
||||
#include "string_util.h"
|
||||
#include <map>
|
||||
|
||||
bool EQEmu::InventorySlot::IsValid() const {
|
||||
if(type_ == InvTypePersonal && EQEmu::ValueWithin(slot_, PersonalSlotCharm, PersonalSlotCursor)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
if(type_ == InvTypeBank && EQEmu::ValueWithin(slot_, 0, 23)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
if(type_ == InvTypeSharedBank && EQEmu::ValueWithin(slot_, 0, 1)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
if(type_ == InvTypeTribute && EQEmu::ValueWithin(slot_, 0, 4)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
if(type_ == InvTypeTrade && EQEmu::ValueWithin(slot_, 0, 7)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
if(type_ == InvTypeWorld && EQEmu::ValueWithin(slot_, 0, 255)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
bool EQEmu::InventorySlot::IsBank() const {
|
||||
if(type_ == InvTypeBank && EQEmu::ValueWithin(slot_, 0, 23)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
if(type_ == InvTypeSharedBank && EQEmu::ValueWithin(slot_, 0, 1)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
bool EQEmu::InventorySlot::IsCursor() const {
|
||||
if(type_ == InvTypePersonal && slot_ == PersonalSlotCursor) {
|
||||
return true;
|
||||
}
|
||||
|
||||
if(type_ == InvTypeCursorBuffer) {
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
bool EQEmu::InventorySlot::IsEquipment() const {
|
||||
if(type_ == InvTypePersonal && EQEmu::ValueWithin(slot_, PersonalSlotCharm, PersonalSlotAmmo)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
bool EQEmu::InventorySlot::IsGeneral() const {
|
||||
if(type_ == InvTypePersonal && EQEmu::ValueWithin(slot_, PersonalSlotGeneral1, PersonalSlotGeneral10)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
const std::string EQEmu::InventorySlot::ToString() const {
|
||||
return StringFormat("(%i, %i, %i, %i)", type_, slot_, bag_index_, aug_index_);
|
||||
}
|
||||
|
||||
struct EQEmu::Inventory::impl
|
||||
{
|
||||
std::map<int, ItemContainer> containers_;
|
||||
@ -35,15 +109,15 @@ EQEmu::Inventory::~Inventory() {
|
||||
}
|
||||
|
||||
std::shared_ptr<EQEmu::ItemInstance> EQEmu::Inventory::Get(const InventorySlot &slot) {
|
||||
auto iter = impl_->containers_.find(slot.type_);
|
||||
auto iter = impl_->containers_.find(slot.Type());
|
||||
if(iter != impl_->containers_.end()) {
|
||||
auto item = iter->second.Get(slot.slot_);
|
||||
auto item = iter->second.Get(slot.Slot());
|
||||
if(item) {
|
||||
if(slot.bag_index_ > -1) {
|
||||
auto sub_item = item->Get(slot.bag_index_);
|
||||
if(slot.BagIndex() > -1) {
|
||||
auto sub_item = item->Get(slot.BagIndex());
|
||||
if(sub_item) {
|
||||
if(slot.aug_index_ > -1) {
|
||||
return sub_item->Get(slot.aug_index_);
|
||||
if(slot.AugIndex() > -1) {
|
||||
return sub_item->Get(slot.AugIndex());
|
||||
} else {
|
||||
return sub_item;
|
||||
}
|
||||
@ -58,42 +132,42 @@ std::shared_ptr<EQEmu::ItemInstance> EQEmu::Inventory::Get(const InventorySlot &
|
||||
}
|
||||
|
||||
bool EQEmu::Inventory::Put(const InventorySlot &slot, std::shared_ptr<ItemInstance> inst) {
|
||||
if(impl_->containers_.count(slot.type_) == 0) {
|
||||
if(slot.type_ == 0) {
|
||||
impl_->containers_.insert(std::pair<int, ItemContainer>(slot.type_, ItemContainer(new ItemContainerPersonalSerialization())));
|
||||
if(impl_->containers_.count(slot.Type()) == 0) {
|
||||
if(slot.Type() == 0) {
|
||||
impl_->containers_.insert(std::pair<int, ItemContainer>(slot.Type(), ItemContainer(new ItemContainerPersonalSerialization())));
|
||||
} else {
|
||||
impl_->containers_.insert(std::pair<int, ItemContainer>(slot.type_, ItemContainer()));
|
||||
impl_->containers_.insert(std::pair<int, ItemContainer>(slot.Type(), ItemContainer()));
|
||||
}
|
||||
}
|
||||
|
||||
//Verify item can be put into the slot requested
|
||||
|
||||
auto &container = impl_->containers_[slot.type_];
|
||||
if(slot.bag_index_ > -1) {
|
||||
auto item = container.Get(slot.slot_);
|
||||
auto &container = impl_->containers_[slot.Type()];
|
||||
if(slot.BagIndex() > -1) {
|
||||
auto item = container.Get(slot.Slot());
|
||||
if(!item)
|
||||
return false;
|
||||
|
||||
if(slot.aug_index_ > -1) {
|
||||
auto bag_item = item->Get(slot.bag_index_);
|
||||
if(slot.AugIndex() > -1) {
|
||||
auto bag_item = item->Get(slot.BagIndex());
|
||||
if(!bag_item) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return bag_item->Put(slot.aug_index_, inst);
|
||||
return bag_item->Put(slot.AugIndex(), inst);
|
||||
} else {
|
||||
return item->Put(slot.bag_index_, inst);
|
||||
return item->Put(slot.BagIndex(), inst);
|
||||
}
|
||||
} else {
|
||||
if(slot.aug_index_ > -1) {
|
||||
auto item = container.Get(slot.slot_);
|
||||
if(slot.AugIndex() > -1) {
|
||||
auto item = container.Get(slot.Slot());
|
||||
if(!item)
|
||||
return false;
|
||||
|
||||
return item->Put(slot.aug_index_, inst);
|
||||
return item->Put(slot.AugIndex(), inst);
|
||||
}
|
||||
|
||||
return container.Put(slot.slot_, inst);
|
||||
return container.Put(slot.Slot(), inst);
|
||||
}
|
||||
|
||||
return false;
|
||||
@ -104,10 +178,10 @@ bool EQEmu::Inventory::Swap(const InventorySlot &src, const InventorySlot &dest,
|
||||
}
|
||||
|
||||
int EQEmu::Inventory::CalcMaterialFromSlot(const InventorySlot &slot) {
|
||||
if(slot.type_ != 0)
|
||||
if(slot.Type() != 0)
|
||||
return _MaterialInvalid;
|
||||
|
||||
switch(slot.slot_) {
|
||||
switch(slot.Slot()) {
|
||||
case PersonalSlotHead:
|
||||
return MaterialHead;
|
||||
case PersonalSlotChest:
|
||||
|
||||
@ -20,24 +20,10 @@
|
||||
#define COMMON_INVENTORY_H
|
||||
|
||||
#include "item_container.h"
|
||||
#include <string>
|
||||
|
||||
namespace EQEmu
|
||||
{
|
||||
struct InventorySlot
|
||||
{
|
||||
InventorySlot(int type, int slot)
|
||||
: type_(type), slot_(slot), bag_index_(-1), aug_index_(-1) { }
|
||||
InventorySlot(int type, int slot, int bag_index)
|
||||
: type_(type), slot_(slot), bag_index_(bag_index), aug_index_(-1) { }
|
||||
InventorySlot(int type, int slot, int bag_index, int aug_index)
|
||||
: type_(type), slot_(slot), bag_index_(bag_index), aug_index_(aug_index) { }
|
||||
|
||||
int type_;
|
||||
int slot_;
|
||||
int bag_index_;
|
||||
int aug_index_;
|
||||
};
|
||||
|
||||
enum InventoryType : int
|
||||
{
|
||||
InvTypePersonal = 0,
|
||||
@ -89,6 +75,48 @@ namespace EQEmu
|
||||
PersonalSlotCursor
|
||||
};
|
||||
|
||||
class InventorySlot
|
||||
{
|
||||
public:
|
||||
InventorySlot() : type_(-1), slot_(-1), bag_index_(-1), aug_index_(-1) { }
|
||||
InventorySlot(int type, int slot)
|
||||
: type_(type), slot_(slot), bag_index_(-1), aug_index_(-1) { }
|
||||
InventorySlot(int type, int slot, int bag_index)
|
||||
: type_(type), slot_(slot), bag_index_(bag_index), aug_index_(-1) { }
|
||||
InventorySlot(int type, int slot, int bag_index, int aug_index)
|
||||
: type_(type), slot_(slot), bag_index_(bag_index), aug_index_(aug_index) { }
|
||||
|
||||
bool IsValid() const;
|
||||
bool IsBank() const;
|
||||
bool IsCursor() const;
|
||||
bool IsEquipment() const;
|
||||
bool IsGeneral() const;
|
||||
|
||||
const std::string ToString() const;
|
||||
|
||||
inline int Type() { return type_; }
|
||||
inline int Type() const { return type_; }
|
||||
inline int Slot() { return slot_; }
|
||||
inline int Slot() const { return slot_; }
|
||||
inline int BagIndex() { return bag_index_; }
|
||||
inline int BagIndex() const { return bag_index_; }
|
||||
inline int AugIndex() { return aug_index_; }
|
||||
inline int AugIndex() const { return aug_index_; }
|
||||
|
||||
private:
|
||||
int type_;
|
||||
int slot_;
|
||||
int bag_index_;
|
||||
int aug_index_;
|
||||
};
|
||||
|
||||
inline bool operator==(const InventorySlot &lhs, const InventorySlot &rhs) {
|
||||
return lhs.Type() == rhs.Type() &&
|
||||
lhs.Slot() == rhs.Slot() &&
|
||||
lhs.BagIndex() == rhs.BagIndex() &&
|
||||
lhs.AugIndex() == rhs.AugIndex(); }
|
||||
inline bool operator!=(const InventorySlot &lhs, const InventorySlot &rhs) { return !(lhs == rhs); }
|
||||
|
||||
class Inventory
|
||||
{
|
||||
public:
|
||||
|
||||
@ -124,14 +124,14 @@ bool EQEmu::ItemInstance::Put(const int index, std::shared_ptr<ItemInstance> ins
|
||||
|
||||
auto *item = impl_->base_item_;
|
||||
if(item->ItemClass == ItemClassContainer) { // Bag
|
||||
if(!EQEmu::ValueWithin(index, 0, (int)item->BagSlots)) {
|
||||
if(!EQEmu::ValueWithin(index, 0, item->BagSlots)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return impl_->contents_.Put(index, inst);
|
||||
}
|
||||
else if(item->ItemClass == ItemClassCommon) { // Augment
|
||||
if(!EQEmu::ValueWithin(index, 0, (int)EmuConstants::ITEM_COMMON_SIZE)) {
|
||||
if(!EQEmu::ValueWithin(index, 0, EmuConstants::ITEM_COMMON_SIZE)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
@ -2167,7 +2167,7 @@ void Client::AddMoneyToPP(uint64 copper, bool updateclient){
|
||||
Log.Out(Logs::General, Logs::None, "Client::AddMoneyToPP() %s should have: plat:%i gold:%i silver:%i copper:%i", GetName(), m_pp.platinum, m_pp.gold, m_pp.silver, m_pp.copper);
|
||||
}
|
||||
|
||||
void Client::EVENT_ITEM_ScriptStopReturn(){
|
||||
void Client::ItemScriptStopReturn(){
|
||||
/* Set a timestamp in an entity variable for plugin check_handin.pl in return_items
|
||||
This will stopgap players from items being returned if global_npc.pl has a catch all return_items
|
||||
*/
|
||||
@ -2175,11 +2175,11 @@ void Client::EVENT_ITEM_ScriptStopReturn(){
|
||||
char buffer[50];
|
||||
gettimeofday(&read_time, 0);
|
||||
sprintf(buffer, "%li.%li \n", read_time.tv_sec, read_time.tv_usec);
|
||||
this->SetEntityVariable("Stop_Return", buffer);
|
||||
SetEntityVariable("Stop_Return", buffer);
|
||||
}
|
||||
|
||||
void Client::AddMoneyToPP(uint32 copper, uint32 silver, uint32 gold, uint32 platinum, bool updateclient){
|
||||
this->EVENT_ITEM_ScriptStopReturn();
|
||||
ItemScriptStopReturn();
|
||||
|
||||
int32 new_value = m_pp.platinum + platinum;
|
||||
if(new_value >= 0 && new_value > m_pp.platinum)
|
||||
|
||||
@ -800,7 +800,7 @@ public:
|
||||
int32 acmod();
|
||||
|
||||
// Item methods
|
||||
void EVENT_ITEM_ScriptStopReturn();
|
||||
void ItemScriptStopReturn();
|
||||
uint32 NukeItem(uint32 itemnum, uint8 where_to_check =
|
||||
(invWhereWorn | invWherePersonal | invWhereBank | invWhereSharedBank | invWhereTrading | invWhereCursor));
|
||||
void SetTint(int16 slot_id, uint32 color);
|
||||
@ -823,6 +823,10 @@ public:
|
||||
void IncStats(uint8 type,int16 increase_val);
|
||||
void DropItem(int16 slot_id);
|
||||
|
||||
//New Inventory
|
||||
bool SwapItem(const EQEmu::InventorySlot &src, const EQEmu::InventorySlot &dest, int number_in_stack);
|
||||
bool CanEquipItem(std::shared_ptr<EQEmu::ItemInstance> inst, const EQEmu::InventorySlot &slot);
|
||||
|
||||
//
|
||||
// class Client::TextLink
|
||||
//
|
||||
|
||||
@ -9593,70 +9593,11 @@ void Client::Handle_OP_MoveItem(const EQApplicationPacket *app)
|
||||
}
|
||||
|
||||
MoveItem_Struct* mi = (MoveItem_Struct*)app->pBuffer;
|
||||
auto res = m_inventory.Swap(EQEmu::InventorySlot(mi->from_type, mi->from_slot, mi->from_bag_slot, mi->from_aug_slot),
|
||||
EQEmu::InventorySlot(mi->to_type, mi->to_slot, mi->to_bag_slot, mi->to_aug_slot),
|
||||
mi->number_in_stack);
|
||||
|
||||
//printf("%i %i %i %i --> %i %i %i %i (%u)\n",
|
||||
// mi->from_type, mi->from_slot, mi->from_bag_slot, mi->from_aug_slot,
|
||||
// mi->to_type, mi->to_slot, mi->to_bag_slot, mi->to_aug_slot,
|
||||
// mi->number_in_stack);
|
||||
|
||||
//if (spellend_timer.Enabled() && casting_spell_id && !IsBardSong(casting_spell_id))
|
||||
//{
|
||||
// if (mi->from_slot != mi->to_slot && (mi->from_slot <= EmuConstants::GENERAL_END || mi->from_slot > 39) && IsValidSlot(mi->from_slot) && IsValidSlot(mi->to_slot))
|
||||
// {
|
||||
// char *detect = nullptr;
|
||||
// const ItemInst *itm_from = GetInv().GetItem(mi->from_slot);
|
||||
// const ItemInst *itm_to = GetInv().GetItem(mi->to_slot);
|
||||
// MakeAnyLenString(&detect, "Player issued a move item from %u(item id %u) to %u(item id %u) while casting %u.",
|
||||
// mi->from_slot,
|
||||
// itm_from ? itm_from->GetID() : 0,
|
||||
// mi->to_slot,
|
||||
// itm_to ? itm_to->GetID() : 0,
|
||||
// casting_spell_id);
|
||||
// database.SetMQDetectionFlag(AccountName(), GetName(), detect, zone->GetShortName());
|
||||
// safe_delete_array(detect);
|
||||
// Kick(); // Kick client to prevent client and server from getting out-of-sync inventory slots
|
||||
// return;
|
||||
// }
|
||||
//}
|
||||
//
|
||||
//// Illegal bagslot usage checks. Currently, user only receives a message if this check is triggered.
|
||||
//bool mi_hack = false;
|
||||
//
|
||||
//if (mi->from_slot >= EmuConstants::GENERAL_BAGS_BEGIN && mi->from_slot <= EmuConstants::CURSOR_BAG_END) {
|
||||
// if (mi->from_slot >= EmuConstants::CURSOR_BAG_BEGIN) { mi_hack = true; }
|
||||
// else {
|
||||
// int16 from_parent = m_inv.CalcSlotId(mi->from_slot);
|
||||
// if (!m_inv[from_parent]) { mi_hack = true; }
|
||||
// else if (!m_inv[from_parent]->IsType(ItemClassContainer)) { mi_hack = true; }
|
||||
// else if (m_inv.CalcBagIdx(mi->from_slot) >= m_inv[from_parent]->GetItem()->BagSlots) { mi_hack = true; }
|
||||
// }
|
||||
//}
|
||||
//
|
||||
//if (mi->to_slot >= EmuConstants::GENERAL_BAGS_BEGIN && mi->to_slot <= EmuConstants::CURSOR_BAG_END) {
|
||||
// if (mi->to_slot >= EmuConstants::CURSOR_BAG_BEGIN) { mi_hack = true; }
|
||||
// else {
|
||||
// int16 to_parent = m_inv.CalcSlotId(mi->to_slot);
|
||||
// if (!m_inv[to_parent]) { mi_hack = true; }
|
||||
// else if (!m_inv[to_parent]->IsType(ItemClassContainer)) { mi_hack = true; }
|
||||
// else if (m_inv.CalcBagIdx(mi->to_slot) >= m_inv[to_parent]->GetItem()->BagSlots) { mi_hack = true; }
|
||||
// }
|
||||
//}
|
||||
//
|
||||
//if (mi_hack) { Message(15, "Caution: Illegal use of inaccessible bag slots!"); }
|
||||
//
|
||||
//if (!SwapItem(mi) && IsValidSlot(mi->from_slot) && IsValidSlot(mi->to_slot)) {
|
||||
// SwapItemResync(mi);
|
||||
//
|
||||
// bool error = false;
|
||||
// InterrogateInventory(this, false, true, false, error, false);
|
||||
// if (error)
|
||||
// InterrogateInventory(this, true, false, true, error);
|
||||
//}
|
||||
//
|
||||
//return;
|
||||
EQEmu::InventorySlot src(mi->from_type, mi->from_slot, mi->from_bag_slot, mi->from_aug_slot);
|
||||
EQEmu::InventorySlot dest(mi->to_type, mi->to_slot, mi->to_bag_slot, mi->to_aug_slot);
|
||||
if(!SwapItem(src, dest, mi->number_in_stack)) {
|
||||
//Send Resync Here
|
||||
}
|
||||
}
|
||||
|
||||
void Client::Handle_OP_OpenContainer(const EQApplicationPacket *app)
|
||||
|
||||
@ -61,7 +61,7 @@ static uint32 MaxBankedRaidLeadershipPoints(int Level)
|
||||
|
||||
void Client::AddEXP(uint32 in_add_exp, uint8 conlevel, bool resexp) {
|
||||
|
||||
this->EVENT_ITEM_ScriptStopReturn();
|
||||
ItemScriptStopReturn();
|
||||
|
||||
uint32 add_exp = in_add_exp;
|
||||
|
||||
|
||||
@ -18,8 +18,8 @@
|
||||
|
||||
#include "../common/global_define.h"
|
||||
#include "../common/eqemu_logsys.h"
|
||||
|
||||
#include "../common/string_util.h"
|
||||
#include "../common/data_verification.h"
|
||||
#include "quest_parser_collection.h"
|
||||
#include "worldserver.h"
|
||||
#include "zonedb.h"
|
||||
@ -191,7 +191,7 @@ bool Client::CheckLoreConflict(const ItemData* item)
|
||||
}
|
||||
|
||||
bool Client::SummonItem(uint32 item_id, int16 charges, uint32 aug1, uint32 aug2, uint32 aug3, uint32 aug4, uint32 aug5, uint32 aug6, bool attuned, uint16 to_slot, uint32 ornament_icon, uint32 ornament_idfile, uint32 ornament_hero_model) {
|
||||
this->EVENT_ITEM_ScriptStopReturn();
|
||||
ItemScriptStopReturn();
|
||||
|
||||
// TODO: update calling methods and script apis to handle a failure return
|
||||
|
||||
@ -3092,3 +3092,74 @@ std::string InventoryOld::GetCustomItemData(int16 slot_id, std::string identifie
|
||||
}
|
||||
return "";
|
||||
}
|
||||
|
||||
//New Inventory
|
||||
bool Client::SwapItem(const EQEmu::InventorySlot &src, const EQEmu::InventorySlot &dest, int number_in_stack) {
|
||||
|
||||
if (spellend_timer.Enabled() && casting_spell_id && !IsBardSong(casting_spell_id))
|
||||
{
|
||||
if(src != dest && !src.IsCursor() && src.IsValid() && dest.IsValid()) {
|
||||
auto i_src = m_inventory.Get(src);
|
||||
auto i_dest = m_inventory.Get(dest);
|
||||
std::string detect = StringFormat("Player issued a move item from %s (item id %u) to %s (item id %u) while casting %u.",
|
||||
src.ToString().c_str(),
|
||||
i_src ? i_src->GetItem()->ID : 0,
|
||||
dest.ToString().c_str(),
|
||||
i_dest ? i_dest->GetItem()->ID : 0,
|
||||
casting_spell_id);
|
||||
database.SetMQDetectionFlag(AccountName(), GetName(), detect.c_str(), zone->GetShortName());
|
||||
Kick();
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
auto i_src = m_inventory.Get(src);
|
||||
auto i_dest = m_inventory.Get(dest);
|
||||
|
||||
if(dest.IsEquipment() && !CanEquipItem(i_dest, dest)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
printf("Equip check passes %s -> %s\n", src.ToString().c_str(), dest.ToString().c_str());
|
||||
|
||||
bool res = m_inventory.Swap(src, dest, number_in_stack);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Client::CanEquipItem(std::shared_ptr<EQEmu::ItemInstance> inst, const EQEmu::InventorySlot &slot) {
|
||||
if(!inst) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if(slot.Type() != 0) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if(!EQEmu::ValueWithin(slot.Slot(), EQEmu::PersonalSlotCharm, EQEmu::PersonalSlotAmmo)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
auto item = inst->GetItem();
|
||||
//check slot
|
||||
|
||||
int use_slot = -1;
|
||||
if(slot.Slot() == EQEmu::PersonalSlotPowerSource) {
|
||||
use_slot = EQEmu::PersonalSlotAmmo;
|
||||
}
|
||||
else if(slot.Slot() == EQEmu::PersonalSlotAmmo) {
|
||||
use_slot = EQEmu::PersonalSlotPowerSource;
|
||||
} else {
|
||||
use_slot = slot.Slot();
|
||||
}
|
||||
|
||||
if(!(item->Slots & (1 << use_slot))) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if(!item->IsEquipable(GetBaseRace(), GetBaseClass())) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@ -923,7 +923,7 @@ void Client::FinishTrade(Mob* tradingWith, bool finalizer, void* event_entry, st
|
||||
if(!tradingWith->IsMoving())
|
||||
tradingWith->FaceTarget(this);
|
||||
|
||||
this->EVENT_ITEM_ScriptStopReturn();
|
||||
ItemScriptStopReturn();
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user