Rev 124 | Go to most recent revision | Details | Last modification | View Log | RSS feed
| Rev | Author | Line No. | Line | 
|---|---|---|---|
| 1 | pmbaty | 1 | // dialog_challenge.cpp | 
        
| 2 | |||
| 3 | #include "../common.h" | 
        ||
| 4 | |||
| 5 | |||
| 6 | // dialog template | 
        ||
| 7 | #define THIS_DIALOG DIALOG_CHALLENGE | 
        ||
| 8 | |||
| 9 | |||
| 10 | // local definitions | 
        ||
| 11 | #define TIMER_REFRESHDIALOG 1 | 
        ||
| 12 | |||
| 13 | |||
| 14 | // global variables used in this module only | 
        ||
| 15 | static bool is_challengeaccepted = false;  | 
        ||
| 16 | static wchar_t challenger_nickname[32];  | 
        ||
| 17 | |||
| 18 | |||
| 19 | // prototypes of local functions | 
        ||
| 20 | static void StartThread_ThisDialog (void *thread_parms);  | 
        ||
| 21 | static int CALLBACK DialogProc_ThisDialog (HWND hWnd, unsigned int message, WPARAM wParam, LPARAM lParam);  | 
        ||
| 22 | |||
| 23 | |||
| 24 | void DialogBox_Challenge (int challenge_index)  | 
        ||
| 25 | { | 
        ||
| 26 |    // helper function to fire up the modeless dialog box | 
        ||
| 27 | |||
| 28 | _beginthread (StartThread_ThisDialog, 0, (void *) challenge_index); // fire up the thread  | 
        ||
| 29 | return; // return as soon as the thread is fired up  | 
        ||
| 30 | } | 
        ||
| 31 | |||
| 32 | |||
| 33 | void DialogBox_Challenge_Validated (void)  | 
        ||
| 34 | { | 
        ||
| 35 |    // callback function called by the main game thread when the dialog box is validated | 
        ||
| 36 | |||
| 37 | player_t *network_player;  | 
        ||
| 38 | interlocutor_t *interlocutor;  | 
        ||
| 39 | |||
| 40 |    // remember this callback is no longer to be called | 
        ||
| 41 | is_dialogbox_challenge_validated = false;  | 
        ||
| 42 | |||
| 43 | network_player = Player_FindByType (PLAYER_INTERNET); // quick access to network player  | 
        ||
| 44 | if (network_player == NULL)  | 
        ||
| 45 | return; // consistency check  | 
        ||
| 46 | |||
| 47 |    // did we accept the challenge ? if so, send an accept reply, else decline it | 
        ||
| 48 | if (is_challengeaccepted)  | 
        ||
| 49 |    { | 
        ||
| 50 |       // send the accept notification and print a notification in this player's chat window | 
        ||
| 51 | Player_SendBuffer_Add (network_player, 1000, L"accept %s\n", challenger_nickname);  | 
        ||
| 52 | interlocutor = Interlocutor_FindOrCreate (challenger_nickname);  | 
        ||
| 53 | Interlocutor_Notify (interlocutor, LOCALIZE (L"Chat_InvitationAcceptedByYou"), challenger_nickname);  | 
        ||
| 54 | if (IsWindow (interlocutor->hWnd))  | 
        ||
| 55 | ShowWindow (interlocutor->hWnd, SW_MINIMIZE); // minimize chat window immediately  | 
        ||
| 56 |    } | 
        ||
| 57 |    else | 
        ||
| 58 |    { | 
        ||
| 59 |       // send the decline notification and print a notification in this player's chat window | 
        ||
| 60 | Player_SendBuffer_Add (network_player, 1000, L"decline %s\n", challenger_nickname);  | 
        ||
| 61 | Interlocutor_Notify (Interlocutor_FindOrCreate (challenger_nickname), LOCALIZE (L"Chat_InvitationDeclinedByYou"), challenger_nickname);  | 
        ||
| 62 |    } | 
        ||
| 63 | |||
| 64 | return; // finished, challenge has been either accepted or declined  | 
        ||
| 65 | } | 
        ||
| 66 | |||
| 67 | |||
| 68 | static void StartThread_ThisDialog (void *thread_parms)  | 
        ||
| 69 | { | 
        ||
| 70 |    // this function runs in a separate thread, for that's the only way (seemingly) | 
        ||
| 71 |    // to implement a non-modal message box using the Common Controls library. | 
        ||
| 72 | |||
| 73 | int challenge_index;  | 
        ||
| 74 | int interlocutor_index;  | 
        ||
| 75 | challenge_t *challenge;  | 
        ||
| 76 |    HWND hParentWnd; | 
        ||
| 77 | int retval;  | 
        ||
| 78 | int error;  | 
        ||
| 79 | |||
| 80 | challenge_index = (int) thread_parms;  | 
        ||
| 81 | |||
| 82 | challenge = &challenges[challenge_index]; // quick access to challenge  | 
        ||
| 83 | |||
| 84 |    // see if we are already talking to this interlocutor, loop through all of them... | 
        ||
| 85 | hParentWnd = hMainWnd; // assume parent window will be the main window, until told otherwise  | 
        ||
| 86 | for (interlocutor_index = 0; interlocutor_index < interlocutor_count; interlocutor_index++)  | 
        ||
| 87 | if (interlocutors[interlocutor_index].is_active && (_wcsicmp (challenge->challenger, interlocutors[interlocutor_index].nickname) == 0))  | 
        ||
| 88 |       { | 
        ||
| 89 | hParentWnd = interlocutors[interlocutor_index].hWnd; // if found, parent window will be this interlocutor's chat window  | 
        ||
| 90 | break; // break as soon as we find it  | 
        ||
| 91 |       } | 
        ||
| 92 | |||
| 93 |    // display the dialog box | 
        ||
| 94 | retval = DialogBoxParam (hAppInstance, MAKEINTRESOURCE (THIS_DIALOG), hParentWnd, DialogProc_ThisDialog, (LPARAM) challenge_index);  | 
        ||
| 95 | error = GetLastError ();  | 
        ||
| 96 | is_challengeaccepted = (retval != 0);  | 
        ||
| 97 | is_dialogbox_challenge_validated = true;  | 
        ||
| 98 | |||
| 99 | challenge = &challenges[challenge_index]; // restore access to challenge (it may have relocated !)  | 
        ||
| 100 | challenge->is_active = false; // remember challenge has gone away  | 
        ||
| 101 | |||
| 102 | return; // _endthread() implied  | 
        ||
| 103 | } | 
        ||
| 104 | |||
| 105 | |||
| 106 | static int CALLBACK DialogProc_ThisDialog (HWND hWnd, unsigned int message, WPARAM wParam, LPARAM lParam)  | 
        ||
| 107 | { | 
        ||
| 108 |    // message handler for the dialog box | 
        ||
| 109 | |||
| 110 | unsigned short wParam_hiword;  | 
        ||
| 111 | unsigned short wParam_loword;  | 
        ||
| 112 | challenge_t *challenge;  | 
        ||
| 113 | wchar_t game_name[64];  | 
        ||
| 114 | wchar_t temp_string[256];  | 
        ||
| 115 | |||
| 116 |    // filter out the commonly used message values | 
        ||
| 117 | wParam_hiword = HIWORD (wParam);  | 
        ||
| 118 | wParam_loword = LOWORD (wParam);  | 
        ||
| 119 | |||
| 120 |    // have we just fired up this window ? | 
        ||
| 121 | if (message == WM_INITDIALOG)  | 
        ||
| 122 |    { | 
        ||
| 123 | challenge = &challenges[lParam]; // quick access to challenge  | 
        ||
| 124 | challenge->hWnd = hWnd; // save challenge window handle  | 
        ||
| 125 | SetWindowLongPtr (hWnd, DWLP_USER, lParam); // and attach challenge number to window  | 
        ||
| 126 | |||
| 127 |       // center the window | 
        ||
| 128 | CenterWindow (hWnd, hMainWnd);  | 
        ||
| 129 | |||
| 130 |       // set window title and control texts | 
        ||
| 131 | SetWindowText (hWnd, LOCALIZE (L"Challenge_Title"));  | 
        ||
| 132 | SetDlgItemText (hWnd, BUTTON_ACCEPT, LOCALIZE (L"Button_Accept"));  | 
        ||
| 133 | SetDlgItemText (hWnd, BUTTON_DECLINE, LOCALIZE (L"Button_Decline"));  | 
        ||
| 134 | SetDlgItemText (hWnd, STATICTEXT_CHALLENGE_STATUSBAR, LOCALIZE (L"Challenge_StatusBar"));  | 
        ||
| 135 | |||
| 136 |       // start refreshing the window every second | 
        ||
| 137 | SetTimer (hWnd, TIMER_REFRESHDIALOG, 1000, NULL);  | 
        ||
| 138 | SendMessage (hWnd, WM_TIMER, TIMER_REFRESHDIALOG, 0);  | 
        ||
| 139 | |||
| 140 |       // convert the challenger name and the status bar message to hyperlinks | 
        ||
| 141 | ConvertStaticToHyperlink (GetDlgItem (hWnd, STATICTEXT_CHALLENGE_CHALLENGER));  | 
        ||
| 142 | ConvertStaticToHyperlink (GetDlgItem (hWnd, STATICTEXT_CHALLENGE_STATUSBAR));  | 
        ||
| 143 |    } | 
        ||
| 144 | |||
| 145 |    // else did we click the close button on the title bar ? | 
        ||
| 146 | else if (message == WM_CLOSE)  | 
        ||
| 147 |    { | 
        ||
| 148 | KillTimer (hWnd, TIMER_REFRESHDIALOG); // destroy the timer we used to refresh the dialog text  | 
        ||
| 149 | EndDialog (hWnd, 0); // close the dialog box  | 
        ||
| 150 |    } | 
        ||
| 151 | |||
| 152 |    // else did we take action on one of the controls ? | 
        ||
| 153 | else if (message == WM_COMMAND)  | 
        ||
| 154 |    { | 
        ||
| 155 |       // did we cancel the dialog box ? (IDCANCEL is a system-wide dialog box handler value, that catches the ESC key) | 
        ||
| 156 |       // OR was it the "decline" button ? | 
        ||
| 157 | if ((wParam_loword == IDCANCEL) || (wParam_loword == BUTTON_DECLINE))  | 
        ||
| 158 |       { | 
        ||
| 159 | challenge = &challenges[GetWindowLongPtr (hWnd, DWLP_USER)]; // quick access to challenge  | 
        ||
| 160 | wcscpy_s (challenger_nickname, WCHAR_SIZEOF (challenger_nickname), challenge->challenger); // have a copy of challenger's name  | 
        ||
| 161 | KillTimer (hWnd, TIMER_REFRESHDIALOG); // destroy the timer we used to refresh the dialog text  | 
        ||
| 162 | EndDialog (hWnd, 0); // close the dialog box  | 
        ||
| 163 |       } | 
        ||
| 164 | |||
| 165 |       // else was it the "accept" button ? | 
        ||
| 166 | else if (wParam_loword == BUTTON_ACCEPT)  | 
        ||
| 167 |       { | 
        ||
| 168 | challenge = &challenges[GetWindowLongPtr (hWnd, DWLP_USER)]; // quick access to challenge  | 
        ||
| 169 | wcscpy_s (challenger_nickname, WCHAR_SIZEOF (challenger_nickname), challenge->challenger); // have a copy of challenger's name  | 
        ||
| 170 | KillTimer (hWnd, TIMER_REFRESHDIALOG); // destroy the timer we used to refresh the dialog text  | 
        ||
| 171 | EndDialog (hWnd, 1); // close the dialog box and return OK  | 
        ||
| 172 |       } | 
        ||
| 173 | |||
| 174 |       // else did we click the challenger name ? | 
        ||
| 175 | else if (wParam_loword == STATICTEXT_CHALLENGE_CHALLENGER)  | 
        ||
| 176 |       { | 
        ||
| 177 | challenge = &challenges[GetWindowLongPtr (hWnd, DWLP_USER)]; // quick access to challenge  | 
        ||
| 178 | PlayerCard_FindOrCreate (challenge->challenger); // fire up the dialog box (TODO: move to ._Validated())  | 
        ||
| 179 |       } | 
        ||
| 180 | |||
| 181 |       // else was it the status bar hyperlink ? | 
        ||
| 182 | else if (wParam_loword == STATICTEXT_CHALLENGE_STATUSBAR)  | 
        ||
| 183 | ShellExecute (NULL, L"open", PROGRAM_URL, NULL, NULL, SW_MAXIMIZE); // open the donation page in the default browser, maximized  | 
        ||
| 184 |    } | 
        ||
| 185 | |||
| 186 |    // else is it a timer event AND is it our refresh timer ? | 
        ||
| 187 | else if ((message == WM_TIMER) && (wParam == TIMER_REFRESHDIALOG))  | 
        ||
| 188 |    { | 
        ||
| 189 | challenge = &challenges[GetWindowLongPtr (hWnd, DWLP_USER)]; // quick access to challenge  | 
        ||
| 190 | |||
| 191 |       // do we need to update dialog ? | 
        ||
| 192 | if (challenge->update_dialog)  | 
        ||
| 193 |       { | 
        ||
| 194 |          // update challenge info | 
        ||
| 195 | SetDlgItemText (hWnd, STATICTEXT_CHALLENGE_CHALLENGER, challenge->challenger);  | 
        ||
| 196 | swprintf_s (game_name, WCHAR_SIZEOF (game_name), L"\"%s\" (%.0f %.0f)", challenge->game_type, challenge->initial_time, challenge->increment);  | 
        ||
| 197 | swprintf_s (temp_string, WCHAR_SIZEOF (temp_string), LOCALIZE (L"Challenge_Question"), game_name);  | 
        ||
| 198 | SetDlgItemText (hWnd, STATICTEXT_CHALLENGE_QUESTION, temp_string);  | 
        ||
| 199 | if (challenge->color == COLOR_BLACK)  | 
        ||
| 200 | swprintf_s (temp_string, WCHAR_SIZEOF (temp_string), LOCALIZE (L"Challenge_OpponentWillPlayAs"), LOCALIZE (L"Games_Black"));  | 
        ||
| 201 | else if (challenge->color == COLOR_WHITE)  | 
        ||
| 202 | swprintf_s (temp_string, WCHAR_SIZEOF (temp_string), LOCALIZE (L"Challenge_OpponentWillPlayAs"), LOCALIZE (L"Games_White"));  | 
        ||
| 203 |          else | 
        ||
| 204 | temp_string[0] = 0;  | 
        ||
| 205 | SetDlgItemText (hWnd, STATICTEXT_CHALLENGE_OPPONENTWILLPLAYAS, temp_string);  | 
        ||
| 206 | SetDlgItemText (hWnd, STATICTEXT_CHALLENGE_ISRATEDORNOT, (challenge->is_rated ? LOCALIZE (L"Challenge_Rated"): LOCALIZE (L"Challenge_Unrated")));  | 
        ||
| 207 | |||
| 208 | challenge->update_dialog = false; // remember we refreshed challenge text  | 
        ||
| 209 |       } | 
        ||
| 210 |    } | 
        ||
| 211 | |||
| 212 |    // call the default dialog message processing function to keep things going | 
        ||
| 213 | return (false);  | 
        ||
| 214 | } |