aboutsummaryrefslogtreecommitdiff
path: root/engines/sherlock
diff options
context:
space:
mode:
authorPaul Gilbert2015-05-16 09:29:40 -0400
committerPaul Gilbert2015-05-16 09:29:40 -0400
commitaf651e19a421781a1498de0e66909a2e9450611c (patch)
treeee5991b696600dd4fe03338b04a684a605215a7c /engines/sherlock
parent32d7690e549f5af8fb5f88d9434ae0f54c0e6c69 (diff)
parent96e929f5233b23917169c7d0121e9c1e264455c1 (diff)
downloadscummvm-rg350-af651e19a421781a1498de0e66909a2e9450611c.tar.gz
scummvm-rg350-af651e19a421781a1498de0e66909a2e9450611c.tar.bz2
scummvm-rg350-af651e19a421781a1498de0e66909a2e9450611c.zip
Merge branch 'sherlock' into sherlock2
Conflicts: engines/sherlock/decompress.cpp engines/sherlock/objects.cpp engines/sherlock/objects.h engines/sherlock/scene.cpp engines/sherlock/scene.h engines/sherlock/sound.cpp
Diffstat (limited to 'engines/sherlock')
-rw-r--r--engines/sherlock/decompress.h36
-rw-r--r--engines/sherlock/detection.cpp21
-rw-r--r--engines/sherlock/detection_tables.h2
-rw-r--r--engines/sherlock/inventory.cpp5
-rw-r--r--engines/sherlock/inventory.h2
-rw-r--r--engines/sherlock/map.cpp4
-rw-r--r--engines/sherlock/map.h2
-rw-r--r--engines/sherlock/module.mk3
-rw-r--r--engines/sherlock/resources.cpp90
-rw-r--r--engines/sherlock/resources.h9
-rw-r--r--engines/sherlock/saveload.cpp2
-rw-r--r--engines/sherlock/scalpel/scalpel.cpp3
-rw-r--r--engines/sherlock/scene.cpp49
-rw-r--r--engines/sherlock/scene.h8
-rw-r--r--engines/sherlock/screen.cpp5
-rw-r--r--engines/sherlock/screen.h3
-rw-r--r--engines/sherlock/sherlock.cpp40
-rw-r--r--engines/sherlock/sherlock.h1
-rw-r--r--engines/sherlock/sound.cpp26
-rw-r--r--engines/sherlock/surface.cpp (renamed from engines/sherlock/graphics.cpp)37
-rw-r--r--engines/sherlock/surface.h (renamed from engines/sherlock/graphics.h)2
-rw-r--r--engines/sherlock/talk.cpp40
-rw-r--r--engines/sherlock/talk.h1
-rw-r--r--engines/sherlock/tattoo/tattoo.cpp1
-rw-r--r--engines/sherlock/user_interface.cpp27
-rw-r--r--engines/sherlock/user_interface.h2
26 files changed, 228 insertions, 193 deletions
diff --git a/engines/sherlock/decompress.h b/engines/sherlock/decompress.h
deleted file mode 100644
index 694f56aa65..0000000000
--- a/engines/sherlock/decompress.h
+++ /dev/null
@@ -1,36 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef SHERLOCK_DECOMPRESS_H
-#define SHERLOCK_DECOMPRESS_H
-
-#include "common/memstream.h"
-
-namespace Sherlock {
-
-#include "common/stream.h"
-
-Common::SeekableReadStream *decompressLZ(Common::SeekableReadStream &source, int32 outSize = -1);
-
-} // namespace Sherlock
-
-#endif
diff --git a/engines/sherlock/detection.cpp b/engines/sherlock/detection.cpp
index 78ab33bfd0..2804ec1d31 100644
--- a/engines/sherlock/detection.cpp
+++ b/engines/sherlock/detection.cpp
@@ -25,6 +25,7 @@
#include "sherlock/scalpel/scalpel.h"
#include "sherlock/tattoo/tattoo.h"
#include "common/system.h"
+#include "common/translation.h"
#include "engines/advancedDetector.h"
namespace Sherlock {
@@ -57,11 +58,29 @@ static const PlainGameDescriptor sherlockGames[] = {
{0, 0}
};
+
+#define GAMEOPTION_ORIGINAL_SAVES GUIO_GAMEOPTIONS1
+
+static const ADExtraGuiOptionsMap optionsList[] = {
+ {
+ GAMEOPTION_ORIGINAL_SAVES,
+ {
+ _s("Use original savegame dialog"),
+ _s("Files button in-game shows original savegame dialog rather than ScummVM menu"),
+ "originalsaveload",
+ false
+ }
+ },
+
+ AD_EXTRA_GUI_OPTIONS_TERMINATOR
+};
+
#include "sherlock/detection_tables.h"
class SherlockMetaEngine : public AdvancedMetaEngine {
public:
- SherlockMetaEngine() : AdvancedMetaEngine(Sherlock::gameDescriptions, sizeof(Sherlock::SherlockGameDescription), sherlockGames) {}
+ SherlockMetaEngine() : AdvancedMetaEngine(Sherlock::gameDescriptions, sizeof(Sherlock::SherlockGameDescription),
+ sherlockGames, optionsList) {}
virtual const char *getName() const {
return "Sherlock Engine";
diff --git a/engines/sherlock/detection_tables.h b/engines/sherlock/detection_tables.h
index 975b7323ec..8300a0ffcf 100644
--- a/engines/sherlock/detection_tables.h
+++ b/engines/sherlock/detection_tables.h
@@ -33,7 +33,7 @@ static const SherlockGameDescription gameDescriptions[] = {
Common::EN_ANY,
Common::kPlatformDOS,
ADGF_UNSTABLE | ADGF_NO_FLAGS,
- GUIO1(GUIO_NOSPEECH)
+ GUIO2(GUIO_NOSPEECH, GAMEOPTION_ORIGINAL_SAVES)
},
GType_SerratedScalpel,
},
diff --git a/engines/sherlock/inventory.cpp b/engines/sherlock/inventory.cpp
index d8c0104e6c..1997807d15 100644
--- a/engines/sherlock/inventory.cpp
+++ b/engines/sherlock/inventory.cpp
@@ -49,8 +49,6 @@ Inventory::Inventory(SherlockEngine *vm) : Common::Array<InventoryItem>(), _vm(v
_invGraphicsLoaded = false;
_invIndex = 0;
_holdings = 0;
- _oldFlag = 0;
- _invFlag = 0;
_invMode = INVMODE_EXIT;
}
@@ -215,7 +213,6 @@ void Inventory::drawInventory(int flag) {
UserInterface &ui = *_vm->_ui;
int tempFlag = flag;
- _oldFlag = 7;
loadInv();
if (flag == 128) {
@@ -257,10 +254,8 @@ void Inventory::drawInventory(int flag) {
if (flag) {
ui._oldKey = INVENTORY_COMMANDS[flag];
- _oldFlag = flag;
} else {
ui._oldKey = -1;
- _invFlag = 6;
}
invCommands(0);
diff --git a/engines/sherlock/inventory.h b/engines/sherlock/inventory.h
index f4cea7729a..eb5aebdd7c 100644
--- a/engines/sherlock/inventory.h
+++ b/engines/sherlock/inventory.h
@@ -75,8 +75,6 @@ public:
int _holdings; // Used to hold number of visible items in active inventory.
// Since Inventory array also contains some special hidden items
void freeGraphics();
- int _oldFlag;
- int _invFlag;
public:
Inventory(SherlockEngine *vm);
~Inventory();
diff --git a/engines/sherlock/map.cpp b/engines/sherlock/map.cpp
index c2eedd46ee..46e233bf7a 100644
--- a/engines/sherlock/map.cpp
+++ b/engines/sherlock/map.cpp
@@ -146,6 +146,10 @@ int Map::show() {
int oldFont = screen.fontNumber();
screen.setFont(0);
+ // Initial screen clear
+ screen._backBuffer1.clear();
+ screen.clear();
+
// Load the entire map
ImageFile bigMap("bigmap.vgs");
screen.setPalette(bigMap._palette);
diff --git a/engines/sherlock/map.h b/engines/sherlock/map.h
index 4432ec8553..4a418138b2 100644
--- a/engines/sherlock/map.h
+++ b/engines/sherlock/map.h
@@ -29,7 +29,7 @@
#include "common/serializer.h"
#include "common/str.h"
#include "common/str-array.h"
-#include "sherlock/graphics.h"
+#include "sherlock/surface.h"
#include "sherlock/objects.h"
namespace Sherlock {
diff --git a/engines/sherlock/module.mk b/engines/sherlock/module.mk
index babd0c49a0..2ded999ed1 100644
--- a/engines/sherlock/module.mk
+++ b/engines/sherlock/module.mk
@@ -5,11 +5,9 @@ MODULE_OBJS = \
scalpel/scalpel.o \
tattoo/tattoo.o \
animation.o \
- decompress.o \
debugger.o \
detection.o \
events.o \
- graphics.o \
inventory.o \
journal.o \
map.o \
@@ -22,6 +20,7 @@ MODULE_OBJS = \
settings.o \
sherlock.o \
sound.o \
+ surface.o \
talk.o \
user_interface.o
diff --git a/engines/sherlock/resources.cpp b/engines/sherlock/resources.cpp
index 9f2704ac62..bff80c2347 100644
--- a/engines/sherlock/resources.cpp
+++ b/engines/sherlock/resources.cpp
@@ -21,14 +21,14 @@
*/
#include "sherlock/resources.h"
-#include "sherlock/decompress.h"
#include "sherlock/screen.h"
#include "sherlock/sherlock.h"
#include "common/debug.h"
+#include "common/memstream.h"
namespace Sherlock {
-Cache::Cache() {
+Cache::Cache(SherlockEngine *vm): _vm(vm) {
}
/**
@@ -66,20 +66,17 @@ void Cache::load(const Common::String &name, Common::SeekableReadStream &stream)
if (_resources.contains(name))
return;
- // Check whether the file is compressed
- const char LZW_HEADER[5] = { "LZV\x1a" };
- char header[5];
- stream.read(header, 5);
- bool isCompressed = !strncmp(header, LZW_HEADER, 5);
+ int32 signature = stream.readUint32BE();
stream.seek(0);
// Allocate a new cache entry
_resources[name] = CacheEntry();
CacheEntry &cacheEntry = _resources[name];
- if (isCompressed) {
+ // Check whether the file is compressed
+ if (signature == MKTAG('L', 'Z', 'V', 26)) {
// It's compressed, so decompress the file and store it's data in the cache entry
- Common::SeekableReadStream *decompressed = decompressLZ(stream);
+ Common::SeekableReadStream *decompressed = _vm->_res->decompressLZ(stream);
cacheEntry.resize(decompressed->size());
decompressed->read(&cacheEntry[0], decompressed->size());
@@ -102,7 +99,7 @@ Common::SeekableReadStream *Cache::get(const Common::String &filename) const {
/*----------------------------------------------------------------*/
-Resources::Resources() {
+Resources::Resources(SherlockEngine *vm): _vm(vm), _cache(vm) {
_resourceIndex = -1;
addToCache("vgs.lib");
@@ -169,8 +166,19 @@ Common::SeekableReadStream *Resources::load(const Common::String &filename) {
stream->seek(entry._offset);
Common::SeekableReadStream *resStream = stream->readStream(entry._size);
- delete stream;
- return resStream;
+ // Check whether the file is compressed
+ if (resStream->readUint32BE() == MKTAG('L', 'Z', 'V', 26)) {
+ resStream->seek(0);
+ // It's compressed, so decompress the sub-file and return it
+ Common::SeekableReadStream *decompressed = decompressLZ(*resStream);
+ delete stream;
+ delete resStream;
+ return decompressed;
+ } else {
+ resStream->seek(0);
+ delete stream;
+ return resStream;
+ }
}
}
@@ -402,4 +410,62 @@ void ImageFile::decompressFrame(ImageFrame &frame, const byte *src) {
}
}
+/**
+ * Decompress an LZW compressed resource
+ */
+Common::SeekableReadStream *Resources::decompressLZ(Common::SeekableReadStream &source) {
+ if (_vm->getGameID() == GType_SerratedScalpel) {
+ uint32 id = source.readUint32BE();
+ assert(id == MKTAG('L', 'Z', 'V', 0x1A));
+ }
+
+ uint32 size = source.readUint32LE();
+ return decompressLZ(source, size);
+}
+
+/**
+ * Decompresses an LZW block of data with a specified output size
+ */
+Common::SeekableReadStream *Resources::decompressLZ(Common::SeekableReadStream &source, uint32 outSize) {
+ byte lzWindow[4096];
+ uint16 lzWindowPos;
+ uint16 cmd;
+
+ byte *outBuffer = (byte *)malloc(outSize);
+ byte *outBufferEnd = outBuffer + outSize;
+ Common::MemoryReadStream *outS = new Common::MemoryReadStream(outBuffer, outSize, DisposeAfterUse::YES);
+
+ memset(lzWindow, 0xFF, 0xFEE);
+ lzWindowPos = 0xFEE;
+ cmd = 0;
+
+ do {
+ cmd >>= 1;
+ if (!(cmd & 0x100))
+ cmd = source.readByte() | 0xFF00;
+
+ if (cmd & 1) {
+ byte literal = source.readByte();
+ *outBuffer++ = literal;
+ lzWindow[lzWindowPos] = literal;
+ lzWindowPos = (lzWindowPos + 1) & 0x0FFF;
+ } else {
+ int copyPos, copyLen;
+ copyPos = source.readByte();
+ copyLen = source.readByte();
+ copyPos = copyPos | ((copyLen & 0xF0) << 4);
+ copyLen = (copyLen & 0x0F) + 3;
+ while (copyLen--) {
+ byte literal = lzWindow[copyPos];
+ copyPos = (copyPos + 1) & 0x0FFF;
+ *outBuffer++ = literal;
+ lzWindow[lzWindowPos] = literal;
+ lzWindowPos = (lzWindowPos + 1) & 0x0FFF;
+ }
+ }
+ } while (outBuffer < outBufferEnd);
+
+ return outS;
+}
+
} // End of namespace Sherlock
diff --git a/engines/sherlock/resources.h b/engines/sherlock/resources.h
index bbaac60a33..041f1c64a9 100644
--- a/engines/sherlock/resources.h
+++ b/engines/sherlock/resources.h
@@ -52,9 +52,10 @@ class SherlockEngine;
class Cache {
private:
+ SherlockEngine *_vm;
CacheHash _resources;
public:
- Cache();
+ Cache(SherlockEngine *_vm);
bool isCached(const Common::String &filename) const;
@@ -66,6 +67,7 @@ public:
class Resources {
private:
+ SherlockEngine *_vm;
Cache _cache;
LibraryIndexes _indexes;
int _resourceIndex;
@@ -73,7 +75,7 @@ private:
void loadLibraryIndex(const Common::String &libFilename, Common::SeekableReadStream *stream,
bool isNewStyle);
public:
- Resources();
+ Resources(SherlockEngine *vm);
void addToCache(const Common::String &filename);
void addToCache(const Common::String &filename, const Common::String &libFilename);
@@ -87,6 +89,9 @@ public:
bool exists(const Common::String &filename) const;
int resourceIndex() const;
+
+ static Common::SeekableReadStream *decompressLZ(Common::SeekableReadStream &source, uint32 outSize);
+ Common::SeekableReadStream *decompressLZ(Common::SeekableReadStream &source);
};
struct ImageFrame {
diff --git a/engines/sherlock/saveload.cpp b/engines/sherlock/saveload.cpp
index a78b89b00c..b9ac3e79d6 100644
--- a/engines/sherlock/saveload.cpp
+++ b/engines/sherlock/saveload.cpp
@@ -21,7 +21,7 @@
*/
#include "sherlock/saveload.h"
-#include "sherlock/graphics.h"
+#include "sherlock/surface.h"
#include "sherlock/sherlock.h"
#include "common/system.h"
#include "graphics/scaler.h"
diff --git a/engines/sherlock/scalpel/scalpel.cpp b/engines/sherlock/scalpel/scalpel.cpp
index b982079714..521aeb338b 100644
--- a/engines/sherlock/scalpel/scalpel.cpp
+++ b/engines/sherlock/scalpel/scalpel.cpp
@@ -255,8 +255,9 @@ void ScalpelEngine::initialize() {
_flags[39] = true; // Turn on Baker Street
// Add some more files to the cache
- _res->addToCache("sequence.txt");
_res->addToCache("portrait.lib");
+ _res->addToCache("sequence.txt");
+ _res->addToCache("snd.snd");
// Load the map co-ordinates for each scene and sequence data
_map->loadPoints(NUM_PLACES, &MAP_X[0], &MAP_Y[0], &MAP_TRANSLATE[0]);
diff --git a/engines/sherlock/scene.cpp b/engines/sherlock/scene.cpp
index d4662ed559..0a25d3dd0f 100644
--- a/engines/sherlock/scene.cpp
+++ b/engines/sherlock/scene.cpp
@@ -23,7 +23,6 @@
#include "sherlock/scene.h"
#include "sherlock/sherlock.h"
#include "sherlock/scalpel/scalpel.h"
-#include "sherlock/decompress.h"
#include "sherlock/screen.h"
namespace Sherlock {
@@ -64,7 +63,10 @@ void BgFileHeader::synchronize(Common::SeekableReadStream &s, bool isRoseTattoo)
/*----------------------------------------------------------------*/
-void BgfileheaderInfo::synchronize(Common::SeekableReadStream &s) {
+/**
+ * Load the data for the object
+ */
+void BgfileheaderInfo::load(Common::SeekableReadStream &s) {
_filesize = s.readUint32LE();
_maxFrames = s.readByte();
@@ -75,7 +77,10 @@ void BgfileheaderInfo::synchronize(Common::SeekableReadStream &s) {
/*----------------------------------------------------------------*/
-void Exit::synchronize(Common::SeekableReadStream &s) {
+/**
+ * Load the data for the object
+ */
+void Exit::load(Common::SeekableReadStream &s) {
int xp = s.readSint16LE();
int yp = s.readSint16LE();
int xSize = s.readSint16LE();
@@ -91,14 +96,20 @@ void Exit::synchronize(Common::SeekableReadStream &s) {
/*----------------------------------------------------------------*/
-void SceneEntry::synchronize(Common::SeekableReadStream &s) {
+/**
+ * Load the data for the object
+ */
+void SceneEntry::load(Common::SeekableReadStream &s) {
_startPosition.x = s.readSint16LE();
_startPosition.y = s.readSint16LE();
_startDir = s.readByte();
_allow = s.readByte();
}
-void SceneSound::synchronize(Common::SeekableReadStream &s) {
+/**
+ * Load the data for the object
+ */
+void SceneSound::load(Common::SeekableReadStream &s) {
char buffer[9];
s.read(buffer, 8);
buffer[8] = '\0';
@@ -109,6 +120,9 @@ void SceneSound::synchronize(Common::SeekableReadStream &s) {
/*----------------------------------------------------------------*/
+/**
+ * Retuurn the index of the passed object in the array
+ */
int ObjectArray::indexOf(const Object &obj) const {
for (uint idx = 0; idx < size(); ++idx) {
if (&(*this)[idx] == &obj)
@@ -236,6 +250,7 @@ bool Scene::loadScene(const Common::String &filename) {
Events &events = *_vm->_events;
Map &map = *_vm->_map;
People &people = *_vm->_people;
+ Resources &res = *_vm->_res;
SaveManager &saves = *_vm->_saves;
Screen &screen = *_vm->_screen;
Sound &sound = *_vm->_sound;
@@ -288,7 +303,7 @@ bool Scene::loadScene(const Common::String &filename) {
// Read in background
if (_lzwMode) {
- Common::SeekableReadStream *stream = decompressLZ(*rrmStream, SHERLOCK_SCREEN_WIDTH * SHERLOCK_SCREEN_HEIGHT);
+ Common::SeekableReadStream *stream = res.decompressLZ(*rrmStream);
stream->read(screen._backBuffer1.getPixels(), stream->size());
delete stream;
} else {
@@ -300,12 +315,12 @@ bool Scene::loadScene(const Common::String &filename) {
bgInfo.resize(bgHeader._numStructs);
for (uint idx = 0; idx < bgInfo.size(); ++idx)
- bgInfo[idx].synchronize(*rrmStream);
+ bgInfo[idx].load(*rrmStream);
// Read information
int shapeSize = _vm->getGameID() == GType_SerratedScalpel ? 569 : 591;
Common::SeekableReadStream *infoStream = !_lzwMode ? rrmStream :
- decompressLZ(*rrmStream, bgHeader._numImages * shapeSize +
+ Resources::decompressLZ(*rrmStream, bgHeader._numImages * shapeSize +
bgHeader._descSize + bgHeader._seqSize);
_bgShapes.resize(bgHeader._numStructs);
@@ -333,7 +348,7 @@ bool Scene::loadScene(const Common::String &filename) {
// Read in the image data
Common::SeekableReadStream *imageStream = _lzwMode ?
- decompressLZ(*rrmStream, bgInfo[idx]._filesize) :
+ Resources::decompressLZ(*rrmStream, bgInfo[idx]._filesize) :
rrmStream->readStream(bgInfo[idx]._filesize);
_images[idx + 1]._images = new ImageFile(*imageStream);
@@ -362,7 +377,7 @@ bool Scene::loadScene(const Common::String &filename) {
_cAnim.clear();
if (bgHeader._numcAnimations) {
Common::SeekableReadStream *canimStream = _lzwMode ?
- decompressLZ(*rrmStream, 65 * bgHeader._numcAnimations) :
+ Resources::decompressLZ(*rrmStream, 65 * bgHeader._numcAnimations) :
rrmStream->readStream(65 * bgHeader._numcAnimations);
_cAnim.resize(bgHeader._numcAnimations);
@@ -375,7 +390,7 @@ bool Scene::loadScene(const Common::String &filename) {
// Read in the room bounding areas
int size = rrmStream->readUint16LE();
Common::SeekableReadStream *boundsStream = !_lzwMode ? rrmStream :
- decompressLZ(*rrmStream, size);
+ Resources::decompressLZ(*rrmStream, size);
_zones.resize(size / 10);
for (uint idx = 0; idx < _zones.size(); ++idx) {
@@ -402,7 +417,7 @@ bool Scene::loadScene(const Common::String &filename) {
// Read in the walk data
size = rrmStream->readUint16LE();
Common::SeekableReadStream *walkStream = !_lzwMode ? rrmStream :
- decompressLZ(*rrmStream, size);
+ Resources::decompressLZ(*rrmStream, size);
_walkData.resize(size);
walkStream->read(&_walkData[0], size);
@@ -415,17 +430,17 @@ bool Scene::loadScene(const Common::String &filename) {
_exits.resize(numExits);
for (int idx = 0; idx < numExits; ++idx)
- _exits[idx].synchronize(*rrmStream);
+ _exits[idx].load(*rrmStream);
// Read in the entrance
- _entrance.synchronize(*rrmStream);
+ _entrance.load(*rrmStream);
// Initialize sound list
int numSounds = rrmStream->readByte();
_sounds.resize(numSounds);
for (int idx = 0; idx < numSounds; ++idx)
- _sounds[idx].synchronize(*rrmStream);
+ _sounds[idx].load(*rrmStream);
for (int idx = 0; idx < numSounds; ++idx)
sound.loadSound(_sounds[idx]._name, _sounds[idx]._priority);
@@ -439,7 +454,7 @@ bool Scene::loadScene(const Common::String &filename) {
// Read in the background
Common::SeekableReadStream *bgStream = !_lzwMode ? rrmStream :
- decompressLZ(*rrmStream, SHERLOCK_SCREEN_WIDTH * SHERLOCK_SCENE_HEIGHT);
+ Resources::decompressLZ(*rrmStream, SHERLOCK_SCREEN_WIDTH * SHERLOCK_SCENE_HEIGHT);
bgStream->read(screen._backBuffer1.getPixels(), SHERLOCK_SCREEN_WIDTH * SHERLOCK_SCENE_HEIGHT);
@@ -1013,7 +1028,7 @@ int Scene::startCAnim(int cAnimNum, int playRate) {
// Load the canimation into the cache
Common::SeekableReadStream *imgStream = !_lzwMode ? rrmStream->readStream(cAnim._size) :
- decompressLZ(*rrmStream, cAnim._size);
+ Resources::decompressLZ(*rrmStream, cAnim._size);
res.addToCache(fname, *imgStream);
delete imgStream;
diff --git a/engines/sherlock/scene.h b/engines/sherlock/scene.h
index b4b88fa0a1..86b1e3d063 100644
--- a/engines/sherlock/scene.h
+++ b/engines/sherlock/scene.h
@@ -65,7 +65,7 @@ struct BgfileheaderInfo {
int _maxFrames; // How many unique frames in object
Common::String _filename; // Filename of object
- void synchronize(Common::SeekableReadStream &s);
+ void load(Common::SeekableReadStream &s);
};
struct Exit {
@@ -76,7 +76,7 @@ struct Exit {
Common::Point _people;
int _peopleDir;
- void synchronize(Common::SeekableReadStream &s);
+ void load(Common::SeekableReadStream &s);
};
struct SceneEntry {
@@ -84,14 +84,14 @@ struct SceneEntry {
int _startDir;
int _allow;
- void synchronize(Common::SeekableReadStream &s);
+ void load(Common::SeekableReadStream &s);
};
struct SceneSound {
Common::String _name;
int _priority;
- void synchronize(Common::SeekableReadStream &s);
+ void load(Common::SeekableReadStream &s);
};
class ObjectArray: public Common::Array<Object> {
diff --git a/engines/sherlock/screen.cpp b/engines/sherlock/screen.cpp
index 0ca10b4a4a..349bf4d024 100644
--- a/engines/sherlock/screen.cpp
+++ b/engines/sherlock/screen.cpp
@@ -149,6 +149,7 @@ void Screen::fadeToBlack(int speed) {
}
setPalette(tempPalette);
+ fillRect(Common::Rect(0, 0, this->w, this->h), 0);
}
/**
@@ -169,7 +170,7 @@ void Screen::fadeIn(const byte palette[PALETTE_SIZE], int speed) {
*/
void Screen::addDirtyRect(const Common::Rect &r) {
_dirtyRects.push_back(r);
- assert(r.isValidRect() && r.width() > 0 && r.height() > 0);
+ assert(r.width() > 0 && r.height() > 0);
}
/**
@@ -224,7 +225,7 @@ void Screen::randomTransition() {
if (offset < (this->w * this->h))
*((byte *)getPixels() + offset) = *((const byte *)_backBuffer->getPixels() + offset);
- if (idx != 0 && (idx % 100) == 0) {
+ if (idx != 0 && (idx % 300) == 0) {
// Ensure there's a full screen dirty rect for the next frame update
if (_dirtyRects.empty())
addDirtyRect(Common::Rect(0, 0, this->w, this->h));
diff --git a/engines/sherlock/screen.h b/engines/sherlock/screen.h
index 25389166d0..8a8eca13fc 100644
--- a/engines/sherlock/screen.h
+++ b/engines/sherlock/screen.h
@@ -26,8 +26,7 @@
#include "common/list.h"
#include "common/rect.h"
#include "common/serializer.h"
-#include "graphics/surface.h"
-#include "sherlock/graphics.h"
+#include "sherlock/surface.h"
#include "sherlock/resources.h"
namespace Sherlock {
diff --git a/engines/sherlock/sherlock.cpp b/engines/sherlock/sherlock.cpp
index 318267bb8f..eea3dcb867 100644
--- a/engines/sherlock/sherlock.cpp
+++ b/engines/sherlock/sherlock.cpp
@@ -21,7 +21,7 @@
*/
#include "sherlock/sherlock.h"
-#include "sherlock/graphics.h"
+#include "sherlock/surface.h"
#include "common/scummsys.h"
#include "common/config-manager.h"
#include "common/debug-channels.h"
@@ -47,6 +47,7 @@ SherlockEngine::SherlockEngine(OSystem *syst, const SherlockGameDescription *gam
_useEpilogue2 = false;
_loadGameSlot = -1;
_canLoadSave = false;
+ _showOriginalSavesDialog = false;
}
SherlockEngine::~SherlockEngine() {
@@ -75,7 +76,7 @@ void SherlockEngine::initialize() {
ImageFile::setVm(this);
Object::setVm(this);
Sprite::setVm(this);
- _res = new Resources();
+ _res = new Resources(this);
_animation = new Animation(this);
_debugger = new Debugger(this);
_events = new Events(this);
@@ -101,6 +102,9 @@ Common::Error SherlockEngine::run() {
// Initialize the engine
initialize();
+ // Flag for whether to show original saves dialog rather than the ScummVM GMM
+ _showOriginalSavesDialog = ConfMan.getBool("originalsaveload");
+
// If requested, load a savegame instead of showing the intro
if (ConfMan.hasKey("save_slot")) {
int saveSlot = ConfMan.getInt("save_slot");
@@ -122,6 +126,9 @@ Common::Error SherlockEngine::run() {
if (shouldQuit())
break;
+ // Clear the screen
+ _screen->clear();
+
// Reset UI flags
_ui->reset();
@@ -207,26 +214,27 @@ void SherlockEngine::loadConfig() {
// Load sound settings
syncSoundSettings();
- // Load other settings
- if (ConfMan.hasKey("font"))
- _screen->setFont(ConfMan.getInt("font"));
- if (ConfMan.hasKey("fade_style"))
- _screen->_fadeStyle = ConfMan.getBool("fade_style");
- if (ConfMan.hasKey("help_style"))
- _ui->_helpStyle = ConfMan.getBool("help_style");
- if (ConfMan.hasKey("window_style"))
- _ui->_windowStyle = ConfMan.getInt("window_style");
- if (ConfMan.hasKey("portraits_on"))
- _people->_portraitsOn = ConfMan.getBool("portraits_on");
+ ConfMan.registerDefault("font", 1);
+ ConfMan.registerDefault("fade_style", true);
+ ConfMan.registerDefault("help_style", false);
+ ConfMan.registerDefault("window_style", 1);
+ ConfMan.registerDefault("portraits_on", true);
+ ConfMan.registerDefault("originalsaveload", false);
+
+ _screen->setFont(ConfMan.getInt("font"));
+ _screen->_fadeStyle = ConfMan.getBool("fade_style");
+ _ui->_helpStyle = ConfMan.getBool("help_style");
+ _ui->_windowStyle = ConfMan.getInt("window_style");
+ _people->_portraitsOn = ConfMan.getBool("portraits_on");
}
/**
* Saves game configuration information
*/
void SherlockEngine::saveConfig() {
- ConfMan.setBool("mute", _sound->_digitized);
- ConfMan.setBool("music_mute", _sound->_music);
- ConfMan.setBool("speech_mute", _sound->_voices);
+ ConfMan.setBool("mute", !_sound->_digitized);
+ ConfMan.setBool("music_mute", !_sound->_music);
+ ConfMan.setBool("speech_mute", !_sound->_voices);
ConfMan.setInt("font", _screen->fontNumber());
ConfMan.setBool("fade_style", _screen->_fadeStyle);
diff --git a/engines/sherlock/sherlock.h b/engines/sherlock/sherlock.h
index e21ac8c6d6..9261ad5b05 100644
--- a/engines/sherlock/sherlock.h
+++ b/engines/sherlock/sherlock.h
@@ -108,6 +108,7 @@ public:
bool _useEpilogue2;
int _loadGameSlot;
bool _canLoadSave;
+ bool _showOriginalSavesDialog;
public:
SherlockEngine(OSystem *syst, const SherlockGameDescription *gameDesc);
virtual ~SherlockEngine();
diff --git a/engines/sherlock/sound.cpp b/engines/sherlock/sound.cpp
index 70451a68da..001907917f 100644
--- a/engines/sherlock/sound.cpp
+++ b/engines/sherlock/sound.cpp
@@ -45,7 +45,8 @@ Sound::Sound(SherlockEngine *vm, Audio::Mixer *mixer): _vm(vm), _mixer(mixer) {
_speechOn = true;
_vm->_res->addToCache("MUSIC.LIB");
- _vm->_res->addToCache(_vm->getGameID() == GType_SerratedScalpel ? "SND.SND" : "SOUND.LIB");
+ _vm->_res->addToCache("TITLE.SND");
+ _vm->_res->addToCache("EPILOGUE.SND");
}
/**
@@ -92,7 +93,11 @@ bool Sound::playSound(const Common::String &name, WaitType waitType, int priorit
Common::String filename = name;
if (!filename.contains('.'))
filename += ".SND";
- Common::SeekableReadStream *stream = _vm->_res->load(filename, "TITLE.SND");
+
+ Common::SeekableReadStream *stream = _vm->_res->load(filename);
+
+ if (!stream)
+ error("Unable to find sound file '%s'", filename.c_str());
stream->skip(2);
int size = stream->readUint32BE();
@@ -115,6 +120,15 @@ bool Sound::playSound(const Common::String &name, WaitType waitType, int priorit
free(data);
+#if 0
+ // Debug : used to dump files
+ Common::DumpFile outFile;
+ outFile.open(filename);
+ outFile.write(decoded, (size - 2) * 2);
+ outFile.flush();
+ outFile.close();
+#endif
+
Audio::AudioStream *audioStream = Audio::makeRawStream(decoded, (size - 2) * 2, rate, Audio::FLAG_UNSIGNED, DisposeAfterUse::YES);
_mixer->playStream(Audio::Mixer::kPlainSoundType, &_effectsHandle, audioStream, -1, Audio::Mixer::kMaxChannelVolume);
_soundPlaying = true;
@@ -138,14 +152,6 @@ bool Sound::playSound(const Common::String &name, WaitType waitType, int priorit
_soundPlaying = false;
_mixer->stopHandle(_effectsHandle);
-#if 0
- // Debug : used to dump files
- Common::DumpFile outFile;
- outFile.open(filename);
- outFile.write(decoded, (size - 2) * 2);
- outFile.flush();
- outFile.close();
-#endif
return retval;
}
diff --git a/engines/sherlock/graphics.cpp b/engines/sherlock/surface.cpp
index 234928156a..36e625794c 100644
--- a/engines/sherlock/graphics.cpp
+++ b/engines/sherlock/surface.cpp
@@ -20,7 +20,7 @@
*
*/
-#include "sherlock/graphics.h"
+#include "sherlock/surface.h"
#include "sherlock/sherlock.h"
#include "common/system.h"
#include "graphics/palette.h"
@@ -62,28 +62,7 @@ void Surface::blitFrom(const Graphics::Surface &src) {
* Draws a surface at a given position within this surface
*/
void Surface::blitFrom(const Graphics::Surface &src, const Common::Point &pt) {
- Common::Rect drawRect(0, 0, src.w, src.h);
- Common::Point destPt = pt;
-
- if (destPt.x < 0) {
- drawRect.left += -destPt.x;
- destPt.x = 0;
- }
- if (destPt.y < 0) {
- drawRect.top += -destPt.y;
- destPt.y = 0;
- }
- int right = destPt.x + src.w;
- if (right > this->w) {
- drawRect.right -= (right - this->w);
- }
- int bottom = destPt.y + src.h;
- if (bottom > this->h) {
- drawRect.bottom -= (bottom - this->h);
- }
-
- if (drawRect.isValidRect())
- blitFrom(src, destPt, drawRect);
+ blitFrom(src, pt, Common::Rect(0, 0, src.w, src.h));
}
/**
@@ -91,11 +70,10 @@ void Surface::blitFrom(const Graphics::Surface &src, const Common::Point &pt) {
*/
void Surface::blitFrom(const Graphics::Surface &src, const Common::Point &pt,
const Common::Rect &srcBounds) {
- Common::Rect destRect(pt.x, pt.y, pt.x + srcBounds.width(),
- pt.y + srcBounds.height());
Common::Rect srcRect = srcBounds;
+ Common::Rect destRect(pt.x, pt.y, pt.x + srcRect.width(), pt.y + srcRect.height());
- if (clip(srcRect, destRect)) {
+ if (srcRect.isValidRect() && clip(srcRect, destRect)) {
// Surface is at least partially or completely on-screen
addDirtyRect(destRect);
copyRectToSurface(src, destRect.left, destRect.top, srcRect);
@@ -194,4 +172,11 @@ bool Surface::clip(Common::Rect &srcBounds, Common::Rect &destBounds) {
return true;
}
+/**
+ * Clear the screen
+ */
+void Surface::clear() {
+ fillRect(Common::Rect(0, 0, this->w, this->h), 0);
+}
+
} // End of namespace Sherlock
diff --git a/engines/sherlock/graphics.h b/engines/sherlock/surface.h
index d4a1584968..b2a759aa8d 100644
--- a/engines/sherlock/graphics.h
+++ b/engines/sherlock/surface.h
@@ -53,6 +53,8 @@ public:
void fillRect(int x1, int y1, int x2, int y2, byte color);
void fillRect(const Common::Rect &r, byte color);
+
+ void clear();
};
} // End of namespace Sherlock
diff --git a/engines/sherlock/talk.cpp b/engines/sherlock/talk.cpp
index 61f0004fd6..d656431823 100644
--- a/engines/sherlock/talk.cpp
+++ b/engines/sherlock/talk.cpp
@@ -104,7 +104,6 @@ Talk::Talk(SherlockEngine *vm): _vm(vm) {
_moreTalkDown = _moreTalkUp = false;
_scriptMoreFlag = 0;
_scriptSaveIndex = -1;
- _scriptCurrentIndex = -1;
}
/**
@@ -1082,10 +1081,6 @@ void Talk::doScript(const Common::String &script) {
// Handle control code
switch (c) {
case SWITCH_SPEAKER:
- // Save the current point in the script, since it might be intterupted by
- // doing bg anims in the next call, so we need to know where to return to
- _scriptCurrentIndex = str - scriptStart;
-
if (!(_speaker & 128))
people.clearTalking();
if (_talkToAbort)
@@ -1103,10 +1098,7 @@ void Talk::doScript(const Common::String &script) {
break;
case RUN_CANIMATION:
- // Save the current point in the script, since it might be intterupted by
- // doing bg anims in the next call, so we need to know where to return to
++str;
- _scriptCurrentIndex = (str + 1) - scriptStart;
scene.startCAnim((str[0] - 1) & 127, (str[0] & 128) ? -1 : 1);
if (_talkToAbort)
return;
@@ -1143,10 +1135,6 @@ void Talk::doScript(const Common::String &script) {
break;
case REMOVE_PORTRAIT:
- // Save the current point in the script, since it might be intterupted by
- // doing bg anims in the next call, so we need to know where to return to
- _scriptCurrentIndex = str - scriptStart;
-
if (_speaker >= 0 && _speaker < 128)
people.clearTalking();
pullSequence();
@@ -1203,10 +1191,7 @@ void Talk::doScript(const Common::String &script) {
}
case WALK_TO_COORDS:
- // Save the current point in the script, since it might be interrupted by
- // doing bg anims in the next call, so we need to know where to return to
++str;
- _scriptCurrentIndex = str - scriptStart;
people.walkToCoords(Common::Point(((str[0] - 1) * 256 + str[1] - 1) * 100,
str[2] * 100), str[3] - 1);
@@ -1217,10 +1202,7 @@ void Talk::doScript(const Common::String &script) {
break;
case PAUSE_WITHOUT_CONTROL:
- // Save the current point in the script, since it might be intterupted by
- // doing bg anims in the next call, so we need to know where to return to
++str;
- _scriptCurrentIndex = str - scriptStart;
for (int idx = 0; idx < (str[0] - 1); ++idx) {
scene.doBgAnim();
@@ -1234,10 +1216,6 @@ void Talk::doScript(const Common::String &script) {
break;
case BANISH_WINDOW:
- // Save the current point in the script, since it might be intterupted by
- // doing bg anims in the next call, so we need to know where to return to
- _scriptCurrentIndex = str - scriptStart;
-
if (!(_speaker & 128))
people.clearTalking();
pullSequence();
@@ -1403,19 +1381,19 @@ void Talk::doScript(const Common::String &script) {
break;
}
- case CALL_TALK_FILE:
+ case CALL_TALK_FILE: {
++str;
for (int idx = 0; idx < 8 && str[idx] != '~'; ++idx)
tempString += str[idx];
str += 8;
- _scriptCurrentIndex = str - scriptStart;
+ int scriptCurrentIndex = str - scriptStart;
// Save the current script position and new talk file
if (_scriptStack.size() < 9) {
ScriptStackEntry rec1;
rec1._name = _scriptName;
- rec1._currentIndex = _scriptCurrentIndex;
+ rec1._currentIndex = scriptCurrentIndex;
rec1._select = _scriptSelect;
_scriptStack.push(rec1);
@@ -1433,12 +1411,10 @@ void Talk::doScript(const Common::String &script) {
endStr = true;
wait = 0;
break;
+ }
case MOVE_MOUSE:
- // Save the current point in the script, since it might be intterupted by
- // doing bg anims in the next call, so we need to know where to return to
++str;
- _scriptCurrentIndex = str - scriptStart;
events.moveMouse(Common::Point((str[0] - 1) * 256 + str[1] - 1, str[2]));
if (_talkToAbort)
return;
@@ -1464,10 +1440,6 @@ void Talk::doScript(const Common::String &script) {
++str;
CAnim &animation = scene._cAnim[str[0] - 1];
- // Save the current point in the script, since it might be interrupted by
- // doing bg anims in the next call, so we need to know where to return to
- _scriptCurrentIndex = (str + 1) - scriptStart;
-
people.walkToCoords(animation._goto, animation._gotoDir);
if (_talkToAbort)
return;
@@ -1614,10 +1586,6 @@ void Talk::doScript(const Common::String &script) {
}
if (wait) {
- // Save the current point in the script, since it might be intterupted by
- // doing bg anims in the next call, so we need to know where to return to
- _scriptCurrentIndex = str - scriptStart;
-
// Handling pausing
if (!pauseFlag && charCount < 160)
charCount = 160;
diff --git a/engines/sherlock/talk.h b/engines/sherlock/talk.h
index d81586228f..b1a735827c 100644
--- a/engines/sherlock/talk.h
+++ b/engines/sherlock/talk.h
@@ -140,7 +140,6 @@ private:
int _talkStealth;
int _talkToFlag;
int _scriptSaveIndex;
- int _scriptCurrentIndex;
private:
void stripVoiceCommands();
void setTalkMap();
diff --git a/engines/sherlock/tattoo/tattoo.cpp b/engines/sherlock/tattoo/tattoo.cpp
index 9039e3f9d4..3c684ff3ee 100644
--- a/engines/sherlock/tattoo/tattoo.cpp
+++ b/engines/sherlock/tattoo/tattoo.cpp
@@ -44,6 +44,7 @@ void TattooEngine::initialize() {
// Add some more files to the cache
_res->addToCache("walk.lib");
+ _res->addToCache("sound.lib");
// Starting scene
_scene->_goToScene = 91;
diff --git a/engines/sherlock/user_interface.cpp b/engines/sherlock/user_interface.cpp
index 8e7254026b..1ab8fe7294 100644
--- a/engines/sherlock/user_interface.cpp
+++ b/engines/sherlock/user_interface.cpp
@@ -172,11 +172,6 @@ void UserInterface::handleInput() {
_vm->quitGame();
events.pollEvents();
return;
- } else if (keyState.keycode == Common::KEYCODE_SPACE ||
- keyState.keycode == Common::KEYCODE_RETURN) {
- events._pressed = false;
- events._oldButtons = 0;
- _keycode = Common::KEYCODE_INVALID;
}
}
@@ -929,7 +924,7 @@ void UserInterface::doEnvControl() {
screen.print(Common::Point(0, CONTROLS_Y + 20), INV_FOREGROUND, "Are you sure you wish to Quit ?");
screen.vgaBar(Common::Rect(0, CONTROLS_Y, SHERLOCK_SCREEN_WIDTH, CONTROLS_Y + 10), BORDER_COLOR);
- screen.makeButton(Common::Rect(112, CONTROLS_Y, 150, CONTROLS_Y + 10), 136 - screen.stringWidth("Yes") / 2, "Yes");
+ screen.makeButton(Common::Rect(112, CONTROLS_Y, 160, CONTROLS_Y + 10), 136 - screen.stringWidth("Yes") / 2, "Yes");
screen.makeButton(Common::Rect(161, CONTROLS_Y, 209, CONTROLS_Y + 10), 184 - screen.stringWidth("No") / 2, "No");
screen.slamArea(112, CONTROLS_Y, 97, 10);
@@ -1430,17 +1425,24 @@ void UserInterface::doMainControl() {
break;
case 'F':
pushButton(10);
- _menuMode = FILES_MODE;
// Create a thumbnail of the current screen before the files dialog is shown, in case
// the user saves the game
saves.createThumbnail();
- // Display the dialog
- saves.drawInterface();
-
_selector = _oldSelector = -1;
- _windowOpen = true;
+
+ if (_vm->_showOriginalSavesDialog) {
+ // Show the original dialog
+ _menuMode = FILES_MODE;
+ saves.drawInterface();
+ _windowOpen = true;
+ } else {
+ // Show the ScummVM GMM instead
+ _vm->_canLoadSave = true;
+ _vm->openMainMenuDialog();
+ _vm->_canLoadSave = false;
+ }
break;
case 'S':
pushButton(11);
@@ -1699,9 +1701,6 @@ void UserInterface::doTalkControl() {
sound._speechOn = false;
}
- // Set the _scriptCurrentIndex so if the statement is irrupted, the entire
- // reply will be shown when it's restarted
- talk._scriptCurrentIndex = 0;
talk.waitForMore(talk._statements[_selector]._statement.size());
if (talk._talkToAbort)
return;
diff --git a/engines/sherlock/user_interface.h b/engines/sherlock/user_interface.h
index 79382a19fe..2ff60715e3 100644
--- a/engines/sherlock/user_interface.h
+++ b/engines/sherlock/user_interface.h
@@ -25,7 +25,7 @@
#include "common/scummsys.h"
#include "common/events.h"
-#include "sherlock/graphics.h"
+#include "sherlock/surface.h"
#include "sherlock/objects.h"
#include "sherlock/resources.h"