1 // ==============================================================
2 // This file is part of Glest (www.glest.org)
3 //
4 // Copyright (C) 2010- by Titus Tscharntke
5 //
6 // You can redistribute this code and/or modify it under
7 // the terms of the GNU General Public License as published
8 // by the Free Software Foundation; either version 2 of the
9 // License, or (at your option) any later version
10 // ==============================================================
11
12 #include "menu_state_masterserver.h"
13
14 #include "server_line.h"
15 #include "renderer.h"
16 #include "sound_renderer.h"
17 #include "core_data.h"
18 #include "config.h"
19 #include "menu_state_connected_game.h"
20 #include "menu_state_custom_game.h"
21 #include "menu_state_new_game.h"
22 #include "metrics.h"
23 #include "network_manager.h"
24 #include "network_message.h"
25 #include "auto_test.h"
26 #include "socket.h"
27 #include "masterserver_info.h"
28 #include <curl/curl.h>
29 #include "cache_manager.h"
30 #include "leak_dumper.h"
31
32 namespace Glest{ namespace Game{
33
34 DisplayMessageFunction MenuStateMasterserver::pCB_DisplayMessage = NULL;
35
36 static string IRC_SERVER = "irc.freenode.net";
37 static string IRC_CHANNEL = "#megaglest-lobby";
38
39 // =====================================================
40 // class MenuStateMasterserver
41 // =====================================================
42
MenuStateMasterserver(Program * program,MainMenu * mainMenu)43 MenuStateMasterserver::MenuStateMasterserver(Program *program, MainMenu *mainMenu) :
44 MenuState(program, mainMenu, "masterserver"), mutexIRCClient(new Mutex(CODE_AT_LINE))
45 {
46 if(SystemFlags::VERBOSE_MODE_ENABLED) printf("\n\n\n\n******************** ENTERING MASTERSERVER MENU\n\n\n\n\n");
47
48 containerName = "MasterServer";
49 masterserverParseErrorShown = false;
50 updateFromMasterserverThread = NULL;
51 ircClient = NULL;
52 serverInfoString="empty";
53 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
54
55 Lang &lang= Lang::getInstance();
56
57 //Configure ConsolePosition
58 consoleIRC.setYPos(60);
59 consoleIRC.setFont(CoreData::getInstance().getMenuFontNormal());
60 consoleIRC.setFont3D(CoreData::getInstance().getMenuFontNormal3D());
61 consoleIRC.setLineHeight(18);
62 consoleIRC.setOnlyChatMessagesInStoredLines(false);
63
64 serverLinesToRender=8;
65 serverLinesLineHeight=25;
66 serverLinesYBase=680;
67
68 userButtonsHeight=20;
69 userButtonsWidth=150;
70 userButtonsLineHeight=userButtonsHeight+2;
71 userButtonsYBase=serverLinesYBase-(serverLinesToRender)*serverLinesLineHeight-90;
72 userButtonsToRender=userButtonsYBase/userButtonsLineHeight;
73 userButtonsXBase=1000-userButtonsWidth;
74
75 userScrollBar.init(1000-20,0,false,200,20);
76 userScrollBar.setLength(userButtonsYBase+userButtonsLineHeight);
77 userScrollBar.setElementCount(0);
78 userScrollBar.setVisibleSize(userButtonsToRender);
79 userScrollBar.setVisibleStart(0);
80
81 userButtonsXBase=1000-userButtonsWidth-userScrollBar.getW();
82
83 serverScrollBar.init(1000-20,serverLinesYBase-serverLinesLineHeight*(serverLinesToRender-1),false,200,20);
84 serverScrollBar.setLength(serverLinesLineHeight*serverLinesToRender);
85 serverScrollBar.setElementCount(0);
86 serverScrollBar.setVisibleSize(serverLinesToRender);
87 serverScrollBar.setVisibleStart(0);
88
89 lines[0].init(0, userButtonsYBase+userButtonsLineHeight+serverLinesLineHeight);
90 lines[1].init(userButtonsXBase-5,0,5,userButtonsYBase+2*userButtonsLineHeight);
91 lines[1].setHorizontal(false);
92
93 autoRefreshTime=0;
94 playServerFoundSound=false;
95 announcementLoaded=false;
96
97 mainMessageBox.registerGraphicComponent(containerName,"mainMessageBox");
98 mainMessageBox.init(lang.getString("Ok"));
99 mainMessageBox.setEnabled(false);
100 mainMessageBoxState=0;
101
102 lastRefreshTimer= time(NULL);
103
104 // announcement
105 announcementLabel.registerGraphicComponent(containerName,"announcementLabel");
106 announcementLabel.init(10, 730);
107 announcementLabel.setFont(CoreData::getInstance().getMenuFontBig());
108 announcementLabel.setFont3D(CoreData::getInstance().getMenuFontBig3D());
109 announcementLabel.setText("");
110
111 // versionInfo
112 versionInfoLabel.registerGraphicComponent(containerName,"versionInfoLabel");
113 versionInfoLabel.init(10, 680);
114 versionInfoLabel.setFont(CoreData::getInstance().getMenuFontBig());
115 versionInfoLabel.setFont3D(CoreData::getInstance().getMenuFontBig3D());
116 versionInfoLabel.setText("");
117
118 // header
119 labelTitle.registerGraphicComponent(containerName,"labelTitle");
120 labelTitle.init(410, serverLinesYBase+45);
121 labelTitle.setFont(CoreData::getInstance().getMenuFontBig());
122 labelTitle.setFont3D(CoreData::getInstance().getMenuFontBig3D());
123 labelTitle.setText(lang.getString("AvailableServers"));
124
125 if(Config::getInstance().getString("Masterserver","") == "") {
126 labelTitle.setText("*** " + lang.getString("AvailableServers"));
127 }
128
129 // bottom
130 int buttonPos=230;
131
132 // Titles for current games - START
133 int lineIndex = 0;
134 int lineOffset=25*lineIndex;
135 int i=5;
136 int startOffset=serverLinesYBase+23;
137
138 //general info:
139 //i+=10;
140 glestVersionLabel.registerGraphicComponent(containerName,"glestVersionLabel");
141 glestVersionLabel.init(i,startOffset-lineOffset);
142 glestVersionLabel.setText(lang.getString("MGVersion"));
143
144 i+=80;
145 platformLabel.registerGraphicComponent(containerName,"platformLabel");
146 platformLabel.init(i+15,startOffset-lineOffset);
147 platformLabel.setText(lang.getString("MGPlatform"));
148
149 // i+=50;
150 // binaryCompileDateLabel.registerGraphicComponent(containerName,"binaryCompileDateLabel");
151 // binaryCompileDateLabel.init(i,startOffset-lineOffset);
152 // binaryCompileDateLabel.setText(lang.getString("MGBuildDateTime"));
153
154 //game info:
155 i+=120;
156 serverTitleLabel.registerGraphicComponent(containerName,"serverTitleLabel");
157 serverTitleLabel.init(i,startOffset-lineOffset);
158 serverTitleLabel.setText(lang.getString("MGGameTitle"));
159
160 i+=170;
161 countryLabel.registerGraphicComponent(containerName,"countryLabel");
162 countryLabel.init(i-10,startOffset-lineOffset);
163 countryLabel.setText(lang.getString("MGGameCountry"));
164
165 i+=60;
166
167 // ipAddressLabel.registerGraphicComponent(containerName,"ipAddressLabel");
168 // ipAddressLabel.init(i,startOffset-lineOffset);
169 // ipAddressLabel.setText(lang.getString("MGGameIP"));
170 // i+=100;
171
172 //game setup info:
173 techLabel.registerGraphicComponent(containerName,"techLabel");
174 techLabel.init(i,startOffset-lineOffset);
175 techLabel.setText(lang.getString("TechTree"));
176
177 i+=165;
178 mapLabel.registerGraphicComponent(containerName,"mapLabel");
179 mapLabel.init(i,startOffset-lineOffset);
180 mapLabel.setText(lang.getString("Map"));
181
182 i+=95;
183 // tilesetLabel.registerGraphicComponent(containerName,"tilesetLabel");
184 // tilesetLabel.init(i,startOffset-lineOffset);
185 // tilesetLabel.setText(lang.getString("Tileset"));
186 // i+=100;
187
188 activeSlotsLabel.registerGraphicComponent(containerName,"activeSlotsLabel");
189 activeSlotsLabel.init(i,startOffset-lineOffset);
190 activeSlotsLabel.setText(lang.getString("MGGameSlots"));
191
192 i+=50;
193 //externalConnectPort.registerGraphicComponent(containerName,"externalConnectPort");
194 //externalConnectPort.init(i,startOffset-lineOffset);
195 //externalConnectPort.setText(lang.getString("Port"));
196
197 i+=30;
198 statusLabel.registerGraphicComponent(containerName,"statusLabel");
199 statusLabel.init(i+5,startOffset-lineOffset);
200 statusLabel.setText(lang.getString("MGGameStatus"));
201
202 i+=130;
203 selectButton.registerGraphicComponent(containerName,"selectButton");
204 selectButton.init(i-5, startOffset-lineOffset);
205 selectButton.setText(lang.getString("MGJoinGameSlots"));
206
207 // Titles for current games - END
208
209 buttonReturn.registerGraphicComponent(containerName,"buttonReturn");
210 buttonReturn.init(50, buttonPos, 150);
211
212 buttonCreateGame.registerGraphicComponent(containerName,"buttonCreateGame");
213 buttonCreateGame.init(275, buttonPos, 150);
214
215 buttonRefresh.registerGraphicComponent(containerName,"buttonRefresh");
216 buttonRefresh.init(500, buttonPos, 150);
217
218 buttonRefresh.setText(lang.getString("RefreshList"));
219 buttonReturn.setText(lang.getString("Return"));
220 buttonCreateGame.setText(lang.getString("HostGame"));
221 labelAutoRefresh.setText(lang.getString("AutoRefreshRate"));
222
223 labelAutoRefresh.registerGraphicComponent(containerName,"labelAutoRefresh");
224 labelAutoRefresh.init(750,buttonPos+30);
225
226 listBoxAutoRefresh.registerGraphicComponent(containerName,"listBoxAutoRefresh");
227 listBoxAutoRefresh.init(750,buttonPos);
228 listBoxAutoRefresh.pushBackItem(lang.getString("Off"));
229 listBoxAutoRefresh.pushBackItem("10 s");
230 listBoxAutoRefresh.pushBackItem("20 s");
231 listBoxAutoRefresh.pushBackItem("30 s");
232 listBoxAutoRefresh.setSelectedItemIndex(2);
233 autoRefreshTime=10*listBoxAutoRefresh.getSelectedItemIndex();
234
235 ircOnlinePeopleLabel.registerGraphicComponent(containerName,"ircOnlinePeopleLabel");
236 ircOnlinePeopleLabel.init(userButtonsXBase,userButtonsYBase+userButtonsLineHeight);
237 ircOnlinePeopleLabel.setText(lang.getString("IRCPeopleOnline"));
238
239 ircOnlinePeopleStatusLabel.registerGraphicComponent(containerName,"ircOnlinePeopleStatusLabel");
240 ircOnlinePeopleStatusLabel.init(userButtonsXBase,userButtonsYBase+userButtonsLineHeight-20);
241 ircOnlinePeopleStatusLabel.setText("");
242
243 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
244
245 NetworkManager::getInstance().end();
246 NetworkManager::getInstance().init(nrClient);
247
248 //console.addLine(lang.getString("ToSwitchOffMusicPress")+" - \""+configKeys.getCharKey("ToggleMusic")+"\"");
249
250 GraphicComponent::applyAllCustomProperties(containerName);
251
252 char szIRCNick[80]="";
253 Chrono seed(true);
254 srand((unsigned int)seed.getCurTicks());
255
256 int randomNickId = rand() % 999;
257 string netPlayerName=Config::getInstance().getString("NetPlayerName",Socket::getHostName().c_str());
258 string ircname=netPlayerName.substr(0,9);
259 snprintf(szIRCNick,80,"MG_%s_%d",ircname.c_str(),randomNickId);
260 normalizeNick(szIRCNick);
261
262 currentIrcNick=ircname;
263 consoleIRC.setStringToHighlight(currentIrcNick);
264
265 lines[2].init(0,consoleIRC.getYPos()-10,userButtonsXBase,5);
266 chatManager.init(&consoleIRC, -1, true, szIRCNick);
267 chatManager.setXPos(0);
268 chatManager.setYPos(consoleIRC.getYPos()-20);
269 chatManager.setFont(CoreData::getInstance().getMenuFontNormal());
270 chatManager.setFont3D(CoreData::getInstance().getMenuFontNormal3D());
271
272 needUpdateFromServer = true;
273
274 static string mutexOwnerId = string(extractFileFromDirectoryPath(__FILE__).c_str()) + string("_") + intToStr(__LINE__);
275 updateFromMasterserverThread = new SimpleTaskThread(this,0,100);
276 updateFromMasterserverThread->setUniqueID(mutexOwnerId);
277 updateFromMasterserverThread->start();
278
279 if(Config::getInstance().getString("IRCServer","") != "") {
280 IRC_SERVER = Config::getInstance().getString("IRCServer");
281 }
282 ircArgs.push_back(IRC_SERVER);
283
284 if(Config::getInstance().getString("IRCNick","") != "") {
285 ircArgs.push_back(Config::getInstance().getString("IRCNick"));
286 }
287 else {
288 ircArgs.push_back(szIRCNick);
289 }
290
291 if(Config::getInstance().getString("IRCChannel","") != "") {
292 IRC_CHANNEL = Config::getInstance().getString("IRCChannel");
293 }
294 ircArgs.push_back(IRC_CHANNEL);
295
296 if(Config::getInstance().getString("IRCUsername","") != "") {
297 ircArgs.push_back(Config::getInstance().getString("IRCUsername"));
298 }
299 else {
300 ircArgs.push_back(szIRCNick);
301 }
302 if(Config::getInstance().getString("IRCPassword","") != "") {
303 ircArgs.push_back("identify " + Config::getInstance().getString("IRCPassword"));
304 }
305 else {
306 ircArgs.push_back("");
307 }
308
309 MutexSafeWrapper safeMutexIRCPtr(mutexIRCClient,string(extractFileFromDirectoryPath(__FILE__).c_str()) + "_" + intToStr(__LINE__));
310
311 if(SystemFlags::VERBOSE_MODE_ENABLED) printf("#1 IRCCLient Cache check\n");
312 IRCThread * &ircThread = CacheManager::getCachedItem< IRCThread * >(GameConstants::ircClientCacheLookupKey);
313
314 // Playername changed so restart the IRC Thread
315 if(ircThread != NULL && netPlayerName != ircThread->getPlayerName()) {
316 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
317 ircThread->leaveChannel();
318 ircThread->setCallbackObj(NULL);
319 ircThread->signalQuit();
320 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
321 ircThread = NULL;
322 }
323
324 if(ircThread == NULL) {
325 if(SystemFlags::VERBOSE_MODE_ENABLED) printf("#2 IRCCLient Cache check\n");
326
327 static string mutexOwnerId = string(extractFileFromDirectoryPath(__FILE__).c_str()) + string("_") + intToStr(__LINE__);
328 ircThread = new IRCThread(ircArgs,this);
329 ircClient = ircThread;
330 ircClient->setUniqueID(mutexOwnerId);
331 ircClient->setPlayerName(netPlayerName);
332 ircClient->start();
333 }
334 else {
335 if(SystemFlags::VERBOSE_MODE_ENABLED) printf("#3 IRCCLient Cache check\n");
336 ircClient = ircThread;
337 ircClient->setCallbackObj(this);
338 ircClient->joinChannel();
339 }
340
341 if(netPlayerName=="newbie"){
342 showMessageBox(lang.getString("PlayerNameNotSetPrompt"),lang.getString("PlayerNameNotSetTitle"),false);
343 }
344 //showMessageBox("Go back and set your name in the game options!\n\nAt the moment you are just called >>newbie<< !","Player name not set!",false);
345
346 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
347 }
348
reloadUI()349 void MenuStateMasterserver::reloadUI() {
350 Lang &lang= Lang::getInstance();
351
352 console.resetFonts();
353 consoleIRC.setFont(CoreData::getInstance().getMenuFontNormal());
354 consoleIRC.setFont3D(CoreData::getInstance().getMenuFontNormal3D());
355
356 mainMessageBox.init(lang.getString("Ok"));
357
358 announcementLabel.setFont(CoreData::getInstance().getMenuFontBig());
359 announcementLabel.setFont3D(CoreData::getInstance().getMenuFontBig3D());
360
361 versionInfoLabel.setFont(CoreData::getInstance().getMenuFontBig());
362 versionInfoLabel.setFont3D(CoreData::getInstance().getMenuFontBig3D());
363
364 labelTitle.setFont(CoreData::getInstance().getMenuFontBig());
365 labelTitle.setFont3D(CoreData::getInstance().getMenuFontBig3D());
366 labelTitle.setText(lang.getString("AvailableServers"));
367
368 if(Config::getInstance().getString("Masterserver","") == "") {
369 labelTitle.setText("*** " + lang.getString("AvailableServers"));
370 }
371
372 glestVersionLabel.setText(lang.getString("MGVersion"));
373
374 platformLabel.setText(lang.getString("MGPlatform"));
375
376 serverTitleLabel.setText(lang.getString("MGGameTitle"));
377
378 countryLabel.setText(lang.getString("MGGameCountry"));
379
380 techLabel.setText(lang.getString("TechTree"));
381
382 mapLabel.setText(lang.getString("Map"));
383
384 activeSlotsLabel.setText(lang.getString("MGGameSlots"));
385
386 //externalConnectPort.setText(lang.getString("Port"));
387
388 statusLabel.setText(lang.getString("MGGameStatus"));
389
390 selectButton.setText(lang.getString("MGJoinGameSlots"));
391
392 // Titles for current games - END
393
394 buttonRefresh.setText(lang.getString("RefreshList"));
395 buttonReturn.setText(lang.getString("Return"));
396 buttonCreateGame.setText(lang.getString("HostGame"));
397 labelAutoRefresh.setText(lang.getString("AutoRefreshRate"));
398
399 ircOnlinePeopleLabel.setText(lang.getString("IRCPeopleOnline"));
400
401 chatManager.setFont(CoreData::getInstance().getMenuFontNormal());
402 chatManager.setFont3D(CoreData::getInstance().getMenuFontNormal3D());
403
404 GraphicComponent::reloadFontsForRegisterGraphicComponents(containerName);
405 }
406
setConsolePos(int yPos)407 void MenuStateMasterserver::setConsolePos(int yPos){
408 consoleIRC.setYPos(yPos);
409 lines[2].setY(consoleIRC.getYPos()-10);
410 chatManager.setYPos(consoleIRC.getYPos()-20);
411 }
412
setButtonLinePosition(int pos)413 void MenuStateMasterserver::setButtonLinePosition(int pos){
414 buttonReturn.setY(pos);
415 buttonCreateGame.setY(pos);
416 buttonRefresh.setY(pos);
417 labelAutoRefresh.setY(pos+30);
418 listBoxAutoRefresh.setY(pos);
419 }
420
IRC_CallbackEvent(IRCEventType evt,const char * origin,const char ** params,unsigned int count)421 void MenuStateMasterserver::IRC_CallbackEvent(IRCEventType evt, const char* origin, const char **params, unsigned int count) {
422 MutexSafeWrapper safeMutexIRCPtr(mutexIRCClient,string(extractFileFromDirectoryPath(__FILE__).c_str()) + "_" + intToStr(__LINE__));
423 if(ircClient != NULL) {
424 if(evt == IRC_evt_exitThread) {
425 ircClient->leaveChannel();
426 ircClient->setCallbackObj(NULL);
427
428 ircClient = NULL;
429 }
430 else if(evt == IRC_evt_chatText) {
431 //printf ("===> IRC: '%s' said in channel %s: %s\n",origin ? origin : "someone",params[0], params[1] );
432
433 char szBuf[8096]="";
434 snprintf(szBuf,8096,"%s: %s",origin ? origin : "someone",params[1]);
435 string helpSTr=szBuf;
436 if(helpSTr.find(currentIrcNick)!=string::npos){
437 CoreData &coreData= CoreData::getInstance();
438 SoundRenderer &soundRenderer= SoundRenderer::getInstance();
439
440 soundRenderer.playFx(coreData.getHighlightSound());
441 }
442 consoleIRC.addLine(szBuf);
443 }
444 }
445 }
446
cleanup()447 void MenuStateMasterserver::cleanup() {
448 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
449
450 MutexSafeWrapper safeMutex((updateFromMasterserverThread != NULL ? updateFromMasterserverThread->getMutexThreadObjectAccessor() : NULL),string(extractFileFromDirectoryPath(__FILE__).c_str()) + "_" + intToStr(__LINE__));
451 needUpdateFromServer = false;
452 safeMutex.ReleaseLock();
453
454 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
455
456 // if(updateFromMasterserverThread != NULL &&
457 // updateFromMasterserverThread->canShutdown(true) == true) {
458 // if(updateFromMasterserverThread->shutdownAndWait() == true) {
459 // delete updateFromMasterserverThread;
460 // }
461 // }
462 // updateFromMasterserverThread = NULL;
463 if(updateFromMasterserverThread != NULL) {
464 updateFromMasterserverThread->signalQuit();
465 }
466 if(updateFromMasterserverThread != NULL && updateFromMasterserverThread->canShutdown(false) == true &&
467 updateFromMasterserverThread->getRunningStatus() == false) {
468 //printf("#2 Ending client SLOT: %d\n",playerIndex);
469
470 if(SystemFlags::getSystemSettingType(SystemFlags::debugNetwork).enabled) SystemFlags::OutputDebug(SystemFlags::debugNetwork,"In [%s::%s Line: %d]\n",__FILE__,__FUNCTION__,__LINE__);
471 delete updateFromMasterserverThread;
472 if(SystemFlags::getSystemSettingType(SystemFlags::debugNetwork).enabled) SystemFlags::OutputDebug(SystemFlags::debugNetwork,"In [%s::%s Line: %d]\n",__FILE__,__FUNCTION__,__LINE__);
473 }
474 //else if(BaseThread::shutdownAndWait(slotThreadWorker) == true) {
475 else if(updateFromMasterserverThread != NULL && updateFromMasterserverThread->canShutdown(true) == true) {
476 if(updateFromMasterserverThread->getRunningStatus() == false) {
477 //printf("#3 Ending client SLOT: %d\n",playerIndex);
478 if(SystemFlags::getSystemSettingType(SystemFlags::debugNetwork).enabled) SystemFlags::OutputDebug(SystemFlags::debugNetwork,"In [%s::%s Line: %d]\n",__FILE__,__FUNCTION__,__LINE__);
479 delete updateFromMasterserverThread;
480 if(SystemFlags::getSystemSettingType(SystemFlags::debugNetwork).enabled) SystemFlags::OutputDebug(SystemFlags::debugNetwork,"In [%s::%s Line: %d]\n",__FILE__,__FUNCTION__,__LINE__);
481 }
482 else {
483 updateFromMasterserverThread->setDeleteSelfOnExecutionDone(true);
484 updateFromMasterserverThread->setDeleteAfterExecute(true);
485 }
486 }
487 //printf("#4 Ending client SLOT: %d\n",playerIndex);
488 updateFromMasterserverThread = NULL;
489
490 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
491
492 clearServerLines();
493 clearUserButtons();
494
495 MutexSafeWrapper safeMutexIRCPtr(mutexIRCClient,string(extractFileFromDirectoryPath(__FILE__).c_str()) + "_" + intToStr(__LINE__));
496 if(ircClient != NULL) {
497 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
498
499 ircClient->leaveChannel();
500 ircClient->setCallbackObj(NULL);
501 //ircClient->signalQuit();
502 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
503 ircClient = NULL;
504 }
505
506 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d] END\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
507 }
508
~MenuStateMasterserver()509 MenuStateMasterserver::~MenuStateMasterserver() {
510 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
511
512 cleanup();
513
514 delete mutexIRCClient;
515 mutexIRCClient = NULL;
516
517 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d] END\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
518 }
519
clearServerLines()520 void MenuStateMasterserver::clearServerLines() {
521 while(!serverLines.empty()) {
522 delete serverLines.back();
523 serverLines.pop_back();
524 }
525 }
526
clearUserButtons()527 void MenuStateMasterserver::clearUserButtons() {
528 while(!userButtons.empty()){
529 delete userButtons.back();
530 userButtons.pop_back();
531 }
532 }
533
mouseClick(int x,int y,MouseButton mouseButton)534 void MenuStateMasterserver::mouseClick(int x, int y, MouseButton mouseButton){
535 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
536
537 CoreData &coreData= CoreData::getInstance();
538 SoundRenderer &soundRenderer= SoundRenderer::getInstance();
539
540 if(mainMessageBox.getEnabled()){
541 int button= 0;
542 if(mainMessageBox.mouseClick(x, y, button)) {
543 soundRenderer.playFx(coreData.getClickSoundA());
544 if(button == 0) {
545 mainMessageBox.setEnabled(false);
546 }
547 }
548 }
549 else if(userScrollBar.mouseClick(x, y)){
550 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
551 soundRenderer.playFx(coreData.getClickSoundA());
552 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
553 }
554 else if(serverScrollBar.mouseClick(x, y)){
555 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
556 soundRenderer.playFx(coreData.getClickSoundA());
557 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
558 }
559 else if(buttonRefresh.mouseClick(x, y)){
560 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
561
562 MutexSafeWrapper safeMutex((updateFromMasterserverThread != NULL ? updateFromMasterserverThread->getMutexThreadObjectAccessor() : NULL),string(extractFileFromDirectoryPath(__FILE__).c_str()) + "_" + intToStr(__LINE__));
563 soundRenderer.playFx(coreData.getClickSoundB());
564 needUpdateFromServer = true;
565
566 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
567 }
568 else if(buttonReturn.mouseClick(x, y)){
569 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
570
571 soundRenderer.playFx(coreData.getClickSoundA());
572
573 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
574 if (ircClient != NULL && ircClient->isConnected() == true
575 && ircClient->getHasJoinedChannel() == true) {
576 ircClient->SendIRCCmdMessage(IRC_CHANNEL, " << left the lobby");
577 sleep(30);
578 }
579 cleanup();
580
581 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
582
583 mainMenu->setState(new MenuStateNewGame(program, mainMenu));
584
585 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
586 }
587 else if(buttonCreateGame.mouseClick(x, y)){
588 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
589
590 MutexSafeWrapper safeMutex((updateFromMasterserverThread != NULL ? updateFromMasterserverThread->getMutexThreadObjectAccessor() : NULL),string(extractFileFromDirectoryPath(__FILE__).c_str()) + "_" + intToStr(__LINE__));
591 soundRenderer.playFx(coreData.getClickSoundB());
592 needUpdateFromServer = false;
593 safeMutex.ReleaseLock();
594
595 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
596 if (ircClient != NULL && ircClient->isConnected() == true
597 && ircClient->getHasJoinedChannel() == true) {
598 ircClient->SendIRCCmdMessage(IRC_CHANNEL, " << tries to create a game");
599 sleep(30);
600 }
601 cleanup();
602 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
603
604 mainMenu->setState(new MenuStateCustomGame(program, mainMenu,true,pMasterServer));
605
606 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
607 }
608 else if(listBoxAutoRefresh.mouseClick(x, y)){
609 MutexSafeWrapper safeMutex((updateFromMasterserverThread != NULL ? updateFromMasterserverThread->getMutexThreadObjectAccessor() : NULL),string(extractFileFromDirectoryPath(__FILE__).c_str()) + "_" + intToStr(__LINE__));
610 soundRenderer.playFx(coreData.getClickSoundA());
611 autoRefreshTime=10*listBoxAutoRefresh.getSelectedItemIndex();
612 }
613 else {
614 MutexSafeWrapper safeMutex((updateFromMasterserverThread != NULL ? updateFromMasterserverThread->getMutexThreadObjectAccessor() : NULL),string(extractFileFromDirectoryPath(__FILE__).c_str()) + "_" + intToStr(__LINE__));
615 bool clicked=false;
616 if(!clicked && serverScrollBar.getElementCount()!=0){
617 for(int i = serverScrollBar.getVisibleStart(); i <= serverScrollBar.getVisibleEnd(); ++i) {
618 if(serverLines[i]->buttonMouseClick(x, y)) {
619 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
620 clicked=true;
621 soundRenderer.playFx(coreData.getClickSoundB());
622 string connectServerIP = serverLines[i]->getMasterServerInfo()->getIpAddress();
623 int connectServerPort = serverLines[i]->getMasterServerInfo()->getExternalConnectPort();
624 bool connected=connectToServer(connectServerIP,connectServerPort);
625 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
626 safeMutex.ReleaseLock();
627 if(connected){
628 soundRenderer.playFx(coreData.getClickSoundB());
629
630 if (ircClient != NULL && ircClient->isConnected() == true
631 && ircClient->getHasJoinedChannel() == true) {
632 ircClient->SendIRCCmdMessage(IRC_CHANNEL, " << is connecting to '"+serverLines[i]->getMasterServerInfo()->getServerTitle()+"'");
633 sleep(30);
634 }
635 cleanup();
636 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
637 mainMenu->setState(new MenuStateConnectedGame(program, mainMenu,jmMasterserver));
638 }
639 break;
640 }
641 }
642 }
643 if(!clicked && userScrollBar.getElementCount()!=0){
644 for(int i = userScrollBar.getVisibleStart(); i <= userScrollBar.getVisibleEnd(); ++i) {
645 if(userButtons[i]->getEnabled() == true && userButtons[i]->mouseClick(x, y)) {
646 //clicked=true;
647 if(!chatManager.getEditEnabled())
648 {
649 chatManager.switchOnEdit();
650 chatManager.addText(userButtons[i]->getText()+" ");
651 }
652 else
653 {
654 chatManager.addText(userButtons[i]->getText());
655 }
656 break;
657 }
658 }
659 }
660 }
661 }
662
mouseUp(int x,int y,const MouseButton mouseButton)663 void MenuStateMasterserver::mouseUp(int x, int y, const MouseButton mouseButton){
664 if (mouseButton == mbLeft) {
665 userScrollBar.mouseUp(x, y);
666 serverScrollBar.mouseUp(x, y);
667 }
668 }
669
mouseMove(int x,int y,const MouseState * ms)670 void MenuStateMasterserver::mouseMove(int x, int y, const MouseState *ms){
671 MutexSafeWrapper safeMutex((updateFromMasterserverThread != NULL ? updateFromMasterserverThread->getMutexThreadObjectAccessor() : NULL),string(extractFileFromDirectoryPath(__FILE__).c_str()) + "_" + intToStr(__LINE__));
672
673 if (mainMessageBox.getEnabled()) {
674 mainMessageBox.mouseMove(x, y);
675 }
676 buttonRefresh.mouseMove(x, y);
677 buttonReturn.mouseMove(x, y);
678 buttonCreateGame.mouseMove(x, y);
679 if (ms->get(mbLeft)) {
680 userScrollBar.mouseDown(x, y);
681 serverScrollBar.mouseDown(x, y);
682 } else {
683 userScrollBar.mouseMove(x, y);
684 serverScrollBar.mouseMove(x, y);
685 }
686 listBoxAutoRefresh.mouseMove(x, y);
687
688 if(serverScrollBar.getElementCount()!=0 ) {
689 for(int i = serverScrollBar.getVisibleStart(); i <= serverScrollBar.getVisibleEnd(); ++i) {
690 serverLines[i]->buttonMouseMove(x, y);
691 }
692 }
693 if(userScrollBar.getElementCount()!=0 ) {
694 for(int i = userScrollBar.getVisibleStart(); i <= userScrollBar.getVisibleEnd(); ++i) {
695 if(userButtons[i]->getEnabled() == true) {
696 userButtons[i]->mouseMove(x, y);
697 }
698 }
699 }
700
701 }
702
render()703 void MenuStateMasterserver::render(){
704 Renderer &renderer= Renderer::getInstance();
705
706 MutexSafeWrapper safeMutex((updateFromMasterserverThread != NULL ? updateFromMasterserverThread->getMutexThreadObjectAccessor() : NULL),string(extractFileFromDirectoryPath(__FILE__).c_str()) + "_" + intToStr(__LINE__));
707 if(mainMessageBox.getEnabled()) {
708 renderer.renderMessageBox(&mainMessageBox);
709 }
710 else
711 {
712 renderer.renderLabel(&labelTitle,&GREEN);
713 renderer.renderLabel(&announcementLabel,&YELLOW);
714 renderer.renderLabel(&versionInfoLabel);
715
716 // Render titles for server games listed
717 const Vec4f titleLabelColor = CYAN;
718
719 //general info:
720 renderer.renderLabel(&glestVersionLabel,&titleLabelColor);
721 renderer.renderLabel(&platformLabel,&titleLabelColor);
722 //renderer.renderLabel(&binaryCompileDateLabel,&titleLabelColor);
723
724 //game info:
725 renderer.renderLabel(&serverTitleLabel,&titleLabelColor);
726 renderer.renderLabel(&countryLabel,&titleLabelColor);
727 renderer.renderLabel(&statusLabel,&titleLabelColor);
728 //renderer.renderLabel(&ipAddressLabel,&titleLabelColor);
729
730 //game setup info:
731 renderer.renderLabel(&techLabel,&titleLabelColor);
732 renderer.renderLabel(&mapLabel,&titleLabelColor);
733 //renderer.renderLabel(&tilesetLabel,&titleLabelColor);
734 renderer.renderLabel(&activeSlotsLabel,&titleLabelColor);
735 //renderer.renderLabel(&externalConnectPort,&titleLabelColor);
736 renderer.renderLabel(&selectButton,&titleLabelColor);
737
738 Lang &lang= Lang::getInstance();
739 MutexSafeWrapper safeMutexIRCPtr(mutexIRCClient,string(extractFileFromDirectoryPath(__FILE__).c_str()) + "_" + intToStr(__LINE__));
740 if(ircClient != NULL &&
741 ircClient->isConnected() == true &&
742 ircClient->getHasJoinedChannel() == true) {
743 const Vec4f titleLabelColor = GREEN;
744
745 if(ircOnlinePeopleStatusLabel.getText() != "") {
746 ircOnlinePeopleStatusLabel.setText("");
747 }
748
749 renderer.renderLabel(&ircOnlinePeopleLabel,&titleLabelColor);
750 //renderer.renderLabel(&ircOnlinePeopleStatusLabel,&titleLabelColor);
751 }
752 else {
753 const Vec4f titleLabelColor = RED;
754
755 if(ircOnlinePeopleStatusLabel.getText() != lang.getString("Connecting")) {
756 ircOnlinePeopleStatusLabel.setText(lang.getString("Connecting"));
757 }
758
759 renderer.renderLabel(&ircOnlinePeopleLabel,&titleLabelColor);
760 renderer.renderLabel(&ircOnlinePeopleStatusLabel,&titleLabelColor);
761 }
762 safeMutexIRCPtr.ReleaseLock();
763
764 //const Vec4f titleLabelColorList = YELLOW;
765
766 if(serverScrollBar.getElementCount()!=0 ) {
767 for(int i = serverScrollBar.getVisibleStart(); i <= serverScrollBar.getVisibleEnd(); ++i) {
768 serverLines[i]->render();
769 }
770 }
771 renderer.renderScrollBar(&serverScrollBar);
772
773 for(int i = 0; i < (int)sizeof(lines) / (int)sizeof(lines[0]); ++i){
774 renderer.renderLine(&lines[i]);
775 }
776 renderer.renderButton(&buttonRefresh);
777 renderer.renderButton(&buttonReturn);
778 renderer.renderLabel(&labelAutoRefresh);
779 renderer.renderButton(&buttonCreateGame);
780 renderer.renderListBox(&listBoxAutoRefresh);
781
782 if(userScrollBar.getElementCount()!=0 ) {
783 for(int i = userScrollBar.getVisibleStart(); i <= userScrollBar.getVisibleEnd(); ++i) {
784 renderer.renderButton(userButtons[i]);
785 }
786 }
787 renderer.renderScrollBar(&userScrollBar);
788 if(ircClient != NULL &&
789 ircClient->isConnected() == true &&
790 ircClient->getHasJoinedChannel() == true) {
791 renderer.renderChatManager(&chatManager);
792 }
793 renderer.renderConsole(&consoleIRC,consoleStoredOnly,21);
794
795 }
796 if(program != NULL) program->renderProgramMsgBox();
797 }
798
update()799 void MenuStateMasterserver::update() {
800 MutexSafeWrapper safeMutex((updateFromMasterserverThread != NULL ? updateFromMasterserverThread->getMutexThreadObjectAccessor() : NULL),string(extractFileFromDirectoryPath(__FILE__).c_str()) + "_" + intToStr(__LINE__));
801 if(autoRefreshTime!=0 && difftime(time(NULL),lastRefreshTimer) >= autoRefreshTime ) {
802 needUpdateFromServer = true;
803 lastRefreshTimer= time(NULL);
804 }
805
806 // calculate button linepos:
807 setButtonLinePosition(serverLinesYBase-(serverLinesToRender)*serverLinesLineHeight-30);
808
809 if(playServerFoundSound)
810 {
811 SoundRenderer::getInstance().playFx(CoreData::getInstance().getAttentionSound());
812 //switch on music again!!
813 Config &config = Config::getInstance();
814 float configVolume = (config.getInt("SoundVolumeMusic") / 100.f);
815 CoreData::getInstance().getMenuMusic()->setVolume(configVolume);
816
817 playServerFoundSound=false;
818 }
819
820 //console.update();
821
822 //call the chat manager
823 chatManager.updateNetwork();
824
825 //console
826 consoleIRC.update();
827
828 MutexSafeWrapper safeMutexIRCPtr(mutexIRCClient,string(extractFileFromDirectoryPath(__FILE__).c_str()) + "_" + intToStr(__LINE__));
829 if(ircClient != NULL) {
830 std::vector<string> nickList = ircClient->getNickList();
831
832 if(currentIrcNick != ircClient->getNick()) {
833 currentIrcNick = ircClient->getNick();
834 consoleIRC.setStringToHighlight(currentIrcNick);
835 }
836
837 bool isNew=false;
838 //check if there is something new
839 if( oldNickList.size() != nickList.size()) {
840 isNew=true;
841 }
842 else {
843 for(unsigned int i = 0; i < nickList.size(); ++i) {
844 if(nickList[i] != oldNickList[i]) {
845 isNew=true;
846 break;
847 }
848 }
849 }
850
851 if(isNew) {
852 clearUserButtons();
853 for(int i = 0; i < (int)nickList.size(); ++i) {
854 GraphicButton *button=new GraphicButton();
855 button->init(userButtonsXBase,userButtonsYBase,userButtonsWidth,userButtonsHeight);
856 //button->init(userButtonsXBase,userButtonsYBase-userButtonsLineHeight*i,userButtonsWidth,userButtonsHeight);
857 button->setFont(CoreData::getInstance().getDisplayFontSmall());
858 button->setFont3D(CoreData::getInstance().getDisplayFontSmall3D());
859 button->setText(nickList[i]);
860 if(strncmp(&nickList[i][0],"MG_",3) != 0 || &nickList[i][0] == currentIrcNick) {
861 button->setEnabled(false);
862 button->setEditable(false);
863 button->setCustomTexture(CoreData::getInstance().getCustomTexture());
864 button->setUseCustomTexture(true);
865 }
866
867 userButtons.push_back(button);
868 }
869 userScrollBar.setElementCount((int)userButtons.size());
870 oldNickList = nickList;
871 chatManager.setAutoCompleteTextList(oldNickList);
872 }
873 if(userScrollBar.getElementCount()!=0 ) {
874 for(int i = userScrollBar.getVisibleStart(); i <= userScrollBar.getVisibleEnd(); ++i) {
875 userButtons[i]->setY(userButtonsYBase-userButtonsLineHeight*(i-userScrollBar.getVisibleStart()));
876 }
877 }
878 }
879 safeMutexIRCPtr.ReleaseLock();
880 if(serverInfoString!="empty")
881 {
882 rebuildServerLines(serverInfoString);
883 serverInfoString="empty";
884 }
885
886 serverScrollBar.setElementCount((int)serverLines.size());
887 if(serverScrollBar.getElementCount()!=0 ) {
888 for(int i = serverScrollBar.getVisibleStart(); i <= serverScrollBar.getVisibleEnd(); ++i) {
889 serverLines[i]->setY(serverLinesYBase-serverLinesLineHeight*(i-serverScrollBar.getVisibleStart()));
890 }
891 }
892
893 if(threadedErrorMsg != "") {
894 std::string sError = threadedErrorMsg;
895 threadedErrorMsg = "";
896
897 if(pCB_DisplayMessage != NULL) {
898 pCB_DisplayMessage(sError.c_str(),false);
899 }
900 else {
901 throw megaglest_runtime_error(sError.c_str());
902 }
903 }
904 }
905
simpleTask(BaseThread * callingThread,void * userdata)906 void MenuStateMasterserver::simpleTask(BaseThread *callingThread,void *userdata) {
907 if(callingThread->getQuitStatus() == true) {
908 return;
909 }
910 MutexSafeWrapper safeMutex(callingThread->getMutexThreadObjectAccessor(),string(extractFileFromDirectoryPath(__FILE__).c_str()) + "_" + intToStr(__LINE__));
911 bool needUpdate = needUpdateFromServer;
912
913 if(needUpdate == true) {
914 try {
915
916 if(callingThread->getQuitStatus() == true) {
917 return;
918 }
919
920 needUpdateFromServer = false;
921
922 if(announcementLoaded == false) {
923 string announcementURL = Config::getInstance().getString("AnnouncementURL","http://master.megaglest.org/files/announcement.txt");
924 if(announcementURL != "") {
925
926 safeMutex.ReleaseLock(true);
927 CURL *handle = SystemFlags::initHTTP();
928 std::string announcementTxt = SystemFlags::getHTTP(announcementURL,handle);
929 SystemFlags::cleanupHTTP(&handle);
930 if(callingThread->getQuitStatus() == true) {
931 return;
932 }
933 safeMutex.Lock();
934
935 if(StartsWith(announcementTxt,"Announcement from Masterserver:") == true) {
936 int newlineCount=0;
937 size_t lastIndex=0;
938
939 //announcementLabel.setText(announcementTxt);
940 consoleIRC.addLine(announcementTxt, true, Vec3f(1.0f,1.0f,0.0f));
941
942 while(true) {
943 lastIndex=announcementTxt.find("\n",lastIndex+1);
944 if(lastIndex==string::npos) {
945 break;
946 }
947 else {
948 newlineCount++;
949 }
950 }
951 newlineCount--;// remove my own line
952 for( int i=0; i< newlineCount;++i ) {
953 consoleIRC.addLine("");
954 }
955 }
956 }
957 consoleIRC.addLine("---------------------------------------------");
958 string versionURL = Config::getInstance().getString("VersionURL","http://master.megaglest.org/files/versions/")+glestVersionString+".txt";
959 //printf("\nversionURL=%s\n",versionURL.c_str());
960 if(versionURL != "") {
961 safeMutex.ReleaseLock(true);
962 CURL *handle = SystemFlags::initHTTP();
963 std::string versionTxt = SystemFlags::getHTTP(versionURL,handle);
964 SystemFlags::cleanupHTTP(&handle);
965 if(callingThread->getQuitStatus() == true) {
966 return;
967 }
968 safeMutex.Lock();
969
970 if(StartsWith(versionTxt,"Version info:") == true) {
971 int newlineCount=0;
972 size_t lastIndex=0;
973
974 //versionInfoLabel.setText(versionTxt);
975 consoleIRC.addLine(versionTxt, true, Vec3f(1.0f,0.0f,0.0f));
976
977 while(true) {
978 lastIndex=versionTxt.find("\n",lastIndex+1);
979 if(lastIndex==string::npos) {
980 break;
981 }
982 else {
983 newlineCount++;
984 }
985 }
986 newlineCount--;// remove my own line
987 for( int i=0; i< newlineCount;++i ) {
988 consoleIRC.addLine("");
989 }
990 }
991 }
992 consoleIRC.addLine("---------------------------------------------");
993 // write hint to console:
994 Config &configKeys = Config::getInstance(std::pair<ConfigType,ConfigType>(cfgMainKeys,cfgUserKeys));
995 consoleIRC.addLine(Lang::getInstance().getString("ToSwitchOffMusicPress")+" - \""+configKeys.getString("ToggleMusic")+"\"");
996
997 announcementLoaded=true;
998 }
999
1000 //Lang &lang= Lang::getInstance();
1001 try {
1002 if(Config::getInstance().getString("Masterserver","") != "") {
1003
1004 safeMutex.ReleaseLock(true);
1005 CURL *handle = SystemFlags::initHTTP();
1006
1007 string playerUUID = "?uuid=" + SystemFlags::escapeURL(Config::getInstance().getString("PlayerId",""));
1008
1009 string baseURL = Config::getInstance().getString("Masterserver");
1010 if(baseURL != "") {
1011 endPathWithSlash(baseURL,false);
1012 }
1013
1014 std::string localServerInfoString = SystemFlags::getHTTP(baseURL + "showServersForGlest.php" + playerUUID,handle);
1015 SystemFlags::cleanupHTTP(&handle);
1016 if(callingThread->getQuitStatus() == true) {
1017 return;
1018 }
1019 safeMutex.Lock();
1020
1021 serverInfoString=localServerInfoString;
1022 }
1023 }
1024 catch(const exception &ex) {
1025 serverInfoString=ex.what();
1026 SystemFlags::OutputDebug(SystemFlags::debugError,"In [%s::%s Line %d] error during Internet game status update: [%s]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__,ex.what());
1027 }
1028 }
1029 catch(const exception &e){
1030 SystemFlags::OutputDebug(SystemFlags::debugError,"In [%s::%s Line: %d] Error [%s]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__,e.what());
1031 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s] Line: %d, error [%s]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__,e.what());
1032 threadedErrorMsg = e.what();
1033 }
1034 }
1035 }
1036
rebuildServerLines(const string & serverInfo)1037 void MenuStateMasterserver::rebuildServerLines(const string &serverInfo) {
1038 int numberOfOldServerLines = (int)serverLines.size();
1039 clearServerLines();
1040 Lang &lang= Lang::getInstance();
1041 try {
1042 if(serverInfo != "") {
1043 if(SystemFlags::VERBOSE_MODE_ENABLED) printf("--------------> serverInfo [%s]\n",serverInfo.c_str());
1044 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
1045
1046 std::vector<std::string> serverList;
1047 Tokenize(serverInfo,serverList,"\n");
1048 for(int i = 0; i < (int)serverList.size(); i++) {
1049 string &server = serverList[i];
1050 if(trim(server) == "") {
1051 continue;
1052 }
1053 std::vector<std::string> serverEntities;
1054 Tokenize(server,serverEntities,"|");
1055 const int MIN_FIELDS_EXPECTED = 14;
1056
1057 if(SystemFlags::VERBOSE_MODE_ENABLED) printf("--------------> server [%s] serverEntities.size() = " MG_SIZE_T_SPECIFIER " MIN_FIELDS_EXPECTED = %d\n",server.c_str(),serverEntities.size(),MIN_FIELDS_EXPECTED);
1058
1059 if((int)serverEntities.size() >= MIN_FIELDS_EXPECTED) {
1060 labelTitle.setText(lang.getString("AvailableServers"));
1061
1062 if(Config::getInstance().getString("Masterserver","") == "") {
1063 labelTitle.setText("*** " + lang.getString("AvailableServers"));
1064 }
1065
1066 MasterServerInfo *masterServerInfo=new MasterServerInfo();
1067
1068 //general info:
1069 masterServerInfo->setGlestVersion(serverEntities[0]);
1070 masterServerInfo->setPlatform(serverEntities[1]);
1071 masterServerInfo->setBinaryCompileDate(serverEntities[2]);
1072
1073 //game info:
1074 masterServerInfo->setServerTitle(serverEntities[3]);
1075 masterServerInfo->setIpAddress(serverEntities[4]);
1076
1077 //game setup info:
1078 masterServerInfo->setTech(serverEntities[5]);
1079 masterServerInfo->setMap(serverEntities[6]);
1080 masterServerInfo->setTileset(serverEntities[7]);
1081 masterServerInfo->setActiveSlots(strToInt(serverEntities[8]));
1082 masterServerInfo->setNetworkSlots(strToInt(serverEntities[9]));
1083 masterServerInfo->setConnectedClients(strToInt(serverEntities[10]));
1084 masterServerInfo->setExternalConnectPort(strToInt(serverEntities[11]));
1085 masterServerInfo->setCountry(serverEntities[12]);
1086 masterServerInfo->setStatus(strToInt(serverEntities[13]));
1087
1088 //printf("--------------> Country [%s] Status [%d]\n",masterServerInfo->getCountry().c_str(),masterServerInfo->getStatus());
1089
1090 //printf("Getting Ping time for host %s\n",masterServerInfo->getIpAddress().c_str());
1091 //float pingTime = Socket::getAveragePingMS(masterServerInfo->getIpAddress().c_str(),1);
1092 //printf("Ping time = %f\n",pingTime);
1093 char szBuf[8096]="";
1094 snprintf(szBuf,8096,"%s",masterServerInfo->getServerTitle().c_str());
1095 masterServerInfo->setServerTitle(szBuf);
1096
1097 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
1098
1099 serverLines.push_back(new ServerLine( masterServerInfo, i, serverLinesYBase, serverLinesLineHeight, containerName));
1100 delete masterServerInfo;
1101 }
1102 else {
1103 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
1104
1105 Lang &lang= Lang::getInstance();
1106 labelTitle.setText("*** " + lang.getString("AvailableServers") + "[" + intToStr(serverEntities.size()) + "][" + intToStr(MIN_FIELDS_EXPECTED) + "] [" + serverInfo + "]");
1107
1108 if(masterserverParseErrorShown == false) {
1109 masterserverParseErrorShown = true;
1110 SystemFlags::OutputDebug(SystemFlags::debugError,"In [%s::%s Line %d] error, no masterserver defined!\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
1111 }
1112 }
1113
1114 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
1115 }
1116
1117 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
1118 }
1119
1120 }
1121 catch(const exception &ex) {
1122 labelTitle.setText("*** " + lang.getString("AvailableServers") + " [" + ex.what() + "]");
1123 SystemFlags::OutputDebug(SystemFlags::debugError,"In [%s::%s Line %d] error during Internet game status update: [%s]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__,ex.what());
1124 }
1125
1126 if((int)serverLines.size() > numberOfOldServerLines) {
1127 playServerFoundSound = true;
1128 }
1129 }
1130
1131
connectToServer(string ipString,int port)1132 bool MenuStateMasterserver::connectToServer(string ipString, int port) {
1133 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s] START ipString='%s'\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,ipString.c_str());
1134
1135 ClientInterface* clientInterface= NetworkManager::getInstance().getClientInterface();
1136 //Config& config= Config::getInstance();
1137 Ip serverIp(ipString);
1138
1139 //int serverPort = Config::getInstance().getInt("PortServer",intToStr(GameConstants::serverPort).c_str());
1140 int serverPort = port;
1141 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s] try to connect to [%s] serverPort = %d\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,serverIp.getString().c_str(),serverPort);
1142 clientInterface->connect(serverIp, serverPort);
1143 if(clientInterface->isConnected() == false) {
1144 NetworkManager::getInstance().end();
1145 NetworkManager::getInstance().init(nrClient);
1146
1147 mainMessageBoxState=1;
1148 Lang &lang= Lang::getInstance();
1149 showMessageBox(lang.getString("CouldNotConnect"), lang.getString("ConnectionFailed"), false);
1150 return false;
1151
1152 //if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s] connection failed\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__);
1153 }
1154 else {
1155 if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s] connected to [%s]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,serverIp.getString().c_str());
1156
1157 //save server ip
1158 //config.setString("ServerIp", serverIp.getString());
1159 //config.save();
1160
1161 for(time_t elapsedWait = time(NULL);
1162 clientInterface->getIntroDone() == false &&
1163 clientInterface->isConnected() &&
1164 difftime(time(NULL),elapsedWait) <= 8;) {
1165 if(clientInterface->isConnected()) {
1166 //update lobby
1167 clientInterface->updateLobby();
1168 sleep(0);
1169 //this->render();
1170 }
1171 }
1172 if( clientInterface->isConnected() == true &&
1173 clientInterface->getIntroDone() == true) {
1174 return true;
1175 }
1176
1177 return false;
1178 }
1179 }
1180
showMessageBox(const string & text,const string & header,bool toggle)1181 void MenuStateMasterserver::showMessageBox(const string &text, const string &header, bool toggle){
1182 if(!toggle){
1183 mainMessageBox.setEnabled(false);
1184 }
1185
1186 if(!mainMessageBox.getEnabled()){
1187 mainMessageBox.setText(text);
1188 mainMessageBox.setHeader(header);
1189 mainMessageBox.setEnabled(true);
1190 }
1191 else{
1192 mainMessageBox.setEnabled(false);
1193 }
1194 }
1195
1196
textInput(std::string text)1197 bool MenuStateMasterserver::textInput(std::string text) {
1198 if (ircClient != NULL && ircClient->isConnected() == true
1199 && ircClient->getHasJoinedChannel() == true) {
1200 return chatManager.textInput(text);
1201 }
1202 return false;
1203 }
1204
keyDown(SDL_KeyboardEvent key)1205 void MenuStateMasterserver::keyDown(SDL_KeyboardEvent key) {
1206 //printf("In [%s::%s Line: %d] key [%d]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__,key.keysym.sym);
1207
1208 Config &configKeys = Config::getInstance(std::pair<ConfigType,ConfigType>(cfgMainKeys,cfgUserKeys));
1209
1210 if (ircClient != NULL && ircClient->isConnected() == true
1211 && ircClient->getHasJoinedChannel() == true) {
1212 //chatmanger only if connected to irc!
1213 if (chatManager.getEditEnabled() == true) {
1214 //printf("keyDown key [%d] chatManager.getText() [%s]\n",key,chatManager.getText().c_str());
1215 MutexSafeWrapper safeMutexIRCPtr(mutexIRCClient,string(extractFileFromDirectoryPath(__FILE__).c_str()) + "_" + intToStr(__LINE__));
1216 //if (key == vkReturn && ircClient != NULL) {
1217 if(isKeyPressed(SDLK_RETURN,key,false) == true && ircClient != NULL) {
1218 ircClient->SendIRCCmdMessage(IRC_CHANNEL, chatManager.getText());
1219 }
1220 }
1221 chatManager.keyDown(key);
1222 }
1223 if(chatManager.getEditEnabled() == false) {
1224 //if(key == configKeys.getCharKey("ToggleMusic")) {
1225 if(isKeyPressed(configKeys.getSDLKey("ToggleMusic"),key) == true) {
1226 Config &config = Config::getInstance();
1227 Lang &lang= Lang::getInstance();
1228
1229 float configVolume = (config.getInt("SoundVolumeMusic") / 100.f);
1230 float currentVolume = CoreData::getInstance().getMenuMusic()->getVolume();
1231 if(currentVolume > 0) {
1232 CoreData::getInstance().getMenuMusic()->setVolume(0.f);
1233 consoleIRC.addLine(lang.getString("GameMusic") + " " + lang.getString("Off"));
1234 }
1235 else {
1236 CoreData::getInstance().getMenuMusic()->setVolume(configVolume);
1237 //If the config says zero, use the default music volume
1238 //gameMusic->setVolume(configVolume ? configVolume : 0.9);
1239 consoleIRC.addLine(lang.getString("GameMusic"));
1240 }
1241 }
1242 //else if(key == configKeys.getCharKey("SaveGUILayout")) {
1243 else if(isKeyPressed(configKeys.getSDLKey("SaveGUILayout"),key) == true) {
1244 bool saved = GraphicComponent::saveAllCustomProperties(containerName);
1245 Lang &lang= Lang::getInstance();
1246 consoleIRC.addLine(lang.getString("GUILayoutSaved") + " [" + (saved ? lang.getString("Yes") : lang.getString("No"))+ "]");
1247 }
1248 }
1249 }
1250
1251 }}//end namespace
1252