From 362a539125dff292614618d5ebf61e0c71dfae9f Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Wed, 18 Aug 2010 23:32:46 +0200 Subject: Fixing overlapping icons in item popups The bug could not be reproduced by everyone. Many thanks to Jaxad0127 for testing it on an affected system. This patch resolves http://bugs.manasource.org/view.php?id=191 Signed-off-by: Jared Adams --- src/gui/itempopup.cpp | 35 ++++++++++++++++++----------------- 1 file changed, 18 insertions(+), 17 deletions(-) diff --git a/src/gui/itempopup.cpp b/src/gui/itempopup.cpp index 0cde9395..b71ca529 100644 --- a/src/gui/itempopup.cpp +++ b/src/gui/itempopup.cpp @@ -50,22 +50,17 @@ ItemPopup::ItemPopup(): mItemName->setFont(boldFont); mItemName->setPosition(getPadding(), getPadding()); - const int fontHeight = getFont()->getHeight(); - // Item Description mItemDesc = new TextBox; mItemDesc->setEditable(false); - mItemDesc->setPosition(getPadding(), fontHeight); // Item Effect mItemEffect = new TextBox; mItemEffect->setEditable(false); - mItemEffect->setPosition(getPadding(), 2 * fontHeight + 2 * getPadding()); // Item Weight mItemWeight = new TextBox; mItemWeight->setEditable(false); - mItemWeight->setPosition(getPadding(), 3 * fontHeight + 4 * getPadding()); mIcon = new Icon(0); @@ -147,28 +142,34 @@ void ItemPopup::setItem(const ItemInfo &item, bool showImage) const int numRowsDesc = mItemDesc->getNumberOfRows(); const int numRowsEffect = mItemEffect->getNumberOfRows(); const int numRowsWeight = mItemWeight->getNumberOfRows(); - const int height = getFont()->getHeight(); + const int fontHeight = getFont()->getHeight(); + + int nameHeight; + if (mIcon->getHeight() > 2 * fontHeight) + nameHeight = mIcon->getHeight(); + else + nameHeight = 2 * fontHeight; if (item.getEffect().empty()) { - setContentSize(minWidth, (numRowsDesc + numRowsWeight + getPadding()) * - height); + setContentSize(minWidth, nameHeight + + (numRowsDesc + numRowsWeight + 1) * fontHeight); - mItemWeight->setPosition(getPadding(), (numRowsDesc + getPadding()) * - height); + mItemWeight->setPosition(getPadding(), + nameHeight + (numRowsDesc + 1) * fontHeight); } else { - setContentSize(minWidth, (numRowsDesc + numRowsEffect + numRowsWeight + - getPadding()) * height); + setContentSize(minWidth, nameHeight + (numRowsDesc + numRowsEffect + + numRowsWeight + 1) * fontHeight); - mItemWeight->setPosition(getPadding(), (numRowsDesc + numRowsEffect + - getPadding()) * height); + mItemWeight->setPosition(getPadding(), nameHeight + (numRowsDesc + + numRowsEffect + 1) * fontHeight); } - mItemDesc->setPosition(getPadding(), 2 * height); - mItemEffect->setPosition(getPadding(), (numRowsDesc + getPadding()) * height); - + mItemDesc->setPosition(getPadding(), nameHeight); + mItemEffect->setPosition(getPadding(), nameHeight + + (numRowsDesc + 1) * fontHeight); } gcn::Color ItemPopup::getColor(ItemType type) -- cgit v1.2.3-70-g09d2 From af7bbb7b4404439580666b31388dd8dbef481011 Mon Sep 17 00:00:00 2001 From: Jared Adams Date: Wed, 18 Aug 2010 15:55:40 -0600 Subject: Fix Theme loading Reviewed-by: Freeyorp --- src/gui/theme.cpp | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/gui/theme.cpp b/src/gui/theme.cpp index 12de1f91..f80fa272 100644 --- a/src/gui/theme.cpp +++ b/src/gui/theme.cpp @@ -326,6 +326,7 @@ bool Theme::tryThemePath(std::string themePath) if (!themePath.empty()) { themePath = defaultThemePath + themePath; + if (PHYSFS_exists(themePath.c_str())) { mThemePath = themePath; @@ -338,6 +339,9 @@ bool Theme::tryThemePath(std::string themePath) void Theme::prepareThemePath() { + // Ensure the Theme object has been created + instance(); + // Try theme from settings if (!tryThemePath(config.getValue("theme", ""))) // Try theme from branding -- cgit v1.2.3-70-g09d2 From db0f5e2a332f82c006729146727d37315de7dfda Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Thu, 19 Aug 2010 16:22:40 +0200 Subject: Fixing some bugs in NPC-shop gui * Price and total money is now shown from the beginning in sell dialog. * Item popup is set invisible when mouse has moved away from items. * Item popup gets deleted when shop closes. Signed-off-by: Jared Adams --- src/gui/sell.cpp | 2 ++ src/gui/widgets/shoplistbox.cpp | 11 +++++++++++ src/gui/widgets/shoplistbox.h | 13 +++++++++++++ 3 files changed, 26 insertions(+) diff --git a/src/gui/sell.cpp b/src/gui/sell.cpp index 69ff7ed2..13e0ba99 100644 --- a/src/gui/sell.cpp +++ b/src/gui/sell.cpp @@ -242,6 +242,8 @@ void SellDialog::setMoney(int amount) { mPlayerMoney = amount; mShopItemList->setPlayersMoney(amount); + + updateButtonsAndLabels(); } void SellDialog::updateButtonsAndLabels() diff --git a/src/gui/widgets/shoplistbox.cpp b/src/gui/widgets/shoplistbox.cpp index 2f5fab34..a5033570 100644 --- a/src/gui/widgets/shoplistbox.cpp +++ b/src/gui/widgets/shoplistbox.cpp @@ -61,6 +61,11 @@ ShopListBox::ShopListBox(gcn::ListModel *listModel, ShopItems *shopListModel): mItemPopup = new ItemPopup; } +ShopListBox::~ShopListBox() +{ + delete mItemPopup; +} + void ShopListBox::setPlayersMoney(int money) { mPlayerMoney = money; @@ -167,3 +172,9 @@ void ShopListBox::mouseMoved(gcn::MouseEvent &event) } } } + +void ShopListBox::mouseExited(gcn::MouseEvent &event) +{ + mItemPopup->setVisible(false); +} + diff --git a/src/gui/widgets/shoplistbox.h b/src/gui/widgets/shoplistbox.h index 062ad93a..9232a5a4 100644 --- a/src/gui/widgets/shoplistbox.h +++ b/src/gui/widgets/shoplistbox.h @@ -47,6 +47,11 @@ class ShopListBox : public ListBox */ ShopListBox(gcn::ListModel *listModel, ShopItems *shopListModel); + /** + * Deconstructor + */ + ~ShopListBox(); + /** * Draws the list box. */ @@ -73,8 +78,16 @@ class ShopListBox : public ListBox */ void setPriceCheck(bool check); + /** + ** Show ItemTooltip + */ void mouseMoved(gcn::MouseEvent &event); + /** + ** Hide ItemTooltip + */ + void mouseExited(gcn::MouseEvent &event); + private: int mPlayerMoney; -- cgit v1.2.3-70-g09d2 From df91c40fa79629adb2652ed1b5141d943113a936 Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Fri, 20 Aug 2010 18:09:37 +0200 Subject: Show info popups for all players Until now popups were only shown for players who are member of a party. This resolves http://bugs.manasource.org/view.php?id=197 Signed-off-by: Jared Adams --- src/gui/beingpopup.cpp | 25 ++++++++++++++----------- 1 file changed, 14 insertions(+), 11 deletions(-) diff --git a/src/gui/beingpopup.cpp b/src/gui/beingpopup.cpp index 687b20c2..2150f7e5 100644 --- a/src/gui/beingpopup.cpp +++ b/src/gui/beingpopup.cpp @@ -65,25 +65,28 @@ void BeingPopup::show(int x, int y, Player *p) return; } + mBeingName->setCaption(p->getName()); + mBeingName->adjustSize(); + + int minWidth = mBeingName->getWidth(); + const int height = getFont()->getHeight(); + if (!(p->getPartyName().empty())) { - mBeingName->setCaption(p->getName()); - mBeingName->adjustSize(); - mBeingParty->setCaption(strprintf(_("Party: %s"), p->getPartyName().c_str())); mBeingParty->adjustSize(); - int minWidth = std::max(mBeingName->getWidth(), - mBeingParty->getWidth()); - - const int height = getFont()->getHeight(); + if (minWidth < mBeingParty->getWidth()) + minWidth = mBeingParty->getWidth(); setContentSize(minWidth + 10, (height * 2) + 10); - - position(x, y); - return; + } + else + { + mBeingParty->setCaption(""); + setContentSize(minWidth + 10, height + 10); } - setVisible(false); + position(x, y); } -- cgit v1.2.3-70-g09d2 From 0009672b80c666b8a7ddc0b7c36951eba1fa2c35 Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Sat, 21 Aug 2010 22:56:44 +0200 Subject: Fixing segmentation fault and improving gui for party MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * Segmentation fault happened if a player left a party while other party members are offline. * While creating a party the key input is not anymore reused for game play. * The vertical scrollbar is only shown when needed. * The default height was raised, because before much of the functionality was hidden. Signed-off-by: Thorbjørn Lindeijer --- src/game.cpp | 2 +- src/gui/socialwindow.cpp | 4 ++-- src/party.cpp | 2 +- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/src/game.cpp b/src/game.cpp index ec5e6b13..d34dc049 100644 --- a/src/game.cpp +++ b/src/game.cpp @@ -754,7 +754,7 @@ void Game::handleInput() // Moving player around if (player_node->isAlive() && !NPC::isTalking() && - !chatWindow->isInputFocused() && !quitDialog) + !chatWindow->isInputFocused() && !quitDialog && !TextDialog::isActive()) { // Get the state of the keyboard keys keyboard.refreshActiveKeys(); diff --git a/src/gui/socialwindow.cpp b/src/gui/socialwindow.cpp index 098ecbc5..f6e1d0aa 100644 --- a/src/gui/socialwindow.cpp +++ b/src/gui/socialwindow.cpp @@ -186,7 +186,7 @@ public: mScroll = new ScrollArea(mList); mScroll->setHorizontalScrollPolicy(gcn::ScrollArea::SHOW_AUTO); - mScroll->setVerticalScrollPolicy(gcn::ScrollArea::SHOW_ALWAYS); + mScroll->setVerticalScrollPolicy(gcn::ScrollArea::SHOW_AUTO); } ~PartyTab() @@ -321,7 +321,7 @@ SocialWindow::SocialWindow() : setCloseButton(true); setMinWidth(120); setMinHeight(55); - setDefaultSize(590, 200, 150, 60); + setDefaultSize(590, 200, 150, 124); setupWindow->registerWindowForReset(this); loadWindowState(); diff --git a/src/party.cpp b/src/party.cpp index 75283916..155de2ba 100644 --- a/src/party.cpp +++ b/src/party.cpp @@ -145,7 +145,7 @@ void Party::removeFromMembers() while(itr != itr_end) { Being *b = beingManager->findBeing((*itr)->getID()); - if (b->getType() == Being::PLAYER) + if (b && b->getType() == Being::PLAYER) static_cast(b)->setParty(NULL); ++itr; } -- cgit v1.2.3-70-g09d2 From 371c36f8817780a913bc2c600c2204e61267972d Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Sun, 22 Aug 2010 20:16:15 +0200 Subject: Fixing segmentation fault when tab gets removed MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit How to reproduce the bug: Leave a party, while the party tab in the chat window is not selected. Then click with the mouse on the chat window. Signed-off-by: Thorbjørn Lindeijer --- src/gui/widgets/tabbedarea.cpp | 20 +++----------------- 1 file changed, 3 insertions(+), 17 deletions(-) diff --git a/src/gui/widgets/tabbedarea.cpp b/src/gui/widgets/tabbedarea.cpp index a774ab22..101c9546 100644 --- a/src/gui/widgets/tabbedarea.cpp +++ b/src/gui/widgets/tabbedarea.cpp @@ -103,16 +103,12 @@ void TabbedArea::addTab(const std::string &caption, gcn::Widget *widget) void TabbedArea::removeTab(Tab *tab) { - int tabIndexToBeSelected = -1; - if (tab == mSelectedTab) { - int index = getSelectedTabIndex(); - - if (index == (int)mTabs.size() - 1 && mTabs.size() == 1) - tabIndexToBeSelected = -1; + if (getNumberOfTabs() > 1) + setSelectedTab(std::max(0, getSelectedTabIndex() - 1)); else - tabIndexToBeSelected = index - 1; + mSelectedTab = 0; } TabContainer::iterator iter; @@ -137,16 +133,6 @@ void TabbedArea::removeTab(Tab *tab) } } - if (tabIndexToBeSelected == -1) - { - mSelectedTab = NULL; - mWidgetContainer->clear(); - } - else - { - setSelectedTab(tabIndexToBeSelected); - } - adjustSize(); adjustTabPositions(); } -- cgit v1.2.3-70-g09d2 From 000c3799eb85234b9baf5ede86dd966d929112d8 Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Mon, 23 Aug 2010 17:28:05 +0200 Subject: Fixing segmentation fault in partyhandler Segmentation fault happens if a player leaves your party while he is out of sight. Signed-off-by: Jared Adams --- src/net/tmwa/partyhandler.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/net/tmwa/partyhandler.cpp b/src/net/tmwa/partyhandler.cpp index e86d41fa..a92a27df 100644 --- a/src/net/tmwa/partyhandler.cpp +++ b/src/net/tmwa/partyhandler.cpp @@ -253,7 +253,7 @@ void PartyHandler::handleMessage(Net::MessageIn &msg) nick.c_str()), BY_SERVER); Being *b = beingManager->findBeing(id); - if (b->getType() == Being::PLAYER) + if (b && b->getType() == Being::PLAYER) static_cast(b)->setParty(NULL); taParty->removeMember(id); -- cgit v1.2.3-70-g09d2 From 38474d0c3c14cf595aed61ee1e4a69d48abbcf92 Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Tue, 24 Aug 2010 17:24:14 +0200 Subject: Giving functionality to invite in socialwindow and allow enter key in textdialog Signed-off-by: Jared Adams --- src/gui/socialwindow.cpp | 3 --- src/gui/textdialog.cpp | 2 ++ src/net/tmwa/partyhandler.cpp | 16 +++++++++++----- 3 files changed, 13 insertions(+), 8 deletions(-) diff --git a/src/gui/socialwindow.cpp b/src/gui/socialwindow.cpp index f6e1d0aa..7a13f96b 100644 --- a/src/gui/socialwindow.cpp +++ b/src/gui/socialwindow.cpp @@ -203,9 +203,6 @@ public: { std::string name = mInviteDialog->getText(); Net::getPartyHandler()->invite(name); - - localChatTab->chatLog(strprintf(_("Invited user %s to party."), - name.c_str()), BY_SERVER); mInviteDialog = NULL; } else if (event.getId() == "~do invite") diff --git a/src/gui/textdialog.cpp b/src/gui/textdialog.cpp index 3e3aafe2..6faa1162 100644 --- a/src/gui/textdialog.cpp +++ b/src/gui/textdialog.cpp @@ -38,6 +38,8 @@ TextDialog::TextDialog(const std::string &title, const std::string &msg, mOkButton = new Button(_("OK"), "OK", this); gcn::Button *cancelButton = new Button(_("Cancel"), "CANCEL", this); + mTextField->addActionListener(this); + place(0, 0, textLabel, 4); place(0, 1, mTextField, 4); place(2, 2, mOkButton); diff --git a/src/net/tmwa/partyhandler.cpp b/src/net/tmwa/partyhandler.cpp index a92a27df..76108e9c 100644 --- a/src/net/tmwa/partyhandler.cpp +++ b/src/net/tmwa/partyhandler.cpp @@ -327,18 +327,24 @@ void PartyHandler::invite(Player *player) void PartyHandler::invite(const std::string &name) { - if (partyTab) + Being *invitee = beingManager->findBeingByName(name, Being::PLAYER); + + if (invitee) { - partyTab->chatLog(_("Inviting like this isn't supported at the moment."), - BY_SERVER); + invite((Player *)invitee); + partyTab->chatLog(strprintf(_("Invited user %s to party."), + name.c_str()), BY_SERVER); + } + else if (partyTab) + { + partyTab->chatLog(strprintf(_("Inviting failed, because you can't see " + "a player called %s."), name.c_str()), BY_SERVER); } else { localChatTab->chatLog(_("You can only inivte when you are in a party!"), BY_SERVER); } - - // TODO? } void PartyHandler::inviteResponse(const std::string &inviter, bool accept) -- cgit v1.2.3-70-g09d2 From 627e1271f0ac2e7bd95a83f521ecbcf1b554ba80 Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Wed, 25 Aug 2010 20:38:06 +0200 Subject: Adding autoComplete for invite Signed-off-by: Jared Adams --- src/gui/chat.h | 1 + src/gui/socialwindow.cpp | 17 ++++++++++++----- src/gui/textdialog.cpp | 10 +++++++--- src/gui/textdialog.h | 2 +- src/gui/widgets/shoplistbox.h | 2 +- src/gui/widgets/textfield.cpp | 16 +++++++++++++++- src/gui/widgets/textfield.h | 11 +++++++++++ 7 files changed, 48 insertions(+), 11 deletions(-) diff --git a/src/gui/chat.h b/src/gui/chat.h index e49d02c9..b0d91556 100644 --- a/src/gui/chat.h +++ b/src/gui/chat.h @@ -177,6 +177,7 @@ class ChatWindow : public Window, protected: friend class ChatTab; friend class WhisperTab; + friend class TextField; /** Remove the given tab from the window */ void removeTab(ChatTab *tab); diff --git a/src/gui/socialwindow.cpp b/src/gui/socialwindow.cpp index 7a13f96b..3d8afa44 100644 --- a/src/gui/socialwindow.cpp +++ b/src/gui/socialwindow.cpp @@ -121,12 +121,16 @@ public: if (event.getId() == "do invite") { std::string name = mInviteDialog->getText(); - Net::getGuildHandler()->invite(mGuild->getId(), name); - localChatTab->chatLog(strprintf(_("Invited user %s to guild %s."), + if (!name.empty()) + { + Net::getGuildHandler()->invite(mGuild->getId(), name); + localChatTab->chatLog(strprintf(_("Invited user %s to guild %s."), name.c_str(), mGuild->getName().c_str()), BY_SERVER); + } + mInviteDialog = NULL; } else if (event.getId() == "~do invite") @@ -153,7 +157,7 @@ protected: mInviteDialog = new TextDialog(_("Member Invite to Guild"), strprintf(_("Who would you like to invite to guild %s?"), mGuild->getName().c_str()), - socialWindow); + socialWindow, true); mInviteDialog->setActionEventId("do invite"); mInviteDialog->addActionListener(this); } @@ -202,7 +206,10 @@ public: if (event.getId() == "do invite") { std::string name = mInviteDialog->getText(); - Net::getPartyHandler()->invite(name); + + if (!name.empty()) + Net::getPartyHandler()->invite(name); + mInviteDialog = NULL; } else if (event.getId() == "~do invite") @@ -229,7 +236,7 @@ protected: mInviteDialog = new TextDialog(_("Member Invite to Party"), strprintf(_("Who would you like to invite to party %s?"), mParty->getName().c_str()), - socialWindow); + socialWindow, true); mInviteDialog->setActionEventId("do invite"); mInviteDialog->addActionListener(this); } diff --git a/src/gui/textdialog.cpp b/src/gui/textdialog.cpp index 6faa1162..28792a0b 100644 --- a/src/gui/textdialog.cpp +++ b/src/gui/textdialog.cpp @@ -30,14 +30,18 @@ int TextDialog::instances = 0; TextDialog::TextDialog(const std::string &title, const std::string &msg, - Window *parent): - Window(title, true, parent), - mTextField(new TextField) + Window *parent, bool autoCompleteEnabled): + Window(title, true, parent) { gcn::Label *textLabel = new Label(msg); mOkButton = new Button(_("OK"), "OK", this); gcn::Button *cancelButton = new Button(_("Cancel"), "CANCEL", this); + // In TextField the escape key will either cause autoComplete or lose focus + mTextField = new TextField("", ! autoCompleteEnabled); + if (autoCompleteEnabled) + mTextField->setAutoComplete(true); + mTextField->addActionListener(this); place(0, 0, textLabel, 4); diff --git a/src/gui/textdialog.h b/src/gui/textdialog.h index d4c611cc..aa8fcf8f 100644 --- a/src/gui/textdialog.h +++ b/src/gui/textdialog.h @@ -42,7 +42,7 @@ public: * @see Window::Window */ TextDialog(const std::string &title, const std::string &msg, - Window *parent = NULL); + Window *parent = NULL, bool autoCompleteEnabled = false); ~TextDialog(); diff --git a/src/gui/widgets/shoplistbox.h b/src/gui/widgets/shoplistbox.h index 9232a5a4..087bdd53 100644 --- a/src/gui/widgets/shoplistbox.h +++ b/src/gui/widgets/shoplistbox.h @@ -48,7 +48,7 @@ class ShopListBox : public ListBox ShopListBox(gcn::ListModel *listModel, ShopItems *shopListModel); /** - * Deconstructor + * Destructor */ ~ShopListBox(); diff --git a/src/gui/widgets/textfield.cpp b/src/gui/widgets/textfield.cpp index 4453f522..60a1f57f 100644 --- a/src/gui/widgets/textfield.cpp +++ b/src/gui/widgets/textfield.cpp @@ -21,9 +21,11 @@ #include "gui/widgets/textfield.h" +#include "beingmanager.h" #include "configuration.h" #include "graphics.h" +#include "gui/chat.h" #include "gui/palette.h" #include "gui/sdlinput.h" #include "gui/theme.h" @@ -43,7 +45,8 @@ ImageRect TextField::skin; TextField::TextField(const std::string &text, bool loseFocusOnTab): gcn::TextField(text), - mNumeric(false) + mNumeric(false), + mAutoComplete(false) { setFrameSize(2); @@ -246,6 +249,17 @@ void TextField::keyPressed(gcn::KeyEvent &keyEvent) break; case Key::TAB: + if (mAutoComplete && mText.size() > 0) + { + std::vector names; + beingManager->getPlayerNames(names, false); + std::string newName = chatWindow->autoComplete(names, mText); + if (newName != "") + { + setText(newName); + setCaretPosition(mText.size()); + } + } if (mLoseFocusOnTab) return; break; diff --git a/src/gui/widgets/textfield.h b/src/gui/widgets/textfield.h index 58e37f5c..1e6df9d6 100644 --- a/src/gui/widgets/textfield.h +++ b/src/gui/widgets/textfield.h @@ -90,6 +90,16 @@ class TextField : public gcn::TextField */ int getValue() const; + /** + * Set if the tabulator key causes auto complete + */ + void setAutoComplete(bool b ) {mAutoComplete = b;} + + /** + * Returns if the tabulator key causes auto complete + */ + bool getAutoComplete() {return mAutoComplete;} + private: void handlePaste(); @@ -100,6 +110,7 @@ class TextField : public gcn::TextField int mMinimum; int mMaximum; bool mLoseFocusOnTab; + bool mAutoComplete; }; #endif -- cgit v1.2.3-70-g09d2 From c538f6372d9068140231749b0225a6a355009074 Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Thu, 26 Aug 2010 17:54:16 +0200 Subject: Fixing segmentation fault when creating a new account This resolves http://bugs.manasource.org/view.php?id=171 Reviewed-by: Bertram. --- src/net/manaserv/loginhandler.cpp | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/net/manaserv/loginhandler.cpp b/src/net/manaserv/loginhandler.cpp index cb25f584..61671824 100644 --- a/src/net/manaserv/loginhandler.cpp +++ b/src/net/manaserv/loginhandler.cpp @@ -425,6 +425,8 @@ void LoginHandler::chooseServer(unsigned int server) void LoginHandler::registerAccount(LoginData *loginData) { + mLoginData = loginData; + MessageOut msg(PAMSG_REGISTER); msg.writeInt32(0); // client version -- cgit v1.2.3-70-g09d2 From ef9eec73b3cc96ebecdc061e9e956a462fdcc19f Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Fri, 27 Aug 2010 19:03:18 +0200 Subject: Changing findBeingByName so that it searches case insensitive Adding error message when trying to create a party with to long name. Removing non-existing files from C::B project. Signed-off-by: Jared Adams --- mana.cbp | 2 -- src/beingmanager.cpp | 2 +- src/gui/socialwindow.cpp | 6 ++++-- src/net/tmwa/partyhandler.cpp | 2 +- 4 files changed, 6 insertions(+), 6 deletions(-) diff --git a/mana.cbp b/mana.cbp index 459a660c..c855a9a9 100644 --- a/mana.cbp +++ b/mana.cbp @@ -137,7 +137,6 @@ - @@ -369,7 +368,6 @@ - diff --git a/src/beingmanager.cpp b/src/beingmanager.cpp index 656b297e..931e4579 100644 --- a/src/beingmanager.cpp +++ b/src/beingmanager.cpp @@ -165,7 +165,7 @@ Being *BeingManager::findBeingByName(const std::string &name, i != i_end; ++i) { Being *being = (*i); - if (being->getName() == name && + if (!compareStrI(being->getName(),name) && (type == Being::UNKNOWN || type == being->getType())) return being; } diff --git a/src/gui/socialwindow.cpp b/src/gui/socialwindow.cpp index 3d8afa44..290fd557 100644 --- a/src/gui/socialwindow.cpp +++ b/src/gui/socialwindow.cpp @@ -498,7 +498,8 @@ void SocialWindow::action(const gcn::ActionEvent &event) if (name.size() > 16) { - // TODO : State too many characters in input. + localChatTab->chatLog(_("Creating guild failed, please choose a " + "shorter name."), BY_SERVER); return; } @@ -518,7 +519,8 @@ void SocialWindow::action(const gcn::ActionEvent &event) if (name.size() > 16) { - // TODO : State too many characters in input. + localChatTab->chatLog(_("Creating party failed, please choose a " + "shorter name."), BY_SERVER); return; } diff --git a/src/net/tmwa/partyhandler.cpp b/src/net/tmwa/partyhandler.cpp index 76108e9c..a88a27b6 100644 --- a/src/net/tmwa/partyhandler.cpp +++ b/src/net/tmwa/partyhandler.cpp @@ -333,7 +333,7 @@ void PartyHandler::invite(const std::string &name) { invite((Player *)invitee); partyTab->chatLog(strprintf(_("Invited user %s to party."), - name.c_str()), BY_SERVER); + invitee->getName().c_str()), BY_SERVER); } else if (partyTab) { -- cgit v1.2.3-70-g09d2 From 919e6bef84e3670b206f192613558274a341b976 Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Sat, 28 Aug 2010 18:56:14 +0200 Subject: Fixing omitted items in equipment window Bug description: If a player has equipable items only, then the equipment backend gets not initialized. As a consequence the equipment window remains empty. This is particularly a problem for new characters. Signed-off-by: Jared Adams --- src/net/tmwa/inventoryhandler.cpp | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/net/tmwa/inventoryhandler.cpp b/src/net/tmwa/inventoryhandler.cpp index fd979dc6..7363c738 100644 --- a/src/net/tmwa/inventoryhandler.cpp +++ b/src/net/tmwa/inventoryhandler.cpp @@ -127,6 +127,7 @@ void InventoryHandler::handleMessage(Net::MessageIn &msg) int index, amount, itemId, equipType, arrow; int identified, cards[4], itemType; Inventory *inventory = player_node->getInventory(); + player_node->mEquipment->setBackend(&mEquips); switch (msg.getId()) { @@ -136,8 +137,6 @@ void InventoryHandler::handleMessage(Net::MessageIn &msg) { // Clear inventory - this will be a complete refresh mEquips.clear(); - player_node->mEquipment->setBackend(&mEquips); - inventory->clear(); } else -- cgit v1.2.3-70-g09d2 From b61faa43db7a48c6a6871fb94dce2de2abd79dfe Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Sun, 29 Aug 2010 19:05:38 +0200 Subject: Changing order in which windows are created The mini status window is higher than its visible area. Creating it first makes sure that it does not overlap other windows. For example put the equipment window right below the mini status window. After a restart you cannot use the close button nor drag it, because you are actually clicking on the mini status window. Signed-off-by: Jared Adams --- src/game.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/game.cpp b/src/game.cpp index d34dc049..eb666fa9 100644 --- a/src/game.cpp +++ b/src/game.cpp @@ -148,14 +148,14 @@ static void createGuiWindows() setupWindow->clearWindowsForReset(); // Create dialogs + miniStatusWindow = new MiniStatusWindow; + minimap = new Minimap; chatWindow = new ChatWindow; tradeWindow = new TradeWindow; equipmentWindow = new EquipmentWindow(player_node->mEquipment.get()); statusWindow = new StatusWindow; - miniStatusWindow = new MiniStatusWindow; inventoryWindow = new InventoryWindow(player_node->getInventory()); skillDialog = new SkillDialog; - minimap = new Minimap; helpWindow = new HelpWindow; debugWindow = new DebugWindow; itemShortcutWindow = new ShortcutWindow("ItemShortcut", -- cgit v1.2.3-70-g09d2 From d55c1345449a34adb3192c23fe3760bd0aae645b Mon Sep 17 00:00:00 2001 From: Jared Adams Date: Sun, 29 Aug 2010 09:01:27 -0600 Subject: Move handling of autocomplete and input history into TextField Reviewed-by: Freeyorp --- src/beingmanager.cpp | 61 +++++++++++---- src/beingmanager.h | 12 ++- src/gui/chat.cpp | 178 ++++-------------------------------------- src/gui/chat.h | 25 ++---- src/gui/textdialog.cpp | 4 +- src/gui/widgets/chattab.cpp | 6 ++ src/gui/widgets/chattab.h | 7 +- src/gui/widgets/textfield.cpp | 137 +++++++++++++++++++++++++++++--- src/gui/widgets/textfield.h | 68 ++++++++++++++-- src/utils/stringutils.cpp | 37 ++++++++- src/utils/stringutils.h | 4 + 11 files changed, 318 insertions(+), 221 deletions(-) diff --git a/src/beingmanager.cpp b/src/beingmanager.cpp index 931e4579..d7045684 100644 --- a/src/beingmanager.cpp +++ b/src/beingmanager.cpp @@ -53,8 +53,48 @@ class FindBeingFunctor Being::Type type; } beingFinder; +class PlayerNamesLister : public AutoCompleteLister +{ + void getAutoCompleteList(std::vector& names) const + { + Beings::iterator i = beingManager->mBeings.begin(); + names.clear(); + + while (i != beingManager->mBeings.end()) + { + Being *being = (*i); + if (being->getType() == Being::PLAYER && being->getName() != "") + names.push_back(being->getName()); + + ++i; + } + } +}; + +class PlayerNPCNamesLister : public AutoCompleteLister +{ + void getAutoCompleteList(std::vector& names) const + { + Beings::iterator i = beingManager->mBeings.begin(); + names.clear(); + + while (i != beingManager->mBeings.end()) + { + Being *being = (*i); + if ((being->getType() == Being::PLAYER + || being->getType() == Being::NPC) + && being->getName() != "") + names.push_back(being->getName()); + + ++i; + } + } +}; + BeingManager::BeingManager() { + mPlayerNames = new PlayerNamesLister; + mPlayerNPCNames = new PlayerNPCNamesLister; } BeingManager::~BeingManager() @@ -263,23 +303,14 @@ bool BeingManager::hasBeing(Being *being) const return false; } -void BeingManager::getPlayerNames(std::vector &names, - bool npcNames) +AutoCompleteLister *BeingManager::getPlayerNameLister() { - Beings::iterator i = mBeings.begin(); - names.clear(); + return mPlayerNames; +} - while (i != mBeings.end()) - { - Being *being = (*i); - if ((being->getType() == Being::PLAYER - || (being->getType() == Being::NPC && npcNames)) - && being->getName() != "") - { - names.push_back(being->getName()); - } - ++i; - } +AutoCompleteLister *BeingManager::getPlayerNPCNameLister() +{ + return mPlayerNPCNames; } void BeingManager::updatePlayerNames() diff --git a/src/beingmanager.h b/src/beingmanager.h index 7fd63afe..f2f8eb6d 100644 --- a/src/beingmanager.h +++ b/src/beingmanager.h @@ -24,6 +24,8 @@ #include "being.h" +#include "gui/widgets/textfield.h" + class LocalPlayer; class Map; @@ -122,12 +124,18 @@ class BeingManager */ void clear(); - void getPlayerNames(std::vector &names, - bool npcNames); + AutoCompleteLister *getPlayerNameLister(); + + AutoCompleteLister *getPlayerNPCNameLister(); void updatePlayerNames(); protected: + friend class PlayerNamesLister; + friend class PlayerNPCNamesLister; + + AutoCompleteLister *mPlayerNames; + AutoCompleteLister *mPlayerNPCNames; Beings mBeings; Map *mMap; }; diff --git a/src/gui/chat.cpp b/src/gui/chat.cpp index f87a8a3d..6d900e98 100644 --- a/src/gui/chat.cpp +++ b/src/gui/chat.cpp @@ -72,9 +72,21 @@ class ChatInput : public TextField, public gcn::FocusListener } }; +class ChatAutoComplete : public AutoCompleteLister +{ + void getAutoCompleteList(std::vector &list) const + { + ChatTab *tab = static_cast(chatWindow->mChatTabs + ->getSelectedTab()); + + return tab->getAutoCompleteList(list); + } +}; ChatWindow::ChatWindow(): Window(_("Chat")), + mHistory(new TextHistory()), + mAutoComplete(new ChatAutoComplete), mTmpVisible(false) { setWindowName("Chat"); @@ -104,9 +116,8 @@ ChatWindow::ChatWindow(): loadWindowState(); - // Add key listener to chat input to be able to respond to up/down - mChatInput->addKeyListener(this); - mCurHist = mHistory.end(); + mChatInput->setHistory(mHistory); + mChatInput->setAutoComplete(mAutoComplete); mReturnToggles = config.getValue("ReturnToggles", "0") == "1"; @@ -119,6 +130,8 @@ ChatWindow::~ChatWindow() delete mRecorder; removeAllWhispers(); delete mItemLinkHandler; + delete mHistory; + delete mAutoComplete; } void ChatWindow::resetToDefaultSize() @@ -173,14 +186,6 @@ void ChatWindow::action(const gcn::ActionEvent &event) if (!message.empty()) { - // If message different from previous, put it in the history - if (mHistory.empty() || message != mHistory.back()) - { - mHistory.push_back(message); - } - // Reset history iterator - mCurHist = mHistory.end(); - // Send the message to the server chatInput(message); @@ -366,48 +371,6 @@ void ChatWindow::mouseDragged(gcn::MouseEvent &event) } } - -void ChatWindow::keyPressed(gcn::KeyEvent &event) -{ - if (event.getKey().getValue() == Key::DOWN) - { - if (mCurHist != mHistory.end()) - { - // Move forward through the history - HistoryIterator prevHist = mCurHist++; - - if (mCurHist != mHistory.end()) - { - mChatInput->setText(*mCurHist); - mChatInput->setCaretPosition(mChatInput->getText().length()); - } - else - { - mChatInput->setText(""); - mCurHist = prevHist; - } - } - else if (mChatInput->getText() != "") - { - mChatInput->setText(""); - } - } - else if (event.getKey().getValue() == Key::UP && - mCurHist != mHistory.begin() && mHistory.size() > 0) - { - // Move backward through the history - mCurHist--; - mChatInput->setText(*mCurHist); - mChatInput->setCaretPosition(mChatInput->getText().length()); - } - else if (event.getKey().getValue() == Key::TAB && - mChatInput->getText() != "") - { - autoComplete(); - return; - } -} - void ChatWindow::addInputText(const std::string &text) { const int caretPos = mChatInput->getCaretPosition(); @@ -516,112 +479,3 @@ ChatTab *ChatWindow::addWhisperTab(const std::string &nick, bool switchTo) return ret; } - -void ChatWindow::autoComplete() -{ - int caretPos = mChatInput->getCaretPosition(); - int startName = 0; - const std::string inputText = mChatInput->getText(); - std::string name = inputText.substr(0, caretPos); - std::string newName(""); - - for (int f = caretPos - 1; f > -1; f --) - { - if (isWordSeparator(inputText[f])) - { - startName = f + 1; - name = inputText.substr(f + 1, caretPos - f); - break; - } - } - - if (caretPos - 1 + 1 == startName) - return; - - - ChatTab *cTab = static_cast(mChatTabs->getSelectedTab()); - std::vector nameList; - cTab->getAutoCompleteList(nameList); - newName = autoComplete(nameList, name); - - if (newName == "") - { - beingManager->getPlayerNames(nameList, true); - newName = autoComplete(nameList, name); - } - if (newName == "") - { - newName = autoCompleteHistory(name); - } - - if (newName != "") - { - if(inputText[0] == '@' || inputText[0] == '/') - newName = "\"" + newName + "\""; - - mChatInput->setText(inputText.substr(0, startName) + newName - + inputText.substr(caretPos, inputText.length() - caretPos)); - - if (startName > 0) - mChatInput->setCaretPosition(caretPos - name.length() + newName.length() + 1); - else - mChatInput->setCaretPosition(caretPos - name.length() + newName.length()); - } -} - -std::string ChatWindow::autoComplete(std::vector &names, - std::string partName) const -{ - std::vector::iterator i = names.begin(); - toLower(partName); - std::string newName(""); - - while (i != names.end()) - { - if (!i->empty()) - { - std::string name = *i; - toLower(name); - - std::string::size_type pos = name.find(partName, 0); - if (pos == 0) - { - if (newName != "") - { - toLower(newName); - newName = findSameSubstring(name, newName); - } - else - { - newName = *i; - } - } - } - ++i; - } - - return newName; -} - -std::string ChatWindow::autoCompleteHistory(std::string partName) -{ - History::iterator i = mHistory.begin(); - std::vector nameList; - - while (i != mHistory.end()) - { - std::string line = *i; - unsigned int f = 0; - while (f < line.length() && !isWordSeparator(line.at(f))) - { - f++; - } - line = line.substr(0, f); - if (line != "") - { - nameList.push_back(line); - } - ++i; - } - return autoComplete(nameList, partName); -} diff --git a/src/gui/chat.h b/src/gui/chat.h index b0d91556..1c673556 100644 --- a/src/gui/chat.h +++ b/src/gui/chat.h @@ -23,6 +23,7 @@ #define CHAT_H #include "gui/widgets/window.h" +#include "gui/widgets/textfield.h" #include #include @@ -61,8 +62,7 @@ struct CHATLOG * \ingroup Interface */ class ChatWindow : public Window, - public gcn::ActionListener, - public gcn::KeyListener + public gcn::ActionListener { public: /** @@ -131,9 +131,6 @@ class ChatWindow : public Window, */ void chatInput(const std::string &msg); - /** Called when key is pressed */ - void keyPressed(gcn::KeyEvent &event); - /** Add the given text to the chat input. */ void addInputText(const std::string &text); @@ -143,11 +140,9 @@ class ChatWindow : public Window, /** Override to reset mTmpVisible */ void setVisible(bool visible); - void mousePressed(gcn::MouseEvent &event); void mouseDragged(gcn::MouseEvent &event); - /** * Scrolls the chat window * @@ -177,7 +172,7 @@ class ChatWindow : public Window, protected: friend class ChatTab; friend class WhisperTab; - friend class TextField; + friend class ChatAutoComplete; /** Remove the given tab from the window */ void removeTab(ChatTab *tab); @@ -189,13 +184,6 @@ class ChatWindow : public Window, void removeAllWhispers(); - void autoComplete(); - - std::string autoCompleteHistory(std::string partName); - - std::string autoComplete(std::vector &names, - std::string partName) const; - /** Used for showing item popup on clicking links **/ ItemLinkHandler *mItemLinkHandler; Recorder *mRecorder; @@ -203,6 +191,9 @@ class ChatWindow : public Window, /** Input box for typing chat messages. */ ChatInput *mChatInput; + TextHistory *mHistory; + AutoCompleteLister *mAutoComplete; + private: bool mTmpVisible; @@ -213,10 +204,6 @@ class ChatWindow : public Window, /** Manage whisper tabs */ TabMap mWhispers; - typedef std::list History; - typedef History::iterator HistoryIterator; - History mHistory; /**< Command history. */ - HistoryIterator mCurHist; /**< History iterator. */ bool mReturnToggles; /**< Marks whether toggles the chat log or not */ }; diff --git a/src/gui/textdialog.cpp b/src/gui/textdialog.cpp index 28792a0b..d9728357 100644 --- a/src/gui/textdialog.cpp +++ b/src/gui/textdialog.cpp @@ -21,6 +21,8 @@ #include "gui/textdialog.h" +#include "beingmanager.h" + #include "gui/widgets/button.h" #include "gui/widgets/label.h" #include "gui/widgets/textfield.h" @@ -40,7 +42,7 @@ TextDialog::TextDialog(const std::string &title, const std::string &msg, // In TextField the escape key will either cause autoComplete or lose focus mTextField = new TextField("", ! autoCompleteEnabled); if (autoCompleteEnabled) - mTextField->setAutoComplete(true); + mTextField->setAutoComplete(beingManager->getPlayerNameLister()); mTextField->addActionListener(this); diff --git a/src/gui/widgets/chattab.cpp b/src/gui/widgets/chattab.cpp index 39ea6887..8bf57508 100644 --- a/src/gui/widgets/chattab.cpp +++ b/src/gui/widgets/chattab.cpp @@ -21,6 +21,7 @@ #include "gui/widgets/chattab.h" +#include "beingmanager.h" #include "commandhandler.h" #include "configuration.h" #include "localplayer.h" @@ -275,6 +276,11 @@ void ChatTab::handleCommand(const std::string &msg) commandHandler->handleCommand(msg, this); } +void ChatTab::getAutoCompleteList(std::vector &names) const +{ + beingManager->getPlayerNPCNameLister()->getAutoCompleteList(names); +} + void ChatTab::addRow(std::string &line) { std::string::size_type idx = 0; diff --git a/src/gui/widgets/chattab.h b/src/gui/widgets/chattab.h index 7fd3931e..c2dfa1c1 100644 --- a/src/gui/widgets/chattab.h +++ b/src/gui/widgets/chattab.h @@ -25,6 +25,7 @@ #include "gui/chat.h" #include "gui/widgets/tab.h" +#include "gui/widgets/textfield.h" class BrowserBox; class Recorder; @@ -45,7 +46,7 @@ enum /** * A tab for the chat window. This is special to ease chat handling. */ -class ChatTab : public Tab +class ChatTab : public Tab, public AutoCompleteLister { public: /** @@ -111,6 +112,8 @@ class ChatTab : public Tab const std::string &args) { return false; } + void getAutoCompleteList(std::vector &names) const; + protected: friend class ChatWindow; friend class WhisperWindow; @@ -121,8 +124,6 @@ class ChatTab : public Tab virtual void handleCommand(const std::string &msg); - virtual void getAutoCompleteList(std::vector&) const {} - void addRow(std::string &line); ScrollArea *mScrollArea; diff --git a/src/gui/widgets/textfield.cpp b/src/gui/widgets/textfield.cpp index 60a1f57f..3e02be98 100644 --- a/src/gui/widgets/textfield.cpp +++ b/src/gui/widgets/textfield.cpp @@ -25,7 +25,6 @@ #include "configuration.h" #include "graphics.h" -#include "gui/chat.h" #include "gui/palette.h" #include "gui/sdlinput.h" #include "gui/theme.h" @@ -34,6 +33,7 @@ #include "utils/copynpaste.h" #include "utils/dtor.h" +#include "utils/stringutils.h" #include @@ -46,7 +46,8 @@ ImageRect TextField::skin; TextField::TextField(const std::string &text, bool loseFocusOnTab): gcn::TextField(text), mNumeric(false), - mAutoComplete(false) + mAutoComplete(NULL), + mHistory(NULL) { setFrameSize(2); @@ -212,6 +213,42 @@ void TextField::keyPressed(gcn::KeyEvent &keyEvent) } } break; + case Key::UP: + { + if (mHistory && !mHistory->atBegining() && !mHistory->empty()) + { + // Move backward through the history + mHistory->current--; + setText(*mHistory->current); + setCaretPosition(getText().length()); + } + } break; + + case Key::DOWN: + { + if (mHistory && !mHistory->atEnd()) + { + // Move forward through the history + TextHistoryIterator prevHist = mHistory->current++; + + if (!mHistory->atEnd()) + { + setText(*mHistory->current); + setCaretPosition(getText().length()); + } + else + { + setText(""); + mHistory->current = prevHist; + } + } + else if (getText() != "") + { + // Always clear (easy access to useful function) + setText(""); + } + } break; + case Key::DELETE: { unsigned sz = mText.size(); @@ -237,6 +274,19 @@ void TextField::keyPressed(gcn::KeyEvent &keyEvent) } break; case Key::ENTER: + if (mHistory) + { + mHistory->toEnd(); + + // If the input is different from previous, put it in the history + if (mHistory->empty() || !mHistory->matchesEntry(getText())) + { + mHistory->addEntry(getText()); + } + + mHistory->toEnd(); + } + distributeActionEvent(); break; @@ -249,17 +299,7 @@ void TextField::keyPressed(gcn::KeyEvent &keyEvent) break; case Key::TAB: - if (mAutoComplete && mText.size() > 0) - { - std::vector names; - beingManager->getPlayerNames(names, false); - std::string newName = chatWindow->autoComplete(names, mText); - if (newName != "") - { - setText(newName); - setCaretPosition(mText.size()); - } - } + autoComplete(); if (mLoseFocusOnTab) return; break; @@ -273,6 +313,77 @@ void TextField::keyPressed(gcn::KeyEvent &keyEvent) fixScroll(); } +void TextField::autoComplete() +{ + if (mAutoComplete && mText.size() > 0) + { + int caretPos = getCaretPosition(); + int startName = 0; + const std::string inputText = getText(); + std::string name = inputText.substr(0, caretPos); + std::string newName(""); + + for (int f = caretPos - 1; f > -1; f --) + { + if (isWordSeparator(inputText[f])) + { + startName = f + 1; + name = inputText.substr(f + 1, caretPos - f); + break; + } + } + + if (caretPos - 1 + 1 != startName) + return; + + + std::vector nameList; + mAutoComplete->getAutoCompleteList(nameList); + newName = autocomplete(nameList, name); + + if (newName == "" && mHistory) + { + + TextHistoryIterator i = mHistory->history.begin(); + std::vector nameList; + + while (i != mHistory->history.end()) + { + std::string line = *i; + unsigned int f = 0; + while (f < line.length() && !isWordSeparator(line.at(f))) + { + f++; + } + line = line.substr(0, f); + if (line != "") + { + nameList.push_back(line); + } + ++i; + } + + newName = autocomplete(nameList, name); + } + + if (newName != "") + { + if(inputText[0] == '@' || inputText[0] == '/') + newName = "\"" + newName + "\""; + + setText(inputText.substr(0, startName) + newName + + inputText.substr(caretPos, inputText.length() + - caretPos)); + + if (startName > 0) + setCaretPosition(caretPos - name.length() + newName.length() + + 1); + else + setCaretPosition(caretPos - name.length() + newName.length()); + } + } +} + void TextField::handlePaste() { std::string text = getText(); diff --git a/src/gui/widgets/textfield.h b/src/gui/widgets/textfield.h index 1e6df9d6..6e50f1e9 100644 --- a/src/gui/widgets/textfield.h +++ b/src/gui/widgets/textfield.h @@ -24,9 +24,48 @@ #include +#include + class ImageRect; class TextField; +typedef std::list TextHistoryList; +typedef TextHistoryList::iterator TextHistoryIterator; + +struct TextHistory { + TextHistoryList history; /**< Command history. */ + TextHistoryIterator current; /**< History iterator. */ + + TextHistory() + { current = history.end(); } + + bool empty() const + { return history.empty(); } + + bool atBegining() const + { return current == history.begin(); } + + bool atEnd() const + { return current == history.end(); } + + void toBegining() + { current = history.begin(); } + + void toEnd() + { current = history.end(); } + + void addEntry(const std::string &text) + { history.push_back(text); } + + bool matchesEntry(const std::string &text) + { return (*current) == text; } +}; + +class AutoCompleteLister { +public: + virtual void getAutoCompleteList(std::vector&) const {} +}; + /** * A text field. * @@ -91,16 +130,32 @@ class TextField : public gcn::TextField int getValue() const; /** - * Set if the tabulator key causes auto complete + * Sets the TextField's source of autocomplete. Passing null will + * disable autocomplete. + */ + void setAutoComplete(AutoCompleteLister *lister) + { mAutoComplete = lister; } + + /** + * Returns the TextField's source of autocomplete. */ - void setAutoComplete(bool b ) {mAutoComplete = b;} + AutoCompleteLister *getAutoComplete() const + { return mAutoComplete; } /** - * Returns if the tabulator key causes auto complete + * Sets the TextField's source of input history. */ - bool getAutoComplete() {return mAutoComplete;} + void setHistory(TextHistory *history) + { mHistory = history; } + + /** + * Returns the TextField's source of input history. + */ + TextHistory *getHistory() const + { return mHistory; } private: + void autoComplete(); void handlePaste(); static int instances; @@ -110,7 +165,10 @@ class TextField : public gcn::TextField int mMinimum; int mMaximum; bool mLoseFocusOnTab; - bool mAutoComplete; + + AutoCompleteLister *mAutoComplete; + + TextHistory *mHistory; /**< Text history. */ }; #endif diff --git a/src/utils/stringutils.cpp b/src/utils/stringutils.cpp index 9fe3de14..445427fe 100644 --- a/src/utils/stringutils.cpp +++ b/src/utils/stringutils.cpp @@ -174,4 +174,39 @@ const char* getSafeUtf8String(std::string text) memcpy(buf, text.c_str(), text.size()); memset(buf + text.size(), 0, UTF8_MAX_SIZE); return buf; -} \ No newline at end of file +} + +std::string autocomplete(std::vector &candidates, + std::string base) +{ + std::vector::iterator i = candidates.begin(); + toLower(base); + std::string newName(""); + + while (i != candidates.end()) + { + if (!i->empty()) + { + std::string name = *i; + toLower(name); + + std::string::size_type pos = name.find(base, 0); + if (pos == 0) + { + if (newName != "") + { + toLower(newName); + newName = findSameSubstring(name, newName); + } + else + { + newName = *i; + } + } + } + + ++i; + } + + return newName; +} diff --git a/src/utils/stringutils.h b/src/utils/stringutils.h index ec82e240..5f1f05f0 100644 --- a/src/utils/stringutils.h +++ b/src/utils/stringutils.h @@ -24,6 +24,7 @@ #include #include +#include /** * Trims spaces off the end and the beginning of the given string. @@ -125,4 +126,7 @@ const std::string findSameSubstring(const std::string &str1, const std::string & const char* getSafeUtf8String(std::string text); +std::string autocomplete(std::vector &candidates, + std::string base); + #endif // UTILS_STRINGUTILS_H -- cgit v1.2.3-70-g09d2 From f63a221850062da5b676c7dce258405f59486530 Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Mon, 30 Aug 2010 19:26:33 +0200 Subject: Fixing segmentation fault and making invite to guild in pop-up conditional How to reproduce the segmentation fault: Open the emote pop-up. Then press the escape key and switch the character. The emote pop-up is still open and clicking on it makes the game crash. Signed-off-by: Jared Adams --- src/gui/popupmenu.cpp | 3 ++- src/gui/windowmenu.cpp | 1 + 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/src/gui/popupmenu.cpp b/src/gui/popupmenu.cpp index 520b4005..01870e62 100644 --- a/src/gui/popupmenu.cpp +++ b/src/gui/popupmenu.cpp @@ -128,7 +128,8 @@ void PopupMenu::showPopup(int x, int y, Being *being) mBrowserBox->addRow(strprintf("@@follow|%s@@", strprintf(_("Follow %s"), name.c_str()).c_str())); - mBrowserBox->addRow(strprintf("@@guild|%s@@", + if (player_node->getNumberOfGuilds()) + mBrowserBox->addRow(strprintf("@@guild|%s@@", strprintf(_("Invite %s to join your guild"), name.c_str()).c_str())); if (player_node->isInParty()) diff --git a/src/gui/windowmenu.cpp b/src/gui/windowmenu.cpp index 5af5a202..4b18de89 100644 --- a/src/gui/windowmenu.cpp +++ b/src/gui/windowmenu.cpp @@ -72,6 +72,7 @@ WindowMenu::WindowMenu(): WindowMenu::~WindowMenu() { + delete mEmotePopup; } void WindowMenu::action(const gcn::ActionEvent &event) -- cgit v1.2.3-70-g09d2 From fe08ffb9047bed67474aa8519051a0d4dcab98c5 Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Tue, 31 Aug 2010 23:15:04 +0200 Subject: Fixing auto complete and chat history Reviewed-by: Jaxad0127 --- src/gui/widgets/textfield.cpp | 18 ++++++------------ src/gui/widgets/textfield.h | 4 ++-- 2 files changed, 8 insertions(+), 14 deletions(-) diff --git a/src/gui/widgets/textfield.cpp b/src/gui/widgets/textfield.cpp index 3e02be98..cffda1e3 100644 --- a/src/gui/widgets/textfield.cpp +++ b/src/gui/widgets/textfield.cpp @@ -276,10 +276,8 @@ void TextField::keyPressed(gcn::KeyEvent &keyEvent) case Key::ENTER: if (mHistory) { - mHistory->toEnd(); - // If the input is different from previous, put it in the history - if (mHistory->empty() || !mHistory->matchesEntry(getText())) + if (mHistory->empty() || !mHistory->matchesLastEntry(getText())) { mHistory->addEntry(getText()); } @@ -317,23 +315,23 @@ void TextField::autoComplete() { if (mAutoComplete && mText.size() > 0) { - int caretPos = getCaretPosition(); + const int caretPos = getCaretPosition(); int startName = 0; const std::string inputText = getText(); std::string name = inputText.substr(0, caretPos); std::string newName(""); - for (int f = caretPos - 1; f > -1; f --) + for (int f = caretPos - 1; f > -1; f--) { if (isWordSeparator(inputText[f])) { startName = f + 1; - name = inputText.substr(f + 1, caretPos - f); + name = inputText.substr(f + 1, caretPos - startName); break; } } - if (caretPos - 1 + 1 != startName) + if (caretPos == startName) return; @@ -375,11 +373,7 @@ void TextField::autoComplete() + inputText.substr(caretPos, inputText.length() - caretPos)); - if (startName > 0) - setCaretPosition(caretPos - name.length() + newName.length() - + 1); - else - setCaretPosition(caretPos - name.length() + newName.length()); + setCaretPosition(caretPos - name.length() + newName.length()); } } } diff --git a/src/gui/widgets/textfield.h b/src/gui/widgets/textfield.h index 6e50f1e9..1963f9fa 100644 --- a/src/gui/widgets/textfield.h +++ b/src/gui/widgets/textfield.h @@ -57,8 +57,8 @@ struct TextHistory { void addEntry(const std::string &text) { history.push_back(text); } - bool matchesEntry(const std::string &text) - { return (*current) == text; } + bool matchesLastEntry(const std::string &text) + { return history.back() == text; } }; class AutoCompleteLister { -- cgit v1.2.3-70-g09d2 From 76ec7d66c0bb691f3409beb2448718a0bcefcc50 Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Thu, 2 Sep 2010 21:17:08 +0200 Subject: Fixing escape key in charselectdialog * In charselectdialog the requestFocus is now called later, because before it had no effect, since it was called before the characters were present. Having no char with focus has the side effect that the escape key gets ignored. * Removing the code for variable width of CharacterDisplay, because with recent changes it is executed before the characters are present, therefore it had no effect. --- src/gui/charselectdialog.cpp | 20 ++++++-------------- 1 file changed, 6 insertions(+), 14 deletions(-) diff --git a/src/gui/charselectdialog.cpp b/src/gui/charselectdialog.cpp index e22c4daf..f8c28c6a 100644 --- a/src/gui/charselectdialog.cpp +++ b/src/gui/charselectdialog.cpp @@ -164,10 +164,10 @@ CharSelectDialog::CharSelectDialog(LoginData *loginData): addKeyListener(this); center(); - mCharacterEntries[0]->requestFocus(); setVisible(true); Net::getCharHandler()->setCharSelectDialog(this); + mCharacterEntries[0]->requestFocus(); } CharSelectDialog::~CharSelectDialog() @@ -328,10 +328,10 @@ CharacterDisplay::CharacterDisplay(CharSelectDialog *charSelectDialog): mCharacter(0), mPlayerBox(new PlayerBox) { - mButton = new Button("wwwwwwwww", "go", charSelectDialog); - mName = new Label("wwwwwwwwwwwwwwwwwwwwwwww"); - mLevel = new Label("(888)"); - mMoney = new Label("wwwwwwwww"); + mButton = new Button("", "go", charSelectDialog); + mName = new Label(""); + mLevel = new Label(""); + mMoney = new Label(""); mDelete = new Button(_("Delete"), "delete", charSelectDialog); @@ -347,15 +347,7 @@ CharacterDisplay::CharacterDisplay(CharSelectDialog *charSelectDialog): update(); - // Setting the width so that the largest label fits. - mName->adjustSize(); - mMoney->adjustSize(); - int width = 74; - if (width < 20 + mName->getWidth()) - width = 20 + mName->getWidth(); - if (width < 20 + mMoney->getWidth()) - width = 20 + mMoney->getWidth(); - h.reflowLayout(width, 112 + mName->getHeight() + mLevel->getHeight() + + h.reflowLayout(80, 112 + mName->getHeight() + mLevel->getHeight() + mMoney->getHeight() + mButton->getHeight() + mDelete->getHeight()); } -- cgit v1.2.3-70-g09d2 From e806e70958f68a3b0dc9c841cacabacf011ac973 Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Thu, 2 Sep 2010 21:26:39 +0200 Subject: Avoiding empty lines in history --- src/gui/widgets/textfield.cpp | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/gui/widgets/textfield.cpp b/src/gui/widgets/textfield.cpp index cffda1e3..4989ae83 100644 --- a/src/gui/widgets/textfield.cpp +++ b/src/gui/widgets/textfield.cpp @@ -277,7 +277,8 @@ void TextField::keyPressed(gcn::KeyEvent &keyEvent) if (mHistory) { // If the input is different from previous, put it in the history - if (mHistory->empty() || !mHistory->matchesLastEntry(getText())) + if (!getText().empty() && (mHistory->empty() || + !mHistory->matchesLastEntry(getText()))) { mHistory->addEntry(getText()); } -- cgit v1.2.3-70-g09d2 From 49452a005f4273b3ec91470883f308690e2269ac Mon Sep 17 00:00:00 2001 From: Jared Adams Date: Thu, 2 Sep 2010 19:14:08 -0600 Subject: Fix crash with missing skill icon Reviewed-by: Bertram --- src/gui/skilldialog.cpp | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/src/gui/skilldialog.cpp b/src/gui/skilldialog.cpp index 53528cee..207e3ded 100644 --- a/src/gui/skilldialog.cpp +++ b/src/gui/skilldialog.cpp @@ -73,9 +73,14 @@ struct SkillInfo float progress; gcn::Color color; + SkillInfo() : + icon(NULL) + {} + ~SkillInfo() { - icon->decRef(); + if (icon) + icon->decRef(); } void setIcon(const std::string &iconPath) @@ -85,7 +90,8 @@ struct SkillInfo { icon = res->getImage(iconPath); } - else + + if (!icon) { icon = Theme::getImageFromTheme("unknown-item.png"); } -- cgit v1.2.3-70-g09d2 From c99347bf9108367c02dcbdebadec0b978a750c57 Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Sat, 4 Sep 2010 23:50:20 +0200 Subject: Fixing segmentation fault if server is given on command line If server and port was given on the command line, then the server type was unknown. The command line options do work now, but only if standard ports 6901 and 9601 are used. This resolves http://bugs.manasource.org/view.php?id=177 TODO: Query the server about itself and choose the server type based on that. Reviewed-by: Jaxad0127 --- src/client.cpp | 12 +++++++----- src/net/net.cpp | 12 +++++++++++- src/net/net.h | 2 +- 3 files changed, 19 insertions(+), 7 deletions(-) diff --git a/src/client.cpp b/src/client.cpp index b63550e6..3946d0f9 100644 --- a/src/client.cpp +++ b/src/client.cpp @@ -604,11 +604,13 @@ int Client::exec() case STATE_CHOOSE_SERVER: logger->log("State: CHOOSE SERVER"); - // Allow changing this using a server choice dialog - // We show the dialog box only if the command-line - // options weren't set. - if (mOptions.serverName.empty() && mOptions.serverPort == 0 - && !branding.getValue("onlineServerList", "a").empty()) + // If a server was passed on the command line, or branding + // provides a server and a blank server list, we skip the + // server selection dialog. + if (mOptions.serverName.empty() || mOptions.serverPort == 0 + || !(!branding.getValue("defaultServer","").empty() && + branding.getValue("defaultPort",0) && + branding.getValue("onlineServerList", "").empty())) { // Don't allow an alpha opacity // lower than the default value diff --git a/src/net/net.cpp b/src/net/net.cpp index 5e7c989f..7e7395a6 100644 --- a/src/net/net.cpp +++ b/src/net/net.cpp @@ -22,6 +22,7 @@ #include "net/net.h" #include "main.h" +#include "log.h" #include "net/adminhandler.h" #include "net/charhandler.h" @@ -41,6 +42,8 @@ #include "net/manaserv/generalhandler.h" +#include "utils/gettext.h" + Net::AdminHandler *adminHandler = NULL; Net::CharHandler *charHandler = NULL; Net::ChatHandler *chatHandler = NULL; @@ -124,12 +127,19 @@ namespace Net { ServerInfo::Type networkType = ServerInfo::UNKNOWN; -void connectToServer(const ServerInfo &server) +void connectToServer(ServerInfo &server) { if (server.type == ServerInfo::UNKNOWN) { // TODO: Query the server about itself and choose the netcode based on // that + + if (server.port == 6901) + server.type = ServerInfo::TMWATHENA; + else if (server.port == 9601) + server.type = ServerInfo::MANASERV; + else + logger->error(_("Unknown Server Type! Exiting.")); } if (networkType == server.type && getGeneralHandler() != NULL) diff --git a/src/net/net.h b/src/net/net.h index 9d9ee10e..6029f3ba 100644 --- a/src/net/net.h +++ b/src/net/net.h @@ -67,7 +67,7 @@ ServerInfo::Type getNetworkType(); /** * Handles server detection and connection */ -void connectToServer(const ServerInfo &server); +void connectToServer(ServerInfo &server); void unload(); -- cgit v1.2.3-70-g09d2 From f82d012e96cf90556a213bf6058de43dc0a9ae7f Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Sun, 5 Sep 2010 17:34:20 +0200 Subject: Fixing ghost characters in charselectdialog How to reproduce the bug: Switch the login to an account with fewer characters. Then those character slots are not empty, but show characters from the previous account. Reviewed-by: thorbjorn --- src/net/tmwa/charserverhandler.cpp | 3 +++ 1 file changed, 3 insertions(+) diff --git a/src/net/tmwa/charserverhandler.cpp b/src/net/tmwa/charserverhandler.cpp index 8711f031..dc9b3108 100644 --- a/src/net/tmwa/charserverhandler.cpp +++ b/src/net/tmwa/charserverhandler.cpp @@ -77,6 +77,9 @@ void CharServerHandler::handleMessage(Net::MessageIn &msg) msg.skip(2); // Length word msg.skip(20); // Unused + delete_all(mCharacters); + mCharacters.clear(); + // Derive number of characters from message length const int count = (msg.getLength() - 24) / 106; -- cgit v1.2.3-70-g09d2 From 6c98fc5c74fce6cf2135d9add874717434d4ac12 Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Sun, 5 Sep 2010 19:03:27 +0200 Subject: Unloading mNamedItemInfos How to reproduce the bug: Switch login, then for every item there is this warning in the log file: "ItemDB: Duplicate name of item found". Reviewed-by: thorbjorn --- src/resources/itemdb.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/src/resources/itemdb.cpp b/src/resources/itemdb.cpp index 3fdee021..cb91e8d3 100644 --- a/src/resources/itemdb.cpp +++ b/src/resources/itemdb.cpp @@ -256,6 +256,7 @@ void ItemDB::unload() delete_all(mItemInfos); mItemInfos.clear(); + mNamedItemInfos.clear(); mLoaded = false; } -- cgit v1.2.3-70-g09d2 From d6f47f1f46c4e0e507a15a1f81903db901c0f4b5 Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Tue, 7 Sep 2010 22:12:46 +0200 Subject: Fixing reconnection after lost connection An orderly disconnect of the map-server does work fine. Then in Game::logic() an OkDialog is created, which triggers an event that set the state to STATE_CHOOSE_SERVER. Upon an unexpected disconnect the same OkDialog is created, but the player does not see it. That is because the state gets changed to STATE_ERROR, which creates another OkDialog. It changes the state to STATE_CHOOSE_SERVER as well, but the ServerDialog does not take any input. Reviewed-by: Jaxad0127 --- src/game.cpp | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/game.cpp b/src/game.cpp index eb666fa9..026b0017 100644 --- a/src/game.cpp +++ b/src/game.cpp @@ -347,10 +347,10 @@ void Game::logic() if (Client::getState() == STATE_CHANGE_MAP) return; // Not a problem here - if (Client::getState() != STATE_ERROR) - { - errorMessage = _("The connection to the server was lost."); - } + if (Client::getState() == STATE_ERROR) + return; // Disconnect gets handled by STATE_ERROR + + errorMessage = _("The connection to the server was lost."); if (!disconnectedDialog) { -- cgit v1.2.3-70-g09d2 From 4092dbd156f84e00c1603274f534963d9f98667f Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Tue, 7 Sep 2010 22:22:27 +0200 Subject: Fixing logic that decides if ServerDialog shows up --- src/client.cpp | 26 +++++++++++++------------- 1 file changed, 13 insertions(+), 13 deletions(-) diff --git a/src/client.cpp b/src/client.cpp index 3946d0f9..5488d8ad 100644 --- a/src/client.cpp +++ b/src/client.cpp @@ -607,19 +607,10 @@ int Client::exec() // If a server was passed on the command line, or branding // provides a server and a blank server list, we skip the // server selection dialog. - if (mOptions.serverName.empty() || mOptions.serverPort == 0 - || !(!branding.getValue("defaultServer","").empty() && - branding.getValue("defaultPort",0) && - branding.getValue("onlineServerList", "").empty())) - { - // Don't allow an alpha opacity - // lower than the default value - Theme::instance()->setMinimumOpacity(0.8f); - - mCurrentDialog = new ServerDialog(&mCurrentServer, - mConfigDir); - } - else + if ((!mOptions.serverName.empty() && mOptions.serverPort) + || (!branding.getValue("defaultServer","").empty() && + branding.getValue("defaultPort",0) && + branding.getValue("onlineServerList", "").empty())) { mState = STATE_CONNECT_SERVER; @@ -628,6 +619,15 @@ int Client::exec() mOptions.serverName.clear(); mOptions.serverPort = 0; } + else + { + // Don't allow an alpha opacity + // lower than the default value + Theme::instance()->setMinimumOpacity(0.8f); + + mCurrentDialog = new ServerDialog(&mCurrentServer, + mConfigDir); + } break; case STATE_CONNECT_SERVER: -- cgit v1.2.3-70-g09d2 From db2f9e4c7af87074f75af14a183db41e5ccdcc21 Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Wed, 8 Sep 2010 16:22:28 +0200 Subject: Adding missing update for attributes in StatusWindow Reviewed-by: Thorbjorn --- src/gui/statuswindow.cpp | 13 +++++++++---- src/gui/statuswindow.h | 2 ++ src/net/tmwa/playerhandler.cpp | 4 ++++ 3 files changed, 15 insertions(+), 4 deletions(-) diff --git a/src/gui/statuswindow.cpp b/src/gui/statuswindow.cpp index ede85133..91f832f5 100644 --- a/src/gui/statuswindow.cpp +++ b/src/gui/statuswindow.cpp @@ -246,10 +246,7 @@ std::string StatusWindow::update(int id) mCorrectionPointsLabel->adjustSize(); } - for (Attrs::iterator it = mAttrs.begin(); it != mAttrs.end(); it++) - { - it->second->update(); - } + updateAttrs(); } else if (id == LEVEL) { @@ -272,6 +269,14 @@ std::string StatusWindow::update(int id) return ""; } +void StatusWindow::updateAttrs() +{ + for (Attrs::iterator it = mAttrs.begin(); it != mAttrs.end(); it++) + { + it->second->update(); + } +} + void StatusWindow::setPointsNeeded(int id, int needed) { Attrs::iterator it = mAttrs.find(id); diff --git a/src/gui/statuswindow.h b/src/gui/statuswindow.h index a1fc4b4b..d99368b8 100644 --- a/src/gui/statuswindow.h +++ b/src/gui/statuswindow.h @@ -59,6 +59,8 @@ class StatusWindow : public Window std::string update(int id); + void updateAttrs(); + void setPointsNeeded(int id, int needed); void addAttribute(int id, const std::string &name, bool modifiable, diff --git a/src/net/tmwa/playerhandler.cpp b/src/net/tmwa/playerhandler.cpp index 5aab94b8..16f1ee53 100644 --- a/src/net/tmwa/playerhandler.cpp +++ b/src/net/tmwa/playerhandler.cpp @@ -318,6 +318,10 @@ void PlayerHandler::handleMessage(Net::MessageIn &msg) player_node->setAction(Being::DEAD); } } + + if (statusWindow) + statusWindow->updateAttrs(); + break; case SMSG_PLAYER_STAT_UPDATE_2: -- cgit v1.2.3-70-g09d2 From 173cbf107b35fb191724e5386cf3bcf0106c80ae Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Wed, 8 Sep 2010 21:56:44 +0200 Subject: Adding missing updates for buttons in InventoryWindow Reviewed-by: Thorbjorn --- src/gui/inventorywindow.cpp | 9 ++++++++- src/gui/inventorywindow.h | 7 ++++++- src/net/tmwa/inventoryhandler.cpp | 10 ++++++++++ src/net/tmwa/inventoryhandler.h | 2 ++ 4 files changed, 26 insertions(+), 2 deletions(-) diff --git a/src/gui/inventorywindow.cpp b/src/gui/inventorywindow.cpp index 591ebd2f..16ac5409 100644 --- a/src/gui/inventorywindow.cpp +++ b/src/gui/inventorywindow.cpp @@ -288,10 +288,18 @@ void InventoryWindow::valueChanged(const gcn::SelectionEvent &event) (item->getQuantity() - 1)); } + updateButtons(); +} + +void InventoryWindow::updateButtons() +{ + Item *item = mItems->getSelectedItem(); + if (!item || item->getQuantity() == 0) { mUseButton->setEnabled(false); mDropButton->setEnabled(false); + mSplitButton->setEnabled(false); return; } @@ -322,7 +330,6 @@ void InventoryWindow::valueChanged(const gcn::SelectionEvent &event) mSplitButton->setEnabled(false); } - void InventoryWindow::setSplitAllowed(bool allowed) { mSplitButton->setVisible(allowed); diff --git a/src/gui/inventorywindow.h b/src/gui/inventorywindow.h index f611e934..0dce0611 100644 --- a/src/gui/inventorywindow.h +++ b/src/gui/inventorywindow.h @@ -100,7 +100,12 @@ class InventoryWindow : public Window, * window has been closed. */ void close(); - + + /** + * Updates the buttons. + */ + void updateButtons(); + /** * Updates the weight bar. */ diff --git a/src/net/tmwa/inventoryhandler.cpp b/src/net/tmwa/inventoryhandler.cpp index 7363c738..f5b379b9 100644 --- a/src/net/tmwa/inventoryhandler.cpp +++ b/src/net/tmwa/inventoryhandler.cpp @@ -245,6 +245,8 @@ void InventoryHandler::handleMessage(Net::MessageIn &msg) inventory->setItem(index, itemId, amount, equipType != 0); } + + inventoryWindow->updateButtons(); } break; case SMSG_PLAYER_INVENTORY_REMOVE: @@ -255,6 +257,7 @@ void InventoryHandler::handleMessage(Net::MessageIn &msg) item->increaseQuantity(-amount); if (item->getQuantity() == 0) inventory->removeItemAt(index); + inventoryWindow->updateButtons(); } break; @@ -266,7 +269,11 @@ void InventoryHandler::handleMessage(Net::MessageIn &msg) msg.readInt8(); // type if (Item *item = inventory->getItem(index)) + { item->setQuantity(amount); + inventoryWindow->updateButtons(); + } + break; case SMSG_ITEM_USE_RESPONSE: @@ -280,7 +287,10 @@ void InventoryHandler::handleMessage(Net::MessageIn &msg) else { if (Item *item = inventory->getItem(index)) + { item->setQuantity(amount); + inventoryWindow->updateButtons(); + } } break; diff --git a/src/net/tmwa/inventoryhandler.h b/src/net/tmwa/inventoryhandler.h index 82738afe..0c4ad092 100644 --- a/src/net/tmwa/inventoryhandler.h +++ b/src/net/tmwa/inventoryhandler.h @@ -87,6 +87,8 @@ class EquipBackend : public Equipment::Backend { { item->setEquipped(true); } + + inventoryWindow->updateButtons(); } private: -- cgit v1.2.3-70-g09d2 From 7c883da9183238a0f1d75e2e815bc5f689956f14 Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Thu, 9 Sep 2010 22:11:47 +0200 Subject: Fixing sound effects The sound effects did not get played, because the path was wrong. Reviewed-by: Turmfalke --- src/sound.cpp | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/sound.cpp b/src/sound.cpp index 241e25e4..d3542a48 100644 --- a/src/sound.cpp +++ b/src/sound.cpp @@ -239,8 +239,7 @@ void Sound::playSfx(const std::string &path) return; ResourceManager *resman = ResourceManager::getInstance(); - SoundEffect *sample = resman->getSoundEffect( - paths.getValue("sfx", "sfx/") + path); + SoundEffect *sample = resman->getSoundEffect(path); if (sample) { logger->log("Sound::playSfx() Playing: %s", path.c_str()); -- cgit v1.2.3-70-g09d2 From 29e9ff188f1d64705ce53e8196e97b5eef30a547 Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Sat, 11 Sep 2010 19:27:17 +0200 Subject: Making sure the inventory window shows the correct number of used slots The SlotsBar is updated, if InventoryWindow::slotsChanged() is called. This did not happen when an item disappeared from the inventory, because of using it. Then the item quantity was just set to 0, but the SlotBar was not notified. Reviewed-by: Jaxad0127 --- src/net/tmwa/inventoryhandler.cpp | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/src/net/tmwa/inventoryhandler.cpp b/src/net/tmwa/inventoryhandler.cpp index f5b379b9..3809399d 100644 --- a/src/net/tmwa/inventoryhandler.cpp +++ b/src/net/tmwa/inventoryhandler.cpp @@ -270,7 +270,11 @@ void InventoryHandler::handleMessage(Net::MessageIn &msg) if (Item *item = inventory->getItem(index)) { - item->setQuantity(amount); + if (amount) + item->setQuantity(amount); + else + inventory->removeItemAt(index); + inventoryWindow->updateButtons(); } @@ -288,7 +292,11 @@ void InventoryHandler::handleMessage(Net::MessageIn &msg) { if (Item *item = inventory->getItem(index)) { - item->setQuantity(amount); + if (amount) + item->setQuantity(amount); + else + inventory->removeItemAt(index); + inventoryWindow->updateButtons(); } } -- cgit v1.2.3-70-g09d2 From 81dd53a536f3f76636b058250750a661911a94ea Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Sat, 11 Sep 2010 20:25:24 +0200 Subject: Fixing misspelling in Setup_Video and removing empty lines from log Reviewed-by: Jaxad0127 --- src/client.cpp | 2 +- src/gui/serverdialog.cpp | 2 +- src/gui/setup_video.cpp | 6 +++--- src/net/tmwa/guildhandler.cpp | 2 +- src/net/tmwa/network.cpp | 2 +- src/net/tmwa/partyhandler.cpp | 4 ++-- 6 files changed, 9 insertions(+), 9 deletions(-) diff --git a/src/client.cpp b/src/client.cpp index 5488d8ad..482bb9dc 100644 --- a/src/client.cpp +++ b/src/client.cpp @@ -961,7 +961,7 @@ int Client::exec() case STATE_ERROR: logger->log("State: ERROR"); - logger->log("Error: %s\n", errorMessage.c_str()); + logger->log("Error: %s", errorMessage.c_str()); mCurrentDialog = new OkDialog(_("Error"), errorMessage); mCurrentDialog->addActionListener(&errorListener); mCurrentDialog = NULL; // OkDialog deletes itself diff --git a/src/gui/serverdialog.cpp b/src/gui/serverdialog.cpp index 0762b00f..09ba7cd1 100644 --- a/src/gui/serverdialog.cpp +++ b/src/gui/serverdialog.cpp @@ -676,7 +676,7 @@ int ServerDialog::downloadUpdate(void *ptr, DownloadStatus status, } else if (status < 0) { - logger->log("Error retreiving server list: %s\n", + logger->log("Error retreiving server list: %s", sd->mDownload->getError()); sd->mDownloadStatus = DOWNLOADING_ERROR; } diff --git a/src/gui/setup_video.cpp b/src/gui/setup_video.cpp index 81ce8107..b576f302 100644 --- a/src/gui/setup_video.cpp +++ b/src/gui/setup_video.cpp @@ -224,11 +224,11 @@ Setup_Video::Setup_Video(): mParticleEffectsCheckBox(new CheckBox(_("Particle effects"), mParticleEffectsEnabled)), mNameCheckBox(new CheckBox(_("Show own name"), mNameEnabled)), - mNPCLogCheckBox(new CheckBox(_("Log NPC interations"), mNPCLogEnabled)), + mNPCLogCheckBox(new CheckBox(_("Log NPC interactions"), mNPCLogEnabled)), mPickupNotifyLabel(new Label(_("Show pickup notification"))), - // TRANSLATORS: Refers to "Show own name" + // TRANSLATORS: Refers to "Show pickup notification" mPickupChatCheckBox(new CheckBox(_("in chat"), mPickupChatEnabled)), - // TRANSLATORS: Refers to "Show own name" + // TRANSLATORS: Refers to "Show pickup notification" mPickupParticleCheckBox(new CheckBox(_("as particle"), mPickupParticleEnabled)), mSpeechSlider(new Slider(0, 3)), diff --git a/src/net/tmwa/guildhandler.cpp b/src/net/tmwa/guildhandler.cpp index 8a106841..dac57b64 100644 --- a/src/net/tmwa/guildhandler.cpp +++ b/src/net/tmwa/guildhandler.cpp @@ -118,7 +118,7 @@ void GuildHandler::handleMessage(Net::MessageIn &msg) msg.readInt8(); // Unused std::string guildName = msg.readString(24); - logger->log("Guild position info: %d %d %d %s\n", guildId, + logger->log("Guild position info: %d %d %d %s", guildId, emblem, posMode, guildName.c_str()); } break; diff --git a/src/net/tmwa/network.cpp b/src/net/tmwa/network.cpp index ddfbbc5d..aff19b11 100644 --- a/src/net/tmwa/network.cpp +++ b/src/net/tmwa/network.cpp @@ -326,7 +326,7 @@ MessageIn Network::getNextMessage() len = readWord(2); #ifdef DEBUG - logger->log("Received packet 0x%x of length %d\n", msgId, len); + logger->log("Received packet 0x%x of length %d", msgId, len); #endif MessageIn msg(mInBuffer, len); diff --git a/src/net/tmwa/partyhandler.cpp b/src/net/tmwa/partyhandler.cpp index a88a27b6..611fe3e6 100644 --- a/src/net/tmwa/partyhandler.cpp +++ b/src/net/tmwa/partyhandler.cpp @@ -189,7 +189,7 @@ void PartyHandler::handleMessage(Net::MessageIn &msg) partyTab->chatLog(_("Experience sharing not possible."), BY_SERVER); break; default: - logger->log("Unknown party exp option: %d\n", exp); + logger->log("Unknown party exp option: %d", exp); } switch (item) @@ -213,7 +213,7 @@ void PartyHandler::handleMessage(Net::MessageIn &msg) partyTab->chatLog(_("Item sharing not possible."), BY_SERVER); break; default: - logger->log("Unknown party item option: %d\n", exp); + logger->log("Unknown party item option: %d", exp); } break; } -- cgit v1.2.3-70-g09d2 From 60f16fea6c08f419bfd3d852ec3696bedfe09196 Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Sun, 12 Sep 2010 00:07:55 +0200 Subject: Deactivating OpenGL by default on Windows For Linux OpenGL was already deactivated. For OSX it is still by default switched on. Reviewed-by: Jaxad0127 --- src/client.cpp | 2 +- src/gui/setup_video.cpp | 14 ++++++++++++-- 2 files changed, 13 insertions(+), 3 deletions(-) diff --git a/src/client.cpp b/src/client.cpp index 482bb9dc..8def205b 100644 --- a/src/client.cpp +++ b/src/client.cpp @@ -1090,7 +1090,7 @@ void Client::initConfiguration() { // Fill configuration with defaults config.setValue("hwaccel", false); -#if (defined __APPLE__ || defined WIN32) && defined USE_OPENGL +#if defined __APPLE__ && defined USE_OPENGL config.setValue("opengl", true); #else config.setValue("opengl", false); diff --git a/src/gui/setup_video.cpp b/src/gui/setup_video.cpp index b576f302..b14a8654 100644 --- a/src/gui/setup_video.cpp +++ b/src/gui/setup_video.cpp @@ -440,8 +440,18 @@ void Setup_Video::apply() config.setValue("opengl", mOpenGLCheckBox->isSelected()); // OpenGL can currently only be changed by restarting, notify user. - new OkDialog(_("Changing to OpenGL"), - _("Applying change to OpenGL requires restart.")); + if (mOpenGLCheckBox->isSelected()) + { + new OkDialog(_("Changing to OpenGL"), + _("Applying change to OpenGL requires restart. " + "In case OpenGL messes up your game graphics, restart " + "the game with the command line option \"--no-opengl\".")); + } + else + { + new OkDialog(_("Deactivating OpenGL"), + _("Applying change to OpenGL requires restart.")); + } } mFps = mFpsCheckBox->isSelected() ? (int) mFpsSlider->getValue() : 0; -- cgit v1.2.3-70-g09d2 From e93253b36b73d7335d98a3c73d532a1bbd7212a5 Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Sun, 12 Sep 2010 13:27:42 +0200 Subject: Fixing command line argument for server The short option for the server -s did not work. Reviewed-by: Thorbjorn --- src/main.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main.cpp b/src/main.cpp index 29713c27..fed7db60 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -69,7 +69,7 @@ static void printVersion() static void parseOptions(int argc, char *argv[], Client::Options &options) { - const char *optstring = "hvud:U:P:Dc:p:C:L:"; + const char *optstring = "hvud:U:P:Dc:s:p:C:L:"; const struct option long_options[] = { { "config-dir", required_argument, 0, 'C' }, -- cgit v1.2.3-70-g09d2 From af176c1f344a78a352ecaa6f252054f5ac38ec73 Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Mon, 13 Sep 2010 14:19:11 +0200 Subject: Avoid loading non-existing music and minimaps Reviewed-by: Thorbjorn --- src/game.cpp | 7 ++++++- src/gui/minimap.cpp | 3 ++- src/sound.cpp | 7 +------ 3 files changed, 9 insertions(+), 8 deletions(-) diff --git a/src/game.cpp b/src/game.cpp index 026b0017..8e856dc0 100644 --- a/src/game.cpp +++ b/src/game.cpp @@ -958,7 +958,12 @@ void Game::changeMap(const std::string &mapPath) std::string oldMusic = mCurrentMap ? mCurrentMap->getMusicFile() : ""; std::string newMusic = newMap ? newMap->getMusicFile() : ""; if (newMusic != oldMusic) - sound.playMusic(newMusic); + { + if (newMusic.empty()) + sound.stopMusic(); + else + sound.playMusic(newMusic); + } delete mCurrentMap; mCurrentMap = newMap; diff --git a/src/gui/minimap.cpp b/src/gui/minimap.cpp index 35844f64..8713d3f9 100644 --- a/src/gui/minimap.cpp +++ b/src/gui/minimap.cpp @@ -106,7 +106,8 @@ void Minimap::setMap(Map *map) if (minimapName.empty() && resman->exists(tempname)) minimapName = tempname; - mMapImage = resman->getImage(minimapName); + if (!minimapName.empty()) + mMapImage = resman->getImage(minimapName); } if (mMapImage) diff --git a/src/sound.cpp b/src/sound.cpp index d3542a48..fa39e49b 100644 --- a/src/sound.cpp +++ b/src/sound.cpp @@ -195,12 +195,7 @@ void Sound::stopMusic() logger->log("Sound::stopMusic()"); - if (mMusic) - { - Mix_HaltMusic(); - Mix_FreeMusic(mMusic); - mMusic = NULL; - } + haltMusic(); } void Sound::fadeInMusic(const std::string &path, int ms) -- cgit v1.2.3-70-g09d2 From 7d0738df0d139af3175fcc1fec5b9be4a467f4f4 Mon Sep 17 00:00:00 2001 From: Stefan Dombrowski Date: Tue, 14 Sep 2010 17:55:53 +0200 Subject: Avoid log message for unhandled SMSG_BEING_SPAWN This log message shows up in mana.log: "Unhandled packet: 7c". Later, the client will have to actually take care of it, though. Reviewed-by: Bertram, jaxad0127. --- src/net/tmwa/beinghandler.cpp | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/src/net/tmwa/beinghandler.cpp b/src/net/tmwa/beinghandler.cpp index 04690c50..889f8777 100644 --- a/src/net/tmwa/beinghandler.cpp +++ b/src/net/tmwa/beinghandler.cpp @@ -48,6 +48,7 @@ BeingHandler::BeingHandler(bool enableSync): static const Uint16 _messages[] = { SMSG_BEING_VISIBLE, SMSG_BEING_MOVE, + SMSG_BEING_SPAWN, SMSG_BEING_MOVE2, SMSG_BEING_REMOVE, SMSG_SKILL_DAMAGE, @@ -236,6 +237,13 @@ void BeingHandler::handleMessage(Net::MessageIn &msg) dstBeing->setStatusEffectBlock(16, statusEffects & 0xffff); break; + case SMSG_BEING_SPAWN: + /* + * TODO: This packet might need handling in the future. + */ + // Do nothing. + break; + case SMSG_BEING_MOVE2: /* * A simplified movement packet, used by the -- cgit v1.2.3-70-g09d2