diff options
author | Paul Gilbert | 2011-07-16 21:12:19 +1000 |
---|---|---|
committer | Paul Gilbert | 2011-07-16 21:12:19 +1000 |
commit | 00061bc5dd6492fcb3be9781b134f1928f69205b (patch) | |
tree | a653973344d39be8659ad4940b3687be04260104 | |
parent | ce070cdd3c664bc5fca80770a40e669fd07a83a0 (diff) | |
download | scummvm-rg350-00061bc5dd6492fcb3be9781b134f1928f69205b.tar.gz scummvm-rg350-00061bc5dd6492fcb3be9781b134f1928f69205b.tar.bz2 scummvm-rg350-00061bc5dd6492fcb3be9781b134f1928f69205b.zip |
CGE: Added support for GMM save/load and launcher loading
-rw-r--r-- | engines/cge/cge.cpp | 20 | ||||
-rw-r--r-- | engines/cge/cge.h | 13 | ||||
-rw-r--r-- | engines/cge/cge_main.cpp | 51 | ||||
-rw-r--r-- | engines/cge/detection.cpp | 90 |
4 files changed, 105 insertions, 69 deletions
diff --git a/engines/cge/cge.cpp b/engines/cge/cge.cpp index 6924f0b14e..bb5b786330 100644 --- a/engines/cge/cge.cpp +++ b/engines/cge/cge.cpp @@ -126,6 +126,7 @@ void CGEEngine::setup() { for (int i = 0; i < 4; i++) _flag[i] = false; + _startGameSlot = ConfMan.hasKey("save_slot") ? ConfMan.getInt("save_slot") : -1; } CGEEngine::~CGEEngine() { @@ -173,12 +174,25 @@ Common::Error CGEEngine::run() { // Setup necessary game objects setup(); - // Additional setup. - debug("CGEEngine::init"); - + // Run the game cge_main(); return Common::kNoError; } +bool CGEEngine::hasFeature(EngineFeature f) const { + return + (f == kSupportsRTL) || + (f == kSupportsLoadingDuringRuntime) || + (f == kSupportsSavingDuringRuntime); +} + +bool CGEEngine::canLoadGameStateCurrently() { + return (_startupMode == 0) && _mouse->_active; +} + +bool CGEEngine::canSaveGameStateCurrently() { + return (_startupMode == 0) && _mouse->_active; +} + } // End of namespace CGE diff --git a/engines/cge/cge.h b/engines/cge/cge.h index 2d67b2218a..851a1166ab 100644 --- a/engines/cge/cge.h +++ b/engines/cge/cge.h @@ -69,19 +69,26 @@ struct SavegameHeader { int totalFrames; }; +extern const char *SAVEGAME_STR; +#define SAVEGAME_STR_SIZE 11 + class CGEEngine : public Engine { private: uint32 _lastFrame; void tick(); void syncHeader(Common::Serializer &s); - bool readSavegameHeader(Common::InSaveFile *in, SavegameHeader &header); - void writeSavegameHeader(Common::OutSaveFile *out, SavegameHeader &header); + static void writeSavegameHeader(Common::OutSaveFile *out, SavegameHeader &header); void syncGame(Common::SeekableReadStream *readStream, Common::WriteStream *writeStream, bool tiny = false); bool savegameExists(int slotNumber); Common::String generateSaveName(int slot); public: CGEEngine(OSystem *syst, const ADGameDescription *gameDescription); ~CGEEngine(); + virtual bool hasFeature(EngineFeature f) const; + virtual bool canLoadGameStateCurrently(); + virtual bool canSaveGameStateCurrently(); + virtual Common::Error loadGameState(int slot); + virtual Common::Error saveGameState(int slot, const Common::String &desc); const ADGameDescription *_gameDescription; bool _isDemo; @@ -107,6 +114,7 @@ public: byte * _mini; BMP_PTR * _miniShp; BMP_PTR * _miniShpList; + int _startGameSlot; virtual Common::Error run(); GUI::Debugger *getDebugger() { @@ -149,6 +157,7 @@ public: void setDMA(); void mainLoop(); void saveGame(int slotNumber, const Common::String &desc); + static bool readSavegameHeader(Common::InSaveFile *in, SavegameHeader &header); void switchMusic(); void selectPocket(int n); void expandSprite(Sprite *spr); diff --git a/engines/cge/cge_main.cpp b/engines/cge/cge_main.cpp index 3ea82e3099..f3b2784ca6 100644 --- a/engines/cge/cge_main.cpp +++ b/engines/cge/cge_main.cpp @@ -224,6 +224,24 @@ Common::String CGEEngine::generateSaveName(int slot) { return Common::String::format("%s.%03d", _targetName.c_str(), slot); } +Common::Error CGEEngine::loadGameState(int slot) { + // Clear current game activity + caveDown(); + + // Load the game + loadGame(slot, NULL, true); + caveUp(); + loadGame(slot, NULL); + + return Common::kNoError; +} + +Common::Error CGEEngine::saveGameState(int slot, const Common::String &desc) { + saveGame(slot, desc); + return Common::kNoError; +} + + void CGEEngine::saveSound() { warning("STUB: CGEEngine::saveSound"); /* Convert to saving any such needed data in ScummVM configuration file @@ -268,7 +286,7 @@ void CGEEngine::writeSavegameHeader(Common::OutSaveFile *out, SavegameHeader &he // Create a thumbnail and save it Graphics::Surface *thumb = new Graphics::Surface(); - Graphics::Surface *s = _vga->_page[1]; + Graphics::Surface *s = _vga->_page[0]; ::createThumbnail(thumb, (const byte *)s->pixels, SCR_WID, SCR_HIG, thumbPalette); Graphics::saveThumbnail(*out, *thumb); delete thumb; @@ -1451,8 +1469,8 @@ void CGEEngine::loadUser() { loadGame(0, NULL); } else { if (Startup::_mode == 1) { - // Load initial game state savegame - loadGame(-1, NULL); + // Load either initial game state savegame or launcher specified savegame + loadGame(_startGameSlot, NULL); } else { error("Creating setup savegames not supported"); } @@ -1681,7 +1699,7 @@ bool CGEEngine::showTitle(const char *name) { //Mouse.On(); // For ScummVM, skip prompting for name if a savegame in slot 0 already exists - if (savegameExists(0)) { + if ((_startGameSlot == -1) && savegameExists(0)) { strcpy(_usrFnam, "User"); usr_ok = true; } else { @@ -1755,18 +1773,29 @@ void CGEEngine::cge_main() { if (_music && Startup::_soundOk) loadMidi(0); - if (Startup::_mode < 2) - movie(LGO_EXT); - if (showTitle("WELCOME")) { - if ((!_isDemo) && (Startup::_mode == 1)) - movie("X02"); // intro + if (_startGameSlot != -1) { + // Starting up a savegame from the launcher + Startup::_mode++; runGame(); + _startupMode = 2; if (_flag[3]) // Flag FINIS movie("X03"); - } else - _vga->sunset(); + } else { + if (Startup::_mode < 2) + movie(LGO_EXT); + + if (showTitle("WELCOME")) { + if ((!_isDemo) && (Startup::_mode == 1)) + movie("X02"); // intro + runGame(); + _startupMode = 2; + if (_flag[3]) // Flag FINIS + movie("X03"); + } else + _vga->sunset(); + } } } // End of namespace CGE diff --git a/engines/cge/detection.cpp b/engines/cge/detection.cpp index 31bf629fcf..24fd3d2043 100644 --- a/engines/cge/detection.cpp +++ b/engines/cge/detection.cpp @@ -103,6 +103,8 @@ public: return "Soltys (c) 1994-1996 L.K. Avalon"; } + + virtual bool hasFeature(MetaEngineFeature f) const; virtual bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const; virtual int getMaximumSaveSlot() const; @@ -146,25 +148,26 @@ SaveStateList CGEMetaEngine::listSaves(const char *target) const { slotNum = atoi(filename->c_str() + filename->size() - 3); if (slotNum >= 0 && slotNum <= 99) { + Common::InSaveFile *file = saveFileMan->openForLoading(*filename); if (file) { - int32 version = file->readSint32BE(); - if (version != CGE_SAVEGAME_VERSION) { - delete file; - continue; - } - - // read name - uint16 nameSize = file->readUint16BE(); - if (nameSize >= 255) { - delete file; - continue; + CGE::SavegameHeader header; + + // Check to see if it's a ScummVM savegame or not + char buffer[SAVEGAME_STR_SIZE + 1]; + file->read(buffer, SAVEGAME_STR_SIZE + 1); + + if (!strncmp(buffer, CGE::SAVEGAME_STR, SAVEGAME_STR_SIZE + 1)) { + // Valid savegame + if (CGE::CGEEngine::readSavegameHeader(file, header)) { + saveList.push_back(SaveStateDescriptor(slotNum, header.saveName)); + delete header.thumbnail; + } + } else { + // Must be an original format savegame + saveList.push_back(SaveStateDescriptor(slotNum, "Unknown")); } - char name[256]; - file->read(name, nameSize); - name[nameSize] = 0; - saveList.push_back(SaveStateDescriptor(slotNum, name)); delete file; } } @@ -175,53 +178,34 @@ SaveStateList CGEMetaEngine::listSaves(const char *target) const { SaveStateDescriptor CGEMetaEngine::querySaveMetaInfos(const char *target, int slot) const { Common::String fileName = Common::String::format("%s.%03d", target, slot); - Common::InSaveFile *file = g_system->getSavefileManager()->openForLoading(fileName); - - if (file) { - - int32 version = file->readSint32BE(); - if (version != CGE_SAVEGAME_VERSION) { - delete file; - return SaveStateDescriptor(); - } + Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(fileName); + assert(f); - uint32 saveNameLength = file->readUint16BE(); - char saveName[256]; - file->read(saveName, saveNameLength); - saveName[saveNameLength] = 0; + CGE::SavegameHeader header; - SaveStateDescriptor desc(slot, saveName); + // Check to see if it's a ScummVM savegame or not + char buffer[SAVEGAME_STR_SIZE + 1]; + f->read(buffer, SAVEGAME_STR_SIZE + 1); - Graphics::Surface *thumbnail = new Graphics::Surface(); - assert(thumbnail); - if (!Graphics::loadThumbnail(*file, *thumbnail)) { - delete thumbnail; - thumbnail = 0; - } - desc.setThumbnail(thumbnail); + bool hasHeader = !strncmp(buffer, CGE::SAVEGAME_STR, SAVEGAME_STR_SIZE + 1) && + CGE::CGEEngine::readSavegameHeader(f, header); + delete f; + if (!hasHeader) { + // Original savegame perhaps? + SaveStateDescriptor desc(slot, "Unknown"); + return desc; + } else { + // Create the return descriptor + SaveStateDescriptor desc(slot, header.saveName); desc.setDeletableFlag(true); desc.setWriteProtectedFlag(false); + desc.setThumbnail(header.thumbnail); + desc.setSaveDate(header.saveYear, header.saveMonth, header.saveDay); + desc.setSaveTime(header.saveHour, header.saveMinutes); - uint32 saveDate = file->readUint32BE(); - uint16 saveTime = file->readUint16BE(); - - int day = (saveDate >> 24) & 0xFF; - int month = (saveDate >> 16) & 0xFF; - int year = saveDate & 0xFFFF; - - desc.setSaveDate(year, month, day); - - int hour = (saveTime >> 8) & 0xFF; - int minutes = saveTime & 0xFF; - - desc.setSaveTime(hour, minutes); - - delete file; return desc; } - - return SaveStateDescriptor(); } bool CGEMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const { |