Rev 179 | Show entire file | Ignore whitespace | Details | Blame | Last modification | View Log | RSS feed
| Rev 179 | Rev 180 | ||
|---|---|---|---|
| Line 13... | Line 13... | ||
| 13 | #define GAMETYPE_TWOPLAYERS 3 |
13 | #define GAMETYPE_TWOPLAYERS 3 |
| 14 | 14 | ||
| 15 | 15 | ||
| 16 | // global variables used in this module only |
16 | // global variables used in this module only |
| 17 | static int newgame_type = 0; |
17 | static int newgame_type = 0; |
| 18 | static |
18 | static HWND hThisDialogWnd = NULL; |
| 19 | static bool is_chessserver_reachable = false; |
- | |
| 20 | 19 | ||
| 21 | 20 | ||
| 22 | // prototypes of local functions |
21 | // prototypes of local functions |
| 23 | static void StartThread_ThisDialog (void *thread_parms); |
22 | static void StartThread_ThisDialog (void *thread_parms); |
| 24 | static int CALLBACK DialogProc_ThisDialog (HWND hWnd, unsigned int message, WPARAM wParam, LPARAM lParam); |
23 | static int CALLBACK DialogProc_ThisDialog (HWND hWnd, unsigned int message, WPARAM wParam, LPARAM lParam); |
| - | 24 | static void StartThread_TestConnectionInBackground (void *thread_parms); |
|
| 25 | 25 | ||
| 26 | 26 | ||
| 27 | void DialogBox_NewGame (void) |
27 | void DialogBox_NewGame (void) |
| 28 | { |
28 | { |
| 29 | // helper function to fire up the modeless dialog box |
29 | // helper function to fire up the modeless dialog box |
| 30 | 30 | ||
| 31 | // HACK to prevent the player to click and block the view angles while the slide-in is not finished |
31 | // HACK to prevent the player to click and block the view angles while the slide-in is not finished |
| 32 | command_ignoretime = current_time + 2.0f; // allow 2 seconds |
32 | command_ignoretime = current_time + 2.0f; // allow 2 seconds |
| 33 | 33 | ||
| 34 | is_dialogbox_displayed = true; |
34 | is_dialogbox_displayed = true; |
| - | 35 | hThisDialogWnd = NULL; |
|
| 35 | _beginthread (StartThread_ThisDialog, 0, NULL); // so fire up a new one |
36 | _beginthread (StartThread_ThisDialog, 0, NULL); // so fire up a new one |
| - | 37 | ||
| - | 38 | // start the thread that will tell whether Internet works |
|
| - | 39 | _beginthread (StartThread_TestConnectionInBackground, 0, NULL); |
|
| 36 | 40 | ||
| 37 | the_scene.gui.want_spinwheel = true; // start spinning wheel |
41 | the_scene.gui.want_spinwheel = true; // start spinning wheel |
| 38 | 42 | ||
| 39 | return; // return as soon as the thread is fired up |
43 | return; // return as soon as the thread is fired up |
| 40 | } |
44 | } |
| Line 71... | Line 75... | ||
| 71 | SetWindowText (hMainWnd, PROGRAM_NAME); // update window title |
75 | SetWindowText (hMainWnd, PROGRAM_NAME); // update window title |
| 72 | the_board.reevaluate = true; // evaluate the new board |
76 | the_board.reevaluate = true; // evaluate the new board |
| 73 | the_scene.update = true; // update scene |
77 | the_scene.update = true; // update scene |
| 74 | 78 | ||
| 75 | return; // finished, a new game of the chosen type is being fired up |
79 | return; // finished, a new game of the chosen type is being fired up |
| 76 | } |
- | |
| 77 | - | ||
| 78 | - | ||
| 79 | static void StartThread_TestConnectionInBackground (void *thread_parms) |
- | |
| 80 | { |
- | |
| 81 | // this function runs in a separate thread and tests the connectivity to the chess server in the background |
- | |
| 82 | - | ||
| 83 | char icmp_send_buffer[32] = "Chess Giants connectivity test"; |
- | |
| 84 | void *icmp_recv_buffer[sizeof (ICMP_ECHO_REPLY) + sizeof (icmp_send_buffer)]; |
- | |
| 85 | char ascii_hostname[256]; |
- | |
| 86 | struct hostent *hostinfo; |
- | |
| 87 | uint32_t server_ipaddr; |
- | |
| 88 | HANDLE icmp_descriptor; |
- | |
| 89 | - | ||
| 90 | // since this is a synchronous operation, it's a good idea to do this on this separate thread |
- | |
| 91 | ConvertTo7BitASCII (ascii_hostname, sizeof (ascii_hostname), options.network.server_address); |
- | |
| 92 | if ((hostinfo = gethostbyname (ascii_hostname)) != NULL) |
- | |
| 93 | { |
- | |
| 94 | // DO NOT CONNECT TO THE SERVER AND DISCONNECT IMMEDIATELY ELSE IT WILL RESULT IN AN IP BAN. Use an ICMP ping instead. |
- | |
| 95 | server_ipaddr = inet_addr (inet_ntoa (*(struct in_addr *) hostinfo->h_addr_list[0])); |
- | |
| 96 | icmp_descriptor = IcmpCreateFile (); |
- | |
| 97 | if ((icmp_descriptor != INVALID_HANDLE_VALUE) |
- | |
| 98 | && (IcmpSendEcho (icmp_descriptor, server_ipaddr, icmp_send_buffer, sizeof (icmp_send_buffer), NULL, icmp_recv_buffer, sizeof (icmp_recv_buffer), 5000) != 0) |
- | |
| 99 | && (((ICMP_ECHO_REPLY *) icmp_recv_buffer)->Status == 0)) |
- | |
| 100 | is_chessserver_reachable = true; // on success, remember we could reach the chess server |
- | |
| 101 | } |
- | |
| 102 | - | ||
| 103 | return; // _endthread() implied |
- | |
| 104 | } |
80 | } |
| 105 | 81 | ||
| 106 | 82 | ||
| 107 | static void StartThread_ThisDialog (void *thread_parms) |
83 | static void StartThread_ThisDialog (void *thread_parms) |
| 108 | { |
84 | { |
| 109 | // this function runs in a separate thread, for that's the only way (seemingly) |
85 | // this function runs in a separate thread, for that's the only way (seemingly) |
| 110 | // to implement a non-modal message box using the Common Controls library. |
86 | // to implement a non-modal message box using the Common Controls library. |
| 111 | - | ||
| 112 | is_internet_available = false; // assume Internet doesn't work until told otherwise |
- | |
| 113 | is_chessserver_reachable = false; |
- | |
| 114 | - | ||
| 115 | // start the thread that will tell whether Internet works |
- | |
| 116 | _beginthread (StartThread_TestConnectionInBackground, 0, NULL); // so fire up a new one |
- | |
| 117 | 87 | ||
| 118 | // display the dialog box |
88 | // display the dialog box |
| 119 | newgame_type = DialogBox (hAppInstance, MAKEINTRESOURCE (THIS_DIALOG), hMainWnd, DialogProc_ThisDialog); |
89 | newgame_type = DialogBox (hAppInstance, MAKEINTRESOURCE (THIS_DIALOG), hMainWnd, DialogProc_ThisDialog); |
| 120 | if (newgame_type > 0) |
90 | if (newgame_type > 0) |
| 121 | is_dialogbox_newgame_validated = true; |
91 | is_dialogbox_newgame_validated = true; |
| Line 134... | Line 104... | ||
| 134 | unsigned short wParam_loword; |
104 | unsigned short wParam_loword; |
| 135 | 105 | ||
| 136 | // filter out the commonly used message values |
106 | // filter out the commonly used message values |
| 137 | wParam_hiword = HIWORD (wParam); |
107 | wParam_hiword = HIWORD (wParam); |
| 138 | wParam_loword = LOWORD (wParam); |
108 | wParam_loword = LOWORD (wParam); |
| 139 | - | ||
| 140 | // any message will do (mouse move, etc.) -- is the chess server reachable ? |
- | |
| 141 | if (!is_internet_available && is_chessserver_reachable) |
- | |
| 142 | { |
- | |
| 143 | is_internet_available = true; // remember we no longer need to look after that (FLAG THIS BEFORE ANY SendMessage() HAPPENS!) |
- | |
| 144 | Static_SetText (GetDlgItem (hWnd, STATICTEXT_NEWGAME_ONLINEDESCRIPTION), LOCALIZE (L"NewGame_OnlineDescription")); |
- | |
| 145 | EnableWindow (GetDlgItem (hWnd, BUTTON_NEWGAME_ONLINE), true); |
- | |
| 146 | EnableWindow (GetDlgItem (hWnd, STATICTEXT_NEWGAME_ONLINEDESCRIPTION), true); |
- | |
| 147 | } |
- | |
| 148 | 109 | ||
| 149 | // have we just fired up this window ? |
110 | // have we just fired up this window ? |
| 150 | if (message == WM_INITDIALOG) |
111 | if (message == WM_INITDIALOG) |
| 151 | { |
112 | { |
| - | 113 | hThisDialogWnd = hWnd; // save the dialog handle |
|
| - | 114 | ||
| 152 | // center the window |
115 | // center the window |
| 153 | CenterWindow (hWnd, hMainWnd); |
116 | CenterWindow (hWnd, hMainWnd); |
| 154 | 117 | ||
| 155 | // set dialog icons (small one for title bar & big one for task manager) |
118 | // set dialog icons (small one for title bar & big one for task manager) |
| 156 | SendMessage (hWnd, WM_SETICON, ICON_SMALL, (LPARAM) LoadIcon (hAppInstance, MAKEINTRESOURCE (ICON_MAIN))); |
119 | SendMessage (hWnd, WM_SETICON, ICON_SMALL, (LPARAM) LoadIcon (hAppInstance, MAKEINTRESOURCE (ICON_MAIN))); |
| Line 177... | Line 140... | ||
| 177 | // convert the status bar message to a hyperlink |
140 | // convert the status bar message to a hyperlink |
| 178 | ConvertStaticToHyperlink (GetDlgItem (hWnd, STATICTEXT_NEWGAME_STATUSBAR)); |
141 | ConvertStaticToHyperlink (GetDlgItem (hWnd, STATICTEXT_NEWGAME_STATUSBAR)); |
| 179 | 142 | ||
| 180 | // and stop the center message display |
143 | // and stop the center message display |
| 181 | the_scene.gui.want_spinwheel = false; |
144 | the_scene.gui.want_spinwheel = false; |
| - | 145 | } |
|
| - | 146 | ||
| - | 147 | // else have we been notified that the chess server is reachable ? |
|
| - | 148 | else if (message == WM_USER) |
|
| - | 149 | { |
|
| - | 150 | Static_SetText (GetDlgItem (hWnd, STATICTEXT_NEWGAME_ONLINEDESCRIPTION), LOCALIZE (L"NewGame_OnlineDescription")); |
|
| - | 151 | EnableWindow (GetDlgItem (hWnd, BUTTON_NEWGAME_ONLINE), true); |
|
| - | 152 | EnableWindow (GetDlgItem (hWnd, STATICTEXT_NEWGAME_ONLINEDESCRIPTION), true); |
|
| 182 | } |
153 | } |
| 183 | 154 | ||
| 184 | // else did we click the close button on the title bar or hit the escape key ? |
155 | // else did we click the close button on the title bar or hit the escape key ? |
| 185 | else if (message == WM_CLOSE) |
156 | else if (message == WM_CLOSE) |
| - | 157 | { |
|
| - | 158 | hThisDialogWnd = NULL; // forget about the dialog handle |
|
| 186 | EndDialog (hWnd, 0); // close the dialog box |
159 | EndDialog (hWnd, 0); // close the dialog box |
| - | 160 | } |
|
| 187 | 161 | ||
| 188 | // else did we take action on one of the controls ? |
162 | // else did we take action on one of the controls ? |
| 189 | else if (message == WM_COMMAND) |
163 | else if (message == WM_COMMAND) |
| 190 | { |
164 | { |
| 191 | // did we cancel the dialog box ? (IDCANCEL is a system-wide dialog box handler value, that catches the ESC key) |
165 | // did we cancel the dialog box ? (IDCANCEL is a system-wide dialog box handler value, that catches the ESC key) |
| Line 209... | Line 183... | ||
| 209 | ShellExecute (NULL, L"open", PROGRAM_URL, NULL, NULL, SW_MAXIMIZE); // open the donation page in the default browser, maximized |
183 | ShellExecute (NULL, L"open", PROGRAM_URL, NULL, NULL, SW_MAXIMIZE); // open the donation page in the default browser, maximized |
| 210 | } |
184 | } |
| 211 | 185 | ||
| 212 | // call the default dialog message processing function to keep things going |
186 | // call the default dialog message processing function to keep things going |
| 213 | return (false); |
187 | return (false); |
| - | 188 | } |
|
| - | 189 | ||
| - | 190 | ||
| - | 191 | static void StartThread_TestConnectionInBackground (void *thread_parms) |
|
| - | 192 | { |
|
| - | 193 | // this function runs in a separate thread and tests the connectivity to the chess server in the background |
|
| - | 194 | ||
| - | 195 | char icmp_send_buffer[32] = "Chess Giants connectivity test"; |
|
| - | 196 | void *icmp_recv_buffer[sizeof (ICMP_ECHO_REPLY) + sizeof (icmp_send_buffer)]; |
|
| - | 197 | char ascii_hostname[256]; |
|
| - | 198 | struct hostent *hostinfo; |
|
| - | 199 | uint32_t server_ipaddr; |
|
| - | 200 | HANDLE icmp_descriptor; |
|
| - | 201 | int wait_count; |
|
| - | 202 | int try_count; |
|
| - | 203 | ||
| - | 204 | // since this is a synchronous operation, it's a good idea to do this on this separate thread |
|
| - | 205 | ConvertTo7BitASCII (ascii_hostname, sizeof (ascii_hostname), options.network.server_address); |
|
| - | 206 | if ((hostinfo = gethostbyname (ascii_hostname)) != NULL) |
|
| - | 207 | { |
|
| - | 208 | // DO NOT CONNECT TO THE SERVER AND DISCONNECT IMMEDIATELY ELSE IT WILL RESULT IN AN IP BAN. Use an ICMP ping instead. |
|
| - | 209 | server_ipaddr = inet_addr (inet_ntoa (*(struct in_addr *) hostinfo->h_addr_list[0])); |
|
| - | 210 | icmp_descriptor = IcmpCreateFile (); |
|
| - | 211 | for (try_count = 0; try_count < 4; try_count++) |
|
| - | 212 | { |
|
| - | 213 | if ((icmp_descriptor != INVALID_HANDLE_VALUE) |
|
| - | 214 | && (IcmpSendEcho (icmp_descriptor, server_ipaddr, icmp_send_buffer, sizeof (icmp_send_buffer), NULL, icmp_recv_buffer, sizeof (icmp_recv_buffer), 5000) != 0) |
|
| - | 215 | && (((ICMP_ECHO_REPLY *) icmp_recv_buffer)->Status == 0)) |
|
| - | 216 | { |
|
| - | 217 | for (wait_count = 0; wait_count < 100; wait_count++) |
|
| - | 218 | { |
|
| - | 219 | if (IsWindow (hThisDialogWnd)) |
|
| - | 220 | { |
|
| - | 221 | PostMessage (hThisDialogWnd, WM_USER, 0, 0); // on success, remember we could reach the chess server |
|
| - | 222 | break; |
|
| - | 223 | } |
|
| - | 224 | Sleep (100); |
|
| - | 225 | } |
|
| - | 226 | break; // one reply is enough |
|
| - | 227 | } |
|
| - | 228 | Sleep (1000); // wait 1 second before retrying |
|
| - | 229 | } |
|
| - | 230 | } |
|
| - | 231 | ||
| - | 232 | return; // _endthread() implied |
|
| 214 | } |
233 | } |