summaryrefslogtreecommitdiff
path: root/src/gui/theme.cpp
diff options
context:
space:
mode:
authorJared Adams <jaxad0127@gmail.com>2010-03-04 22:41:19 -0700
committerJared Adams <jaxad0127@gmail.com>2010-03-12 14:49:27 -0700
commit781b3c9f17708cc5fe08eb3c9ee38d596364d97c (patch)
tree833797c9b9168ab58864ffe4cf8ed028060e44a2 /src/gui/theme.cpp
parent96b64757954f07d196599b3c1131a6603982c930 (diff)
downloadmana-client-781b3c9f17708cc5fe08eb3c9ee38d596364d97c.tar.gz
mana-client-781b3c9f17708cc5fe08eb3c9ee38d596364d97c.tar.bz2
mana-client-781b3c9f17708cc5fe08eb3c9ee38d596364d97c.tar.xz
mana-client-781b3c9f17708cc5fe08eb3c9ee38d596364d97c.zip
Split Palette into Theme and UserPalette
Themes can now control the colors they use. Colors in the Viewport (being names, particles, etc) can still be changed by the user. Also make ProgressBars more easily colored. DyePalette was made more flexible in the process. Also fixes comparing strings of different lengths insensitively. Reviewed-by: Thorbjørn Lindeijer
Diffstat (limited to 'src/gui/theme.cpp')
-rw-r--r--src/gui/theme.cpp225
1 files changed, 214 insertions, 11 deletions
diff --git a/src/gui/theme.cpp b/src/gui/theme.cpp
index 961694e6..1841f8d9 100644
--- a/src/gui/theme.cpp
+++ b/src/gui/theme.cpp
@@ -27,6 +27,7 @@
#include "configuration.h"
#include "log.h"
+#include "resources/dye.h"
#include "resources/image.h"
#include "resources/imageset.h"
#include "resources/resourcemanager.h"
@@ -39,6 +40,8 @@
#include <algorithm>
+#define GUI_ROOT "graphics/gui"
+
std::string Theme::mThemePath;
Theme *Theme::mInstance = 0;
@@ -92,9 +95,12 @@ int Skin::getMinHeight() const
}
Theme::Theme():
- mMinimumOpacity(-1.0f)
+ Palette(THEME_COLORS_END),
+ mMinimumOpacity(-1.0f),
+ mProgressColors(ProgressColors(THEME_PROG_END))
{
config.addListener("guialpha", this);
+ loadColors();
}
Theme::~Theme()
@@ -117,6 +123,18 @@ void Theme::deleteInstance()
mInstance = 0;
}
+gcn::Color Theme::getProgressColor(int type, float progress)
+{
+ DyePalette *dye = mInstance->mProgressColors[type];
+
+ int color[3] = {0, 0, 0};
+ int intensity = (int) (255 * progress);
+
+ dye->getColor(intensity, color);
+
+ return gcn::Color(color[0], color[1], color[2]);
+}
+
Skin *Theme::load(const std::string &filename, const std::string &defaultPath)
{
// Check if this skin was already loaded
@@ -283,7 +301,7 @@ bool Theme::tryThemePath(std::string themePath)
{
if (!themePath.empty())
{
- themePath = "graphics/gui/" + themePath;
+ themePath = GUI_ROOT + themePath;
if (PHYSFS_exists(themePath.c_str()))
{
mThemePath = themePath;
@@ -297,15 +315,13 @@ bool Theme::tryThemePath(std::string themePath)
void Theme::prepareThemePath()
{
// Try theme from settings
- if (tryThemePath(config.getValue("theme", "")))
- return;
+ if (!tryThemePath(config.getValue("theme", "")))
+ // Try theme from branding
+ if (!tryThemePath(branding.getValue("theme", "")))
+ // Use default
+ mThemePath = GUI_ROOT;
- // Try theme from branding
- if (tryThemePath(branding.getValue("theme", "")))
- return;
-
- // Use default
- mThemePath = "graphics/gui";
+ instance()->loadColors(mThemePath);
}
std::string Theme::resolveThemePath(const std::string &path)
@@ -328,7 +344,7 @@ std::string Theme::resolveThemePath(const std::string &path)
return getThemePath() + "/" + path;
// Backup
- return "graphics/gui/" + path;
+ return std::string(GUI_ROOT) + "/" + path;
}
Image *Theme::getImageFromTheme(const std::string &path)
@@ -343,3 +359,190 @@ ImageSet *Theme::getImageSetFromTheme(const std::string &path,
ResourceManager *resman = ResourceManager::getInstance();
return resman->getImageSet(resolveThemePath(path), w, h);
}
+
+static int readColorType(const std::string &type)
+{
+ static std::string colors[] = {
+ "TEXT",
+ "SHADOW",
+ "OUTLINE",
+ "PROGRESS_BAR",
+ "BUTTON",
+ "BUTTON_DISABLED",
+ "TAB",
+ "BACKGROUND",
+ "HIGHLIGHT",
+ "TAB_FLASH",
+ "SHOP_WARNING",
+ "ITEM_EQUIPPED",
+ "CHAT",
+ "GM",
+ "PLAYER",
+ "WHISPER",
+ "IS",
+ "PARTY",
+ "GUILD",
+ "SERVER",
+ "LOGGER",
+ "HYPERLINK",
+ "UNKNOWN_ITEM",
+ "GENERIC",
+ "HEAD",
+ "USABLE",
+ "TORSO",
+ "ONEHAND",
+ "LEGS",
+ "FEET",
+ "TWOHAND",
+ "SHIELD",
+ "RING",
+ "NECKLACE",
+ "ARMS",
+ "AMMO"
+ };
+
+ if (type.empty())
+ return -1;
+
+ for (int i = 0; i < Theme::THEME_COLORS_END; i++)
+ {
+ if (compareStrI(type, colors[i]) == 0)
+ {
+ return i;
+ }
+ }
+
+ return -1;
+}
+
+static gcn::Color readColor(const std::string &description)
+{
+ int size = description.length();
+ if (size < 7 || description[0] != '#')
+ {
+ error:
+ logger->log("Error, invalid theme color palette: %s",
+ description.c_str());
+ return Palette::BLACK;
+ }
+
+ int v = 0;
+ for (int i = 1; i < 7; ++i)
+ {
+ char c = description[i];
+ int n;
+
+ if ('0' <= c && c <= '9')
+ n = c - '0';
+ else if ('A' <= c && c <= 'F')
+ n = c - 'A' + 10;
+ else if ('a' <= c && c <= 'f')
+ n = c - 'a' + 10;
+ else
+ goto error;
+
+ v = (v << 4) | n;
+ }
+
+ return gcn::Color(v);
+}
+
+static Palette::GradientType readColorGradient(const std::string &grad)
+{
+ static std::string grads[] = {
+ "STATIC",
+ "PULSE",
+ "SPECTRUM",
+ "RAINBOW"
+ };
+
+ if (grad.empty())
+ return Palette::STATIC;
+
+ for (int i = 0; i < 4; i++)
+ {
+ if (compareStrI(grad, grads[i]))
+ return (Palette::GradientType) i;
+ }
+
+ return Palette::STATIC;
+}
+
+static int readProgressType(const std::string &type)
+{
+ static std::string colors[] = {
+ "DEFAULT",
+ "HP",
+ "MP",
+ "NO_MP",
+ "EXP",
+ "INVY_SLOTS",
+ "WEIGHT",
+ "JOB"
+ };
+
+ if (type.empty())
+ return -1;
+
+ for (int i = 0; i < Theme::THEME_PROG_END; i++)
+ {
+ if (compareStrI(type, colors[i]) == 0)
+ return i;
+ }
+
+ return -1;
+}
+
+void Theme::loadColors(std::string file)
+{
+ if (file == GUI_ROOT)
+ return; // No need to reload
+
+ if (file == "")
+ file = GUI_ROOT;
+
+ file += "/colors.xml";
+
+ XML::Document doc(file);
+ xmlNodePtr root = doc.rootNode();
+
+ if (!root || !xmlStrEqual(root->name, BAD_CAST "colors"))
+ {
+ logger->log("Error loading colors file: %s", file.c_str());
+ return;
+ }
+
+ int type;
+ std::string temp;
+ gcn::Color color;
+ GradientType grad;
+
+ for_each_xml_child_node(node, root)
+ {
+ if (xmlStrEqual(node->name, BAD_CAST "color"))
+ {
+ type = readColorType(XML::getProperty(node, "id", ""));
+ if (type < 0) // invalid or no type given
+ continue;
+
+ temp = XML::getProperty(node, "color", "");
+ if (temp.empty()) // no color set, so move on
+ continue;
+
+ color = readColor(temp);
+ grad = readColorGradient(XML::getProperty(node, "effect", ""));
+
+ mColors[type].set(type, color, grad, "", 0, 10);
+ }
+
+ if (xmlStrEqual(node->name, BAD_CAST "progressbar"))
+ {
+ type = readProgressType(XML::getProperty(node, "id", ""));
+ if (type < 0) // invalid or no type given
+ continue;
+
+ mProgressColors[type] = new DyePalette(XML::getProperty(node,
+ "color", ""));
+ }
+ }
+}