00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022 #include "gui/widgets/chattab.h"
00023
00024 #include "commandhandler.h"
00025 #include "configuration.h"
00026 #include "localplayer.h"
00027
00028 #include "gui/widgets/browserbox.h"
00029 #include "gui/widgets/scrollarea.h"
00030
00031 #include "gui/itemlinkhandler.h"
00032 #include "gui/recorder.h"
00033
00034 #include "net/chathandler.h"
00035 #include "net/net.h"
00036
00037 #include "resources/iteminfo.h"
00038 #include "resources/itemdb.h"
00039
00040 #include "utils/gettext.h"
00041 #include "utils/strprintf.h"
00042 #include "utils/stringutils.h"
00043
00044 #include <guichan/widgets/tabbedarea.hpp>
00045
00046 ChatTab::ChatTab(const std::string &name) : Tab()
00047 {
00048 setCaption(name);
00049
00050 mTextOutput = new BrowserBox(BrowserBox::AUTO_WRAP);
00051 mTextOutput->setOpaque(false);
00052 mTextOutput->setMaxRow((int) config.getValue("ChatLogLength", 0));
00053 mTextOutput->setLinkHandler(chatWindow->mItemLinkHandler);
00054
00055 mScrollArea = new ScrollArea(mTextOutput);
00056 mScrollArea->setScrollPolicy(gcn::ScrollArea::SHOW_NEVER,
00057 gcn::ScrollArea::SHOW_ALWAYS);
00058 mScrollArea->setScrollAmount(0, 1);
00059 mScrollArea->setOpaque(false);
00060
00061 chatWindow->addTab(this);
00062 }
00063
00064 ChatTab::~ChatTab()
00065 {
00066 chatWindow->removeTab(this);
00067 delete mTextOutput;
00068 delete mScrollArea;
00069 }
00070
00071 void ChatTab::chatLog(std::string line, int own, bool ignoreRecord)
00072 {
00073
00074 trim(line);
00075
00076 if (line.empty())
00077 return;
00078
00079 CHATLOG tmp;
00080 tmp.own = own;
00081 tmp.nick = "";
00082 tmp.text = line;
00083
00084 std::string::size_type pos = line.find(" : ");
00085 if (pos != std::string::npos)
00086 {
00087 tmp.nick = line.substr(0, pos);
00088 tmp.text = line.substr(pos + 3);
00089 }
00090 else
00091 {
00092
00093 if (line.substr(0, 7) == "Welcome")
00094 {
00095 own = BY_SERVER;
00096 }
00097 }
00098
00099
00100 if ((own == BY_PLAYER || own == BY_OTHER) &&
00101 tmp.text.at(0) == '*' &&
00102 tmp.text.at(tmp.text.length()-1) == '*')
00103 {
00104 printf("Action from %s: %s\n", tmp.nick.c_str(), tmp.text.c_str());
00105 tmp.text[0] = ' ';
00106 tmp.text.erase(tmp.text.length() - 1);
00107 own = ACT_IS;
00108 }
00109
00110 std::string lineColor = "##C";
00111 switch (own)
00112 {
00113 case BY_GM:
00114 if (tmp.nick.empty())
00115 {
00116 tmp.nick = std::string(_("Global announcement:"));
00117 tmp.nick += " ";
00118 lineColor = "##G";
00119 }
00120 else
00121 {
00122 tmp.nick = strprintf(_("Global announcement from %s:"),
00123 tmp.nick.c_str());
00124 tmp.nick += " ";
00125 lineColor = "##1";
00126 }
00127 break;
00128 case BY_PLAYER:
00129 tmp.nick += ": ";
00130 lineColor = "##Y";
00131 break;
00132 case BY_OTHER:
00133 tmp.nick += ": ";
00134 lineColor = "##C";
00135 break;
00136 case BY_SERVER:
00137 tmp.nick = _("Server:");
00138 tmp.nick += " ";
00139 tmp.text = line;
00140 lineColor = "##S";
00141 break;
00142 case BY_CHANNEL:
00143 tmp.nick = "";
00144
00145 lineColor = "##2";
00146 break;
00147 case ACT_WHISPER:
00148 tmp.nick = strprintf(_("%s whispers: "), tmp.nick.c_str());
00149 lineColor = "##W";
00150 break;
00151 case ACT_IS:
00152 lineColor = "##I";
00153 break;
00154 case BY_LOGGER:
00155 tmp.nick = "";
00156 tmp.text = line;
00157 lineColor = "##L";
00158 break;
00159 }
00160
00161 if (tmp.nick == ": ")
00162 {
00163 tmp.nick = "";
00164 lineColor = "##S";
00165 }
00166
00167 #ifdef EATHENA_SUPPORT
00168 if (tmp.nick.empty() && tmp.text.substr(0, 17) == "Visible GM status")
00169 {
00170 player_node->setGM();
00171 }
00172 #endif
00173
00174
00175 time_t t;
00176 time(&t);
00177
00178
00179 std::stringstream timeStr;
00180 timeStr << "[" << ((((t / 60) / 60) % 24 < 10) ? "0" : "")
00181 << (int) (((t / 60) / 60) % 24)
00182 << ":" << (((t / 60) % 60 < 10) ? "0" : "")
00183 << (int) ((t / 60) % 60)
00184 << "] ";
00185
00186 line = lineColor + timeStr.str() + tmp.nick + tmp.text;
00187
00188
00189
00190
00191 if (mScrollArea->getVerticalScrollAmount() >= mScrollArea->getVerticalMaxScroll())
00192 {
00193 mTextOutput->addRow(line);
00194 mScrollArea->setVerticalScrollAmount(mScrollArea->getVerticalMaxScroll());
00195 }
00196 else
00197 {
00198 mTextOutput->addRow(line);
00199 }
00200
00201 mScrollArea->logic();
00202 chatWindow->mRecorder->record(line.substr(3));
00203 if (this != getTabbedArea()->getSelectedTab() &&
00204 own != BY_PLAYER)
00205 setHighlighted(true);
00206 }
00207
00208 void ChatTab::chatLog(const std::string &nick, const std::string &msg)
00209 {
00210 chatLog(nick + ": " + msg,
00211 nick == player_node->getName() ? BY_PLAYER : BY_OTHER,
00212 false);
00213 }
00214
00215 void ChatTab::chatInput(std::string &msg)
00216 {
00217 trim(msg);
00218
00219 if (msg.empty())
00220 return;
00221
00222
00223 std::string::size_type start = msg.find('[');
00224 while (start != std::string::npos && msg[start+1] != '@')
00225 {
00226 std::string::size_type end = msg.find(']', start);
00227 if (start+1 != end && end != std::string::npos)
00228 {
00229
00230
00231 while ((msg.find('[', start + 1) != std::string::npos) &&
00232 (msg.find('[', start + 1) < end))
00233 {
00234 start = msg.find('[', start + 1);
00235 }
00236
00237 std::string temp = msg.substr(start + 1, end - start - 1);
00238
00239 toLower(trim(temp));
00240
00241 const ItemInfo itemInfo = ItemDB::get(temp);
00242 if (itemInfo.getName() != _("Unknown item"))
00243 {
00244 msg.insert(end, "@@");
00245 msg.insert(start+1, "|");
00246 msg.insert(start+1, toString(itemInfo.getId()));
00247 msg.insert(start+1, "@@");
00248 }
00249 }
00250 start = msg.find('[', start + 1);
00251 }
00252
00253
00254 if (msg[0] != '/')
00255 handleInput(msg);
00256 else
00257 handleCommand(std::string(msg, 1));
00258 }
00259
00260 void ChatTab::scroll(int amount)
00261 {
00262 int range = mScrollArea->getHeight() / 8 * amount;
00263 gcn::Rectangle scr;
00264 scr.y = mScrollArea->getVerticalScrollAmount() + range;
00265 scr.height = abs(range);
00266 mTextOutput->showPart(scr);
00267 }
00268
00269 void ChatTab::clearText()
00270 {
00271 mTextOutput->clearRows();
00272 }
00273
00274 void ChatTab::handleInput(const std::string &msg)
00275 {
00276 Net::getChatHandler()->talk(msg);
00277 }
00278
00279 void ChatTab::handleCommand(const std::string &msg)
00280 {
00281 commandHandler->handleCommand(msg, this);
00282 }