1 /////////////////////////////////////////
2 //
3 // OpenLieroX
4 //
5 // code under LGPL, based on JasonBs work,
6 // enhanced by Dark Charlie and Albert Zeyer
7 //
8 //
9 /////////////////////////////////////////
10
11
12 // Net menu - Internet
13 // Created 29/12/02
14 // Jason Boettcher
15
16
17 #include "LieroX.h"
18 #include "Sounds.h"
19 #include "Clipboard.h"
20 #include "AuxLib.h"
21 #include "HTTP.h"
22 #include "DeprecatedGUI/Graphics.h"
23 #include "CClient.h"
24 #include "DeprecatedGUI/Menu.h"
25 #include "GfxPrimitives.h"
26 #include "FindFile.h"
27 #include "StringUtils.h"
28 #include "DeprecatedGUI/CButton.h"
29 #include "DeprecatedGUI/CListview.h"
30 #include "DeprecatedGUI/CLabel.h"
31 #include "DeprecatedGUI/CCombobox.h"
32 #include "DeprecatedGUI/CMenu.h"
33 #include "DeprecatedGUI/CTextbox.h"
34 #include "DeprecatedGUI/CChatWidget.h"
35 #include "ProfileSystem.h"
36 #include "IpToCountryDB.h"
37 #include "Debug.h"
38
39
40
41
42 namespace DeprecatedGUI {
43
44 CGuiLayout cInternet;
45 std::string szNetCurServer;
46
47 // Internet widgets
48 enum {
49 mi_Join=0,
50 mi_ServerList,
51 mi_Refresh,
52 mi_UpdateList,
53 mi_AddServer,
54 mi_Back,
55 mi_PopupMenu,
56 mi_PlayerSelection,
57 };
58
59 ///////////////////
60 // Initialize the Internet menu
Menu_Net_NETInitialize()61 bool Menu_Net_NETInitialize()
62 {
63 iNetMode = net_internet;
64 szNetCurServer = "";
65
66 cInternet.Shutdown();
67 cInternet.Initialize();
68
69 cInternet.Add( new CListview(), mi_ServerList, 40, 180, 560, 242);
70 cInternet.Add( new CButton(BUT_BACK, tMenu->bmpButtons), mi_Back, 25, 440, 50, 15);
71 cInternet.Add( new CButton(BUT_ADD, tMenu->bmpButtons), mi_AddServer, 140,440, 40, 15);
72 cInternet.Add( new CButton(BUT_REFRESH, tMenu->bmpButtons), mi_Refresh, 250,440, 83, 15);
73 cInternet.Add( new CButton(BUT_UPDATELIST, tMenu->bmpButtons), mi_UpdateList, 390,440, 125, 15);
74 cInternet.Add( new CButton(BUT_JOIN, tMenu->bmpButtons), mi_Join, 570,440, 43, 15);
75 cInternet.Add( new CLabel("Select player:",tLX->clNormalLabel),-1, 125, 152, 180,15);
76 cInternet.Add( new CCombobox(), mi_PlayerSelection, 225,150, 170, 19);
77 if( tLXOptions->bEnableChat && tLXOptions->bEnableMiniChat )
78 cInternet.Add( new CChatWidget(), -1, 25, 15, 585, 85 );
79
80 Menu_Net_AddTabBarButtons(&cInternet);
81
82 /*
83 Server list columns
84
85 Connection speed
86 Name
87 State
88 Players
89 Ping
90 Address
91 */
92
93 // Add players to the list
94 profile_t *p = GetProfiles();
95 bool validName = false;
96 for(;p;p=p->tNext) {
97 /*if(p->iType == PRF_COMPUTER)
98 continue;*/
99
100 int i = ((CCombobox*) cInternet.getWidget( mi_PlayerSelection ))->addItem(p->sName, p->sName);
101 ((CCombobox*) cInternet.getWidget( mi_PlayerSelection ))->setImage(p->cSkin.getPreview(), i);
102 if( p->sName == tLXOptions->sLastSelectedPlayer )
103 validName=true;
104 }
105
106 if( ! validName )
107 tLXOptions->sLastSelectedPlayer = GetProfiles()->sName;
108
109 ((CCombobox*) cInternet.getWidget( mi_PlayerSelection ))->setCurSIndexItem( tLXOptions->sLastSelectedPlayer );
110
111 Menu_redrawBufferRect(0, 0, 640, 480);
112
113 cInternet.SendMessage( mi_ServerList, LVS_ADDCOLUMN, "", tLXOptions->iInternetList[0]);
114 cInternet.SendMessage( mi_ServerList, LVS_ADDCOLUMN, "Server Name", tLXOptions->iInternetList[1]);
115 cInternet.SendMessage( mi_ServerList, LVS_ADDCOLUMN, "State", tLXOptions->iInternetList[2]);
116 cInternet.SendMessage( mi_ServerList, LVS_ADDCOLUMN, "Players", tLXOptions->iInternetList[3]);
117 cInternet.SendMessage( mi_ServerList, LVS_ADDCOLUMN, "Ping", tLXOptions->iInternetList[4]);
118
119 if (tLXOptions->bUseIpToCountry)
120 { // Too lazy to update tLXOptions, so I'll calculate last column width from width of listview
121 //int CountryColumnWidth = 21; // TODO: not used
122
123 // HINT: because this column is optional, it is at the end of the array from options
124 cInternet.SendMessage( mi_ServerList, LVS_ADDCOLUMN, "Country", tLXOptions->iInternetList[5]);
125 }
126
127 cInternet.SendMessage( mi_ServerList, LVS_ADDCOLUMN, "Address", tLXOptions->iInternetList[6]);
128
129 ((CListview*) cInternet.getWidget( mi_ServerList ))->SetSortColumn( tLXOptions->iInternetSortColumn, true ); // Sorting
130
131 // Clear the server list & grab an update
132 Menu_SvrList_Clear();
133
134 // Load the list
135 Menu_SvrList_LoadList("cfg/svrlist.dat");
136 Menu_SvrList_FillList( (CListview *)cInternet.getWidget( mi_ServerList ) );
137 Menu_SvrList_UpdateUDPList();
138
139 Timer("Menu_Net_NETInitialize serverlist timeout", null, NULL, SVRLIST_TIMEOUT, true).startHeadless();
140
141 return true;
142 }
143
144
145 ///////////////////
146 // Shutdown the internet menu
Menu_Net_NETShutdown()147 void Menu_Net_NETShutdown()
148 {
149 if (tLXOptions) {
150
151 // Save the list
152 if( iNetMode == net_internet ) {
153 Menu_SvrList_SaveList("cfg/svrlist.dat");
154
155 CListview* l = (CListview *)cInternet.getWidget(mi_ServerList);
156 if(l) {
157 // Save the column widths
158 for (int i=0;i<7;i++)
159 tLXOptions->iInternetList[i] = l->GetColumnWidth(i);
160
161 // Save the sorting column
162 tLXOptions->iInternetSortColumn = l->GetSortColumn();
163 }
164 }
165
166 // Save the selected player
167 cb_item_t *item = (cb_item_t *)cInternet.SendMessage(mi_PlayerSelection,CBM_GETCURITEM,(DWORD)0,0); // TODO: 64bit unsafe (pointer cast)
168 if (item)
169 tLXOptions->sLastSelectedPlayer = item->sIndex;
170 }
171
172 cInternet.Shutdown();
173 }
174
175
176 ///////////////////
177 // Net Internet frame
Menu_Net_NETFrame(int mouse)178 void Menu_Net_NETFrame(int mouse)
179 {
180 gui_event_t *ev = NULL;
181 std::string addr;
182
183
184 // Process & Draw the gui
185 ev = cInternet.Process();
186 cInternet.Draw( VideoPostProcessor::videoSurface() );
187
188 if (Menu_Net_ProcessTabBarButtons(ev))
189 return;
190
191 // Process the server list
192 static bool wasLoadedBefore = false;
193 if( Menu_SvrList_Process() || (tIpToCountryDB->Loaded() && !wasLoadedBefore) ) {
194 // Add the servers to the listview
195 Menu_SvrList_FillList( (CListview *)cInternet.getWidget( mi_ServerList ) );
196 wasLoadedBefore = tIpToCountryDB->Loaded();
197 }
198
199
200
201 // Process any events
202 if(ev) {
203
204 switch(ev->iControlID) {
205
206 // Add Server
207 case mi_AddServer:
208 if(ev->iEventMsg == BTN_CLICKED) {
209 // Click!
210 PlaySoundSample(sfxGeneral.smpClick);
211
212 Menu_Net_NETAddServer();
213 }
214 break;
215
216 // Back
217 case mi_Back:
218 if(ev->iEventMsg == BTN_CLICKED) {
219
220 // Shutdown
221 Menu_Net_NETShutdown();
222
223 // Click!
224 PlaySoundSample(sfxGeneral.smpClick);
225
226 // Back to main menu
227 Menu_MainInitialize();
228 }
229 break;
230
231 // Refresh
232 case mi_Refresh:
233 if(ev->iEventMsg == BTN_CLICKED) {
234
235 // Click!
236 PlaySoundSample(sfxGeneral.smpClick);
237
238 // Refresh the currently visible servers
239 Menu_SvrList_RefreshList();
240 Menu_SvrList_FillList( (CListview *)cInternet.getWidget( mi_ServerList ) );
241 }
242 break;
243
244 // Join
245 case mi_Join:
246 if(ev->iEventMsg == BTN_CLICKED) {
247
248 addr = "";
249 int result = cInternet.SendMessage(mi_ServerList, LVS_GETCURSINDEX, &addr, 0);
250 if(result != -1 && addr != "") {
251
252 // Save the list
253 Menu_SvrList_SaveList("cfg/svrlist.dat");
254
255 // Click!
256 PlaySoundSample(sfxGeneral.smpClick);
257
258 lv_subitem_t *sub = ((CListview *)cInternet.getWidget(mi_ServerList))->getCurSubitem(1);
259
260 // Join
261 if (sub)
262 Menu_Net_NETJoinServer(addr,sub->sText);
263 return;
264 }
265 }
266 break;
267
268 // Serverlist
269 case mi_ServerList:
270
271 // Double click
272 if(ev->iEventMsg == LV_DOUBLECLK) {
273
274 /*
275 Now.... Should a double click refresh the server (like tribes)?
276 Or should it join the server like other games???
277 */
278
279 // Just join for the moment
280 addr = "";
281 int result = cInternet.SendMessage(mi_ServerList, LVS_GETCURSINDEX, &addr, 0);
282 lv_subitem_t *sub = ((CListview *)cInternet.getWidget(mi_ServerList))->getCurSubitem(1);
283 if(result != -1 && addr != "" && sub) {
284 // Save the list
285 Menu_SvrList_SaveList("cfg/svrlist.dat");
286
287 Menu_Net_NETJoinServer(addr,sub->sText);
288 return;
289 }
290 }
291
292 // Right click
293 if( ev->iEventMsg == LV_RIGHTCLK ) {
294 addr = "";
295 int result = cInternet.SendMessage(mi_ServerList, LVS_GETCURSINDEX, &addr, 0);
296 if(result && addr != "") {
297 // Display a menu
298 szNetCurServer = addr;
299 mouse_t *m = GetMouse();
300
301 cInternet.Add( new CMenu(m->X, m->Y), mi_PopupMenu, 0,0, 640,480 );
302 cInternet.SendMessage( mi_PopupMenu, MNS_ADDITEM, "Delete server", 0 );
303 cInternet.SendMessage( mi_PopupMenu, MNS_ADDITEM, "Refresh server", 1 );
304 cInternet.SendMessage( mi_PopupMenu, MNS_ADDITEM, "Join server", 2 );
305 cInternet.SendMessage( mi_PopupMenu, MNS_ADDITEM, "Add to favourites", 3 );
306 cInternet.SendMessage( mi_PopupMenu, MNS_ADDITEM, "Send \"I want to join message\"",4 );
307 cInternet.SendMessage( mi_PopupMenu, MNS_ADDITEM, "Copy IP to clipboard", 5 );
308 cInternet.SendMessage( mi_PopupMenu, MNS_ADDITEM, "Server details", 6 );
309 }
310 }
311
312
313 // Enter key
314 if( ev->iEventMsg == LV_ENTER ) {
315 // Join
316 addr = "";
317 int result = cInternet.SendMessage(mi_ServerList, LVS_GETCURSINDEX, &addr, 0);
318 lv_subitem_t *sub = ((CListview *)cInternet.getWidget(mi_ServerList))->getCurSubitem(1);
319 if(result != -1 && addr != "" && sub) {
320 // Save the list
321 Menu_SvrList_SaveList("cfg/svrlist.dat");
322
323 Menu_Net_NETJoinServer(addr,sub->sText);
324 return;
325 }
326 }
327
328 // Delete
329 if( ev->iEventMsg == LV_DELETE ) {
330 addr = "";
331 int result = cInternet.SendMessage(mi_ServerList, LVS_GETCURSINDEX, &addr, 0);
332 if(result && addr != "") {
333 Menu_SvrList_RemoveServer(addr);
334 // Re-Fill the server list
335 Menu_SvrList_FillList( (CListview *)cInternet.getWidget( mi_ServerList ) );
336 }
337 }
338 break;
339
340 // Popup menu
341 case mi_PopupMenu:
342 switch( ev->iEventMsg ) {
343 // Delete the server
344 case MNU_USER+0:
345 Menu_SvrList_RemoveServer(szNetCurServer);
346 break;
347
348 // Refresh the server
349 case MNU_USER+1:
350 {
351 server_t *sv = Menu_SvrList_FindServerStr(szNetCurServer);
352 if(sv)
353 Menu_SvrList_RefreshServer(sv);
354 }
355 break;
356
357 // Join a server
358 case MNU_USER+2: {
359 // Save the list
360 Menu_SvrList_SaveList("cfg/svrlist.dat");
361 lv_subitem_t *sub = ((CListview *)cInternet.getWidget(mi_ServerList))->getCurSubitem(1);
362 if (sub)
363 Menu_Net_NETJoinServer(szNetCurServer,sub->sText);
364 }
365 return;
366
367 // Add server to favourites
368 case MNU_USER+3:
369 {
370 server_t *sv = Menu_SvrList_FindServerStr(szNetCurServer);
371 if (sv)
372 Menu_SvrList_AddFavourite(sv->szName,sv->szAddress);
373 }
374 break;
375
376 // Send a "wants to join" message
377 case MNU_USER+4:
378 {
379 server_t *sv = Menu_SvrList_FindServerStr(szNetCurServer);
380 std::string Nick;
381 cInternet.SendMessage(mi_PlayerSelection, CBS_GETCURNAME, &Nick, 0);
382 if (sv)
383 Menu_SvrList_WantsJoin(Nick, sv);
384 }
385 break;
386
387 // Copy the IP to clipboard
388 case MNU_USER+5:
389 {
390 copy_to_clipboard(szNetCurServer);
391 }
392 break;
393
394 // Show server details
395 case MNU_USER+6:
396 cInternet.removeWidget(mi_PopupMenu);
397 Menu_Net_NETShowServer(szNetCurServer);
398 break;
399 }
400
401 // Re-Fill the server list
402 Menu_SvrList_FillList( (CListview *)cInternet.getWidget( mi_ServerList ) );
403
404 // Remove the menu widget
405 cInternet.SendMessage( mi_PopupMenu, MNM_REDRAWBUFFER, (DWORD)0, 0);
406 cInternet.removeWidget(mi_PopupMenu);
407 break;
408
409 // Update server list
410 case mi_UpdateList:
411 if(ev->iEventMsg == BTN_CLICKED) {
412 // Click!
413 PlaySoundSample(sfxGeneral.smpClick);
414
415 Menu_Net_NETUpdateList();
416 }
417 break;
418 }
419
420 }
421
422 // F5 updates the list
423 if (WasKeyboardEventHappening(SDLK_F5))
424 Menu_Net_NETUpdateList();
425
426 // Draw the mouse
427 DrawCursor(VideoPostProcessor::videoSurface());
428
429 }
430
431
432
433 ///////////////////
434 // Join a server
Menu_Net_NETJoinServer(const std::string & sAddress,const std::string & sName)435 void Menu_Net_NETJoinServer(const std::string& sAddress, const std::string& sName)
436 {
437 // Fill in the game structure
438 CCombobox* combo = (CCombobox *) cInternet.getWidget(mi_PlayerSelection);
439 const cb_item_t* item = combo->getSelectedItem();
440 if(!item) {
441 errors << "no player selected" << endl;
442 return;
443 }
444
445 tLXOptions->sLastSelectedPlayer = item->sIndex;
446
447 if(!JoinServer(sAddress, sName, item->sIndex))
448 return;
449
450 // Shutdown
451 cInternet.Shutdown();
452
453 iNetMode = net_join;
454 tMenu->iReturnTo = net_internet;
455
456 // Connect to the server
457 Menu_Net_JoinConnectionInitialize(sAddress);
458 }
459
460
461 ///////////////////
462 // Show an 'add server' box to enter in an address
463 enum {
464 na_Cancel=0,
465 na_Add,
466 na_Address
467 };
468
Menu_Net_NETAddServer()469 void Menu_Net_NETAddServer()
470 {
471 CGuiLayout cAddSvr;
472 gui_event_t *ev = NULL;
473 bool addServerMsg = true;
474
475
476 // Create the background
477 cInternet.Draw( tMenu->bmpBuffer.get() );
478 Menu_DrawBox(tMenu->bmpBuffer.get(), 200, 220, 440, 340);
479 //DrawImageAdv(tMenu->bmpBuffer, tMenu->bmpMainBack, 202,222, 202,222, 237,117);
480 DrawRectFill(tMenu->bmpBuffer.get(), 202,222,439,339,tLX->clDialogBackground);
481
482 Menu_RedrawMouse(true);
483
484
485 cAddSvr.Initialize();
486 cAddSvr.Add( new CButton(BUT_ADD, tMenu->bmpButtons), na_Add, 220, 320, 40,15);
487 cAddSvr.Add( new CButton(BUT_CANCEL, tMenu->bmpButtons),na_Cancel, 350, 320, 70,15);
488 cAddSvr.Add( new CLabel("Add a server", tLX->clNormalLabel), -1,275, 225, 0, 0);
489 cAddSvr.Add( new CLabel("Address", tLX->clNormalLabel), -1,215, 267, 0, 0);
490 cAddSvr.Add( new CTextbox(), na_Address, 280, 265, 140, tLX->cFont.GetHeight());
491
492 ProcessEvents();
493 while(!WasKeyboardEventHappening(SDLK_ESCAPE,false) && addServerMsg && tMenu->bMenuRunning) {
494 Menu_RedrawMouse(true);
495 DrawImageAdv(VideoPostProcessor::videoSurface(),tMenu->bmpBuffer, 200,220, 200,220, 240, 240);
496
497 ProcessEvents();
498
499 // Process the server list
500 if( Menu_SvrList_Process() ) {
501 // Add the servers to the listview
502 Menu_SvrList_FillList( (CListview *)cInternet.getWidget( mi_ServerList ) );
503 }
504
505 cAddSvr.Draw( VideoPostProcessor::videoSurface() );
506 ev = cAddSvr.Process();
507
508 // Process any events
509 if(ev) {
510
511 switch(ev->iControlID) {
512
513 // Add
514 case na_Add:
515 if(ev->iEventMsg == BTN_CLICKED) {
516
517 std::string addr;
518 cAddSvr.SendMessage(na_Address, TXS_GETTEXT, &addr, 0);
519
520 Menu_SvrList_AddServer(addr, true);
521 Menu_SvrList_FillList( (CListview *)cInternet.getWidget( mi_ServerList ) );
522
523 // Click!
524 PlaySoundSample(sfxGeneral.smpClick);
525
526 addServerMsg = false;
527 }
528 break;
529
530 // Cancel
531 case na_Cancel:
532 if(ev->iEventMsg == BTN_CLICKED) {
533 // Click!
534 PlaySoundSample(sfxGeneral.smpClick);
535
536 addServerMsg = false;
537 }
538 break;
539 }
540 }
541
542
543 DrawCursor(VideoPostProcessor::videoSurface());
544 doVideoFrameInMainThread();
545 CapFPS();
546 }
547
548
549 cAddSvr.Shutdown();
550
551 // Re-draw the background
552 DrawImage(tMenu->bmpBuffer.get(),tMenu->bmpMainBack_common,0,0);
553 Menu_DrawSubTitle(tMenu->bmpBuffer.get(),SUB_NETWORK);
554 if (tMenu->tFrontendInfo.bPageBoxes)
555 Menu_DrawBox(tMenu->bmpBuffer.get(), 15,130, 625, 465);
556 Menu_RedrawMouse(true);
557 }
558
559
560
561 ///////////////////
562 // Update the server list
Menu_Net_NETUpdateList()563 void Menu_Net_NETUpdateList()
564 {
565 CGuiLayout cListUpdate;
566 gui_event_t *ev = NULL;
567 bool updateList = true;
568 int http_result = 0;
569 std::string szLine;
570
571 // Clear the server list
572 Menu_SvrList_ClearAuto();
573
574 // UDP list
575 Menu_SvrList_UpdateUDPList();
576
577 //
578 // Get the number of master servers for a progress bar
579 //
580 int SvrCount = 0;
581 int CurServer = 0;
582 bool SentRequest = false;
583 FILE *fp = OpenGameFile("cfg/masterservers.txt","rt");
584 if( !fp ) {
585 errors << "Cannot update list because there is no masterservers.txt file available\n" << endl;
586 return;
587 }
588
589 // TODO: i don't understand it, why are we doing it so complicated here, why not just save it in a list?
590 while( !feof(fp) ) {
591 szLine = ReadUntil(fp);
592 TrimSpaces(szLine);
593
594 if( szLine.length() > 0 && szLine[0] != '#' )
595 SvrCount++;
596 }
597
598 // Back to the start
599 fseek(fp, 0, SEEK_SET);
600
601 // Create the background
602 cInternet.Draw( tMenu->bmpBuffer.get() );
603 Menu_DrawBox(tMenu->bmpBuffer.get(), 200, 220, 440, 340);
604 //DrawImageAdv(tMenu->bmpBuffer, tMenu->bmpMainBack, 202,222, 202,222, 237,117);
605 DrawRectFill(tMenu->bmpBuffer.get(), 202, 222, 439, 339, tLX->clDialogBackground);
606 Menu_DrawBox(tMenu->bmpBuffer.get(), 220, 280, 420, 300);
607
608 Menu_RedrawMouse(true);
609
610
611 cListUpdate.Initialize();
612 cListUpdate.Add( new CButton(BUT_CANCEL, tMenu->bmpButtons),0, 285, 320, 70,15);
613 cListUpdate.Add( new CLabel("Getting server list", tLX->clNormalLabel), -1,260, 227, 0, 0);
614
615
616 CHttp http;
617
618 while(!WasKeyboardEventHappening(SDLK_ESCAPE,false) && updateList && tMenu->bMenuRunning) {
619 tLX->currentTime = GetTime();
620
621 Menu_RedrawMouse(true);
622 ProcessEvents();
623 DrawImageAdv(VideoPostProcessor::videoSurface(),tMenu->bmpBuffer, 200,220, 200,220, 240, 240);
624
625 if( SvrCount > 0 ) {
626 DrawRectFill(VideoPostProcessor::videoSurface(), 222,282, (int) (222+((float)CurServer/(float)SvrCount)*200.0f), 299, tLX->clProgress);
627 tLX->cOutlineFont.DrawCentre(VideoPostProcessor::videoSurface(), 320,283,tLX->clWhite, itoa(CurServer) + "/" + itoa(SvrCount));
628 }
629
630 // Do the HTTP requests of the master servers
631 if( !SentRequest ) {
632
633 // Have we gone through all the servers?
634 if( CurServer >= SvrCount )
635 break;
636
637 // Get the next server in the list
638 while( !feof(fp) ) {
639 szLine = ReadUntil(fp);
640 TrimSpaces(szLine);
641
642 if( szLine.length() > 0 && szLine[0] != '#' ) {
643
644 // Send the request
645 //notes << "Getting serverlist from " + szLine + "..." << endl;
646 http.RequestData(szLine + LX_SVRLIST, tLXOptions->sHttpProxy);
647 SentRequest = true;
648
649 break;
650 }
651 }
652 } else { // Process the http request
653 http_result = http.ProcessRequest();
654
655 // Parse the list if the request was successful
656 if (http_result == HTTP_PROC_FINISHED) {
657 Menu_Net_NETParseList(http);
658
659 // Other master servers could have more server so we process them anyway
660 SentRequest = false;
661 CurServer++;
662 } else if (http_result == HTTP_PROC_ERROR) {
663 if (http.GetError().iError != HTTP_NO_ERROR)
664 errors << "HTTP ERROR: " << http.GetError().sErrorMsg << endl;
665 // Jump to next server
666 SentRequest = false;
667 CurServer++;
668 http.CancelProcessing();
669 }
670 }
671
672 cListUpdate.Draw( VideoPostProcessor::videoSurface() );
673 ev = cListUpdate.Process();
674
675 // Process any events
676 if(ev) {
677 if (ev->iControlID == 0 && ev->iEventMsg == BTN_CLICKED) { // Cancel
678 // Click!
679 PlaySoundSample(sfxGeneral.smpClick);
680
681 http_result = 0;
682 updateList = false;
683 break;
684 }
685 }
686
687
688 DrawCursor(VideoPostProcessor::videoSurface());
689 doVideoFrameInMainThread();
690 CapFPS();
691 }
692
693 cListUpdate.Shutdown();
694 fclose(fp);
695
696 Menu_SvrList_FillList( (CListview *)cInternet.getWidget( mi_ServerList ) );
697
698
699 // Re-draw the background
700 DrawImage(tMenu->bmpBuffer.get(),tMenu->bmpMainBack_common,0,0);
701 if (tMenu->tFrontendInfo.bPageBoxes)
702 Menu_DrawBox(tMenu->bmpBuffer.get(), 15,130, 625, 465);
703 Menu_DrawSubTitle(tMenu->bmpBuffer.get(),SUB_NETWORK);
704 Menu_RedrawMouse(true);
705 }
706
707
708 ///////////////////
709 // Parse the downloaded server list
Menu_Net_NETParseList(CHttp & http)710 void Menu_Net_NETParseList(CHttp &http)
711 {
712 const std::string& content = http.GetData();
713
714 std::string addr, ptr;
715
716 std::string::const_iterator it = content.begin();
717 size_t i = 0;
718 size_t startpos = 0;
719 for(; it != content.end(); it++, i++) {
720 if(*it != '\n') continue;
721 std::vector<std::string> tokens = explode(content.substr(startpos, i-startpos), ",");
722 startpos = i+1;
723
724 // we need at least 2 items
725 if(tokens.size() < 2) continue;
726
727 addr = tokens[0];
728 ptr = tokens[1];
729
730 TrimSpaces(addr);
731 TrimSpaces(ptr);
732
733 // If the address, or port does NOT have quotes around it, the line must be mangled and cannot be used
734 if(addr.size() <= 2 || ptr.size() <= 2) continue;
735 if(addr[0] != '\"' || ptr[0] != '\"') continue;
736 if(addr[addr.size()-1] != '\"' || ptr[ptr.size()-1] != '\"') continue;
737
738 StripQuotes(addr);
739 StripQuotes(ptr);
740
741 // Create the server address
742 Menu_SvrList_AddServer(addr + ":" + ptr, false);
743 }
744
745 // Update the GUI
746 Timer("Menu_Net_NETParseList ping waiter", null, NULL, PingWait, true).startHeadless();
747 }
748
749 enum {
750 nd_Ok=0,
751 nd_Refresh,
752 nd_Join
753 };
754
755 ///////////////////
756 // Show a server's details
Menu_Net_NETShowServer(const std::string & szAddress)757 void Menu_Net_NETShowServer(const std::string& szAddress)
758 {
759 CGuiLayout cDetails;
760
761 // Create the buffer
762 DrawImage(tMenu->bmpBuffer.get(),tMenu->bmpMainBack_common,0,0);
763 Menu_DrawBox(tMenu->bmpBuffer.get(), 15,130, 625, 465);
764 Menu_DrawSubTitle(tMenu->bmpBuffer.get(),SUB_NETWORK);
765 cInternet.Draw(tMenu->bmpBuffer.get());
766
767 Menu_RedrawMouse(true);
768
769 int center = VideoPostProcessor::videoSurface()->w/2;
770 int y = VideoPostProcessor::videoSurface()->h/2 - INFO_H/2;
771
772 cDetails.Initialize();
773 cDetails.Add( new CButton(BUT_REFRESH, tMenu->bmpButtons), nd_Refresh, center - 105, y+INFO_H-20, 85,15);
774 cDetails.Add( new CButton(BUT_JOIN, tMenu->bmpButtons), nd_Join, center, y+INFO_H-20, 40,45);
775 cDetails.Add( new CButton(BUT_OK, tMenu->bmpButtons), nd_Ok, center + 60, y+INFO_H-20, 40,15);
776 ((CButton *)cDetails.getWidget(nd_Refresh))->setRedrawMenu(false);
777 ((CButton *)cDetails.getWidget(nd_Ok))->setRedrawMenu(false);
778 ((CButton *)cDetails.getWidget(nd_Join))->setRedrawMenu(false);
779
780 bGotDetails = false;
781 bOldLxBug = false;
782 nTries = 0;
783 fStart = AbsTime();
784
785 while(!WasKeyboardEventHappening(SDLK_ESCAPE,false) && tMenu->bMenuRunning) {
786 tLX->currentTime = GetTime();
787
788 Menu_RedrawMouse(true);
789 ProcessEvents();
790 //DrawImageAdv(VideoPostProcessor::videoSurface(),tMenu->bmpBuffer, 200,220, 200,220, 240, 240);
791
792 Menu_SvrList_DrawInfo(szAddress, INFO_W, INFO_H);
793
794 cDetails.Draw(VideoPostProcessor::videoSurface());
795 gui_event_t *ev = NULL;
796
797 ev = cDetails.Process();
798 if(ev) {
799
800 // Ok
801 if(ev->iControlID == nd_Ok && ev->iEventMsg == BTN_CLICKED) {
802 break;
803 // Refresh
804 } else if (ev->iControlID == nd_Refresh && ev->iEventMsg == BTN_CLICKED) {
805 fStart = AbsTime();
806 bGotDetails = false;
807 bOldLxBug = false;
808 nTries = 0;
809 } else if (ev->iControlID == nd_Join && ev->iEventMsg == BTN_CLICKED) {
810 // Save the list
811 Menu_SvrList_SaveList("cfg/svrlist.dat");
812
813 lv_subitem_t *sub = ((CListview *)cInternet.getWidget(mi_ServerList))->getCurSubitem(1);
814
815 // Join
816 if (sub)
817 Menu_Net_NETJoinServer(szAddress, sub->sText);
818
819 break;
820 }
821 }
822
823 DrawCursor(VideoPostProcessor::videoSurface());
824 doVideoFrameInMainThread();
825 CapFPS();
826 }
827
828 cDetails.Shutdown();
829
830
831 // Redraw the background
832 DrawImage(tMenu->bmpBuffer.get(),tMenu->bmpMainBack_common,0,0);
833 if (tMenu->tFrontendInfo.bPageBoxes)
834 Menu_DrawBox(tMenu->bmpBuffer.get(), 15,130, 625, 465);
835 Menu_DrawSubTitle(tMenu->bmpBuffer.get(),SUB_NETWORK);
836 Menu_RedrawMouse(true);
837 }
838
839 }; // namespace DeprecatedGUI
840