From 37c53c420f9a3ccf2bc21de8caea9e0b65edacec Mon Sep 17 00:00:00 2001 From: Jaromir Wysoglad Date: Tue, 2 Jul 2019 11:39:35 +0200 Subject: SUPERNOVA: Load info files from .dat file --- engines/supernova/game-manager.cpp | 10 +---- engines/supernova/supernova.cpp | 85 +++++++++++++++++++++++++++++++++++--- engines/supernova/supernova.h | 3 +- 3 files changed, 83 insertions(+), 15 deletions(-) diff --git a/engines/supernova/game-manager.cpp b/engines/supernova/game-manager.cpp index 5cf54d4b09..e98218d02b 100644 --- a/engines/supernova/game-manager.cpp +++ b/engines/supernova/game-manager.cpp @@ -265,19 +265,13 @@ void GameManager::processInput(Common::KeyState &state) { // show game manual if (!_guiEnabled) return; - if (_vm->_MSPart == 1) - _vm->showTextReader("msn.doc"); - else if (_vm->_MSPart == 2) - _vm->showTextReader("ms2.doc"); + _vm->showTextReader("doc"); break; case Common::KEYCODE_F3: // show game info if (!_guiEnabled) return; - if (_vm->_MSPart == 1) - _vm->showTextReader("msn.inf"); - else if (_vm->_MSPart == 2) - _vm->showTextReader("ms2.inf"); + _vm->showTextReader("inf"); break; case Common::KEYCODE_F4: if (!_guiEnabled) diff --git a/engines/supernova/supernova.cpp b/engines/supernova/supernova.cpp index 07d91285e8..d186995f6b 100644 --- a/engines/supernova/supernova.cpp +++ b/engines/supernova/supernova.cpp @@ -510,14 +510,87 @@ void SupernovaEngine::showHelpScreen2() { _gm->animationOn(); } -Common::Error SupernovaEngine::showTextReader(const char *filename) { - Common::File file; +Common::SeekableReadStream *SupernovaEngine::getBlockFromDatFile(Common::String name) { + Common::String cur_lang = ConfMan.get("language"); + + // Validate the data file header + Common::File f; + char id[5], lang[5]; + id[4] = lang[4] = '\0'; + if (_MSPart == 1) { + if (!f.open(SUPERNOVA_DAT)) { + GUIErrorMessageFormat(_("Unable to locate the '%s' engine data file."), SUPERNOVA_DAT); + return nullptr; + } + f.read(id, 3); + if (strncmp(id, "MSN", 3) != 0) { + GUIErrorMessageFormat(_("The '%s' engine data file is corrupt."), SUPERNOVA_DAT); + return nullptr; + } + + int version = f.readByte(); + if (version != SUPERNOVA_DAT_VERSION) { + GUIErrorMessageFormat( + _("Incorrect version of the '%s' engine data file found. Expected %d but got %d."), + SUPERNOVA_DAT, SUPERNOVA_DAT_VERSION, version); + return nullptr; + } + } + else if (_MSPart == 2) { + if (!f.open(SUPERNOVA2_DAT)) { + GUIErrorMessageFormat(_("Unable to locate the '%s' engine data file."), SUPERNOVA2_DAT); + return nullptr; + } + f.read(id, 3); + if (strncmp(id, "MS2", 3) != 0) { + GUIErrorMessageFormat(_("The '%s' engine data file is corrupt."), SUPERNOVA2_DAT); + return nullptr; + } + + int version = f.readByte(); + if (version != SUPERNOVA2_DAT_VERSION) { + GUIErrorMessageFormat( + _("Incorrect version of the '%s' engine data file found. Expected %d but got %d."), + SUPERNOVA2_DAT, SUPERNOVA2_DAT_VERSION, version); + return nullptr; + } + } - if (!file.open(filename)) { - GUIErrorMessageFormat(_("Unable to find '%s' in game folder."), filename); - return Common::kReadingFailed; + + while (!f.eos()) { + f.read(id, 4); + f.read(lang, 4); + uint32 size = f.readUint32LE(); + if (f.eos()) + break; + if (name == id && cur_lang == lang) { + return f.readStream(size); + } else + f.skip(size); + } + + return nullptr; +} + +Common::Error SupernovaEngine::showTextReader(const char *extension) { + Common::SeekableReadStream *stream; + Common::String blockName; + blockName = Common::String::format("%s%d", extension, _MSPart); + blockName.toUppercase(); + if ((stream = getBlockFromDatFile(blockName)) == nullptr) { + Common::File file; + Common::String filename; + if (_MSPart == 1) + filename = Common::String::format("msn.%s", extension); + if (_MSPart == 2) + filename = Common::String::format("ms2.%s", extension); + + if (!file.open(filename)) { + GUIErrorMessageFormat(_("Unable to find '%s' in game folder or the engine data file."), filename); + return Common::kReadingFailed; + } + stream = file.readStream(file.size()); } - Common::SeekableReadStream *stream = file.readStream(file.size()); int linesInFile = 0; while (!stream->eos()) { stream->readLine(); diff --git a/engines/supernova/supernova.h b/engines/supernova/supernova.h index 55a021dfd3..8a6fe0f9c1 100644 --- a/engines/supernova/supernova.h +++ b/engines/supernova/supernova.h @@ -105,7 +105,8 @@ public: void setGameString(int idx, const Common::String &string); void showHelpScreen1(); void showHelpScreen2(); - Common::Error showTextReader(const char *filename); + Common::SeekableReadStream *getBlockFromDatFile(Common::String name); + Common::Error showTextReader(const char *extension); // forwarding calls void playSound(AudioId sample); -- cgit v1.2.3