summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/actorsprite.cpp4
-rw-r--r--src/flooritem.cpp2
-rw-r--r--src/gui/charcreatedialog.cpp8
-rw-r--r--src/item.cpp4
-rw-r--r--src/net/manaserv/beinghandler.cpp4
-rw-r--r--src/net/manaserv/charhandler.cpp2
-rw-r--r--src/net/tmwa/beinghandler.cpp6
-rw-r--r--src/net/tmwa/charserverhandler.cpp2
-rw-r--r--src/resources/colordb.cpp74
-rw-r--r--src/resources/colordb.h32
-rw-r--r--src/resources/itemdb.cpp2
-rw-r--r--src/resources/iteminfo.cpp36
-rw-r--r--src/resources/iteminfo.h12
-rw-r--r--src/utils/stringutils.cpp41
-rw-r--r--src/utils/stringutils.h5
15 files changed, 186 insertions, 48 deletions
diff --git a/src/actorsprite.cpp b/src/actorsprite.cpp
index 4188ff224..686c871e7 100644
--- a/src/actorsprite.cpp
+++ b/src/actorsprite.cpp
@@ -312,7 +312,7 @@ void ActorSprite::setupSpriteDisplay(const SpriteDisplay &display,
it != it_end; ++it)
{
std::string file = "graphics/sprites/"
- + combineDye((*it)->sprite, color);
+ + combineDye2((*it)->sprite, color);
int variant = (*it)->variant;
addSprite(AnimatedSprite::load(file, variant));
@@ -339,7 +339,7 @@ void ActorSprite::setupSpriteDisplay(const SpriteDisplay &display,
imagePath = "graphics/items/" + display.floor;
break;
}
- imagePath = combineDye(imagePath, color);
+ imagePath = combineDye2(imagePath, color);
Image *img = resman->getImage(imagePath);
diff --git a/src/flooritem.cpp b/src/flooritem.cpp
index 700d9ed25..740daf387 100644
--- a/src/flooritem.cpp
+++ b/src/flooritem.cpp
@@ -72,7 +72,7 @@ FloorItem::FloorItem(int id,
}
ItemInfo info = ItemDB::get(itemId);
- setupSpriteDisplay(info.getDisplay(), true, 1, info.getDyeString(mColor));
+ setupSpriteDisplay(info.getDisplay(), true, 1, info.getDyeColorsString(mColor));
}
const ItemInfo &FloorItem::getInfo() const
diff --git a/src/gui/charcreatedialog.cpp b/src/gui/charcreatedialog.cpp
index dff591dd9..ae4401572 100644
--- a/src/gui/charcreatedialog.cpp
+++ b/src/gui/charcreatedialog.cpp
@@ -58,7 +58,7 @@ CharCreateDialog::CharCreateDialog(CharSelectDialog *parent, int slot):
mPlayer = new Being(0, ActorSprite::PLAYER, 0, NULL);
mPlayer->setGender(GENDER_MALE);
- int numberOfHairColors = ColorDB::size();
+ int numberOfHairColors = ColorDB::getHairSize();
mHairStyle = rand() % mPlayer->getNumOfHairstyles();
mHairColor = rand() % numberOfHairColors;
@@ -364,10 +364,10 @@ void CharCreateDialog::updateHair()
if (mHairStyle < 0)
mHairStyle += Being::getNumOfHairstyles();
- mHairColor %= ColorDB::size();
+ mHairColor %= ColorDB::getHairSize();
if (mHairColor < 0)
- mHairColor += ColorDB::size();
+ mHairColor += ColorDB::getHairSize();
mPlayer->setSprite(Net::getCharHandler()->hairSprite(),
- mHairStyle * -1, ColorDB::get(mHairColor));
+ mHairStyle * -1, ColorDB::getHairColor(mHairColor));
}
diff --git a/src/item.cpp b/src/item.cpp
index 02f775834..ed0685a9d 100644
--- a/src/item.cpp
+++ b/src/item.cpp
@@ -75,7 +75,7 @@ void Item::setId(int id, unsigned char color)
SpriteDisplay display = info.getDisplay();
std::string imagePath = paths.getStringValue("itemIcons")
+ display.image;
- std::string dye = combineDye(imagePath, info.getDyeString(color));
+ std::string dye = combineDye2(imagePath, info.getDyeColorsString(color));
mImage = resman->getImage(dye);
mDrawImage = resman->getImage(dye);
@@ -106,7 +106,7 @@ Image *Item::getImage(int id, unsigned char color)
SpriteDisplay display = info.getDisplay();
std::string imagePath = "graphics/items/" + display.image;
Image *image;
- image = resman->getImage(combineDye(imagePath, info.getDyeString(color)));
+ image = resman->getImage(combineDye2(imagePath, info.getDyeColorsString(color)));
if (!image)
image = Theme::getImageFromTheme("unknown-item.png");
diff --git a/src/net/manaserv/beinghandler.cpp b/src/net/manaserv/beinghandler.cpp
index 8ba2e5967..b726bc52e 100644
--- a/src/net/manaserv/beinghandler.cpp
+++ b/src/net/manaserv/beinghandler.cpp
@@ -185,7 +185,7 @@ void BeingHandler::handleBeingEnterMessage(Net::MessageIn &msg)
being->setName(name);
}
int hs = msg.readInt8(), hc = msg.readInt8();
- being->setSprite(SPRITE_HAIR, hs * -1, ColorDB::get(hc));
+ being->setSprite(SPRITE_HAIR, hs * -1, ColorDB::getHairColor(hc));
being->setGender(msg.readInt8() == GENDER_MALE ?
GENDER_MALE : GENDER_FEMALE);
handleLooks(being, msg);
@@ -350,7 +350,7 @@ void BeingHandler::handleBeingLooksChangeMessage(Net::MessageIn &msg)
{
int style = msg.readInt16();
int color = msg.readInt16();
- being->setSprite(SPRITE_HAIR, style * -1, ColorDB::get(color));
+ being->setSprite(SPRITE_HAIR, style * -1, ColorDB::getHairColor(color));
}
}
diff --git a/src/net/manaserv/charhandler.cpp b/src/net/manaserv/charhandler.cpp
index 20dda5b70..163aad988 100644
--- a/src/net/manaserv/charhandler.cpp
+++ b/src/net/manaserv/charhandler.cpp
@@ -377,7 +377,7 @@ void CharHandler::updateCharacters()
player->setName(info.name);
player->setGender(info.gender);
player->setSprite(SPRITE_HAIR, info.hairStyle * -1,
- ColorDB::get(info.hairColor));
+ ColorDB::getHairColor(info.hairColor));
character->data.mAttributes[LEVEL] = info.level;
character->data.mAttributes[CHAR_POINTS] = info.characterPoints;
character->data.mAttributes[CORR_POINTS] = info.correctionPoints;
diff --git a/src/net/tmwa/beinghandler.cpp b/src/net/tmwa/beinghandler.cpp
index 0548a2715..b1c173df6 100644
--- a/src/net/tmwa/beinghandler.cpp
+++ b/src/net/tmwa/beinghandler.cpp
@@ -290,7 +290,7 @@ void BeingHandler::handleMessage(Net::MessageIn &msg)
? GENDER_FEMALE : GENDER_MALE);
// Set these after the gender, as the sprites may be gender-specific
dstBeing->setSprite(SPRITE_HAIR, hairStyle * -1,
- ColorDB::get(hairColor));
+ ColorDB::getHairColor(hairColor));
dstBeing->setSprite(SPRITE_BOTTOMCLOTHES, headBottom);
dstBeing->setSprite(SPRITE_TOPCLOTHES, headMid);
dstBeing->setSprite(SPRITE_HAT, headTop);
@@ -671,7 +671,7 @@ void BeingHandler::handleMessage(Net::MessageIn &msg)
player_node->imitateOutfit(dstBeing, SPRITE_TOPCLOTHES);
break;
case 6: // eAthena LOOK_HAIR_COLOR
- dstBeing->setSpriteColor(SPRITE_HAIR, ColorDB::get(id));
+ dstBeing->setSpriteColor(SPRITE_HAIR, ColorDB::getHairColor(id));
break;
case 8: // eAthena LOOK_SHIELD
if (!config.getBoolValue("hideShield"))
@@ -927,7 +927,7 @@ void BeingHandler::handleMessage(Net::MessageIn &msg)
//dstBeing->setSprite(SPRITE_MISC1, misc1);
//dstBeing->setSprite(SPRITE_MISC2, misc2);
dstBeing->setSprite(SPRITE_HAIR, hairStyle * -1,
- ColorDB::get(hairColor));
+ ColorDB::getHairColor(hairColor));
player_node->imitateOutfit(dstBeing);
diff --git a/src/net/tmwa/charserverhandler.cpp b/src/net/tmwa/charserverhandler.cpp
index 35cca6f07..daf531f04 100644
--- a/src/net/tmwa/charserverhandler.cpp
+++ b/src/net/tmwa/charserverhandler.cpp
@@ -309,7 +309,7 @@ void CharServerHandler::readPlayerData(Net::MessageIn &msg,
int topClothes = msg.readInt16();
tempPlayer->setSprite(SPRITE_HAIR, hairStyle * -1,
- ColorDB::get(msg.readInt16()));
+ ColorDB::getHairColor(msg.readInt16()));
int misc2 = msg.readInt16();
tempPlayer->setName(msg.readString(24));
diff --git a/src/resources/colordb.cpp b/src/resources/colordb.cpp
index c35cec95e..79622e8ed 100644
--- a/src/resources/colordb.cpp
+++ b/src/resources/colordb.cpp
@@ -28,9 +28,10 @@
namespace
{
- ColorDB::Colors mColors;
+ ColorDB::Colors mHairColors;
bool mLoaded = false;
std::string mFail = "#ffffff";
+ ColorDB::ColorLists mColorLists;
}
void ColorDB::load()
@@ -38,6 +39,12 @@ void ColorDB::load()
if (mLoaded)
unload();
+ loadHair();
+ loadColorLists();
+}
+
+void ColorDB::loadHair()
+{
XML::Document *doc = new XML::Document("hair.xml");
xmlNodePtr root = doc->rootNode();
bool hairXml = true;
@@ -55,7 +62,7 @@ void ColorDB::load()
if (!root || !xmlStrEqual(root->name, BAD_CAST "colors"))
{
logger->log1("ColorDB: Failed to find any color files.");
- mColors[0] = mFail;
+ mHairColors[0] = mFail;
mLoaded = true;
delete doc;
@@ -69,10 +76,10 @@ void ColorDB::load()
{
int id = XML::getProperty(node, "id", 0);
- if (mColors.find(id) != mColors.end())
+ if (mHairColors.find(id) != mHairColors.end())
logger->log("ColorDB: Redefinition of dye ID %d", id);
- mColors[id] = hairXml ?
+ mHairColors[id] = hairXml ?
XML::getProperty(node, "value", "#FFFFFF") :
XML::getProperty(node, "dye", "#FFFFFF");
}
@@ -83,22 +90,59 @@ void ColorDB::load()
mLoaded = true;
}
+void ColorDB::loadColorLists()
+{
+ XML::Document *doc = new XML::Document("itemcolors.xml");
+ xmlNodePtr root = doc->rootNode();
+ if (!root)
+ return;
+
+ for_each_xml_child_node(node, root)
+ {
+ if (xmlStrEqual(node->name, BAD_CAST "list"))
+ {
+ std::string name = XML::getProperty(node, "name", "");
+ if (name.empty())
+ continue;
+
+ std::map <int, ItemColor> colors;
+ ColorListsIterator it = mColorLists.find(name);
+
+ if (it != mColorLists.end())
+ colors = it->second;
+
+ for_each_xml_child_node(colorNode, node)
+ {
+ if (xmlStrEqual(colorNode->name, BAD_CAST "color"))
+ {
+ ItemColor c(XML::getProperty(colorNode, "id", -1),
+ XML::getProperty(colorNode, "name", ""),
+ XML::getProperty(colorNode, "value", ""));
+ if (c.id > -1)
+ colors[c.id] = c;
+ }
+ }
+ mColorLists[name] = colors;
+ }
+ }
+}
+
void ColorDB::unload()
{
logger->log1("Unloading color database...");
- mColors.clear();
+ mHairColors.clear();
mLoaded = false;
}
-std::string &ColorDB::get(int id)
+std::string &ColorDB::getHairColor(int id)
{
if (!mLoaded)
load();
- ColorIterator i = mColors.find(id);
+ ColorIterator i = mHairColors.find(id);
- if (i == mColors.end())
+ if (i == mHairColors.end())
{
logger->log("ColorDB: Error, unknown dye ID# %d", id);
return mFail;
@@ -109,7 +153,17 @@ std::string &ColorDB::get(int id)
}
}
-int ColorDB::size()
+int ColorDB::getHairSize()
{
- return static_cast<int>(mColors.size());
+ return static_cast<int>(mHairColors.size());
+}
+
+std::map <int, ColorDB::ItemColor> *ColorDB::getColorsList(std::string name)
+{
+ std::map <int, ItemColor> colors;
+ ColorListsIterator it = mColorLists.find(name);
+
+ if (it != mColorLists.end())
+ return &it->second;
+ return 0;
}
diff --git a/src/resources/colordb.h b/src/resources/colordb.h
index 72d34afe8..fb0da0036 100644
--- a/src/resources/colordb.h
+++ b/src/resources/colordb.h
@@ -29,23 +29,51 @@
*/
namespace ColorDB
{
+ class ItemColor
+ {
+ public:
+ ItemColor()
+ { }
+ ItemColor(int id, std::string name, std::string color)
+ {
+ this->id = id;
+ this->name = name;
+ this->color = color;
+ }
+
+ int id;
+ std::string name;
+ std::string color;
+ };
+
/**
* Loads the color data from <code>colors.xml</code>.
*/
void load();
/**
+ * Loads the color data from <code>colors.xml</code>.
+ */
+ void loadHair();
+
+ void loadColorLists();
+
+ /**
* Clear the color data
*/
void unload();
- std::string &get(int id);
+ std::string &getHairColor(int id);
+
+ int getHairSize();
- int size();
+ std::map <int, ItemColor> *getColorsList(std::string name);
// Color DB
typedef std::map<int, std::string> Colors;
typedef Colors::iterator ColorIterator;
+ typedef std::map <std::string, std::map <int, ItemColor> > ColorLists;
+ typedef ColorLists::iterator ColorListsIterator;
}
#endif
diff --git a/src/resources/itemdb.cpp b/src/resources/itemdb.cpp
index 418bfb848..d515495de 100644
--- a/src/resources/itemdb.cpp
+++ b/src/resources/itemdb.cpp
@@ -207,6 +207,7 @@ void ItemDB::load()
std::string drawBefore = XML::getProperty(node, "drawBefore", "");
std::string drawAfter = XML::getProperty(node, "drawAfter", "");
std::string removeSprite = XML::getProperty(node, "removeSprite", "");
+ std::string colors = XML::getProperty(node, "colors", "");
std::string tags[3];
tags[0] = XML::getProperty(node, "tag",
@@ -266,6 +267,7 @@ void ItemDB::load()
itemInfo->setDrawBefore(parseSpriteName(drawBefore));
itemInfo->setDrawAfter(parseSpriteName(drawAfter));
itemInfo->setDrawPriority(drawPriority);
+ itemInfo->setColorsList(colors);
std::string effect;
for (int i = 0; i < int(sizeof(fields) / sizeof(fields[0])); ++i)
diff --git a/src/resources/iteminfo.cpp b/src/resources/iteminfo.cpp
index 49aadc23d..990c78f45 100644
--- a/src/resources/iteminfo.cpp
+++ b/src/resources/iteminfo.cpp
@@ -82,30 +82,28 @@ std::map<int, int> &ItemInfo::addReplaceSprite(int sprite)
return it->second;
}
-std::string ItemInfo::getDyeString(int color) const
+void ItemInfo::setColorsList(std::string name)
{
- if (mId == 1172)
+ if (name.empty())
{
- if (color == 1)
- return "W:#115511,22aa22,99dd99;R:#547000,a5dc00,d1ff46";
- if (color == 0)
- return "W:#547000,a5dc00,d1ff46;R:#115511,22aa22,99dd99";
- if (color == 3)
- return "W:#ffffff,000000,000000;R:#333333,333333,333333";
+ mColors = 0;
+ mColorList = "";
+ }
+ else
+ {
+ mColors = ColorDB::getColorsList(name);
+ mColorList = name;
}
- return "";
}
std::string ItemInfo::getDyeColorsString(int color) const
{
- if (mId == 1172)
- {
- if (color == 1)
- return "#115511,22aa22,99dd99;#547000,a5dc00,d1ff46";
- if (color == 0)
- return "#547000,a5dc00,d1ff46;#115511,22aa22,99dd99";
- if (color == 3)
- return "#ffffff,000000,000000;#333333,333333,333333";
- }
- return "";
+ if (!mColors || mColorList.empty())
+ return "";
+
+ std::map <int, ColorDB::ItemColor>::iterator it = mColors->find(color);
+ if (it == mColors->end())
+ return "";
+
+ return it->second.color;
} \ No newline at end of file
diff --git a/src/resources/iteminfo.h b/src/resources/iteminfo.h
index 3b72c7830..297c1b036 100644
--- a/src/resources/iteminfo.h
+++ b/src/resources/iteminfo.h
@@ -25,6 +25,7 @@
#include "being.h"
+#include "resources/colordb.h"
#include "resources/spritedef.h"
#include <map>
@@ -111,7 +112,9 @@ class ItemInfo
mDrawPriority(0),
mIsRemoveSprites(false),
mAttackAction(SpriteAction::INVALID),
- mAttackRange(0)
+ mAttackRange(0),
+ mColors(0),
+ mColorList("")
{
}
@@ -235,6 +238,11 @@ class ItemInfo
std::string getDyeColorsString(int color) const;
+ void setColorsList(std::string name);
+
+ bool isHaveColors()
+ { return !mColorList.empty(); }
+
protected:
SpriteDisplay mDisplay; /**< Display info (like icon) */
std::string mName;
@@ -269,6 +277,8 @@ class ItemInfo
/** Stores the names of sounds to be played at certain event. */
std::map < EquipmentSoundEvent, std::vector<std::string> > mSounds;
std::map <int, int> mTags;
+ std::map <int, ColorDB::ItemColor> *mColors;
+ std::string mColorList;
};
#endif
diff --git a/src/utils/stringutils.cpp b/src/utils/stringutils.cpp
index 835f9ce00..63924eb78 100644
--- a/src/utils/stringutils.cpp
+++ b/src/utils/stringutils.cpp
@@ -388,6 +388,19 @@ std::list<int> splitToIntList(const std::string &text, char separator)
return tokens;
}
+
+std::list<std::string> splitToStringList(const std::string &text,
+ char separator)
+{
+ std::list<std::string> tokens;
+ std::stringstream ss(text);
+ std::string item;
+ while(std::getline(ss, item, separator))
+ tokens.push_back(item);
+
+ return tokens;
+}
+
std::string combineDye(std::string file, std::string dye)
{
if (dye.empty())
@@ -397,3 +410,31 @@ std::string combineDye(std::string file, std::string dye)
return file.substr(0, pos) + "|" + dye;
return file + "|" + dye;
}
+
+std::string combineDye2(std::string file, std::string dye)
+{
+ if (dye.empty())
+ return file;
+
+ size_t pos = file.find_last_of("|");
+ if (pos != std::string::npos)
+ {
+ std::string dye1 = file.substr(pos + 1);
+ std::string str = "";
+ file = file.substr(0, pos);
+ std::list<std::string> list1 = splitToStringList(dye1, ';');
+ std::list<std::string> list2 = splitToStringList(dye, ';');
+ std::list<std::string>::iterator it1, it1_end = list1.end();
+ std::list<std::string>::iterator it2, it2_end = list2.end();
+ for (it1 = list1.begin(), it2 = list2.begin();
+ it1 != it1_end && it2 != it2_end; ++it1, ++it2)
+ {
+ str += (*it1) + ":" + (*it2) + ";";
+ }
+ return file + "|" + str;
+ }
+ else
+ {
+ return file;
+ }
+}
diff --git a/src/utils/stringutils.h b/src/utils/stringutils.h
index 52b47e6a2..02c25eddb 100644
--- a/src/utils/stringutils.h
+++ b/src/utils/stringutils.h
@@ -170,6 +170,11 @@ std::set<int> splitToIntSet(const std::string &text, char separator);
std::list<int> splitToIntList(const std::string &text, char separator);
+std::list<std::string> splitToStringList(const std::string &text,
+ char separator);
+
std::string combineDye(std::string file, std::string dye);
+std::string combineDye2(std::string file, std::string dye);
+
#endif // UTILS_STRINGUTILS_H