summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAndrei Karas <akaras@inbox.ru>2017-04-21 04:44:53 +0300
committerAndrei Karas <akaras@inbox.ru>2017-04-21 20:37:02 +0300
commit862e8f821789014b6167f37976b80694d6d310e3 (patch)
tree7c4d77a370f4da3d84a649b0d10e4d0a05725e6a
parent62fa051ace7097e78134d46505070a70c08e128f (diff)
downloadmv-862e8f821789014b6167f37976b80694d6d310e3.tar.gz
mv-862e8f821789014b6167f37976b80694d6d310e3.tar.bz2
mv-862e8f821789014b6167f37976b80694d6d310e3.tar.xz
mv-862e8f821789014b6167f37976b80694d6d310e3.zip
Add item options into item and get it from server.
-rw-r--r--src/CMakeLists.txt3
-rw-r--r--src/Makefile.am3
-rw-r--r--src/const/resources/item/itemoptions.h26
-rw-r--r--src/gui/windows/tradewindow.cpp5
-rw-r--r--src/gui/windows/tradewindow.h3
-rw-r--r--src/net/ea/inventoryitem.h11
-rw-r--r--src/net/eathena/inventoryrecv.cpp58
-rw-r--r--src/net/eathena/traderecv.cpp11
-rw-r--r--src/net/eathena/vendingrecv.cpp12
-rw-r--r--src/net/tmwa/inventoryrecv.cpp2
-rw-r--r--src/net/tmwa/traderecv.cpp2
-rw-r--r--src/resources/inventory/inventory.cpp14
-rw-r--r--src/resources/inventory/inventory.h5
-rw-r--r--src/resources/item/item.cpp11
-rw-r--r--src/resources/item/item.h8
-rw-r--r--src/resources/item/itemoption.h32
-rw-r--r--src/resources/item/itemoptionslist.h100
17 files changed, 287 insertions, 19 deletions
diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt
index 5e2d15a3f..bd031ecd6 100644
--- a/src/CMakeLists.txt
+++ b/src/CMakeLists.txt
@@ -1103,6 +1103,8 @@ SET(SRCS
resources/item/item.cpp
resources/item/item.h
resources/item/itemfieldtype.h
+ resources/item/itemoption.h
+ resources/item/itemoptionslist.h
itemcolormanager.cpp
itemcolormanager.h
gui/shortcut/itemshortcut.cpp
@@ -1157,6 +1159,7 @@ SET(SRCS
resources/map/map.cpp
resources/map/map.h
const/resources/item/cards.h
+ const/resources/item/itemoptions.h
const/resources/map/map.h
resources/map/mapheights.cpp
resources/map/mapheights.h
diff --git a/src/Makefile.am b/src/Makefile.am
index 404c10e58..eff7ba47f 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -927,6 +927,8 @@ SRC = ${BASE_SRC} \
resources/item/item.cpp \
resources/item/item.h \
resources/item/itemfieldtype.h \
+ resources/item/itemoption.h \
+ resources/item/itemoptionslist.h \
itemcolormanager.cpp \
itemcolormanager.h \
gui/shortcut/itemshortcut.cpp \
@@ -1442,6 +1444,7 @@ SRC = ${BASE_SRC} \
resources/map/map.cpp \
resources/map/map.h \
const/resources/item/cards.h \
+ const/resources/item/itemoptions.h \
const/resources/map/map.h \
resources/map/mapheights.cpp \
resources/map/mapheights.h \
diff --git a/src/const/resources/item/itemoptions.h b/src/const/resources/item/itemoptions.h
new file mode 100644
index 000000000..3c028ea64
--- /dev/null
+++ b/src/const/resources/item/itemoptions.h
@@ -0,0 +1,26 @@
+/*
+ * The ManaPlus Client
+ * Copyright (C) 2011-2017 The ManaPlus Developers
+ *
+ * This file is part of The ManaPlus Client.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef CONST_RESOURCES_ITEM_ITEMOPTIONS_H
+#define CONST_RESOURCES_ITEM_ITEMOPTIONS_H
+
+#define maxItemOptions 5
+
+#endif // CONST_RESOURCES_ITEM_ITEMOPTIONS_H
diff --git a/src/gui/windows/tradewindow.cpp b/src/gui/windows/tradewindow.cpp
index 995db35eb..bab8da9c2 100644
--- a/src/gui/windows/tradewindow.cpp
+++ b/src/gui/windows/tradewindow.cpp
@@ -52,6 +52,7 @@
#include "resources/db/unitsdb.h"
#include "resources/item/item.h"
+#include "resources/item/itemoptionslist.h"
#include "net/serverfeatures.h"
#include "net/tradehandler.h"
@@ -222,6 +223,7 @@ void TradeWindow::addItem(const int id,
void TradeWindow::addItem2(const int id,
const ItemTypeT type,
const int *const cards,
+ const ItemOptionsList *const options,
const int sz,
const bool own,
const int quantity,
@@ -244,7 +246,10 @@ void TradeWindow::addItem2(const int id,
equipment,
Equipped_false);
if (slot >= 0)
+ {
inv->setCards(slot, cards, sz);
+ inv->setOptions(slot, options);
+ }
}
void TradeWindow::changeQuantity(const int index, const bool own,
diff --git a/src/gui/windows/tradewindow.h b/src/gui/windows/tradewindow.h
index 4cf062c76..6cfc89a3f 100644
--- a/src/gui/windows/tradewindow.h
+++ b/src/gui/windows/tradewindow.h
@@ -43,6 +43,8 @@ class ItemContainer;
class Label;
class TextField;
+struct ItemOptionsList;
+
/**
* Trade dialog.
*
@@ -94,6 +96,7 @@ class TradeWindow final : public Window,
void addItem2(const int id,
const ItemTypeT type,
const int *const cards,
+ const ItemOptionsList *const options,
const int sz,
const bool own,
const int quantity,
diff --git a/src/net/ea/inventoryitem.h b/src/net/ea/inventoryitem.h
index bc5611dfc..da0f63283 100644
--- a/src/net/ea/inventoryitem.h
+++ b/src/net/ea/inventoryitem.h
@@ -33,6 +33,8 @@
#include "enums/simpletypes/identified.h"
#include "enums/simpletypes/itemcolor.h"
+#include "resources/item/itemoptionslist.h"
+
#include <vector>
#include "localconsts.h"
@@ -50,6 +52,7 @@ class InventoryItem final
int id;
ItemTypeT type;
int cards[maxCards];
+ ItemOptionsList *options;
int quantity;
uint8_t refine;
ItemColor color;
@@ -62,6 +65,7 @@ class InventoryItem final
const int id0,
const ItemTypeT type0,
const int *const cards0,
+ ItemOptionsList *options0,
const int quantity0,
const uint8_t refine0,
const ItemColor color0,
@@ -72,6 +76,8 @@ class InventoryItem final
slot(slot0),
id(id0),
type(type0),
+ cards(),
+ options(ItemOptionsList::copy(options0)),
quantity(quantity0),
refine(refine0),
color(color0),
@@ -87,6 +93,11 @@ class InventoryItem final
}
A_DEFAULT_COPY(InventoryItem)
+
+ ~InventoryItem()
+ {
+ delete [] options;
+ }
};
typedef std::vector<InventoryItem> InventoryItems;
diff --git a/src/net/eathena/inventoryrecv.cpp b/src/net/eathena/inventoryrecv.cpp
index 7887cba7c..b0a79df47 100644
--- a/src/net/eathena/inventoryrecv.cpp
+++ b/src/net/eathena/inventoryrecv.cpp
@@ -54,6 +54,8 @@
#include "resources/iteminfo.h"
+#include "resources/item/itemoptionslist.h"
+
#include "utils/gettext.h"
#include "utils/stringutils.h"
@@ -156,14 +158,16 @@ void InventoryRecv::processPlayerEquipment(Net::MessageIn &msg)
msg.readInt16("equip type");
if (msg.getVersion() >= 20100629)
msg.readInt16("item sprite number");
+ ItemOptionsList *options = nullptr;
if (msg.getVersion() >= 20150226)
{
- msg.readUInt8("option count");
+ options = new ItemOptionsList(msg.readUInt8("option count"));
for (int f = 0; f < 5; f ++)
{
- msg.readInt16("option index");
- msg.readInt16("option value");
+ const uint16_t idx = msg.readInt16("option index");
+ const uint16_t val = msg.readInt16("option value");
msg.readUInt8("option param");
+ options->add(idx, val);
}
}
ItemFlags flags;
@@ -185,7 +189,9 @@ void InventoryRecv::processPlayerEquipment(Net::MessageIn &msg)
Equipm_true,
Equipped_false);
inventory->setCards(index, cards, 4);
+ inventory->setOptions(index, options);
}
+ delete options;
if (equipType)
{
@@ -230,13 +236,16 @@ void InventoryRecv::processPlayerInventoryAdd(Net::MessageIn &msg)
msg.readInt32("hire expire date");
if (msg.getVersion() >= 20071002)
msg.readInt16("bind on equip");
+ ItemOptionsList *options = nullptr;
if (msg.getVersion() >= 20150226)
{
+ options = new ItemOptionsList;
for (int f = 0; f < 5; f ++)
{
- msg.readInt16("option index");
- msg.readInt16("option value");
+ const uint16_t idx = msg.readInt16("option index");
+ const uint16_t val = msg.readInt16("option value");
msg.readUInt8("option param");
+ options->add(idx, val);
}
}
@@ -341,9 +350,11 @@ void InventoryRecv::processPlayerInventoryAdd(Net::MessageIn &msg)
fromBool(equipType, Equipm),
Equipped_false);
inventory->setCards(index, cards, 4);
+ inventory->setOptions(index, options);
}
ArrowsListener::distributeEvent();
}
+ delete options;
BLOCK_END("InventoryRecv::processPlayerInventoryAdd")
}
@@ -492,6 +503,7 @@ void InventoryRecv::processPlayerStorage(Net::MessageIn &msg)
itemId,
itemType,
cards,
+ nullptr,
amount,
0,
ItemColorManager::getColorFromCards(&cards[0]),
@@ -685,14 +697,16 @@ void InventoryRecv::processPlayerStorageEquip(Net::MessageIn &msg)
msg.readInt16("bind on equip");
if (msg.getVersion() >= 20100629)
msg.readInt16("sprite");
+ ItemOptionsList *options = nullptr;
if (msg.getVersion() >= 20150226)
{
- msg.readUInt8("option count");
+ options = new ItemOptionsList(msg.readUInt8("option count"));
for (int f = 0; f < 5; f ++)
{
- msg.readInt16("option index");
- msg.readInt16("option value");
+ const uint16_t idx = msg.readInt16("option index");
+ const uint16_t val = msg.readInt16("option value");
msg.readUInt8("option param");
+ options->add(idx, val);
}
}
@@ -707,6 +721,7 @@ void InventoryRecv::processPlayerStorageEquip(Net::MessageIn &msg)
itemId,
itemType,
cards,
+ options,
amount,
refine,
ItemColorManager::getColorFromCards(&cards[0]),
@@ -736,13 +751,16 @@ void InventoryRecv::processPlayerStorageAdd(Net::MessageIn &msg)
int cards[maxCards];
for (int f = 0; f < maxCards; f++)
cards[f] = msg.readUInt16("card");
+ ItemOptionsList *options = nullptr;
if (msg.getVersion() >= 20150226)
{
+ options = new ItemOptionsList;
for (int f = 0; f < 5; f ++)
{
- msg.readInt16("option index");
- msg.readInt16("option value");
+ const uint16_t idx = msg.readInt16("option index");
+ const uint16_t val = msg.readInt16("option value");
msg.readUInt8("option param");
+ options->add(idx, val);
}
}
@@ -768,6 +786,7 @@ void InventoryRecv::processPlayerStorageAdd(Net::MessageIn &msg)
Equipm_false,
Equipped_false);
Ea::InventoryRecv::mStorage->setCards(index, cards, 4);
+ Ea::InventoryRecv::mStorage->setOptions(index, options);
}
}
BLOCK_END("InventoryRecv::processPlayerStorageAdd")
@@ -942,13 +961,16 @@ void InventoryRecv::processPlayerCartAdd(Net::MessageIn &msg)
int cards[maxCards];
for (int f = 0; f < maxCards; f++)
cards[f] = msg.readUInt16("card");
+ ItemOptionsList *options = nullptr;
if (msg.getVersion() >= 20150226)
{
+ options = new ItemOptionsList;
for (int f = 0; f < 5; f ++)
{
- msg.readInt16("option index");
- msg.readInt16("option value");
+ const uint16_t idx = msg.readInt16("option index");
+ const uint16_t val = msg.readInt16("option value");
msg.readUInt8("option param");
+ options->add(idx, val);
}
}
@@ -972,6 +994,7 @@ void InventoryRecv::processPlayerCartAdd(Net::MessageIn &msg)
Equipm_false,
Equipped_false);
inventory->setCards(index, cards, 4);
+ inventory->setOptions(index, options);
}
else
{
@@ -979,6 +1002,7 @@ void InventoryRecv::processPlayerCartAdd(Net::MessageIn &msg)
itemId,
itemType,
cards,
+ options,
amount,
refine,
ItemColorManager::getColorFromCards(&cards[0]),
@@ -1039,14 +1063,16 @@ void InventoryRecv::processPlayerCartEquip(Net::MessageIn &msg)
msg.readInt16("bind on equip");
if (msg.getVersion() >= 20100629)
msg.readInt16("sprite");
+ ItemOptionsList *options = nullptr;
if (msg.getVersion() >= 20150226)
{
- msg.readUInt8("option count");
+ options = new ItemOptionsList(msg.readUInt8("option count"));
for (int f = 0; f < 5; f ++)
{
- msg.readInt16("option index");
- msg.readInt16("option value");
+ const uint16_t idx = msg.readInt16("option index");
+ const uint16_t val = msg.readInt16("option value");
msg.readUInt8("option param");
+ options->add(idx, val);
}
}
ItemFlags flags;
@@ -1059,6 +1085,7 @@ void InventoryRecv::processPlayerCartEquip(Net::MessageIn &msg)
itemId,
itemType,
cards,
+ options,
amount,
refine,
ItemColorManager::getColorFromCards(&cards[0]),
@@ -1122,6 +1149,7 @@ void InventoryRecv::processPlayerCartItems(Net::MessageIn &msg)
itemId,
itemType,
cards,
+ nullptr,
amount,
0,
ItemColorManager::getColorFromCards(&cards[0]),
diff --git a/src/net/eathena/traderecv.cpp b/src/net/eathena/traderecv.cpp
index 03dcf62a6..2dcacc609 100644
--- a/src/net/eathena/traderecv.cpp
+++ b/src/net/eathena/traderecv.cpp
@@ -38,6 +38,7 @@
#include "resources/inventory/inventory.h"
#include "resources/item/item.h"
+#include "resources/item/itemoptionslist.h"
#include "debug.h"
@@ -87,13 +88,16 @@ void TradeRecv::processTradeItemAdd(Net::MessageIn &msg)
int cards[maxCards];
for (int f = 0; f < maxCards; f++)
cards[f] = msg.readUInt16("card");
+ ItemOptionsList *options = nullptr;
if (msg.getVersion() >= 20150226)
{
+ options = new ItemOptionsList;
for (int f = 0; f < 5; f ++)
{
- msg.readInt16("option index");
- msg.readInt16("option value");
+ const uint16_t idx = msg.readInt16("option index");
+ const uint16_t val = msg.readInt16("option value");
msg.readUInt8("option param");
+ options->add(idx, val);
}
}
@@ -108,6 +112,7 @@ void TradeRecv::processTradeItemAdd(Net::MessageIn &msg)
tradeWindow->addItem2(type,
itemType,
cards,
+ options,
4,
false,
amount,
@@ -119,6 +124,7 @@ void TradeRecv::processTradeItemAdd(Net::MessageIn &msg)
Equipm_false);
}
}
+ delete options;
}
void TradeRecv::processTradeItemAddResponse(Net::MessageIn &msg)
@@ -139,6 +145,7 @@ void TradeRecv::processTradeItemAddResponse(Net::MessageIn &msg)
tradeWindow->addItem2(item->getId(),
item->getType(),
item->getCards(),
+ item->getOptions(),
4,
true,
mQuantity,
diff --git a/src/net/eathena/vendingrecv.cpp b/src/net/eathena/vendingrecv.cpp
index 119e5ffa9..bf0cd20eb 100644
--- a/src/net/eathena/vendingrecv.cpp
+++ b/src/net/eathena/vendingrecv.cpp
@@ -48,6 +48,7 @@
#include "resources/inventory/inventory.h"
+#include "resources/item/itemoptionslist.h"
#include "resources/item/shopitem.h"
#include "utils/gettext.h"
@@ -125,13 +126,16 @@ void VendingRecv::processItemsList(Net::MessageIn &msg)
msg.readUInt8("refine");
for (int d = 0; d < maxCards; d ++)
cards[d] = msg.readUInt16("card");
+ ItemOptionsList *options = nullptr;
if (msg.getVersion() >= 20150226)
{
+ options = new ItemOptionsList;
for (int d = 0; d < 5; d ++)
{
- msg.readInt16("option index");
- msg.readInt16("option value");
+ const uint16_t idx = msg.readInt16("option index");
+ const uint16_t val = msg.readInt16("option value");
msg.readUInt8("option param");
+ options->add(idx, val);
}
}
@@ -139,7 +143,11 @@ void VendingRecv::processItemsList(Net::MessageIn &msg)
ShopItem *const item = mBuyDialog->addItem(itemId, type,
color, amount, value);
if (item)
+ {
item->setInvIndex(index);
+ item->setOptions(options);
+ }
+ delete options;
}
mBuyDialog->sort();
}
diff --git a/src/net/tmwa/inventoryrecv.cpp b/src/net/tmwa/inventoryrecv.cpp
index 9be77c993..974fd40c8 100644
--- a/src/net/tmwa/inventoryrecv.cpp
+++ b/src/net/tmwa/inventoryrecv.cpp
@@ -362,6 +362,7 @@ void InventoryRecv::processPlayerStorage(Net::MessageIn &msg)
itemId,
itemType,
cards,
+ nullptr,
amount,
0,
ItemColor_one,
@@ -448,6 +449,7 @@ void InventoryRecv::processPlayerStorageEquip(Net::MessageIn &msg)
itemId,
itemType,
cards,
+ nullptr,
amount,
refine,
ItemColor_one,
diff --git a/src/net/tmwa/traderecv.cpp b/src/net/tmwa/traderecv.cpp
index a737845fe..a8233ef50 100644
--- a/src/net/tmwa/traderecv.cpp
+++ b/src/net/tmwa/traderecv.cpp
@@ -79,6 +79,7 @@ void TradeRecv::processTradeItemAdd(Net::MessageIn &msg)
tradeWindow->addItem2(type,
ItemType::Unknown,
cards,
+ nullptr,
4,
false,
amount,
@@ -118,6 +119,7 @@ void TradeRecv::processTradeItemAddResponse(Net::MessageIn &msg)
tradeWindow->addItem2(item->getId(),
item->getType(),
item->getCards(),
+ nullptr,
4,
true,
quantity,
diff --git a/src/resources/inventory/inventory.cpp b/src/resources/inventory/inventory.cpp
index 0f34ea977..ddc9acc1a 100644
--- a/src/resources/inventory/inventory.cpp
+++ b/src/resources/inventory/inventory.cpp
@@ -31,6 +31,7 @@
#include "resources/iteminfo.h"
#include "resources/item/item.h"
+#include "resources/item/itemoptionslist.h"
#include "listeners/inventorylistener.h"
@@ -204,6 +205,19 @@ void Inventory::setCards(const int index,
item1->setCards(cards, size);
}
+void Inventory::setOptions(const int index,
+ const ItemOptionsList *const options)
+{
+ if (index < 0 || index >= CAST_S32(mSize))
+ {
+ logger->log("Warning: invalid inventory index: %d", index);
+ return;
+ }
+ Item *const item1 = mItems[index];
+ if (item1)
+ item1->setOptions(options);
+}
+
void Inventory::clear()
{
for (unsigned i = 0; i < mSize; i++)
diff --git a/src/resources/inventory/inventory.h b/src/resources/inventory/inventory.h
index f4d275eae..5180e49e1 100644
--- a/src/resources/inventory/inventory.h
+++ b/src/resources/inventory/inventory.h
@@ -47,6 +47,8 @@
class InventoryListener;
class Item;
+struct ItemOptionsList;
+
class Inventory notfinal
{
public:
@@ -121,6 +123,9 @@ class Inventory notfinal
const int *const cards,
const int size) const;
+ void setOptions(const int index,
+ const ItemOptionsList *const options);
+
void moveItem(const int index1,
const int index2);
diff --git a/src/resources/item/item.cpp b/src/resources/item/item.cpp
index d738ca0e3..bc6614e52 100644
--- a/src/resources/item/item.cpp
+++ b/src/resources/item/item.cpp
@@ -30,10 +30,14 @@
#include "resources/iteminfo.h"
+#include "resources/item/itemoptionslist.h"
+
#include "resources/loaders/imageloader.h"
#include "net/serverfeatures.h"
+#include "utils/delete2.h"
+
#include "debug.h"
DragDrop dragDrop(nullptr, DragDropSource::Empty);
@@ -56,6 +60,7 @@ Item::Item(const int id,
mDescription(),
mTags(),
mCards(),
+ mOptions(nullptr),
mRefine(refine),
mInvIndex(0),
mType(type),
@@ -78,6 +83,7 @@ Item::~Item()
mImage->decRef();
mImage = nullptr;
}
+ delete2(mOptions);
dragDrop.clearItem(this);
}
@@ -176,6 +182,11 @@ void Item::addCard(const int card)
}
}
+void Item::setOptions(const ItemOptionsList *const options)
+{
+ mOptions = ItemOptionsList::copy(options);
+}
+
void Item::updateColor()
{
if (serverFeatures && serverFeatures->haveItemColors())
diff --git a/src/resources/item/item.h b/src/resources/item/item.h
index 2a638f68a..f1712d26a 100644
--- a/src/resources/item/item.h
+++ b/src/resources/item/item.h
@@ -40,6 +40,8 @@
class Image;
+struct ItemOptionsList;
+
/**
* Represents one or more instances of a certain item type.
*/
@@ -211,6 +213,11 @@ class Item notfinal
const int *getCards() const noexcept2 A_WARN_UNUSED
{ return mCards; }
+ void setOptions(const ItemOptionsList *const options);
+
+ const ItemOptionsList *getOptions() const noexcept2 A_WARN_UNUSED
+ { return mOptions; }
+
void setType(const ItemTypeT type) noexcept2
{ mType = type; }
@@ -245,6 +252,7 @@ class Item notfinal
std::string mDescription;
std::map <int, int> mTags;
int mCards[maxCards];
+ const ItemOptionsList *mOptions;
uint8_t mRefine; /**< Item refine level. */
int mInvIndex; /**< Inventory index. */
ItemTypeT mType; /**< Item type. */
diff --git a/src/resources/item/itemoption.h b/src/resources/item/itemoption.h
new file mode 100644
index 000000000..9d3745f28
--- /dev/null
+++ b/src/resources/item/itemoption.h
@@ -0,0 +1,32 @@
+/*
+ * The ManaPlus Client
+ * Copyright (C) 2011-2017 The ManaPlus Developers
+ *
+ * This file is part of The ManaPlus Client.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef RESOURCES_ITEM_ITEMOPTION_H
+#define RESOURCES_ITEM_ITEMOPTION_H
+
+#include "localconsts.h"
+
+struct ItemOption final
+{
+ uint16_t index;
+ int16_t value;
+};
+
+#endif // RESOURCES_ITEM_ITEMOPTION_H
diff --git a/src/resources/item/itemoptionslist.h b/src/resources/item/itemoptionslist.h
new file mode 100644
index 000000000..7bb259028
--- /dev/null
+++ b/src/resources/item/itemoptionslist.h
@@ -0,0 +1,100 @@
+/*
+ * The ManaPlus Client
+ * Copyright (C) 2004-2009 The Mana World Development Team
+ * Copyright (C) 2009-2010 The Mana Developers
+ * Copyright (C) 2011-2017 The ManaPlus Developers
+ *
+ * This file is part of The ManaPlus Client.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef RESOURCES_ITEM_ITEMOPTIONSLIST_H
+#define RESOURCES_ITEM_ITEMOPTIONSLIST_H
+
+#include "const/resources/item/itemoptions.h"
+
+#include "resources/item/itemoption.h"
+
+#include "localconsts.h"
+
+struct ItemOptionsList final
+{
+ explicit ItemOptionsList(const int amount0) :
+ amount(amount0),
+ pointer(0U)
+ {
+ options = new ItemOption[amount];
+ }
+
+ ItemOptionsList() :
+ amount(maxItemOptions),
+ pointer(0U)
+ {
+ options = new ItemOption[amount];
+ }
+
+ A_DEFAULT_COPY(ItemOptionsList)
+
+ ~ItemOptionsList()
+ {
+ delete [] options;
+ options = nullptr;
+ }
+
+ void add(const uint16_t index,
+ const uint16_t value)
+ {
+ if (pointer >= amount)
+ return;
+ options[pointer].index = index;
+ options[pointer].value = value;
+ pointer ++;
+ }
+
+ static ItemOptionsList *copy(const ItemOptionsList *const options0)
+ {
+ if (options0 == nullptr)
+ return nullptr;
+
+ const int amount0 = options0->amount;
+ ItemOptionsList *const obj = new ItemOptionsList(amount0);
+ for (int f = 0; f < amount0; f ++)
+ {
+ obj->options[f].index = options0->options[f].index;
+ obj->options[f].value = options0->options[f].value;
+ }
+ obj->amount = options0->amount;
+ obj->pointer = options0->pointer;
+ return obj;
+ }
+
+ size_t size() const
+ {
+ if (pointer < amount)
+ return pointer;
+ return amount;
+ }
+
+ const ItemOption &get(const size_t index) const
+ {
+ return options[index];
+ }
+
+ ItemOption *options;
+ size_t amount;
+ size_t pointer;
+};
+
+#endif // RESOURCES_ITEM_ITEMOPTIONSLIST_H