1 /* ScummVM - Graphic Adventure Engine
2 *
3 * ScummVM is the legal property of its developers, whose names
4 * are too numerous to list here. Please refer to the COPYRIGHT
5 * file distributed with this source distribution.
6 *
7 * This program is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU General Public License
9 * as published by the Free Software Foundation; either version 2
10 * of the License, or (at your option) any later version.
11 *
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
20 *
21 */
22
23 #include "common/config-manager.h"
24 #include "common/savefile.h"
25 #include "common/system.h"
26 #include "common/events.h"
27 #include "common/localization.h"
28 #include "common/translation.h"
29 #include "common/ustr.h"
30
31 #include "graphics/scaler.h"
32
33 #include "gui/gui-manager.h"
34 #include "gui/widget.h"
35 #include "gui/ThemeEval.h"
36
37 #include "scumm/dialogs.h"
38 #include "scumm/sound.h"
39 #include "scumm/scumm.h"
40 #include "scumm/imuse/imuse.h"
41 #include "scumm/imuse_digi/dimuse.h"
42 #include "scumm/verbs.h"
43
44 #ifndef DISABLE_HELP
45 #include "scumm/help.h"
46 #endif
47
48 using Graphics::kTextAlignCenter;
49 using Graphics::kTextAlignLeft;
50 using GUI::WIDGET_ENABLED;
51
52 namespace Scumm {
53
54 struct ResString {
55 int num;
56 char string[80];
57 };
58
59 static const ResString string_map_table_v8[] = {
60 {0, "/BT_100/Please insert disk %d. Press ENTER"},
61 {0, "/BT__003/Unable to Find %s, (%s %d) Press Button."},
62 {0, "/BT__004/Error reading disk %c, (%c%d) Press Button."},
63 {0, "/BT__002/Game Paused. Press SPACE to Continue."},
64 {0, "/BT__005/Are you sure you want to restart? (Y/N)"}, //BOOT.004
65 {0, "/BT__006/Are you sure you want to quit? (Y/N)"}, //BOOT.005
66 {0, "/BT__008/Save"},
67 {0, "/BT__009/Load"},
68 {0, "/BT__010/Play"},
69 {0, "/BT__011/Cancel"},
70 {0, "/BT__012/Quit"},
71 {0, "/BT__013/OK"},
72 {0, ""},
73 {0, "/BT__014/You must enter a name"},
74 {0, "/BT__015/The game was NOT saved (disk full?)"},
75 {0, "/BT__016/The game was NOT loaded"},
76 {0, "/BT__017/Saving '%s'"},
77 {0, "/BT__018/Loading '%s'"},
78 {0, "/BT__019/Name your SAVE game"},
79 {0, "/BT__020/Select a game to LOAD"}
80 };
81
82 static const ResString string_map_table_v7[] = {
83 {96, "game name and version"}, //that's how it's supposed to be
84 {83, "Unable to Find %s, (%c%d) Press Button."},
85 {84, "Error reading disk %c, (%c%d) Press Button."},
86 {85, "/BOOT.003/Game Paused. Press SPACE to Continue."},
87 {86, "/BOOT.004/Are you sure you want to restart? (Y/N)"},
88 {87, "/BOOT.005/Are you sure you want to quit? (Y/N)"},
89 {70, "/BOOT.008/Save"},
90 {71, "/BOOT.009/Load"},
91 {72, "/BOOT.010/Play"},
92 {73, "/BOOT.011/Cancel"},
93 {74, "/BOOT.012/Quit"},
94 {75, "/BOOT.013/OK"},
95 {0, ""},
96 {78, "/BOOT.014/You must enter a name"},
97 {81, "/BOOT.015/The game was NOT saved (disk full?)"},
98 {82, "/BOOT.016/The game was NOT loaded"},
99 {79, "/BOOT.017/Saving '%s'"},
100 {80, "/BOOT.018/Loading '%s'"},
101 {76, "/BOOT.019/Name your SAVE game"},
102 {77, "/BOOT.020/Select a game to LOAD"}
103
104 /* This is the complete string map for v7
105 {68, "/BOOT.007/c:\\dig"},
106 {69, "/BOOT.021/The Dig"},
107 {70, "/BOOT.008/Save"},
108 {71, "/BOOT.009/Load"},
109 {72, "/BOOT.010/Play"},
110 {73, "/BOOT.011/Cancel"},
111 {74, "/BOOT.012/Quit"},
112 {75, "/BOOT.013/OK"},
113 {76, "/BOOT.019/Name your SAVE game"},
114 {77, "/BOOT.020/Select a game to LOAD"},
115 {78, "/BOOT.014/You must enter a name"},
116 {79, "/BOOT.017/Saving '%s'"},
117 {80, "/BOOT.018/Loading '%s'"},
118 {81, "/BOOT.015/The game was NOT saved (disk full?)"},
119 {82, "/BOOT.016/The game was NOT loaded"},
120 {83, "Unable to Find %s, (%c%d) Press Button."},
121 {84, "Error reading disk %c, (%c%d) Press Button."},
122 {85, "/BOOT.003/Game Paused. Press SPACE to Continue."},
123 {86, "/BOOT.004/Are you sure you want to restart? (Y/N)"},
124 {87, "/BOOT.005/Are you sure you want to quit? (Y/N)"},
125 {90, "/BOOT.022/Music"},
126 {91, "/BOOT.023/Voice"},
127 {92, "/BOOT.024/Sfx"},
128 {93, "/BOOT.025/disabled"},
129 {94, "/BOOT.026/Text speed"},
130 {95, "/BOOT.027/Display Text"},
131 {96, "The Dig v1.0"},
132 {138, "/BOOT.028/Spooled Music"),
133 {139, "/BOOT.029/Do you want to replace this saved game? (Y/N)"},
134 {141, "Voice Only"},
135 {142, "Voice and Text"},
136 {143, "Text Display Only"}, */
137
138 };
139
140 static const ResString string_map_table_v6[] = {
141 {90, "Insert Disk %c and Press Button to Continue."},
142 {91, "Unable to Find %s, (%c%d) Press Button."},
143 {92, "Error reading disk %c, (%c%d) Press Button."},
144 {93, "Game Paused. Press SPACE to Continue."},
145 {94, "Are you sure you want to restart? (Y/N)Y"},
146 {95, "Are you sure you want to quit? (Y/N)Y"},
147 {96, "Save"},
148 {97, "Load"},
149 {98, "Play"},
150 {99, "Cancel"},
151 {100, "Quit"},
152 {101, "OK"},
153 {102, "Insert save/load game disk"},
154 {103, "You must enter a name"},
155 {104, "The game was NOT saved (disk full?)"},
156 {105, "The game was NOT loaded"},
157 {106, "Saving '%s'"},
158 {107, "Loading '%s'"},
159 {108, "Name your SAVE game"},
160 {109, "Select a game to LOAD"},
161 {117, "How may I serve you?"}
162 };
163
164 static const ResString string_map_table_v345[] = {
165 {1, _s("Insert Disk %c and Press Button to Continue.")},
166 {2, _s("Unable to Find %s, (%c%d) Press Button.")},
167 {3, _s("Error reading disk %c, (%c%d) Press Button.")},
168 {4, _s("Game Paused. Press SPACE to Continue.")},
169 // I18N: You may specify 'Yes' symbol at the end of the line, like this:
170 // "Moechten Sie wirklich neu starten? (J/N)J"
171 // Will react to J as 'Yes'
172 {5, _s("Are you sure you want to restart? (Y/N)Y")},
173 // I18N: you may specify 'Yes' symbol at the end of the line. See previous comment
174 {6, _s("Are you sure you want to quit? (Y/N)Y")},
175
176 // Added in SCUMM4
177 {7, _s("Save")},
178 {8, _s("Load")},
179 {9, _s("Play")},
180 {10, _s("Cancel")},
181 {11, _s("Quit")},
182 {12, _s("OK")},
183 {13, _s("Insert save/load game disk")},
184 {14, _s("You must enter a name")},
185 {15, _s("The game was NOT saved (disk full?)")},
186 {16, _s("The game was NOT loaded")},
187 {17, _s("Saving '%s'")},
188 {18, _s("Loading '%s'")},
189 {19, _s("Name your SAVE game")},
190 {20, _s("Select a game to LOAD")},
191 {28, _s("Game title)")}
192 };
193
194 #pragma mark -
195
196 #ifndef DISABLE_HELP
197
198 class HelpDialog : public ScummDialog {
199 public:
200 HelpDialog(const GameSettings &game);
201 void handleCommand(GUI::CommandSender *sender, uint32 cmd, uint32 data) override;
202
203 void reflowLayout() override;
204
205 protected:
206 typedef Common::String String;
207
208 GUI::ButtonWidget *_nextButton;
209 GUI::ButtonWidget *_prevButton;
210
211 GUI::StaticTextWidget *_title;
212 GUI::StaticTextWidget *_key[HELP_NUM_LINES];
213 GUI::StaticTextWidget *_dsc[HELP_NUM_LINES];
214
215 int _page;
216 int _numPages;
217 int _numLines;
218
219 const GameSettings _game;
220
221 void displayKeyBindings();
222 };
223
224 #endif
225
226 #pragma mark -
227
ScummDialog(int x,int y,int w,int h)228 ScummDialog::ScummDialog(int x, int y, int w, int h) : GUI::Dialog(x, y, w, h) {
229 _backgroundType = GUI::ThemeEngine::kDialogBackgroundSpecial;
230 }
231
ScummDialog(String name)232 ScummDialog::ScummDialog(String name) : GUI::Dialog(name) {
233 _backgroundType = GUI::ThemeEngine::kDialogBackgroundSpecial;
234 }
235
236 #pragma mark -
237
238 #ifndef DISABLE_HELP
239
ScummMenuDialog(ScummEngine * scumm)240 ScummMenuDialog::ScummMenuDialog(ScummEngine *scumm)
241 : MainMenuDialog(scumm) {
242 _helpDialog = new HelpDialog(scumm->_game);
243 _helpButton->setEnabled(true);
244 }
245
~ScummMenuDialog()246 ScummMenuDialog::~ScummMenuDialog() {
247 delete _helpDialog;
248 }
249
handleCommand(GUI::CommandSender * sender,uint32 cmd,uint32 data)250 void ScummMenuDialog::handleCommand(GUI::CommandSender *sender, uint32 cmd, uint32 data) {
251 switch (cmd) {
252 case kHelpCmd:
253 _helpDialog->runModal();
254 break;
255 default:
256 MainMenuDialog::handleCommand(sender, cmd, data);
257 }
258 }
259
260 #pragma mark -
261
262 enum {
263 kNextCmd = 'NEXT',
264 kPrevCmd = 'PREV'
265 };
266
HelpDialog(const GameSettings & game)267 HelpDialog::HelpDialog(const GameSettings &game)
268 : ScummDialog("ScummHelp"), _game(game) {
269 _title = new GUI::StaticTextWidget(this, "ScummHelp.Title", Common::U32String());
270
271 _page = 1;
272 _backgroundType = GUI::ThemeEngine::kDialogBackgroundDefault;
273
274 _numPages = ScummHelp::numPages(_game.id);
275
276 // I18N: Previous page button
277 _prevButton = new GUI::ButtonWidget(this, "ScummHelp.Prev", _("~P~revious"), Common::U32String(), kPrevCmd);
278 // I18N: Next page button
279 _nextButton = new GUI::ButtonWidget(this, "ScummHelp.Next", _("~N~ext"), Common::U32String(), kNextCmd);
280 new GUI::ButtonWidget(this, "ScummHelp.Close", _("~C~lose"), Common::U32String(), GUI::kCloseCmd);
281 _prevButton->clearFlags(WIDGET_ENABLED);
282
283 GUI::ContainerWidget *placeHolder = new GUI::ContainerWidget(this, "ScummHelp.HelpText");
284 placeHolder->setBackgroundType(GUI::ThemeEngine::kWidgetBackgroundNo);
285
286 _numLines = HELP_NUM_LINES;
287
288 // Dummy entries
289 for (int i = 0; i < HELP_NUM_LINES; i++) {
290 _key[i] = new GUI::StaticTextWidget(this, 0, 0, 10, 10, Common::U32String(), Graphics::kTextAlignRight);
291 _dsc[i] = new GUI::StaticTextWidget(this, 0, 0, 10, 10, Common::U32String(), Graphics::kTextAlignLeft);
292 }
293
294 }
295
reflowLayout()296 void HelpDialog::reflowLayout() {
297 ScummDialog::reflowLayout();
298
299 int lineHeight = g_gui.getFontHeight();
300 int16 x, y;
301 int16 w, h;
302
303 assert(lineHeight);
304
305 g_gui.xmlEval()->getWidgetData("ScummHelp.HelpText", x, y, w, h);
306
307 // Make sure than we don't have more lines than what we can fit
308 // on the space that the layout reserves for text
309 _numLines = MIN(HELP_NUM_LINES, (int)(h / lineHeight));
310
311 int keyW = w * 20 / 100;
312 int dscX = x + keyW + 32;
313 int dscW = w * 80 / 100;
314
315 int xoff = (_w >> 1) - (w >> 1);
316
317 for (int i = 0; i < _numLines; i++) {
318 _key[i]->resize(xoff + x, y + lineHeight * i, keyW, lineHeight, false);
319 _dsc[i]->resize(xoff + dscX, y + lineHeight * i, dscW, lineHeight, false);
320 }
321
322 displayKeyBindings();
323 }
324
displayKeyBindings()325 void HelpDialog::displayKeyBindings() {
326 U32String titleStr, *keyStr, *dscStr;
327
328 ScummHelp::updateStrings(_game.id, _game.version, _game.platform, _page, titleStr, keyStr, dscStr);
329
330 _title->setLabel(titleStr);
331 for (int i = 0; i < _numLines; i++) {
332 _key[i]->setLabel(keyStr[i]);
333 _dsc[i]->setLabel(dscStr[i]);
334 }
335
336 delete[] keyStr;
337 delete[] dscStr;
338 }
339
handleCommand(GUI::CommandSender * sender,uint32 cmd,uint32 data)340 void HelpDialog::handleCommand(GUI::CommandSender *sender, uint32 cmd, uint32 data) {
341
342 switch (cmd) {
343 case kNextCmd:
344 _page++;
345 if (_page >= _numPages) {
346 _nextButton->clearFlags(WIDGET_ENABLED);
347 }
348 if (_page >= 2) {
349 _prevButton->setFlags(WIDGET_ENABLED);
350 }
351 displayKeyBindings();
352 g_gui.scheduleTopDialogRedraw();
353 break;
354 case kPrevCmd:
355 _page--;
356 if (_page <= _numPages) {
357 _nextButton->setFlags(WIDGET_ENABLED);
358 }
359 if (_page <= 1) {
360 _prevButton->clearFlags(WIDGET_ENABLED);
361 }
362 displayKeyBindings();
363 g_gui.scheduleTopDialogRedraw();
364 break;
365 default:
366 ScummDialog::handleCommand(sender, cmd, data);
367 }
368 }
369
370 #endif
371
372 #pragma mark -
373
isCJKLanguage(Common::Language lang)374 static bool isCJKLanguage(Common::Language lang) {
375 switch (lang) {
376 case Common::KO_KOR:
377 case Common::JA_JPN:
378 case Common::ZH_TWN:
379 case Common::ZH_CNA:
380 return true;
381 default:
382 return false;
383 }
384 }
385
InfoDialog(ScummEngine * scumm,int res)386 InfoDialog::InfoDialog(ScummEngine *scumm, int res)
387 : ScummDialog(0, 0, 0, 0), _vm(scumm), _style(GUI::ThemeEngine::kFontStyleBold) { // dummy x and w
388
389 _message = queryResString(res);
390
391 Common::Language lang = isCJKLanguage(_vm->_language) ? _vm->_language : Common::UNK_LANG;
392
393 // Width and height are dummy
394 _text = new GUI::StaticTextWidget(this, 0, 0, 10, 10, _message, kTextAlignCenter, Common::U32String(), GUI::ThemeEngine::kFontStyleBold, lang);
395
396 // Store this for the calls to getStringWidth() and getStringHeight() in reflowLayout().
397 if (lang != Common::UNK_LANG)
398 _style = GUI::ThemeEngine::kFontStyleLangExtra;
399 }
400
InfoDialog(ScummEngine * scumm,const U32String & message)401 InfoDialog::InfoDialog(ScummEngine *scumm, const U32String &message)
402 : ScummDialog(0, 0, 0, 0), _vm(scumm), _style(GUI::ThemeEngine::kFontStyleBold) { // dummy x and w
403
404 _message = message;
405
406 // Width and height are dummy
407 _text = new GUI::StaticTextWidget(this, 0, 0, 10, 10, _message, kTextAlignCenter);
408 }
409
setInfoText(const U32String & message)410 void InfoDialog::setInfoText(const U32String &message) {
411 _message = message;
412 _text->setLabel(_message);
413 //reflowLayout(); // FIXME: Should we call this here? Depends on the usage patterns, I guess...
414 }
415
reflowLayout()416 void InfoDialog::reflowLayout() {
417 const int screenW = g_system->getOverlayWidth();
418 const int screenH = g_system->getOverlayHeight();
419
420 int width = g_gui.getStringWidth(_message, _style) + 16;
421 int height = g_gui.getFontHeight(_style) + 8;
422
423 _w = width;
424 _h = height;
425 _x = (screenW - width) / 2;
426 _y = (screenH - height) / 2;
427
428 _text->setSize(_w, _h);
429 }
430
queryResString(int stringno)431 const Common::U32String InfoDialog::queryResString(int stringno) {
432 byte buf[256];
433 byte reverseBuf[256];
434 const byte *result;
435
436 if (stringno == 0)
437 return String();
438
439 if (_vm->_game.heversion >= 80)
440 return _(string_map_table_v6[stringno - 1].string);
441 else if (_vm->_game.version == 8)
442 result = (const byte *)string_map_table_v8[stringno - 1].string;
443 else if (_vm->_game.version == 7)
444 result = _vm->getStringAddressVar(string_map_table_v7[stringno - 1].num);
445 else if (_vm->_game.version == 6)
446 result = _vm->getStringAddressVar(string_map_table_v6[stringno - 1].num);
447 else if (_vm->_game.version >= 3)
448 result = _vm->getStringAddress(string_map_table_v345[stringno - 1].num);
449 else
450 return _(string_map_table_v345[stringno - 1].string);
451
452 if (result && *result == '/') {
453 _vm->translateText(result, buf);
454 result = buf;
455 }
456
457 if (!result || *result == '\0') { // Gracelessly degrade to english :)
458 return _(string_map_table_v345[stringno - 1].string);
459 }
460
461 if (_vm->reverseIfNeeded(result, reverseBuf))
462 result = reverseBuf;
463 // Convert to a proper string (take care of FF codes)
464 byte chr;
465 String tmp;
466 while ((chr = *result++)) {
467 if (chr == 0xFF) {
468 result += 3;
469 } else if (chr != '@') {
470 tmp += chr;
471 }
472 }
473
474 const Common::CodePage convertFromCodePage = _vm->getDialogCodePage();
475 return convertFromCodePage == Common::kCodePageInvalid ? _(tmp) : U32String(tmp, convertFromCodePage);
476 }
477
478 #pragma mark -
479
PauseDialog(ScummEngine * scumm,int res)480 PauseDialog::PauseDialog(ScummEngine *scumm, int res)
481 : InfoDialog(scumm, res) {
482 }
483
handleKeyDown(Common::KeyState state)484 void PauseDialog::handleKeyDown(Common::KeyState state) {
485 if (state.ascii == ' ') // Close pause dialog if space key is pressed
486 close();
487 else
488 ScummDialog::handleKeyDown(state);
489 }
490
ConfirmDialog(ScummEngine * scumm,int res)491 ConfirmDialog::ConfirmDialog(ScummEngine *scumm, int res)
492 : InfoDialog(scumm, res), _yesKey('y'), _noKey('n') {
493
494 if (_message.empty())
495 return;
496
497 if (_message[_message.size() - 1] != ')') {
498 _yesKey = _message[_message.size() - 1];
499 _message.deleteLastChar();
500
501 if (_yesKey >= 'A' && _yesKey <= 'Z')
502 _yesKey += 'a' - 'A';
503
504 _text->setLabel(_message);
505 reflowLayout();
506 }
507 }
508
handleKeyDown(Common::KeyState state)509 void ConfirmDialog::handleKeyDown(Common::KeyState state) {
510 Common::KeyCode keyYes, keyNo;
511
512 Common::getLanguageYesNo(keyYes, keyNo);
513
514 if (state.keycode == Common::KEYCODE_n || state.ascii == _noKey || state.ascii == keyNo) {
515 setResult(0);
516 close();
517 } else if (state.keycode == Common::KEYCODE_y || state.ascii == _yesKey || state.ascii == keyYes) {
518 setResult(1);
519 close();
520 } else
521 ScummDialog::handleKeyDown(state);
522 }
523
524 #pragma mark -
525
ValueDisplayDialog(const Common::U32String & label,int minVal,int maxVal,int val,uint16 incKey,uint16 decKey)526 ValueDisplayDialog::ValueDisplayDialog(const Common::U32String &label, int minVal, int maxVal,
527 int val, uint16 incKey, uint16 decKey)
528 : GUI::Dialog(0, 0, 0, 0),
529 _label(label), _min(minVal), _max(maxVal),
530 _value(val), _incKey(incKey), _decKey(decKey), _timer(0) {
531 assert(_min <= _value && _value <= _max);
532 }
533
drawDialog(GUI::DrawLayer layerToDraw)534 void ValueDisplayDialog::drawDialog(GUI::DrawLayer layerToDraw) {
535 Dialog::drawDialog(layerToDraw);
536
537 const int labelWidth = _w - 8 - _percentBarWidth;
538 g_gui.theme()->drawText(Common::Rect(_x+4, _y+4, _x+labelWidth+4,
539 _y+g_gui.theme()->getFontHeight()+4), _label);
540 g_gui.theme()->drawSlider(Common::Rect(_x+4+labelWidth, _y+4, _x+_w-4, _y+_h-4),
541 _percentBarWidth * (_value - _min) / (_max - _min));
542 }
543
handleTickle()544 void ValueDisplayDialog::handleTickle() {
545 if (g_system->getMillis() > _timer) {
546 close();
547 }
548 }
549
reflowLayout()550 void ValueDisplayDialog::reflowLayout() {
551 const int screenW = g_system->getOverlayWidth();
552 const int screenH = g_system->getOverlayHeight();
553
554 _percentBarWidth = screenW * 100 / 640;
555
556 int width = g_gui.getStringWidth(_label) + 16 + _percentBarWidth;
557 int height = g_gui.getFontHeight() + 4 * 2;
558
559 _x = (screenW - width) / 2;
560 _y = (screenH - height) / 2;
561 _w = width;
562 _h = height;
563 }
564
handleKeyDown(Common::KeyState state)565 void ValueDisplayDialog::handleKeyDown(Common::KeyState state) {
566 if (state.ascii == _incKey || state.ascii == _decKey) {
567 if (state.ascii == _incKey && _value < _max)
568 _value++;
569 else if (state.ascii == _decKey && _value > _min)
570 _value--;
571
572 setResult(_value);
573 _timer = g_system->getMillis() + kDisplayDelay;
574 g_gui.scheduleTopDialogRedraw();
575 } else {
576 close();
577 }
578 }
579
open()580 void ValueDisplayDialog::open() {
581 GUI::Dialog::open();
582 setResult(_value);
583 _timer = g_system->getMillis() + kDisplayDelay;
584 }
585
SubtitleSettingsDialog(ScummEngine * scumm,int value)586 SubtitleSettingsDialog::SubtitleSettingsDialog(ScummEngine *scumm, int value)
587 : InfoDialog(scumm, U32String()), _value(value), _timer(0) {
588
589 }
590
handleTickle()591 void SubtitleSettingsDialog::handleTickle() {
592 InfoDialog::handleTickle();
593 if (g_system->getMillis() > _timer)
594 close();
595 }
596
handleKeyDown(Common::KeyState state)597 void SubtitleSettingsDialog::handleKeyDown(Common::KeyState state) {
598 if (state.keycode == Common::KEYCODE_t && state.hasFlags(Common::KBD_CTRL)) {
599 cycleValue();
600
601 reflowLayout();
602 g_gui.scheduleTopDialogRedraw();
603 } else {
604 close();
605 }
606 }
607
open()608 void SubtitleSettingsDialog::open() {
609 cycleValue();
610 InfoDialog::open();
611 setResult(_value);
612 }
613
cycleValue()614 void SubtitleSettingsDialog::cycleValue() {
615 static const char *const subtitleDesc[] = {
616 _s("Speech Only"),
617 _s("Speech and Subtitles"),
618 _s("Subtitles Only")
619 };
620
621 _value += 1;
622 if (_value > 2)
623 _value = 0;
624
625 if (_value == 1 && g_system->getOverlayWidth() <= 320)
626 setInfoText(_c("Speech & Subs", "lowres"));
627 else
628 setInfoText(_(subtitleDesc[_value]));
629
630 _timer = g_system->getMillis() + 1500;
631 }
632
Indy3IQPointsDialog(ScummEngine * scumm,char * text)633 Indy3IQPointsDialog::Indy3IQPointsDialog(ScummEngine *scumm, char* text)
634 : InfoDialog(scumm, Common::U32String(text)) {
635 }
636
handleKeyDown(Common::KeyState state)637 void Indy3IQPointsDialog::handleKeyDown(Common::KeyState state) {
638 if (state.ascii == 'i')
639 close();
640 else
641 ScummDialog::handleKeyDown(state);
642 }
643
DebugInputDialog(ScummEngine * scumm,char * text)644 DebugInputDialog::DebugInputDialog(ScummEngine *scumm, char* text)
645 : InfoDialog(scumm, U32String(text)) {
646 mainText = text;
647 done = 0;
648 }
649
handleKeyDown(Common::KeyState state)650 void DebugInputDialog::handleKeyDown(Common::KeyState state) {
651 if (state.keycode == Common::KEYCODE_BACKSPACE && buffer.size() > 0) {
652 buffer.deleteLastChar();
653 Common::String total = mainText + ' ' + buffer;
654 setInfoText(total);
655 g_gui.scheduleTopDialogRedraw();
656 reflowLayout();
657 } else if (state.keycode == Common::KEYCODE_RETURN) {
658 done = 1;
659 close();
660 return;
661 } else if ((state.ascii >= '0' && state.ascii <= '9') || (state.ascii >= 'A' && state.ascii <= 'Z') || (state.ascii >= 'a' && state.ascii <= 'z') || state.ascii == '.' || state.ascii == ' ') {
662 buffer += state.ascii;
663 Common::String total = mainText + ' ' + buffer;
664 g_gui.scheduleTopDialogRedraw();
665 reflowLayout();
666 setInfoText(total);
667 }
668 }
669
LoomTownsDifficultyDialog()670 LoomTownsDifficultyDialog::LoomTownsDifficultyDialog()
671 : Dialog("LoomTownsDifficultyDialog"), _difficulty(-1) {
672 GUI::StaticTextWidget *text1 = new GUI::StaticTextWidget(this, "LoomTownsDifficultyDialog.Description1", _("Select a Proficiency Level."));
673 text1->setAlign(Graphics::kTextAlignCenter);
674 GUI::StaticTextWidget *text2 = new GUI::StaticTextWidget(this, "LoomTownsDifficultyDialog.Description2", _("Refer to your Loom(TM) manual for help."));
675 text2->setAlign(Graphics::kTextAlignCenter);
676
677 new GUI::ButtonWidget(this, "LoomTownsDifficultyDialog.Standard", _("Standard"), Common::U32String(), kStandardCmd);
678 new GUI::ButtonWidget(this, "LoomTownsDifficultyDialog.Practice", _("Practice"), Common::U32String(), kPracticeCmd);
679 new GUI::ButtonWidget(this, "LoomTownsDifficultyDialog.Expert", _("Expert"), Common::U32String(), kExpertCmd);
680 }
681
handleCommand(GUI::CommandSender * sender,uint32 cmd,uint32 data)682 void LoomTownsDifficultyDialog::handleCommand(GUI::CommandSender *sender, uint32 cmd, uint32 data) {
683 switch (cmd) {
684 case kStandardCmd:
685 _difficulty = 1;
686 close();
687 break;
688
689 case kPracticeCmd:
690 _difficulty = 0;
691 close();
692 break;
693
694 case kExpertCmd:
695 _difficulty = 2;
696 close();
697 break;
698
699 default:
700 GUI::Dialog::handleCommand(sender, cmd, data);
701 }
702 }
703
704 } // End of namespace Scumm
705