summaryrefslogtreecommitdiff
path: root/src/gui/skilldialog.cpp
diff options
context:
space:
mode:
authorPhilipp Sehmisch <crush@themanaworld.org>2009-08-16 17:47:51 +0200
committerPhilipp Sehmisch <crush@themanaworld.org>2009-08-16 17:47:51 +0200
commite0ba8f7f67ddd08c54f0d453a316b3620d52529d (patch)
tree7324fa33f2c6af04067b77e0ce7f73d9effed1c6 /src/gui/skilldialog.cpp
parent346d68307553c18777df4c49f9b3fe57955c5c0d (diff)
parent6460413ee2f50be561fd0824e3eaa9c2c09415b1 (diff)
downloadmana-client-e0ba8f7f67ddd08c54f0d453a316b3620d52529d.tar.gz
mana-client-e0ba8f7f67ddd08c54f0d453a316b3620d52529d.tar.bz2
mana-client-e0ba8f7f67ddd08c54f0d453a316b3620d52529d.tar.xz
mana-client-e0ba8f7f67ddd08c54f0d453a316b3620d52529d.zip
Merged changes from last month with a commit I forgot to commit before I went on vacation.
Diffstat (limited to 'src/gui/skilldialog.cpp')
-rw-r--r--src/gui/skilldialog.cpp425
1 files changed, 241 insertions, 184 deletions
diff --git a/src/gui/skilldialog.cpp b/src/gui/skilldialog.cpp
index f0cd01ce..14e0e5a4 100644
--- a/src/gui/skilldialog.cpp
+++ b/src/gui/skilldialog.cpp
@@ -25,105 +25,78 @@
#include "gui/widgets/container.h"
#include "gui/widgets/icon.h"
#include "gui/widgets/label.h"
+#include "gui/widgets/layouthelper.h"
#include "gui/widgets/listbox.h"
#include "gui/widgets/progressbar.h"
#include "gui/widgets/scrollarea.h"
+#include "gui/widgets/tab.h"
#include "gui/widgets/tabbedarea.h"
+#include "gui/widgets/vertcontainer.h"
#include "gui/widgets/windowcontainer.h"
+#include "gui/setup.h"
#include "localplayer.h"
+#include "log.h"
+
+#include "net/net.h"
+#include "net/playerhandler.h"
#include "utils/dtor.h"
#include "utils/gettext.h"
#include "utils/stringutils.h"
+#include "utils/xml.h"
#include <string>
#include <vector>
-class SkillTab : public Container, public gcn::ActionListener
+class SkillEntry;
+
+struct SkillInfo
+{
+ unsigned short id;
+ std::string name;
+ std::string icon;
+ bool modifiable;
+ SkillEntry *display;
+};
+
+class SkillEntry : public Container, gcn::WidgetListener
{
public:
- /**
- * The type of this skill tab
- */
- const std::string type;
-
- /**
- * Constructor
- */
- SkillTab(const std::string &type);
-
- /**
- * Update this tab
- */
+ SkillEntry(SkillInfo *info);
+
+ void widgetResized(const gcn::Event &event);
+
void update();
- /**
- * Called when receiving actions from widget.
- */
- void action(const gcn::ActionEvent &event) {}
+ protected:
+ friend class SkillDialog;
+ SkillInfo *mInfo;
private:
- /**
- * Update the information of a skill at
- * the given index
- */
- void updateSkill(int index);
-
- /**
- * Gets the number of skills in this particular
- * type of tab.
- */
- int getSkillNum();
-
- /**
- * Get the first enumeration of this skill tab's
- * skill type.
- */
- int getSkillBegin();
-
- /**
- * Get the icon associated with the given index
- */
- Icon *getIcon(int index);
-
- std::vector<Icon *> mSkillIcons;
- std::vector<gcn::Label *> mSkillNameLabels;
- std::vector<gcn::Label *> mSkillLevelLabels;
- std::vector<gcn::Label *> mSkillExpLabels;
- std::vector<ProgressBar *> mSkillProgress;
+ Icon *mIcon;
+ Label *mNameLabel;
+ Label *mLevelLabel;
+ Label *mExpLabel;
+ Button *mIncrease;
+ ProgressBar *mProgress;
};
-
SkillDialog::SkillDialog():
Window(_("Skills"))
{
setWindowName("Skills");
setCloseButton(true);
+ setResizable(true);
setSaveVisible(true);
setDefaultSize(windowContainer->getWidth() - 280, 30, 275, 425);
+ setupWindow->registerWindowForReset(this);
- TabbedArea *panel = new TabbedArea;
- panel->setDimension(gcn::Rectangle(5, 5, 270, 420));
-
- SkillTab *tab;
-
- // Add each type of skill tab to the panel
- tab = new SkillTab("Weapon");
- panel->addTab(_("Weapons"), tab);
- mTabs.push_back(tab);
+ mTabs = new TabbedArea();
+ mPointsLabel = new Label("0");
- tab = new SkillTab("Magic");
- panel->addTab(_("Magic"), tab);
- mTabs.push_back(tab);
-
- tab = new SkillTab("Craft");
- panel->addTab(_("Crafts"), tab);
- mTabs.push_back(tab);
-
- add(panel);
-
- update();
+ place(0, 0, mTabs, 5, 5);
+ place(0, 5, mPointsLabel);
setLocationRelativeTo(getParent());
loadWindowState();
@@ -131,13 +104,17 @@ SkillDialog::SkillDialog():
SkillDialog::~SkillDialog()
{
- delete_all(mTabs);
+ //delete_all(mTabs);
}
void SkillDialog::action(const gcn::ActionEvent &event)
{
- if (event.getId() == "skill")
+ if (event.getId() == "inc")
{
+ SkillEntry *disp = dynamic_cast<SkillEntry*>(event.getSource()->getParent());
+
+ if (disp)
+ Net::getPlayerHandler()->increaseSkill(disp->mInfo->id);
}
else if (event.getId() == "close")
{
@@ -145,174 +122,254 @@ void SkillDialog::action(const gcn::ActionEvent &event)
}
}
-void SkillDialog::draw(gcn::Graphics *g)
+void SkillDialog::adjustTabSize()
{
- update();
+ gcn::Widget *content = mTabs->getCurrentWidget();
+ if (content) {
+ int width = mTabs->getWidth() - 2 * content->getFrameSize() - 2 * mTabs->getFrameSize();
+ int height = mTabs->getContainerHeight() - 2 * content->getFrameSize();
+ content->setSize(width, height);
+ content->setVisible(true);
+ content->logic();
+ }
+}
+
+void SkillDialog::widgetResized(const gcn::Event &event)
+{
+ Window::widgetResized(event);
- Window::draw(g);
+ adjustTabSize();
}
-void SkillDialog::update()
+void SkillDialog::logic()
{
- for(std::list<SkillTab*>::const_iterator i = mTabs.begin();
- i != mTabs.end(); ++i)
- {
- (*i)->update();
+ Window::logic();
+
+ Tab *tab = dynamic_cast<Tab*>(mTabs->getSelectedTab());
+ if (tab != mCurrentTab) {
+ mCurrentTab = tab;
+ adjustTabSize();
}
}
-SkillTab::SkillTab(const std::string &type): type(type)
+std::string SkillDialog::update(int id)
{
- setOpaque(false);
- setDimension(gcn::Rectangle(0, 0, 270, 420));
- int skillNum = getSkillNum();
-
- mSkillIcons.resize(skillNum);
- mSkillNameLabels.resize(skillNum);
- mSkillLevelLabels.resize(skillNum);
- mSkillExpLabels.resize(skillNum);
- mSkillProgress.resize(skillNum);
+ SkillMap::iterator i = mSkills.find(id);
- // Set the initial positions of the skill information
- for (int a = 0; a < skillNum; a++)
+ if (i != mSkills.end())
{
- mSkillIcons.at(a) = getIcon(a);
- mSkillIcons.at(a)->setPosition(1, a*32);
- add(mSkillIcons.at(a));
-
- mSkillNameLabels.at(a) = new Label("");
- mSkillNameLabels.at(a)->setPosition(35, a*32 );
- add(mSkillNameLabels.at(a));
+ SkillInfo *info = i->second;
+ info->display->update();
+ return info->name;
+ }
- mSkillProgress.at(a) = new ProgressBar(0.0f, 200, 20, gcn::Color(150, 150, 150));
- mSkillProgress.at(a)->setPosition(35, a*32 + 13);
- add(mSkillProgress.at(a));
+ return std::string();
+}
- mSkillExpLabels.at(a) = new Label("");
- mSkillExpLabels.at(a)->setPosition(45, a*32 + 16);
- add(mSkillExpLabels.at(a));
+void SkillDialog::update()
+{
+ mPointsLabel->setCaption(strprintf(_("Skill points available: %d"),
+ player_node->getSkillPoints()));
+ mPointsLabel->adjustSize();
- mSkillLevelLabels.at(a) = new Label("");
- mSkillLevelLabels.at(a)->setPosition(165, a*32);
- add(mSkillLevelLabels.at(a));
+ for (SkillMap::iterator it = mSkills.begin(); it != mSkills.end(); it++)
+ {
+ if ((*it).second->modifiable)
+ (*it).second->display->update();
}
-
- update();
}
-int SkillTab::getSkillNum()
+void SkillDialog::loadSkills(const std::string &file)
{
- int skillNum = 0;
+ // TODO: mTabs->clear();
+ delete_all(mSkills);
+ mSkills.clear();
- if (type == "Weapon")
+ XML::Document doc(file);
+ xmlNodePtr root = doc.rootNode();
+
+ if (!root || !xmlStrEqual(root->name, BAD_CAST "skills"))
{
- skillNum = CHAR_SKILL_WEAPON_NB;
- return skillNum;
+ logger->log("Error loading skills file: %s", file.c_str());
+ return;
}
- else if (type == "Magic")
+
+ int setCount = 0;
+ std::string setName;
+ ScrollArea *scroll;
+ VertContainer *container;
+
+ for_each_xml_child_node(set, root)
{
- skillNum = CHAR_SKILL_MAGIC_NB;
- return skillNum;
+ if (xmlStrEqual(set->name, BAD_CAST "set"))
+ {
+ setCount++;
+ setName = XML::getProperty(set, "name", strprintf(_("Skill Set %d"), setCount));
+
+ container = new VertContainer(32);
+ container->setOpaque(false);
+ scroll = new ScrollArea(container);
+ scroll->setOpaque(false);
+ scroll->setHorizontalScrollPolicy(ScrollArea::SHOW_NEVER);
+ scroll->setVerticalScrollPolicy(ScrollArea::SHOW_ALWAYS);
+
+ mTabs->addTab(setName, scroll);
+ for_each_xml_child_node(node, set)
+ {
+ if (xmlStrEqual(node->name, BAD_CAST "skill"))
+ {
+ int id = atoi(XML::getProperty(node, "id", "-1").c_str());
+ std::string name = XML::getProperty(node, "name", strprintf(_("Skill %d"), id));
+ std::string icon = XML::getProperty(node, "icon", "");
+
+ SkillInfo *skill = new SkillInfo;
+ skill->id = id;
+ skill->name = name;
+ skill->icon = icon;
+ skill->modifiable = 0;
+ skill->display = new SkillEntry(skill);
+
+ container->add(skill->display);
+
+ mSkills[id] = skill;
+ }
+ }
+ }
}
- else if (type == "Craft")
+
+ adjustTabSize();
+ update();
+}
+
+void SkillDialog::setModifiable(int id, bool modifiable)
+{
+ SkillMap::iterator i = mSkills.find(id);
+
+ if (i != mSkills.end())
{
- skillNum = CHAR_SKILL_CRAFT_NB;
- return skillNum;
+ SkillInfo *info = i->second;
+ info->modifiable = modifiable;
+ info->display->update();
}
- else return skillNum;
}
-int SkillTab::getSkillBegin()
+SkillEntry::SkillEntry(SkillInfo *info) :
+ mInfo(info),
+ mIcon(NULL),
+ mNameLabel(new Label(info->name)),
+ mLevelLabel(new Label("999")),
+ mIncrease(new Button(_("+"), "inc", skillDialog)),
+ mProgress(new ProgressBar(0.0f, 200, 20, gcn::Color(150, 150, 150)))
+{
+ setFrameSize(1);
+ setOpaque(false);
+
+ addWidgetListener(this);
+
+ if (!info->icon.empty())
+ mIcon = new Icon(info->icon);
+ else
+ mIcon = new Icon("graphics/gui/unknown-item.png");
+
+ mIcon->setPosition(1, 0);
+ add(mIcon);
+
+ mNameLabel->setPosition(35, 0);
+ add(mNameLabel);
+
+ mLevelLabel->setPosition(165, 0);
+ add(mLevelLabel);
+
+ mProgress->setPosition(35, 13);
+ add(mProgress);
+
+ mIncrease->setPosition(getWidth() - mIncrease->getWidth(), 13);
+ add(mIncrease);
+
+ update();
+}
+
+void SkillEntry::widgetResized(const gcn::Event &event)
{
- int skillBegin = 0;
+ gcn::Rectangle size = getChildrenArea();
- if (type == "Weapon")
+ if (mProgress->isVisible() && mIncrease->isVisible())
{
- skillBegin = CHAR_SKILL_WEAPON_BEGIN - CHAR_SKILL_BEGIN;
- return skillBegin;
+ mLevelLabel->setPosition(size.width - mLevelLabel->getWidth()
+ - mIncrease->getWidth() - 4, 0);
+ mProgress->setWidth(size.width - mIncrease->getWidth() - 39);
+ mIncrease->setPosition(getWidth() - mIncrease->getWidth() - 2, 6);
}
- else if (type == "Magic")
+ else if (mProgress->isVisible())
{
- skillBegin = CHAR_SKILL_MAGIC_BEGIN - CHAR_SKILL_BEGIN;
- return skillBegin;
+ mLevelLabel->setPosition(size.width - mLevelLabel->getWidth(), 0);
+ mProgress->setWidth(size.width - 39);
}
- else if (type == "Craft")
+ else if (mIncrease->isVisible())
{
- skillBegin = CHAR_SKILL_CRAFT_BEGIN - CHAR_SKILL_BEGIN;
- return skillBegin;
+ mLevelLabel->setPosition(size.width - mLevelLabel->getWidth()
+ - mIncrease->getWidth() - 4, 0);
+ mIncrease->setPosition(getWidth() - mIncrease->getWidth() - 2, 6);
}
- else return skillBegin;
+ else
+ mLevelLabel->setPosition(size.width - mLevelLabel->getWidth(), 0);
}
-Icon* SkillTab::getIcon(int index)
+void SkillEntry::update()
{
- int skillBegin = getSkillBegin();
- std::string icon = LocalPlayer::getSkillInfo(index + skillBegin).icon;
- return new Icon(icon);
-}
+ int baseLevel = player_node->getAttributeBase(mInfo->id);
+ int effLevel = player_node->getAttributeEffective(mInfo->id);
-void SkillTab::updateSkill(int index)
-{
- int skillBegin = getSkillBegin();
+ if (baseLevel <= 0 && !mInfo->modifiable)
+ {
+ setVisible(false);
+ return;
+ }
+
+ setVisible(true);
- int baseLevel = player_node->getAttributeBase(index +
- skillBegin +
- CHAR_SKILL_BEGIN);
+ std::string skillLevel;
- int effLevel = player_node->getAttributeEffective(index +
- skillBegin +
- CHAR_SKILL_BEGIN);
- if(baseLevel <= 0)
+ if (effLevel != baseLevel)
{
- mSkillProgress.at(index)->setVisible(false);
- mSkillExpLabels.at(index)->setVisible(false);
- mSkillLevelLabels.at(index)->setVisible(false);
- mSkillNameLabels.at(index)->setVisible(false);
- mSkillIcons.at(index)->setVisible(false);
+ skillLevel = strprintf(_("Lvl: %d (%+d)"),
+ baseLevel, baseLevel - effLevel);
}
else
{
- mSkillProgress.at(index)->setVisible(true);
- mSkillExpLabels.at(index)->setVisible(true);
- mSkillLevelLabels.at(index)->setVisible(true);
- mSkillNameLabels.at(index)->setVisible(true);
- mSkillIcons.at(index)->setVisible(true);
- std::string skillLevel("Lvl: " + toString(baseLevel));
- if (effLevel < baseLevel)
- {
- skillLevel.append(" - " + toString(baseLevel - effLevel));
- }
- else if (effLevel > baseLevel)
- {
- skillLevel.append(" + " + toString(effLevel - baseLevel));
- }
- mSkillLevelLabels.at(index)->setCaption(skillLevel);
+ skillLevel = strprintf(_("Lvl: %d"), baseLevel);
+ }
- std::pair<int, int> exp = player_node->getExperience(index + skillBegin);
- std::string sExp (toString(exp.first) + " / " + toString(exp.second));
+ mLevelLabel->setCaption(skillLevel);
+ std::pair<int, int> exp = player_node->getExperience(mInfo->id);
+ std::string sExp (toString(exp.first) + " / " + toString(exp.second));
- mSkillNameLabels.at(index)->setCaption(LocalPlayer::getSkillInfo(index + skillBegin).name);
- mSkillNameLabels.at(index)->adjustSize();
- mSkillLevelLabels.at(index)->adjustSize();
- mSkillExpLabels.at(index)->setCaption(sExp);
- mSkillExpLabels.at(index)->adjustSize();
- mSkillExpLabels.at(index)->setAlignment(gcn::Graphics::RIGHT);
+ mLevelLabel->adjustSize();
+
+ if (exp.second)
+ {
+ mProgress->setVisible(true);
+ mProgress->setText(sExp);
// More intense red as exp grows
int color = 150 - (int)(150 * ((float) exp.first / exp.second));
- mSkillProgress.at(index)->setColor(244, color, color);
- mSkillProgress.at(index)->setProgress((float) exp.first / exp.second);
+ mProgress->setColor(244, color, color);
+ mProgress->setProgress((float) exp.first / exp.second);
}
-}
-
-void SkillTab::update()
-{
- int skillNum = getSkillNum();
+ else
+ mProgress->setVisible(false);
- // Update the skill information for reach skill
- for (int a = 0; a < skillNum; a++)
+ if (mInfo->modifiable)
{
- updateSkill(a);
+ mIncrease->setVisible(true);
+ mIncrease->setEnabled(player_node->getSkillPoints());
}
+ else
+ {
+ mIncrease->setVisible(false);
+ mIncrease->setEnabled(false);
+ }
+
+ widgetResized(NULL);
}