Metin2 Envanterde İtem Değiş-Tokuş ( C++ )

Bildiğimiz üzere Metin2 oyununda envanter dolu olduğunda bir itemi başka bir yere taşımak gerçekten büyük problem oluyordu. Özellikle bir yere item koyacağımız zaman 3’lü yer kaplayan itemlerde çok büyük sorun yaratıyordu. 2’li yer kaplayan yerlere atmak için tek yer kaplayan itemleri farklı yere aldıktan sonra 3’lü itemi yerleştirebiliyorduk ve bu büyük zaman kaybına yol açıyordu. Artık bu sorundan kurtulabilirsiniz. Aşağıdaki gif resimde gördüğünüz gibi envanter içerisinde Metin2 Envanterde İtem Değiş-Tokuş sistemi sayesinde artık sorunsuz şekilde item yeri değiştirebileceksiniz. Hemen nasıl kurulacağı konusunda bilgi verelim!

Sistem Örneğini Görmek İçin Tıklayın. 

KURULUM

char.h dosyasını açıyoruz ve aşağıdaki kodu aratıyoruz.

bool IsEmptyItemGrid(TItemPos Cell, BYTE size, int iExceptionCell = -1) const;

Yukarıdaki kodu arattıktan sonra altına aşağıdaki kodu ekliyoruz.

bool SwapItemToItem(TItemPos srcCell, TItemPos destCell);

 

Ardından Char_item.cpp dosyasını açıyoruz ve aşağıdaki kodu aratıyoruz.

if (!IsEmptyItemGrid(DestCell, item->GetSize(), Cell.cell))
return false;

Yukarıdaki kodu aşağıdaki kod ile değiştiriyoruz.

if (!IsEmptyItemGrid(DestCell, item->GetSize(), Cell.cell))
{
if (!SwapItemToItem(Cell, DestCell))
return false;
else
return true;
}

 

Son olarak char_item.cpp dosyasında yine aşağıdaki kodu aratıyoruz.

bool CHARACTER::CanUnequipNow(const LPITEM item, const TItemPos& srcCell, const TItemPos& destCell) /*const*/

Arattığımız yukarıdaki kodun sonuna aşağıdaki kodu ekliyoruz.

 

bool CHARACTER::SwapItemToItem(TItemPos srcCell, TItemPos destCell)
{
if (!CanHandleItem())
return false;
BYTE bCell = srcCell.cell;
BYTE bDestCell = destCell.cell;
BYTE pages_count = 4;

if (srcCell.IsDragonSoulEquipPosition() || destCell.IsDragonSoulEquipPosition())
return false;

if (bCell == bDestCell)
return false;

if (srcCell.IsEquipPosition() || destCell.IsEquipPosition())
return false;
if (srcCell.window_type != INVENTORY || destCell.window_type != INVENTORY || destCell.cell >= INVENTORY_MAX_NUM)
return false;

LPITEM item1, item2;

item1 = GetInventoryItem(bCell);
item2 = GetInventoryItem(bDestCell);

if (!item1 || !item2)
return false;

if (item1 == item2)
{
sys_log(0, “[WARNING][WARNING][HACK USER!] : %s %d %d”, m_stName.c_str(), bCell, bDestCell);
return false;
}
if (item1->GetSize() == item2->GetSize())
{
BYTE bCell1 = item1->GetCell();
BYTE bCell2 = item2->GetCell();

item1->RemoveFromCharacter();
item2->RemoveFromCharacter();

item1->AddToCharacter(this, TItemPos(INVENTORY, bCell2));
item2->AddToCharacter(this, TItemPos(INVENTORY, bCell1));
}

if (item1->GetSize() > item2->GetSize())
{
BYTE bCell1 = item1->GetCell();
ChatPacket(CHAT_TYPE_INFO, “Slot %d”, bDestCell);
BYTE pPageDest = bDestCell / (INVENTORY_MAX_NUM / pages_count);
BYTE pPageDest2 = (((item1->GetSize()-1) * 5) + bDestCell) / (INVENTORY_MAX_NUM / pages_count);
if (bDestCell >= INVENTORY_MAX_NUM)
return false;
if (pPageDest != pPageDest2)
{
for (int ii = 1; ii < 4; ++ii)
{
pPageDest2 = (bDestCell + (5*(item1->GetSize()-1)) – (5 * ii)) / (INVENTORY_MAX_NUM / pages_count);
if (pPageDest == pPageDest2)
{
bDestCell = bDestCell – (5 * ii);
break;
}
}
}
if (pPageDest != pPageDest2)
return false;
item1->RemoveFromCharacter();
for (int i = 0; i < item1->GetSize(); ++i)
{
BYTE bBusyCell = bDestCell + (5 * i);
BYTE lpage = bBusyCell / (INVENTORY_MAX_NUM / pages_count);
if (lpage != pPageDest)
continue;
TItemPos busyCell(INVENTORY, bBusyCell);
LPITEM busy = GetItem(busyCell);
if (busy)
{
busy->RemoveFromCharacter();
busy->AddToCharacter(this, TItemPos(INVENTORY, bCell1 + (5 * i)));
}
}
item1->AddToCharacter(this, TItemPos(INVENTORY, bDestCell));
}

return true;
}

 

İşlemimiz tamamdır. Metin2 Envanterde İtem Değiş-Tokuş sistemi sorunsuz şekilde çalışacaktır. Sorunlarınızı yorum yaparak iletebilirsiniz. İyi oyunlar.