1 /* 2 * ReactOS kernel 3 * Copyright (C) 2008 ReactOS Team 4 * 5 * This program is free software; you can redistribute it and/or modify 6 * it under the terms of the GNU General Public License as published by 7 * the Free Software Foundation; either version 2 of the License, or 8 * (at your option) any later version. 9 * 10 * This program is distributed in the hope that it will be useful, 11 * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 * GNU General Public License for more details. 14 * 15 * You should have received a copy of the GNU General Public License along 16 * with this program; if not, write to the Free Software Foundation, Inc., 17 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. 18 */ 19 /* 20 * COPYRIGHT: See COPYING in the top level directory 21 * PROJECT: ReactOS text-mode setup 22 * FILE: base/setup/usetup/mui.c 23 * PURPOSE: Text-mode setup 24 * PROGRAMMER: 25 */ 26 27 #include "usetup.h" 28 #include "muilanguages.h" 29 30 #define NDEBUG 31 #include <debug.h> 32 33 static 34 ULONG 35 FindLanguageIndex(VOID) 36 { 37 ULONG lngIndex = 0; 38 39 if (SelectedLanguageId == NULL) 40 { 41 /* Default to en-US */ 42 return 0; // FIXME!! 43 // SelectedLanguageId = L"00000409"; 44 } 45 46 while (ResourceList[lngIndex].MuiPages != NULL) 47 { 48 if (_wcsicmp(ResourceList[lngIndex].LanguageID, SelectedLanguageId) == 0) 49 { 50 return lngIndex; 51 } 52 53 lngIndex++; 54 } 55 56 return 0; 57 } 58 59 60 #if 0 61 BOOLEAN 62 IsLanguageAvailable( 63 PWCHAR LanguageId) 64 { 65 ULONG lngIndex = 0; 66 67 while (ResourceList[lngIndex].MuiPages != NULL) 68 { 69 if (_wcsicmp(ResourceList[lngIndex].LanguageID, LanguageId) == 0) 70 return TRUE; 71 72 lngIndex++; 73 } 74 75 return FALSE; 76 } 77 #endif 78 79 80 static 81 const MUI_ENTRY * 82 FindMUIEntriesOfPage( 83 IN ULONG PageNumber) 84 { 85 ULONG muiIndex = 0; 86 ULONG lngIndex; 87 const MUI_PAGE * Pages = NULL; 88 89 lngIndex = max(FindLanguageIndex(), 0); 90 Pages = ResourceList[lngIndex].MuiPages; 91 92 while (Pages[muiIndex].MuiEntry != NULL) 93 { 94 if (Pages[muiIndex].Number == PageNumber) 95 return Pages[muiIndex].MuiEntry; 96 97 muiIndex++; 98 } 99 100 return NULL; 101 } 102 103 static 104 const MUI_ERROR * 105 FindMUIErrorEntries(VOID) 106 { 107 ULONG lngIndex = max(FindLanguageIndex(), 0); 108 return ResourceList[lngIndex].MuiErrors; 109 } 110 111 static 112 const MUI_STRING * 113 FindMUIStringEntries(VOID) 114 { 115 ULONG lngIndex = max(FindLanguageIndex(), 0); 116 return ResourceList[lngIndex].MuiStrings; 117 } 118 119 120 VOID 121 MUIClearPage( 122 IN ULONG page) 123 { 124 const MUI_ENTRY * entry; 125 ULONG index; 126 127 entry = FindMUIEntriesOfPage(page); 128 if (!entry) 129 { 130 PopupError("Error: Failed to find translated page", 131 NULL, 132 NULL, 133 POPUP_WAIT_NONE); 134 return; 135 } 136 137 index = 0; 138 while (entry[index].Buffer != NULL) 139 { 140 CONSOLE_ClearStyledText(entry[index].X, 141 entry[index].Y, 142 entry[index].Flags, 143 strlen(entry[index].Buffer)); 144 index++; 145 } 146 } 147 148 VOID 149 MUIDisplayPage( 150 IN ULONG page) 151 { 152 const MUI_ENTRY * entry; 153 ULONG index; 154 155 entry = FindMUIEntriesOfPage(page); 156 if (!entry) 157 { 158 PopupError("Error: Failed to find translated page", 159 NULL, 160 NULL, 161 POPUP_WAIT_NONE); 162 return; 163 } 164 165 index = 0; 166 while (entry[index].Buffer != NULL) 167 { 168 CONSOLE_SetStyledText(entry[index].X, 169 entry[index].Y, 170 entry[index].Flags, 171 entry[index].Buffer); 172 173 index++; 174 } 175 } 176 177 VOID 178 MUIDisplayErrorV( 179 IN ULONG ErrorNum, 180 OUT PINPUT_RECORD Ir, 181 IN ULONG WaitEvent, 182 IN va_list args) 183 { 184 const MUI_ERROR* entry; 185 CHAR Buffer[2048]; 186 187 if (ErrorNum >= ERROR_LAST_ERROR_CODE) 188 { 189 PopupError("Invalid error number provided", 190 "Press ENTER to continue", 191 Ir, 192 POPUP_WAIT_ENTER); 193 return; 194 } 195 196 entry = FindMUIErrorEntries(); 197 if (!entry) 198 { 199 PopupError("Error: Failed to find translated error message", 200 NULL, 201 NULL, 202 POPUP_WAIT_NONE); 203 return; 204 } 205 206 vsprintf(Buffer, entry[ErrorNum].ErrorText, args); 207 208 PopupError(Buffer, 209 entry[ErrorNum].ErrorStatus, 210 Ir, 211 WaitEvent); 212 } 213 214 VOID 215 __cdecl 216 MUIDisplayError( 217 IN ULONG ErrorNum, 218 OUT PINPUT_RECORD Ir, 219 IN ULONG WaitEvent, 220 ...) 221 { 222 va_list arg_ptr; 223 224 va_start(arg_ptr, WaitEvent); 225 MUIDisplayErrorV(ErrorNum, Ir, WaitEvent, arg_ptr); 226 va_end(arg_ptr); 227 } 228 229 PCSTR 230 MUIGetString( 231 ULONG Number) 232 { 233 ULONG i; 234 const MUI_STRING * entry; 235 CHAR szErr[128]; 236 237 entry = FindMUIStringEntries(); 238 if (entry) 239 { 240 for (i = 0; entry[i].Number != 0; i++) 241 { 242 if (entry[i].Number == Number) 243 { 244 return entry[i].String; 245 } 246 } 247 } 248 249 sprintf(szErr, "Error: failed find string id %lu for language index %lu\n", Number, FindLanguageIndex()); 250 251 PopupError(szErr, 252 NULL, 253 NULL, 254 POPUP_WAIT_NONE); 255 256 return "<nostring>"; 257 } 258 259 /** 260 * @MUIGetEntry 261 * 262 * Retrieves a MUI entry of a page, given the page number and the text ID. 263 * 264 * @param[in] Page 265 * The MUI (Multilingual User Interface) entry page number, as a unsigned long integer. 266 * 267 * @param[in] TextID 268 * The text identification number (ID), as a unsigned integer. The parameter is used to identify 269 * its MUI properties like the coordinates, text style flag and its buffer content. 270 * 271 * @return 272 * Returns a constant MUI entry. 273 * 274 */ 275 const MUI_ENTRY * 276 MUIGetEntry( 277 IN ULONG Page, 278 IN INT TextID) 279 { 280 const MUI_ENTRY * entry; 281 ULONG index; 282 283 /* Retrieve the entries of a MUI page */ 284 entry = FindMUIEntriesOfPage(Page); 285 if (!entry) 286 { 287 DPRINT("MUIGetEntryData(): Failed to get the translated entry page!\n"); 288 return NULL; 289 } 290 291 /* Loop over the ID entries and check if it matches with one of them */ 292 for (index = 0; entry[index].Buffer != NULL; index++) 293 { 294 if (entry[index].TextID == TextID) 295 { 296 /* They match so return the MUI entry */ 297 return &entry[index]; 298 } 299 } 300 301 /* Page number or ID are incorrect so in this case bail out */ 302 DPRINT("Couldn't get the MUI entry field from the page!\n"); 303 return NULL; 304 } 305 306 /** 307 * @MUIClearText 308 * 309 * Clears a portion of text from the console output. 310 * 311 * @param[in] Page 312 * The MUI (Multilingual User Interface) entry page number, as a unsigned long integer. 313 * 314 * @param[in] TextID 315 * The text identification number (ID), as an integer. The parameter is used to identify 316 * its MUI properties like the coordinates, text style flag and its buffer content. 317 * 318 * @return 319 * Nothing. 320 * 321 */ 322 VOID 323 MUIClearText( 324 IN ULONG Page, 325 IN INT TextID) 326 { 327 const MUI_ENTRY * entry; 328 329 /* Get the MUI entry */ 330 entry = MUIGetEntry(Page, TextID); 331 332 if (!entry) 333 return; 334 335 /* Remove the text by using CONSOLE_ClearTextXY() */ 336 CONSOLE_ClearTextXY( 337 entry->X, 338 entry->Y, 339 (ULONG)strlen(entry->Buffer)); 340 } 341 342 /** 343 * @MUIClearStyledText 344 * 345 * Clears a portion of text from the console output, given the actual state style flag of the text. 346 * 347 * @param[in] Page 348 * The MUI (Multilingual User Interface) entry page number, as a unsigned long integer. 349 * 350 * @param[in] TextID 351 * The text identification number (ID), as an integer. The parameter is used to identify 352 * its MUI properties like the coordinates, text style flag and its buffer content. 353 * 354 * @param[in] Flags 355 * The text style flag, as an integer. The flag determines the style of the text, such 356 * as being highlighted, underlined, high padding and so on. 357 * 358 * @return 359 * Nothing. 360 * 361 */ 362 VOID 363 MUIClearStyledText( 364 IN ULONG Page, 365 IN INT TextID, 366 IN INT Flags) 367 { 368 const MUI_ENTRY * entry; 369 370 /* Get the MUI entry */ 371 entry = MUIGetEntry(Page, TextID); 372 373 if (!entry) 374 return; 375 376 /* Now, begin removing the text by calling CONSOLE_ClearStyledText() */ 377 CONSOLE_ClearStyledText( 378 entry->X, 379 entry->Y, 380 Flags, 381 (ULONG)strlen(entry->Buffer)); 382 } 383 384 /** 385 * @MUISetText 386 * 387 * Prints a text to the console output. 388 * 389 * @param[in] Page 390 * The MUI (Multilingual User Interface) entry page number, as a unsigned long integer. 391 * 392 * @param[in] TextID 393 * The text identification number (ID), as an integer. The parameter is used to identify 394 * its MUI properties like the coordinates, text style flag and its buffer content. 395 * 396 * @return 397 * Nothing. 398 * 399 */ 400 VOID 401 MUISetText( 402 IN ULONG Page, 403 IN INT TextID) 404 { 405 const MUI_ENTRY * entry; 406 407 /* Get the MUI entry */ 408 entry = MUIGetEntry(Page, TextID); 409 410 if (!entry) 411 return; 412 413 /* Print the text to the console output by calling CONSOLE_SetTextXY() */ 414 CONSOLE_SetTextXY(entry->X, entry->Y, entry->Buffer); 415 } 416 417 /** 418 * @MUISetStyledText 419 * 420 * Prints a text to the console output, with a style for it. 421 * 422 * @param[in] Page 423 * The MUI (Multilingual User Interface) entry page number, as a unsigned long integer. 424 * 425 * @param[in] TextID 426 * The text identification number (ID), as an integer. The parameter is used to identify 427 * its MUI properties like the coordinates, text style flag and its buffer content. 428 * 429 * @param[in] Flags 430 * The text style flag, as an integer. The flag determines the style of the text, such 431 * as being highlighted, underlined, high padding and so on. 432 * 433 * @return 434 * Nothing. 435 * 436 */ 437 VOID 438 MUISetStyledText( 439 IN ULONG Page, 440 IN INT TextID, 441 IN INT Flags) 442 { 443 const MUI_ENTRY * entry; 444 445 /* Get the MUI entry */ 446 entry = MUIGetEntry(Page, TextID); 447 448 if (!entry) 449 return; 450 451 /* Print the text to the console output by calling CONSOLE_SetStyledText() */ 452 CONSOLE_SetStyledText(entry->X, entry->Y, Flags, entry->Buffer); 453 } 454 455 VOID 456 SetConsoleCodePage(VOID) 457 { 458 UINT wCodePage; 459 460 #if 0 461 ULONG lngIndex = 0; 462 463 while (ResourceList[lngIndex].MuiPages != NULL) 464 { 465 if (_wcsicmp(ResourceList[lngIndex].LanguageID, SelectedLanguageId) == 0) 466 { 467 wCodePage = (UINT) wcstoul(ResourceList[lngIndex].OEMCPage, NULL, 10); 468 SetConsoleOutputCP(wCodePage); 469 return; 470 } 471 472 lngIndex++; 473 } 474 #else 475 wCodePage = (UINT)wcstoul(MUIGetOEMCodePage(SelectedLanguageId), NULL, 10); 476 SetConsoleOutputCP(wCodePage); 477 #endif 478 } 479 480 /* EOF */ 481