[REQ] Fegyver/Vért áthelyezése inventoryban 'kockánként'

Indította whadez, 2017-09-19, 21:17:08

2017-09-19, 21:17:08 Utolsó szerkesztés: 2017-09-21, 20:27:57 Szerző: whadez
Nem nagyom vagyok vele tisztába hogy ezt hogyan lehetne értelmesen megfogalmazni, úgy hogy megpróbálom elmagyarázni hogy mit szeretnék elérni, avagy hogy milyen rendszert keresek.

Tegyük fel van 1x4 férőhelyem:



O - Szabad
X - Foglalt


A Triton kard az alsó 2 kockába van, tehát:
O
O
X
X


Én viszont a Tritont EGGYEL fentebb szeretném tenni hogy így nézen ki:
O
X
X
O


Viszont nem engedi, csak ha kettővel teszem fel, vagy le:
X
X
O
O


Olyan módosítást keresek ami lehetővé teszi hogy a fegyvereket / vérteket 'kockánként' tudjam fel/le helyezni, és ne kelljen mindenáron (2) avagy (3) [pallós esetén] szabad férőhelyemnek lennie. A szerverek javarészén ez már megvalósításra került, úgy hogy gondolom van már róla téma valahol, csak nem tudom hogyan keressek rá. :D

inb4 félreértés: Nem azt akarom hogy a fegyverek/vértek egy slotot foglaljanak, hanem hogy slotonként tudjam őket helyezni fel/le.

Erre lenne szükségem egész pontosan (GIF):
https://i.gyazo.com/857ed11019c40587a73d0672994284e0.mp4

Az én problémám (GIF):
https://i.gyazo.com/20879c235d7ad8f7dbd5fabea4567f7c.mp4

Ály dont nó for suör: GetEmptyInventory
Talán ő a hibás, ugyanis mikor pakolnád át, megnézi h az adott cella üres-e, ha nagyobb a cucc mérete 1-nél, márpedig ez 2-es, ezért megnézi a slot alatti mezőt is h elfér-e, és mivel ugyanazt akarod mozgatni, ezért az még ottmarad 1-gyel alatta, így "nem fér" el oda.
Tehát ki kell szűrni, hogy ha talál foglalt helyet, akkor megvizsgálod h egyezik-e a mozgatandó tárggyal és akkor átpakoltatod vele.
Kicsit lehet nyers vót, de remélem érthető.

Vagy a szerveroldalon a size-t át írja 1-re?

Igaz akkor meg egybe fog folyni

2017-09-19, 22:44:37 #3 Utolsó szerkesztés: 2017-09-19, 22:50:24 Szerző: whadez
A switchen belül az INVENTORY részhez kéne hozzáírnom, viszont nem tudom az általad leírt algoritmust levezetni programkódba.

Ha jól értelmezem:
bool CHARACTER::IsEmptyItemGrid(TItemPos Cell, BYTE bSize, int iExceptionCell)
// Cell = INVENTORY
// bSize = Slot amin az adott item van JELENLEG (?)
// iExceptionCell  = A slot ahova tenni akarom (?)

int itemvar = GetItem(bSize);
if(itemvar->GetType()==ITEM_WEAPON) { // Hozzáírnám a vértet még.
// 5*9-es méretű az inventorym, valamilyen függvényt létrehoznék rá hogy adja meg a feletti lévő cellát
// Lekérdezem hogy a cella megegyezik a kiválasztott tárggyal egy ternary operator-al return boolean ?
}


Esetleg rátudnál vezetni konkrétabban? :D


bool CHARACTER::IsEmptyItemGrid(TItemPos Cell, BYTE bSize, int iExceptionCell) const
{
switch (Cell.window_type)
{
case INVENTORY:
{
int bCell = Cell.cell;

// bItemCellŔş 0ŔĚ falseŔÓŔ» łŞĹ¸ł»±â Ŕ§ÇŘ + 1 ÇŘĽ­ Ăł¸®ÇŃ´Ů.
// µű¶óĽ­ iExceptionCellżˇ 1Ŕ» ´őÇŘ şń±łÇŃ´Ů.
++iExceptionCell;

if (Cell.IsBeltInventoryPosition())
{
LPITEM beltItem = GetWear(WEAR_BELT);

if (NULL == beltItem)
return false;

if (false == CBeltInventoryHelper::IsAvailableCell(bCell - BELT_INVENTORY_SLOT_START, beltItem->GetValue(0)))
return false;

if (m_pointsInstant.bItemGrid[bCell])
{
if (m_pointsInstant.bItemGrid[bCell] == iExceptionCell)
return true;

return false;
}

if (bSize == 1)
return true;

}
else if (bCell >= INVENTORY_MAX_NUM)
return false;

if (m_pointsInstant.bItemGrid[bCell])
{
if (m_pointsInstant.bItemGrid[bCell] == iExceptionCell)
{
if (bSize == 1)
return true;

int j = 1;
BYTE bPage = bCell / (INVENTORY_MAX_NUM / 4);

do
{
BYTE p = bCell + (5 * j);

if (p >= INVENTORY_MAX_NUM)
return false;

if (p / (INVENTORY_MAX_NUM / 4) != bPage)
return false;

if (m_pointsInstant.bItemGrid[p])
if (m_pointsInstant.bItemGrid[p] != iExceptionCell)
return false;
}
while (++j < bSize);

return true;
}
else
return false;
}

// Ĺ©±â°ˇ 1Ŕ̸é ÇŃÄ­Ŕ» Â÷ÁöÇĎ´Â °ÍŔ̹ǷΠ±×łÉ ¸®ĹĎ
if (1 == bSize)
return true;
else
{
int j = 1;
BYTE bPage = bCell / (INVENTORY_MAX_NUM / 4);

do
{
BYTE p = bCell + (5 * j);

if (p >= INVENTORY_MAX_NUM)
return false;

if (p / (INVENTORY_MAX_NUM / 4) != bPage)
return false;

if (m_pointsInstant.bItemGrid[p])
if (m_pointsInstant.bItemGrid[p] != iExceptionCell)
return false;
}
while (++j < bSize);

return true;
}
}
break;
case DRAGON_SOUL_INVENTORY:
{
WORD wCell = Cell.cell;
if (wCell >= DRAGON_SOUL_INVENTORY_MAX_NUM)
return false;

// bItemCellŔş 0ŔĚ falseŔÓŔ» łŞĹ¸ł»±â Ŕ§ÇŘ + 1 ÇŘĽ­ Ăł¸®ÇŃ´Ů.
// µű¶óĽ­ iExceptionCellżˇ 1Ŕ» ´őÇŘ şń±łÇŃ´Ů.
iExceptionCell++;

if (m_pointsInstant.wDSItemGrid[wCell])
{
if (m_pointsInstant.wDSItemGrid[wCell] == iExceptionCell)
{
if (bSize == 1)
return true;

int j = 1;

do
{
BYTE p = wCell + (DRAGON_SOUL_BOX_COLUMN_NUM * j);

if (p >= DRAGON_SOUL_INVENTORY_MAX_NUM)
return false;

if (m_pointsInstant.wDSItemGrid[p])
if (m_pointsInstant.wDSItemGrid[p] != iExceptionCell)
return false;
}
while (++j < bSize);

return true;
}
else
return false;
}

// Ĺ©±â°ˇ 1Ŕ̸é ÇŃÄ­Ŕ» Â÷ÁöÇĎ´Â °ÍŔ̹ǷΠ±×łÉ ¸®ĹĎ
if (1 == bSize)
return true;
else
{
int j = 1;

do
{
BYTE p = wCell + (DRAGON_SOUL_BOX_COLUMN_NUM * j);

if (p >= DRAGON_SOUL_INVENTORY_MAX_NUM)
return false;

if (m_pointsInstant.bItemGrid[p])
if (m_pointsInstant.wDSItemGrid[p] != iExceptionCell)
return false;
}
while (++j < bSize);

return true;
}
}
}
}

int CHARACTER::GetEmptyInventory(BYTE size) const
{
for ( int i = 0; i < INVENTORY_MAX_NUM; ++i)
if (IsEmptyItemGrid(TItemPos (INVENTORY, i), size))
return i;
return -1;
}

Most kicsit le vagyok fáradva ehhez, majd később, ha addig nem írja le vki más.


Idézetet írta: Distraught Dátum 2017-09-20, 11:33:40
https://www.elitepvpers.com/forum/metin2-pserver-guides-strategies/4256251-c-check-moving-item-minor-bug-fix.html
Ez volt az egyetlen ami "közel áll" ahhoz amit elszeretnék érni, valamilyen szinten az egyik része, csak tiltás helyett engedélyezni kell. Ezen felül nem tudom áthelyezni a tárgyat úgy ahogy szeretném, csak nem piros boxot ad, hanem fehéret.  :'(

a kommenteket olvasva elvileg átírta a csávó

C++ programmer at Gameloft




Szóóóóóóval arra van szükséged, ami abban a topicban van mert a két link teljesen megegyezik. GONDOLOM ÉN.  ::)

2017-09-21, 01:00:46 #9 Utolsó szerkesztés: 2017-09-21, 20:27:43 Szerző: whadez

Ezt én is kipróbáltam de nekem sem működik. :-X Később ha több időm lesz majd még részletesebben is ránézek, de én kizártnak tartom hogy ennyi elég legyen.
"Tisztelet a kivételnek! Mindig tisztelet a kivételnek!"
"KezdÅ' vagyok, ne nézz le... (:"

Nekem sem jó azzal, de majd valahogy megpróbálom működésre bírni :-X.
[spoiler]
Kód (Régi GF) Kijelölés
signed int __thiscall CGridSlotWindow::CheckMoving(int this, unsigned int a2, int a3, int a4)
{
  signed int result; // eax@3
  int v5; // ebx@4
  int *v6; // edi@4
  int v7; // esi@5
  int v8; // eax@10
  int v9; // eax@13
  int v10; // ecx@13
  int v11; // edx@14
  int v12; // eax@18

  if ( a2 >= 45 )
    a2 -= 45;
  result = 1;
  if ( *(_DWORD *)(this + 168) == 1 )
  {
    v5 = **(_DWORD **)(a4 + 20);
    v6 = *(int **)a4;
    while ( 1 )
    {
      v7 = *(_DWORD *)(a4 + 20);
      if ( !v6 || v6 != *(int **)a4 )
        sub_5DC12E();
      if ( v5 == v7 )
        break;
      if ( v6 )
      {
        v8 = *v6;
      }
      else
      {
        sub_5DC12E();
        v8 = 0;
      }
      if ( v5 == *(_DWORD *)(v8 + 20) )
        sub_5DC12E();
      v9 = *(_DWORD *)(v5 + 8);
      v10 = *(_DWORD *)(v9 + 8);
      if ( a2 != v10 )
      {
        v11 = *(_DWORD *)(v9 + 12);
        if ( (v11 || v10 != *(_DWORD *)(v9 + 4)) && a3 != v11 )
          return 0;
      }
      if ( v6 )
      {
        v12 = *v6;
      }
      else
      {
        sub_5DC12E();
        v12 = 0;
      }
      if ( v5 == *(_DWORD *)(v12 + 20) )
        sub_5DC12E();
      v5 = *(_DWORD *)v5;
    }
    result = 1;
  }
  return result;


Kód (Új GF) Kijelölés
signed int __fastcall CGridSlotWindow::CheckMoving(int a1, int a2, unsigned int a3, int a4, int a5, int a6)
{
  int v6; // edx@1
  signed int v7; // ecx@1
  unsigned int v8; // eax@2
  int v10; // ebx@8
  int *v11; // edi@8
  int v12; // esi@9
  int v13; // eax@14
  int v14; // eax@17
  int v15; // edx@18
  int v16; // ecx@19
  char v17; // zf@21
  int v18; // eax@29
  int v19; // [sp+0h] [bp-4h]@1

  v6 = a1;
  v19 = a1;
  v7 = 1;
  while ( 1 )
  {
    v8 = 45 * (4 - v7);
    if ( a3 >= v8 )
      break;
    if ( (unsigned int)++v7 >= 4 )
      goto LABEL_6;
  }
  a3 -= v8;
LABEL_6:
  if ( *(_DWORD *)(v6 + 168) != 1 )
    return 1;
  v10 = **(_DWORD **)(a5 + 20);
  v11 = *(int **)a5;
  while ( 1 )
  {
    v12 = *(_DWORD *)(a5 + 20);
    if ( !v11 || v11 != *(int **)a5 )
      ((void (*)(void))unk_6FE8F6)();
    if ( v10 == v12 )
      return 1;
    if ( v11 )
    {
      v13 = *v11;
    }
    else
    {
      ((void (*)(void))unk_6FE8F6)();
      v13 = 0;
    }
    if ( v10 == *(_DWORD *)(v13 + 20) )
      ((void (*)(void))unk_6FE8F6)();
    v14 = *(_DWORD *)(v10 + 8);
    if ( a6 == *(_DWORD *)(v19 + 164) )
    {
      v15 = *(_DWORD *)(v14 + 8);
      if ( a3 == v15 )
        goto LABEL_28;
      v16 = *(_DWORD *)(v14 + 12);
      if ( !v16 && v15 == *(_DWORD *)(v14 + 4) )
      {
        v17 = (*(_BYTE *)v14 & 1) == 0;
        goto LABEL_27;
      }
    }
    else
    {
      v16 = *(_DWORD *)(v14 + 12);
      if ( !v16 && *(_DWORD *)(v14 + 8) == *(_DWORD *)(v14 + 4) )
      {
        v17 = (*(_BYTE *)v14 & 1) == 0;
        goto LABEL_27;
      }
    }
    v17 = a4 == v16;
LABEL_27:
    if ( !v17 )
      return 0;
LABEL_28:
    if ( v11 )
    {
      v18 = *v11;
    }
    else
    {
      ((void (*)(void))unk_6FE8F6)();
      v18 = 0;
    }
    if ( v10 == *(_DWORD *)(v18 + 20) )
      ((void (*)(void))unk_6FE8F6)();
    v10 = *(_DWORD *)v10;
  }
}
[/spoiler]


Na, tessék keresni hibát benne, én nem találtam még.
[spoiler]BOOL CGridSlotWindow::CheckMoving(DWORD dwSlotNumber, DWORD dwItemIndex, const std::list<TSlot*> & c_rSlotList)
{
if (m_dwSlotStyle != SLOT_STYLE_PICK_UP)
return TRUE;

WORD wCellMaxPerPage = m_SlotVector.size();
while (dwSlotNumber >= wCellMaxPerPage)
dwSlotNumber -= wCellMaxPerPage;

for (std::list<TSlot*>::const_iterator itor = c_rSlotList.begin(); itor != c_rSlotList.end(); ++itor)
{
TSlot* pSlot = *itor;
if (dwSlotNumber == pSlot->dwSlotNumber && itor == c_rSlotList.begin())
return TRUE;

if (dwSlotNumber != pSlot->dwCenterSlotNumber)
{
if (c_rSlotList.size() == 2)
{
std::list<TSlot*>::const_iterator it = c_rSlotList.begin();
std::advance(it, 1);
if (0 != pSlot->dwItemIndex && 0 != (*it)->dwItemIndex)
return FALSE;
}
if (c_rSlotList.size() == 3)
{
std::list<TSlot*>::const_iterator it = c_rSlotList.begin();
std::advance(it, 1);
if (0 != pSlot->dwItemIndex && 0 != (*it)->dwItemIndex)
return FALSE;
else
{
std::advance(it, 1);
if (0 != pSlot->dwItemIndex && 0 != (*it)->dwItemIndex)
return FALSE;
}
}

if (0 != pSlot->dwItemIndex || pSlot->dwCenterSlotNumber != pSlot->dwSlotNumber)
if (dwItemIndex != pSlot->dwItemIndex)
return FALSE;
else if (dwItemIndex != pSlot->dwItemIndex)
return FALSE;
}
}

return TRUE;
}
[/spoiler]

Idézetet írta: [VIP]P3NG3R Dátum 2017-09-24, 15:44:08
Na, tessék keresni hibát benne, én nem találtam még.
[spoiler]BOOL CGridSlotWindow::CheckMoving(DWORD dwSlotNumber, DWORD dwItemIndex, const std::list<TSlot*> & c_rSlotList)
{
if (m_dwSlotStyle != SLOT_STYLE_PICK_UP)
return TRUE;

WORD wCellMaxPerPage = m_SlotVector.size();
while (dwSlotNumber >= wCellMaxPerPage)
dwSlotNumber -= wCellMaxPerPage;

for (std::list<TSlot*>::const_iterator itor = c_rSlotList.begin(); itor != c_rSlotList.end(); ++itor)
{
TSlot* pSlot = *itor;
if (dwSlotNumber == pSlot->dwSlotNumber && itor == c_rSlotList.begin())
return TRUE;

if (dwSlotNumber != pSlot->dwCenterSlotNumber)
{
if (c_rSlotList.size() == 2)
{
std::list<TSlot*>::const_iterator it = c_rSlotList.begin();
std::advance(it, 1);
if (0 != pSlot->dwItemIndex && 0 != (*it)->dwItemIndex)
return FALSE;
}
if (c_rSlotList.size() == 3)
{
std::list<TSlot*>::const_iterator it = c_rSlotList.begin();
std::advance(it, 1);
if (0 != pSlot->dwItemIndex && 0 != (*it)->dwItemIndex)
return FALSE;
else
{
std::advance(it, 1);
if (0 != pSlot->dwItemIndex && 0 != (*it)->dwItemIndex)
return FALSE;
}
}

if (0 != pSlot->dwItemIndex || pSlot->dwCenterSlotNumber != pSlot->dwSlotNumber)
if (dwItemIndex != pSlot->dwItemIndex)
return FALSE;
else if (dwItemIndex != pSlot->dwItemIndex)
return FALSE;
}
}

return TRUE;
}
[/spoiler]

Beraktam kíváncsiságból, hát a leltárban a tárgyakat lefelé tudom kockánként vinni, de felfelé kockánként nem.

Az első leltárban alapból is lehet, próbáld ki a többinél is.
"Tisztelet a kivételnek! Mindig tisztelet a kivételnek!"
"KezdÅ' vagyok, ne nézz le... (:"

Arra kért(ek) bizonyos személy(ek) aki(ke)t nem nevezhetek nevén (Sztepim), hogy eme fontos üzenetet osszam meg veletek:
Ha nem látod a válaszom, valamit elrontottál:

Idézetet írta: masodikbela Dátum 2017-09-26, 20:55:23
Arra kért(ek) bizonyos személy(ek) aki(ke)t nem nevezhetek nevén (Sztepim), hogy eme fontos üzenetet osszam meg veletek:
ezt eddig is tudtuk , más valami?  ???

Hát nem úgy fest :D
A kód csak arra hivatott szolgálni, hogy piros vagy szürke legyen a háttér mozgatás közben. Azt, hogy mozduljon is a tárgy szerver oldalon is meg kell piszkálni, odáig még nem volt időm eljutni.

Értem szóval most akk az epvp-re, a türkmmo-s témákra, a csodára vagy egy másik fórumos megoldás fellépésére várunk?