mirror of
https://github.com/EQEmu/Server.git
synced 2025-12-21 22:41:29 +00:00
Fix for losing 2nd and 3rd cursor items after zoning
This commit is contained in:
parent
da121137e5
commit
1d0a6bdc71
@ -1,5 +1,8 @@
|
|||||||
EQEMu Changelog (Started on Sept 24, 2003 15:50)
|
EQEMu Changelog (Started on Sept 24, 2003 15:50)
|
||||||
-------------------------------------------------------
|
-------------------------------------------------------
|
||||||
|
== 09/05/2014 ==
|
||||||
|
Uleat: Fix for cursor item loss when zoning. (Thanks to the other devs who traced and fixed the 'macro' issue!)
|
||||||
|
|
||||||
== 09/03/2014 ==
|
== 09/03/2014 ==
|
||||||
Secrets: Identified the routines needed to augment items in RoF. Currently, only Insert and Remove are supported. Swap and Destroy do not work due to missing functions related to the cursor.
|
Secrets: Identified the routines needed to augment items in RoF. Currently, only Insert and Remove are supported. Swap and Destroy do not work due to missing functions related to the cursor.
|
||||||
demonstar55: Added work around command to show numhits on your buffs (#shownumhits)
|
demonstar55: Added work around command to show numhits on your buffs (#shownumhits)
|
||||||
|
|||||||
@ -143,19 +143,22 @@ uint32 SharedDatabase::GetTotalTimeEntitledOnAccount(uint32 AccountID) {
|
|||||||
|
|
||||||
bool SharedDatabase::SaveCursor(uint32 char_id, std::list<ItemInst*>::const_iterator &start, std::list<ItemInst*>::const_iterator &end)
|
bool SharedDatabase::SaveCursor(uint32 char_id, std::list<ItemInst*>::const_iterator &start, std::list<ItemInst*>::const_iterator &end)
|
||||||
{
|
{
|
||||||
iter_queue it;
|
iter_queue it;
|
||||||
int i;
|
int i;
|
||||||
bool ret=true;
|
bool ret = true;
|
||||||
char errbuf[MYSQL_ERRMSG_SIZE];
|
char errbuf[MYSQL_ERRMSG_SIZE];
|
||||||
char* query = 0;
|
char* query = 0;
|
||||||
// Delete cursor items
|
// Delete cursor items
|
||||||
if ((ret = RunQuery(query, MakeAnyLenString(&query, "DELETE FROM inventory WHERE charid=%i AND ( (slotid >=8000 and slotid<=8999) or slotid=%i or (slotid>=%i and slotid<=%i))", char_id, MainCursor,EmuConstants::CURSOR_BAG_BEGIN,EmuConstants::CURSOR_BAG_END), errbuf))) {
|
if ((ret = RunQuery(query, MakeAnyLenString(&query, "DELETE FROM inventory WHERE charid = %i AND ((slotid >= 8000 AND slotid <= 8999) OR slotid = %i OR (slotid >= %i AND slotid <= %i))",
|
||||||
for(it=start,i=8000;it!=end;++it,i++) {
|
char_id, MainCursor, EmuConstants::CURSOR_BAG_BEGIN, EmuConstants::CURSOR_BAG_END), errbuf))) {
|
||||||
ItemInst *inst=*it;
|
|
||||||
if (!(ret=SaveInventory(char_id,inst,(i==8000) ? MainCursor : i)))
|
for (it = start, i = 8000; it != end; ++it, i++) {
|
||||||
|
ItemInst *inst = *it;
|
||||||
|
if (!(ret = SaveInventory(char_id, inst, (i == 8000) ? MainCursor : i)))
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
} else {
|
}
|
||||||
|
else {
|
||||||
std::cout << "Clearing cursor failed: " << errbuf << std::endl;
|
std::cout << "Clearing cursor failed: " << errbuf << std::endl;
|
||||||
}
|
}
|
||||||
safe_delete_array(query);
|
safe_delete_array(query);
|
||||||
|
|||||||
@ -836,8 +836,6 @@ void Client::BulkSendInventoryItems() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Where are cursor buffer items processed? They need to be validated as well... -U
|
|
||||||
|
|
||||||
bool deletenorent = database.NoRentExpired(GetName());
|
bool deletenorent = database.NoRentExpired(GetName());
|
||||||
if(deletenorent){ RemoveNoRent(false); } //client was offline for more than 30 minutes, delete no rent items
|
if(deletenorent){ RemoveNoRent(false); } //client was offline for more than 30 minutes, delete no rent items
|
||||||
|
|
||||||
|
|||||||
@ -2002,11 +2002,10 @@ bool Client::DecreaseByID(uint32 type, uint8 amt) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void Client::RemoveNoRent(bool client_update) {
|
void Client::RemoveNoRent(bool client_update) {
|
||||||
|
int16 slot_id = 0;
|
||||||
|
|
||||||
int16 slot_id;
|
// equipment
|
||||||
|
for(slot_id = EmuConstants::EQUIPMENT_BEGIN; slot_id <= EmuConstants::EQUIPMENT_END; slot_id++) {
|
||||||
// personal
|
|
||||||
for(slot_id = MAIN_BEGIN; slot_id < EmuConstants::MAP_POSSESSIONS_SIZE; slot_id++) {
|
|
||||||
const ItemInst* inst = m_inv[slot_id];
|
const ItemInst* inst = m_inv[slot_id];
|
||||||
if(inst && !inst->GetItem()->NoRent) {
|
if(inst && !inst->GetItem()->NoRent) {
|
||||||
mlog(INVENTORY__SLOTS, "NoRent Timer Lapse: Deleting %s from slot %i", inst->GetItem()->Name, slot_id);
|
mlog(INVENTORY__SLOTS, "NoRent Timer Lapse: Deleting %s from slot %i", inst->GetItem()->Name, slot_id);
|
||||||
@ -2014,12 +2013,23 @@ void Client::RemoveNoRent(bool client_update) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// general
|
||||||
|
for (slot_id = EmuConstants::GENERAL_BEGIN; slot_id <= EmuConstants::GENERAL_END; slot_id++) {
|
||||||
|
const ItemInst* inst = m_inv[slot_id];
|
||||||
|
if (inst && !inst->GetItem()->NoRent) {
|
||||||
|
mlog(INVENTORY__SLOTS, "NoRent Timer Lapse: Deleting %s from slot %i", inst->GetItem()->Name, slot_id);
|
||||||
|
DeleteItemInInventory(slot_id, 0, client_update);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// power source
|
// power source
|
||||||
|
if (m_inv[MainPowerSource]) {
|
||||||
const ItemInst* inst = m_inv[MainPowerSource];
|
const ItemInst* inst = m_inv[MainPowerSource];
|
||||||
if(inst && !inst->GetItem()->NoRent) {
|
if (inst && !inst->GetItem()->NoRent) {
|
||||||
mlog(INVENTORY__SLOTS, "NoRent Timer Lapse: Deleting %s from slot %i", inst->GetItem()->Name, MainPowerSource);
|
mlog(INVENTORY__SLOTS, "NoRent Timer Lapse: Deleting %s from slot %i", inst->GetItem()->Name, MainPowerSource);
|
||||||
DeleteItemInInventory(MainPowerSource, 0, (GetClientVersion() >= EQClientSoF) ? client_update : false); // Ti slot non-existent
|
DeleteItemInInventory(MainPowerSource, 0, (GetClientVersion() >= EQClientSoF) ? client_update : false); // Ti slot non-existent
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// containers
|
// containers
|
||||||
for(slot_id = EmuConstants::GENERAL_BAGS_BEGIN; slot_id <= EmuConstants::CURSOR_BAG_END; slot_id++) {
|
for(slot_id = EmuConstants::GENERAL_BAGS_BEGIN; slot_id <= EmuConstants::CURSOR_BAG_END; slot_id++) {
|
||||||
@ -2065,15 +2075,41 @@ void Client::RemoveNoRent(bool client_update) {
|
|||||||
DeleteItemInInventory(slot_id, 0, false); // Can't delete from client Shared Bank Container slots
|
DeleteItemInInventory(slot_id, 0, false); // Can't delete from client Shared Bank Container slots
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// cursor & limbo
|
||||||
|
if (!m_inv.CursorEmpty()) {
|
||||||
|
std::list<ItemInst*> local;
|
||||||
|
ItemInst* inst = nullptr;
|
||||||
|
|
||||||
|
while (!m_inv.CursorEmpty()) {
|
||||||
|
inst = m_inv.PopItem(MainCursor);
|
||||||
|
if (inst)
|
||||||
|
local.push_back(inst);
|
||||||
|
}
|
||||||
|
|
||||||
|
std::list<ItemInst*>::iterator iter = local.begin();
|
||||||
|
while (iter != local.end()) {
|
||||||
|
inst = *iter;
|
||||||
|
if (!inst->GetItem()->NoRent)
|
||||||
|
mlog(INVENTORY__SLOTS, "NoRent Timer Lapse: Deleting %s from `Limbo`", inst->GetItem()->Name);
|
||||||
|
else
|
||||||
|
m_inv.PushCursor(**iter);
|
||||||
|
|
||||||
|
safe_delete(*iter);
|
||||||
|
iter = local.erase(iter);
|
||||||
|
}
|
||||||
|
|
||||||
|
database.SaveCursor(this->character_id, m_inv.cursor_begin(), m_inv.cursor_end());
|
||||||
|
local.clear();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Two new methods to alleviate perpetual login desyncs
|
// Two new methods to alleviate perpetual login desyncs
|
||||||
void Client::RemoveDuplicateLore(bool client_update) {
|
void Client::RemoveDuplicateLore(bool client_update) {
|
||||||
// Split-charge stacking may be added at some point -U
|
int16 slot_id = 0;
|
||||||
int16 slot_id;
|
|
||||||
|
|
||||||
// personal
|
// equipment
|
||||||
for(slot_id = MAIN_BEGIN; slot_id < EmuConstants::MAP_POSSESSIONS_SIZE; slot_id++) {
|
for(slot_id = EmuConstants::EQUIPMENT_BEGIN; slot_id <= EmuConstants::EQUIPMENT_END; slot_id++) {
|
||||||
ItemInst* inst = m_inv.PopItem(slot_id);
|
ItemInst* inst = m_inv.PopItem(slot_id);
|
||||||
if(inst) {
|
if(inst) {
|
||||||
if(CheckLoreConflict(inst->GetItem())) {
|
if(CheckLoreConflict(inst->GetItem())) {
|
||||||
@ -2087,10 +2123,26 @@ void Client::RemoveDuplicateLore(bool client_update) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// general
|
||||||
|
for (slot_id = EmuConstants::GENERAL_BEGIN; slot_id <= EmuConstants::GENERAL_END; slot_id++) {
|
||||||
|
ItemInst* inst = m_inv.PopItem(slot_id);
|
||||||
|
if (inst) {
|
||||||
|
if (CheckLoreConflict(inst->GetItem())) {
|
||||||
|
mlog(INVENTORY__ERROR, "Lore Duplication Error: Deleting %s from slot %i", inst->GetItem()->Name, slot_id);
|
||||||
|
database.SaveInventory(character_id, nullptr, slot_id);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
m_inv.PutItem(slot_id, *inst);
|
||||||
|
}
|
||||||
|
safe_delete(inst);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// power source
|
// power source
|
||||||
|
if (m_inv[MainPowerSource]) {
|
||||||
ItemInst* inst = m_inv.PopItem(MainPowerSource);
|
ItemInst* inst = m_inv.PopItem(MainPowerSource);
|
||||||
if(inst) {
|
if (inst) {
|
||||||
if(CheckLoreConflict(inst->GetItem())) {
|
if (CheckLoreConflict(inst->GetItem())) {
|
||||||
mlog(INVENTORY__ERROR, "Lore Duplication Error: Deleting %s from slot %i", inst->GetItem()->Name, slot_id);
|
mlog(INVENTORY__ERROR, "Lore Duplication Error: Deleting %s from slot %i", inst->GetItem()->Name, slot_id);
|
||||||
database.SaveInventory(character_id, nullptr, MainPowerSource);
|
database.SaveInventory(character_id, nullptr, MainPowerSource);
|
||||||
}
|
}
|
||||||
@ -2099,6 +2151,7 @@ void Client::RemoveDuplicateLore(bool client_update) {
|
|||||||
}
|
}
|
||||||
safe_delete(inst);
|
safe_delete(inst);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// containers
|
// containers
|
||||||
for(slot_id = EmuConstants::GENERAL_BAGS_BEGIN; slot_id <= EmuConstants::CURSOR_BAG_END; slot_id++) {
|
for(slot_id = EmuConstants::GENERAL_BAGS_BEGIN; slot_id <= EmuConstants::CURSOR_BAG_END; slot_id++) {
|
||||||
@ -2146,11 +2199,55 @@ void Client::RemoveDuplicateLore(bool client_update) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Shared Bank and Shared Bank Containers are not checked due to their allowing duplicate lore items -U
|
// Shared Bank and Shared Bank Containers are not checked due to their allowing duplicate lore items -U
|
||||||
|
|
||||||
|
// cursor & limbo
|
||||||
|
if (!m_inv.CursorEmpty()) {
|
||||||
|
std::list<ItemInst*> local;
|
||||||
|
ItemInst* inst = nullptr;
|
||||||
|
|
||||||
|
while (!m_inv.CursorEmpty()) {
|
||||||
|
inst = m_inv.PopItem(MainCursor);
|
||||||
|
if (inst)
|
||||||
|
local.push_back(inst);
|
||||||
|
}
|
||||||
|
|
||||||
|
std::list<ItemInst*>::iterator iter = local.begin();
|
||||||
|
while (iter != local.end()) {
|
||||||
|
inst = *iter;
|
||||||
|
if (CheckLoreConflict(inst->GetItem())) {
|
||||||
|
mlog(INVENTORY__ERROR, "Lore Duplication Error: Deleting %s from `Limbo`", inst->GetItem()->Name);
|
||||||
|
safe_delete(*iter);
|
||||||
|
iter = local.erase(iter);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
++iter;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
iter = local.begin();
|
||||||
|
while (iter != local.end()) {
|
||||||
|
inst = *iter;
|
||||||
|
if (!inst->GetItem()->LoreFlag ||
|
||||||
|
((inst->GetItem()->LoreGroup == -1) && (m_inv.HasItem(inst->GetID(), 0, invWhereCursor) == INVALID_INDEX)) ||
|
||||||
|
(inst->GetItem()->LoreGroup && ~inst->GetItem()->LoreGroup && (m_inv.HasItemByLoreGroup(inst->GetItem()->LoreGroup, invWhereCursor) == INVALID_INDEX))) {
|
||||||
|
|
||||||
|
m_inv.PushCursor(**iter);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
mlog(INVENTORY__ERROR, "Lore Duplication Error: Deleting %s from `Limbo`", inst->GetItem()->Name);
|
||||||
|
}
|
||||||
|
|
||||||
|
safe_delete(*iter);
|
||||||
|
iter = local.erase(iter);
|
||||||
|
}
|
||||||
|
|
||||||
|
database.SaveCursor(this->character_id, m_inv.cursor_begin(), m_inv.cursor_end());
|
||||||
|
local.clear();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void Client::MoveSlotNotAllowed(bool client_update) {
|
void Client::MoveSlotNotAllowed(bool client_update) {
|
||||||
|
int16 slot_id = 0;
|
||||||
int16 slot_id;
|
|
||||||
|
|
||||||
// equipment
|
// equipment
|
||||||
for(slot_id = EmuConstants::EQUIPMENT_BEGIN; slot_id <= EmuConstants::EQUIPMENT_END; slot_id++) {
|
for(slot_id = EmuConstants::EQUIPMENT_BEGIN; slot_id <= EmuConstants::EQUIPMENT_END; slot_id++) {
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user