diff options
-rw-r--r-- | kyra/gui.cpp | 236 | ||||
-rw-r--r-- | kyra/kyra.cpp | 22 | ||||
-rw-r--r-- | kyra/kyra.h | 26 | ||||
-rw-r--r-- | kyra/screen.cpp | 2 | ||||
-rw-r--r-- | kyra/staticres.cpp | 44 |
5 files changed, 274 insertions, 56 deletions
diff --git a/kyra/gui.cpp b/kyra/gui.cpp index 2f48556a83..10d66a42f2 100644 --- a/kyra/gui.cpp +++ b/kyra/gui.cpp @@ -389,7 +389,7 @@ int KyraEngine::buttonMenuCallback(Button *caller) { _displayMenu = true; // XXX setLabels - if (_currentCharacter->sceneId == 210 || caller == 0) { + if (_currentCharacter->sceneId == 210) { snd_playSoundEffect(0x36); return 0; } @@ -407,11 +407,17 @@ int KyraEngine::buttonMenuCallback(Button *caller) { calcCoords(_menu[0]); calcCoords(_menu[1]); calcCoords(_menu[2]); - - initMenu(_menu[0]); - processAllMenuButtons(); + calcCoords(_menu[3]); _menuRestoreScreen = true; + + if (_menuDirectlyToLoad) + gui_loadGameMenu(0); + else { + initMenu(_menu[0]); + processAllMenuButtons(); + } + while (_displayMenu) { gui_processHighlights(_menu[0]); processButtonList(_menuButtonList); @@ -535,6 +541,7 @@ void KyraEngine::calcCoords(Menu &menu) { void KyraEngine::gui_getInput() { OSystem::Event event; + uint32 now = _system->getMillis(); _mousePressFlag = false; while (_system->pollEvent(event)) { @@ -550,11 +557,24 @@ void KyraEngine::gui_getInput() { _mouseY = event.mouse.y; _system->updateScreen(); break; + case OSystem::EVENT_KEYDOWN: + _keyboardEvent.pending = true; + _keyboardEvent.repeat = now + 400; + _keyboardEvent.ascii = event.kbd.ascii; + break; + case OSystem::EVENT_KEYUP: + _keyboardEvent.repeat = 0; + break; default: break; } } - _system->delayMillis(10); + + if (!_keyboardEvent.pending && _keyboardEvent.repeat && now >= _keyboardEvent.repeat) { + _keyboardEvent.pending = true; + _keyboardEvent.repeat = now + 100; + } + _system->delayMillis(3); } int KyraEngine::gui_resumeGame(Button *button) { @@ -565,21 +585,43 @@ int KyraEngine::gui_resumeGame(Button *button) { return 0; } -const char *KyraEngine::getSavegameName(int num) { +const char *KyraEngine::getSavegameFilename(int num) { static char saveLoadSlot[12]; sprintf(saveLoadSlot, "%s.%.3d", _targetName.c_str(), num); return saveLoadSlot; } +int KyraEngine::getNextSavegameSlot() { + Common::InSaveFile *in; + + for (int i = 1; i < 1000; i++) { + if ((in = _saveFileMan->openForLoading(getSavegameFilename(i)))) { + delete in; + } else { + return i; + } + } + warning("Didn't save: Ran out of savegame filenames!"); + return 0; +} + void KyraEngine::setupSavegames(Menu &menu, int num) { Common::InSaveFile *in; static char savenames[5][31]; - + uint8 startSlot; assert(num <= 5); - for (int i = 0; i < num; i++) { - if ((in = _saveFileMan->openForLoading(getSavegameName(i + _savegameOffset)))) { + if (_savegameOffset == 0) { + menu.item[0].itemString = _specialSavegameString; + menu.item[0].enabled = 1; + menu.item[0].field_1b = 0; + startSlot = 1; + } else + startSlot = 0; + + for (int i = startSlot; i < num; i++) { + if ((in = _saveFileMan->openForLoading(getSavegameFilename(i + _savegameOffset)))) { in->skip(8); in->read(savenames[i], 31); menu.item[i].itemString = savenames[i]; @@ -594,21 +636,73 @@ void KyraEngine::setupSavegames(Menu &menu, int num) { } } +int KyraEngine::gui_saveGameMenu(Button *button) { + debug(9, "KyraEngine::gui_saveGameMenu()"); + processMenuButton(button); + _menu[2].item[5].enabled = true; + + _screen->loadPageFromDisk("SEENPAGE.TMP", 0); + _screen->savePageToDisk("SEENPAGE.TMP", 0); + + _menu[2].menuName = "Select a position to save to:"; + _specialSavegameString = "[ EMPTY SLOT ]"; + for (int i = 0; i < 5; i++) + _menu[2].item[i].callback = &KyraEngine::gui_saveGame; + + _savegameOffset = 0; + setupSavegames(_menu[2], 5); + + initMenu(_menu[2]); + processAllMenuButtons(); + + _displaySubMenu = true; + _cancelSubMenu = false; + + while (_displaySubMenu) { + gui_getInput(); + gui_processHighlights(_menu[2]); + processButtonList(_menuButtonList); + } + + _screen->loadPageFromDisk("SEENPAGE.TMP", 0); + _screen->savePageToDisk("SEENPAGE.TMP", 0); + + if (_cancelSubMenu) { + initMenu(_menu[0]); + processAllMenuButtons(); + } else { + _displayMenu = false; + } + return 0; +} + int KyraEngine::gui_loadGameMenu(Button *button) { debug(9, "KyraEngine::gui_loadGameMenu()"); - processMenuButton(button); + if (_menuDirectlyToLoad) + _menu[2].item[5].enabled = false; + else { + processMenuButton(button); + _menu[2].item[5].enabled = true; + } + _screen->loadPageFromDisk("SEENPAGE.TMP", 0); _screen->savePageToDisk("SEENPAGE.TMP", 0); + _specialSavegameString = "[ START A NEW GAME ]"; + _menu[2].menuName = "Which game would you like to reload?"; + for (int i = 0; i < 5; i++) + _menu[2].item[i].callback = &KyraEngine::gui_loadGame; + _savegameOffset = 0; setupSavegames(_menu[2], 5); + initMenu(_menu[2]); processAllMenuButtons(); - _displayLoadGameMenu = true; - _cancelLoadGameMenu = false; + _displaySubMenu = true; + _cancelSubMenu = false; - while (_displayLoadGameMenu) { + while (_displaySubMenu) { gui_getInput(); gui_processHighlights(_menu[2]); processButtonList(_menuButtonList); @@ -617,31 +711,119 @@ int KyraEngine::gui_loadGameMenu(Button *button) { _screen->loadPageFromDisk("SEENPAGE.TMP", 0); _screen->savePageToDisk("SEENPAGE.TMP", 0); - if (_cancelLoadGameMenu) { + if (_cancelSubMenu) { initMenu(_menu[0]); processAllMenuButtons(); } else { - loadGame(getSavegameName(_gameToLoad)); + loadGame(getSavegameFilename(_gameToLoad)); _displayMenu = false; _menuRestoreScreen = false; } return 0; } +void KyraEngine::gui_redrawTextfield() { + _screen->fillRect(38, 91, 287, 102, 250); + _text->printText(_savegameName, 38, 91, 30, 0, 0); + _screen->updateScreen(); +} + +void KyraEngine::gui_updateSavegameString() { + int length; + + if (_keyboardEvent.pending && _keyboardEvent.ascii) { + length = strlen(_savegameName); + + if (_keyboardEvent.ascii > 31 && _keyboardEvent.ascii < 127) { + if (length < 31) { + _savegameName[length] = _keyboardEvent.ascii; + _savegameName[length+1] = 0; + gui_redrawTextfield(); + } + } else if (_keyboardEvent.ascii == 8 ||_keyboardEvent.ascii == 127) { + if (length > 0) { + _savegameName[length-1] = 0; + gui_redrawTextfield(); + } + } else if (_keyboardEvent.ascii == 13) { + _displaySubMenu = false; + } + } + + _keyboardEvent.pending = false; +} + +int KyraEngine::gui_saveGame(Button *button) { + debug(9, "KyraEngine::gui_saveGame()"); + processMenuButton(button); + _gameToLoad = button->specialValue; + + _screen->loadPageFromDisk("SEENPAGE.TMP", 0); + _screen->savePageToDisk("SEENPAGE.TMP", 0); + + initMenu(_menu[3]); + processAllMenuButtons(); + + _displaySubMenu = true; + _cancelSubMenu = false; + + if (_savegameOffset == 0 && _gameToLoad == 0) { + _savegameName[0] = 0; + } else { + for (int i = 0; i < 5; i++) { + if (_menu[2].item[i].field_1b == _gameToLoad) { + strncpy(_savegameName, _menu[2].item[i].itemString, 31); + break; + } + } + } + gui_redrawTextfield(); + + _keyboardEvent.pending = 0; + while (_displaySubMenu) { + gui_getInput(); + gui_updateSavegameString(); + gui_processHighlights(_menu[3]); + processButtonList(_menuButtonList); + } + + if (_cancelSubMenu) { + _displaySubMenu = true; + _cancelSubMenu = false; + initMenu(_menu[2]); + processAllMenuButtons(); + } else { + if (_savegameOffset == 0 && _gameToLoad == 0) + _gameToLoad = getNextSavegameSlot(); + if (_gameToLoad > 0) + saveGame(getSavegameFilename(_gameToLoad), _savegameName); + } + + return 0; +} + +int KyraEngine::gui_savegameConfirm(Button *button) { + debug(9, "KyraEngine::gui_savegameConfirm()"); + processMenuButton(button); + _displaySubMenu = false; + + return 0; +} + int KyraEngine::gui_loadGame(Button *button) { debug(9, "KyraEngine::gui_loadGame()"); processMenuButton(button); - _displayLoadGameMenu = false; + _displaySubMenu = false; _gameToLoad = button->specialValue; return 0; } -int KyraEngine::gui_cancelLoadGameMenu(Button *button) { +int KyraEngine::gui_cancelSubMenu(Button *button) { debug(9, "KyraEngine::gui_cancelLoadGameMenu()"); processMenuButton(button); - _displayLoadGameMenu = false; - _cancelLoadGameMenu = true; + _displaySubMenu = false; + _cancelSubMenu = true; return 0; } @@ -669,10 +851,10 @@ bool KyraEngine::gui_quitConfirm(const char *str) { _menu[1].menuName = str; initMenu(_menu[1]); - _displayQuitConfirmDialog = true; - _quitConfirmed = false; + _displaySubMenu = true; + _cancelSubMenu = true; - while (_displayQuitConfirmDialog) { + while (_displaySubMenu) { gui_getInput(); gui_processHighlights(_menu[1]); processButtonList(_menuButtonList); @@ -681,14 +863,14 @@ bool KyraEngine::gui_quitConfirm(const char *str) { _screen->loadPageFromDisk("SEENPAGE.TMP", 0); _screen->savePageToDisk("SEENPAGE.TMP", 0); - return _quitConfirmed; + return !_cancelSubMenu; } int KyraEngine::gui_quitConfirmYes(Button *button) { debug(9, "KyraEngine::gui_quitConfirmYes()"); processMenuButton(button); - _displayQuitConfirmDialog = false; - _quitConfirmed = true; + _displaySubMenu = false; + _cancelSubMenu = false; return 0; } @@ -696,8 +878,8 @@ int KyraEngine::gui_quitConfirmYes(Button *button) { int KyraEngine::gui_quitConfirmNo(Button *button) { debug(9, "KyraEngine::gui_quitConfirmNo()"); processMenuButton(button); - _displayQuitConfirmDialog = false; - _quitConfirmed = false; + _displaySubMenu = false; + _cancelSubMenu = true; return 0; } diff --git a/kyra/kyra.cpp b/kyra/kyra.cpp index 554ad9934a..2ed9509d69 100644 --- a/kyra/kyra.cpp +++ b/kyra/kyra.cpp @@ -410,6 +410,7 @@ int KyraEngine::init(GameDetector &detector) { _mousePressFlag = false; _targetName = detector._targetName; + _menuDirectlyToLoad = false; _lastMusicCommand = 0; @@ -491,6 +492,8 @@ int KyraEngine::go() { setGameFlag(0xFD); setGameFlag(0xEF); seq_intro(); + if (_skipIntroFlag &&_abortIntroFlag) + resetGameFlag(0xEF); startup(); resetGameFlag(0xEF); mainLoop(); @@ -576,6 +579,14 @@ void KyraEngine::startup() { snd_playTheme(1); snd_setSoundEffectFile(1); enterNewScene(_currentCharacter->sceneId, _currentCharacter->facing, 0, 0, 1); + + if (_abortIntroFlag && _skipIntroFlag) { + _menuDirectlyToLoad = true; + _screen->setMouseCursor(1, 1, _shapes[4]); + buttonMenuCallback(0); + _menuDirectlyToLoad = false; + } else + saveGame(getSavegameFilename(0), "New game"); } void KyraEngine::delay(uint32 amount, bool update, bool isMainLoop) { @@ -589,7 +600,7 @@ void KyraEngine::delay(uint32 amount, bool update, bool isMainLoop) { while (_system->pollEvent(event)) { switch (event.type) { case OSystem::EVENT_KEYDOWN: - if (event.kbd.keycode >= '0' && event.kbd.keycode <= '9' && + if (event.kbd.keycode >= '1' && event.kbd.keycode <= '9' && (event.kbd.flags == OSystem::KBD_CTRL || event.kbd.flags == OSystem::KBD_ALT) && isMainLoop) { sprintf(saveLoadSlot, "%s.00%d", _targetName.c_str(), event.kbd.keycode - '0'); if (event.kbd.flags == OSystem::KBD_CTRL) @@ -887,7 +898,14 @@ void KyraEngine::seq_intro() { &KyraEngine::seq_introKallakWriting, &KyraEngine::seq_introKallakMalcolm }; - _skipIntroFlag = true; // only true if user already saved the game once + + Common::InSaveFile *in; + if ((in = _saveFileMan->openForLoading(getSavegameFilename(0)))) { + delete in; + _skipIntroFlag = true; + } else + _skipIntroFlag = false; + _seq->setCopyViewOffs(true); _screen->setFont(Screen::FID_8_FNT); snd_playTheme(MUSIC_INTRO, 2); diff --git a/kyra/kyra.h b/kyra/kyra.h index 462049ceb8..cd1867351a 100644 --- a/kyra/kyra.h +++ b/kyra/kyra.h @@ -214,6 +214,12 @@ struct Menu { MenuItem item[6]; }; +struct KeyboardEvent { + bool pending; + uint32 repeat; + uint8 ascii; +}; + class KyraEngine : public Engine { friend class MusicPlayer; friend class Debugger; @@ -657,16 +663,20 @@ protected: void processMenuButton(Button *button); void processAllMenuButtons(); - const char *getSavegameName(int num); + const char *getSavegameFilename(int num); void setupSavegames(Menu &menu, int num); + int getNextSavegameSlot(); int gui_resumeGame(Button *button); int gui_loadGameMenu(Button *button); + int gui_saveGameMenu(Button *button); int gui_quitPlaying(Button *button); int gui_quitConfirmYes(Button *button); int gui_quitConfirmNo(Button *button); int gui_loadGame(Button *button); - int gui_cancelLoadGameMenu(Button *button); + int gui_saveGame(Button *button); + int gui_savegameConfirm(Button *button); + int gui_cancelSubMenu(Button *button); int gui_scrollUp(Button *button); int gui_scrollDown(Button *button); @@ -675,12 +685,15 @@ protected: void gui_redrawText(Menu menu); void gui_redrawHighlight(Menu menu); void gui_processHighlights(Menu &menu); + void gui_updateSavegameString(); + void gui_redrawTextfield(); uint8 _game; bool _fastMode; bool _quitFlag; bool _skipIntroFlag; bool _abortIntroFlag; + bool _menuDirectlyToLoad; bool _abortWalkFlag; bool _abortWalkFlag2; bool _mousePressFlag; @@ -813,12 +826,13 @@ protected: Button *_menuButtonList; bool _displayMenu; bool _menuRestoreScreen; - bool _displayQuitConfirmDialog; - bool _displayLoadGameMenu; - bool _cancelLoadGameMenu; - bool _quitConfirmed; + bool _displaySubMenu; + bool _cancelSubMenu; int _savegameOffset; int _gameToLoad; + char _savegameName[31]; + const char *_specialSavegameString; + KeyboardEvent _keyboardEvent; uint8 *_seq_Forest; uint8 *_seq_KallakWriting; diff --git a/kyra/screen.cpp b/kyra/screen.cpp index 30b8ac6987..40a3936ae6 100644 --- a/kyra/screen.cpp +++ b/kyra/screen.cpp @@ -451,7 +451,7 @@ void Screen::drawBox(int x1, int y1, int x2, int y2, int color) { void Screen::drawShadedBox(int x1, int y1, int x2, int y2, int color1, int color2) { debug(9, "Screen::drawShadedBox(%i, %i, %i, %i, %i, %i)", x1, y1, x2, y2, color1, color2); - + assert(x1 > 0 && y1 > 0); hideMouse(); fillRect(x1, y1, x2, y1 + 1, color1); diff --git a/kyra/staticres.cpp b/kyra/staticres.cpp index 6a44a0b83a..ebf9edb4c3 100644 --- a/kyra/staticres.cpp +++ b/kyra/staticres.cpp @@ -768,14 +768,13 @@ Menu KyraEngine::_menu[] = { {1, 0, 0, "Load a Game", -1, -1, 30, 148, 15, 252, 253, 24, 0, 248, 249, 250, &KyraEngine::gui_loadGameMenu, -1, 0, 0, 0, 0, 0}, {1, 0, 0, "Save this Game", -1, -1, 47, 148, 15, 252, 253, 24, 0, - 248, 249, 250, /*&menu_saveGame*/ 0, -1, 0, 0, 0, 0, 0}, + 248, 249, 250, &KyraEngine::gui_saveGameMenu, -1, 0, 0, 0, 0, 0}, {1, 0, 0, "Game Controls", -1, -1, 64, 148, 15, 252, 253, 24, 0, 248, 249, 250, /*&menu_gameControls*/ 0, -1, 0, 0, 0, 0, 0}, {1, 0, 0, "Quit playing", -1, -1, 81, 148, 15, 252, 253, 24, 0, 248, 249, 250, &KyraEngine::gui_quitPlaying, -1, 0, 0, 0, 0, 0}, {1, 0, 0, "Resume game", 86, 0, 110, 92, 15, 252, 253, -1, 255, - 248, 249, 250, &KyraEngine::gui_resumeGame, -1, 0, 0, 0, 0, 0}, - {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} + 248, 249, 250, &KyraEngine::gui_resumeGame, -1, 0, 0, 0, 0, 0} } }, { -1, -1, 288, 56, 248, 249, 250, 0, 254,-1, 8, 0, 2, -1, -1, -1, -1, @@ -783,28 +782,33 @@ Menu KyraEngine::_menu[] = { {1, 0, 0, "Yes", 24, 0, 30, 72, 15, 252, 253, -1, 255, 248, 249, 250, &KyraEngine::gui_quitConfirmYes, -1, 0, 0, 0, 0, 0}, {1, 0, 0, "No", 192, 0, 30, 72, 15, 252, 253, -1, 255, - 248, 249, 250, &KyraEngine::gui_quitConfirmNo, -1, 0, 0, 0, 0, 0}, - {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, - {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, - {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, - {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} + 248, 249, 250, &KyraEngine::gui_quitConfirmNo, -1, 0, 0, 0, 0, 0} } }, - { -1, -1, 288, 160, 248, 249, 250, "Which game would you like to reload?", 251, -1, 8, 0, 6, 132, 22, 132, 124, + { -1, -1, 288, 160, 248, 249, 250, 0, 251, -1, 8, 0, 6, 132, 22, 132, 124, { {1, 0, 0, 0, -1, 255, 39, 256, 15, 252, 253, 5, 0, - 248, 249, 250, &KyraEngine::gui_loadGame, -1, 0, 0, 0, 0, 0}, - {1, 0, 0, "", -1, 255, 56, 256, 15, 252, 253, 5, 0, - 248, 249, 250, &KyraEngine::gui_loadGame, -1, 0, 0, 0, 0, 0}, - {1, 0, 0, "", -1, 255, 73, 256, 15, 252, 253, 5, 0, - 248, 249, 250, &KyraEngine::gui_loadGame, -1, 0, 0, 0, 0, 0}, - {1, 0, 0, "", -1, 255, 90, 256, 15, 252, 253, 5, 0, - 248, 249, 250, &KyraEngine::gui_loadGame, -1, 0, 0, 0, 0, 0}, - {1, 0, 0, "", -1, 255, 107, 256, 15, 252, 253, 5, 0, - 248, 249, 250, &KyraEngine::gui_loadGame, -1, 0, 0, 0, 0, 0}, - //{0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} + 248, 249, 250, 0, -1, 0, 0, 0, 0, 0}, + {1, 0, 0, 0, -1, 255, 56, 256, 15, 252, 253, 5, 0, + 248, 249, 250, 0, -1, 0, 0, 0, 0, 0}, + {1, 0, 0, 0, -1, 255, 73, 256, 15, 252, 253, 5, 0, + 248, 249, 250, 0, -1, 0, 0, 0, 0, 0}, + {1, 0, 0, 0, -1, 255, 90, 256, 15, 252, 253, 5, 0, + 248, 249, 250, 0, -1, 0, 0, 0, 0, 0}, + {1, 0, 0, 0, -1, 255, 107, 256, 15, 252, 253, 5, 0, + 248, 249, 250, 0, -1, 0, 0, 0, 0, 0}, {1, 0, 0, "Cancel", 184, 0, 134, 88, 15, 252, 253, -1, 255, - 248, 249, 250, &KyraEngine::gui_cancelLoadGameMenu, -1, 0, 0, 0, 0, 0}, + 248, 249, 250, &KyraEngine::gui_cancelSubMenu, -1, 0, 0, 0, 0, 0}, + } + }, + { -1, -1, 288, 67, 248, 249, 250, "Enter a description of your saved game:", 251, -1, 8, 0, 3, -1, -1, -1, -1, + { + {1, 0, 0, "Save", 24, 0, 44, 72, 15, 252, 253, -1, 255, + 248, 249, 250, &KyraEngine::gui_savegameConfirm, -1, 0, 0, 0, 0, 0}, + // {1, 0, 0, "Cancel", 110, 0, 44, 72, 15, 252, 253, -1, 255, + // 248, 249, 250, /*&menu_cancelconfirmsave*/ 0, -1, 0, 0, 0, 0, 0}, + {1, 0, 0, "Cancel", 192, 0, 44, 72, 15, 252, 253, -1, 255, + 248, 249, 250, &KyraEngine::gui_cancelSubMenu, -1, 0, 0, 0, 0, 0} } } }; |