mirror of
https://github.com/libretro/scummvm.git
synced 2025-02-10 04:43:26 +00:00
![Colin Snover](/assets/img/avatar_default.png)
This commit implements all of the known plane transitions from SCI2 through SCI2.1mid games. Because kSetShowStyle is always called indirectly via the Styler game script, it is difficult to find all the places where transitions are used. As such, transitions that appeared to never be used have been added as stubs which will trigger a game crash with a message to report what was being done, so any missed transition types can be identified quickly and then implemented.
475 lines
14 KiB
C++
475 lines
14 KiB
C++
/* 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 SCI_SCI_H
|
|
#define SCI_SCI_H
|
|
|
|
#include "engines/engine.h"
|
|
#include "common/macresman.h"
|
|
#include "common/util.h"
|
|
#include "common/random.h"
|
|
#include "sci/engine/vm_types.h" // for Selector
|
|
#include "sci/debug.h" // for DebugState
|
|
|
|
struct ADGameDescription;
|
|
|
|
/**
|
|
* This is the namespace of the SCI engine.
|
|
*
|
|
* Status of this engine: ???
|
|
*
|
|
* Games using this engine:
|
|
* - Newer Sierra adventure games (based on FreeSCI)
|
|
*
|
|
* @todo give a concrete list of supported games. Could also
|
|
* list future games, with status for each.
|
|
*/
|
|
namespace Sci {
|
|
|
|
struct EngineState;
|
|
class Vocabulary;
|
|
class ResourceManager;
|
|
class Kernel;
|
|
class GameFeatures;
|
|
class Console;
|
|
class AudioPlayer;
|
|
class SoundCommandParser;
|
|
class EventManager;
|
|
class SegManager;
|
|
class ScriptPatcher;
|
|
class Sync;
|
|
|
|
class GfxAnimate;
|
|
class GfxCache;
|
|
class GfxCompare;
|
|
class GfxControls16;
|
|
class GfxControls32;
|
|
class GfxCoordAdjuster;
|
|
class GfxCursor;
|
|
class GfxMacIconBar;
|
|
class GfxMenu;
|
|
class GfxPaint16;
|
|
class GfxPaint32;
|
|
class GfxPalette;
|
|
class GfxPalette32;
|
|
class GfxRemap;
|
|
class GfxRemap32;
|
|
class GfxPorts;
|
|
class GfxScreen;
|
|
class GfxText16;
|
|
class GfxText32;
|
|
class GfxTransitions;
|
|
|
|
#ifdef ENABLE_SCI32
|
|
// TODO: Move RobotDecoder to Video32
|
|
class RobotDecoder;
|
|
class GfxFrameout;
|
|
class Audio32;
|
|
class Video32;
|
|
class GfxTransitions32;
|
|
#endif
|
|
|
|
// our engine debug levels
|
|
enum kDebugLevels {
|
|
kDebugLevelError = 1 << 0,
|
|
kDebugLevelNodes = 1 << 1,
|
|
kDebugLevelGraphics = 1 << 2,
|
|
kDebugLevelStrings = 1 << 3,
|
|
kDebugLevelMemory = 1 << 4,
|
|
kDebugLevelFuncCheck = 1 << 5,
|
|
kDebugLevelBresen = 1 << 6,
|
|
kDebugLevelSound = 1 << 7,
|
|
kDebugLevelBaseSetter = 1 << 8,
|
|
kDebugLevelParser = 1 << 9,
|
|
kDebugLevelSaid = 1 << 10,
|
|
kDebugLevelFile = 1 << 11,
|
|
kDebugLevelTime = 1 << 12,
|
|
kDebugLevelRoom = 1 << 13,
|
|
kDebugLevelAvoidPath = 1 << 14,
|
|
kDebugLevelDclInflate = 1 << 15,
|
|
kDebugLevelVM = 1 << 16,
|
|
kDebugLevelScripts = 1 << 17,
|
|
kDebugLevelGC = 1 << 18,
|
|
kDebugLevelResMan = 1 << 19,
|
|
kDebugLevelOnStartup = 1 << 20,
|
|
kDebugLevelDebugMode = 1 << 21,
|
|
kDebugLevelScriptPatcher = 1 << 22,
|
|
kDebugLevelWorkarounds = 1 << 23
|
|
};
|
|
|
|
enum SciGameId {
|
|
GID_ASTROCHICKEN,
|
|
GID_CAMELOT,
|
|
GID_CASTLEBRAIN,
|
|
GID_CHEST,
|
|
GID_CHRISTMAS1988,
|
|
GID_CHRISTMAS1990,
|
|
GID_CHRISTMAS1992,
|
|
GID_CNICK_KQ,
|
|
GID_CNICK_LAURABOW,
|
|
GID_CNICK_LONGBOW,
|
|
GID_CNICK_LSL,
|
|
GID_CNICK_SQ,
|
|
GID_ECOQUEST,
|
|
GID_ECOQUEST2,
|
|
GID_FAIRYTALES,
|
|
GID_FREDDYPHARKAS,
|
|
GID_FUNSEEKER,
|
|
GID_GK1DEMO, // We have a separate ID for GK1 demo, because it's actually a completely different game (SCI1.1 vs SCI2/SCI2.1)
|
|
GID_GK1,
|
|
GID_GK2,
|
|
GID_HOYLE1,
|
|
GID_HOYLE2,
|
|
GID_HOYLE3,
|
|
GID_HOYLE4,
|
|
GID_HOYLE5,
|
|
GID_ICEMAN,
|
|
GID_INNDEMO,
|
|
GID_ISLANDBRAIN,
|
|
GID_JONES,
|
|
GID_KQ1,
|
|
GID_KQ4,
|
|
GID_KQ5,
|
|
GID_KQ6,
|
|
GID_KQ7,
|
|
GID_KQUESTIONS,
|
|
GID_LAURABOW,
|
|
GID_LAURABOW2,
|
|
GID_LIGHTHOUSE,
|
|
GID_LONGBOW,
|
|
GID_LSL1,
|
|
GID_LSL2,
|
|
GID_LSL3,
|
|
GID_LSL5,
|
|
GID_LSL6,
|
|
GID_LSL6HIRES, // We have a separate ID for LSL6 SCI32, because it's actually a completely different game
|
|
GID_LSL7,
|
|
GID_MOTHERGOOSE, // this one is the SCI0 version
|
|
GID_MOTHERGOOSE256, // this one handles SCI1 and SCI1.1 variants, at least those 2 share a bit in common
|
|
GID_MOTHERGOOSEHIRES, // this one is the SCI2.1 hires version, completely different from the other ones
|
|
GID_MSASTROCHICKEN,
|
|
GID_PEPPER,
|
|
GID_PHANTASMAGORIA,
|
|
GID_PHANTASMAGORIA2,
|
|
GID_PQ1,
|
|
GID_PQ2,
|
|
GID_PQ3,
|
|
GID_PQ4,
|
|
GID_PQ4DEMO, // We have a separate ID for PQ4 demo, because it's actually a completely different game (SCI1.1 vs SCI2/SCI2.1)
|
|
GID_PQSWAT,
|
|
GID_QFG1,
|
|
GID_QFG1VGA,
|
|
GID_QFG2,
|
|
GID_QFG3,
|
|
GID_QFG4,
|
|
GID_QFG4DEMO, // We have a separate ID for QFG4 demo, because it's actually a completely different game (SCI1.1 vs SCI2/SCI2.1)
|
|
GID_RAMA,
|
|
GID_SHIVERS,
|
|
//GID_SHIVERS2, // Not SCI
|
|
GID_SLATER,
|
|
GID_SQ1,
|
|
GID_SQ3,
|
|
GID_SQ4,
|
|
GID_SQ5,
|
|
GID_SQ6,
|
|
GID_TORIN,
|
|
|
|
GID_FANMADE // FIXME: Do we really need/want this?
|
|
};
|
|
|
|
/**
|
|
* SCI versions
|
|
* For more information, check here:
|
|
* http://wiki.scummvm.org/index.php/Sierra_Game_Versions#SCI_Games
|
|
*/
|
|
enum SciVersion {
|
|
SCI_VERSION_NONE,
|
|
SCI_VERSION_0_EARLY, // KQ4 early, LSL2 early, XMAS card 1988
|
|
SCI_VERSION_0_LATE, // KQ4, LSL2, LSL3, SQ3 etc
|
|
SCI_VERSION_01, // KQ1 and multilingual games (S.old.*)
|
|
SCI_VERSION_1_EGA_ONLY, // SCI 1 EGA with parser (i.e. QFG2 only)
|
|
SCI_VERSION_1_EARLY, // KQ5 floppy, SQ4 floppy, XMAS card 1990, Fairy tales, Jones floppy
|
|
SCI_VERSION_1_MIDDLE, // LSL1, Jones CD
|
|
SCI_VERSION_1_LATE, // Dr. Brain 1, EcoQuest 1, Longbow, PQ3, SQ1, LSL5, KQ5 CD
|
|
SCI_VERSION_1_1, // Dr. Brain 2, EcoQuest 1 CD, EcoQuest 2, KQ6, QFG3, SQ4CD, XMAS 1992 and many more
|
|
SCI_VERSION_2, // GK1, PQ4 floppy, QFG4 floppy
|
|
SCI_VERSION_2_1_EARLY, // GK2 demo, KQ7 1.4/1.51, LSL6 hires, PQ4CD, QFG4 floppy
|
|
SCI_VERSION_2_1_MIDDLE, // GK2, KQ7 2.00b, MUMG Deluxe, Phantasmagoria 1, PQ:SWAT, QFG4CD, Shivers 1, SQ6, Torin
|
|
SCI_VERSION_2_1_LATE, // demos of LSL7, Lighthouse, RAMA
|
|
SCI_VERSION_3 // LSL7, Lighthouse, RAMA, Phantasmagoria 2
|
|
};
|
|
|
|
/** Supported languages */
|
|
enum kLanguage {
|
|
K_LANG_NONE = 0,
|
|
K_LANG_ENGLISH = 1,
|
|
K_LANG_FRENCH = 33,
|
|
K_LANG_SPANISH = 34,
|
|
K_LANG_ITALIAN = 39,
|
|
K_LANG_GERMAN = 49,
|
|
K_LANG_JAPANESE = 81,
|
|
K_LANG_PORTUGUESE = 351
|
|
};
|
|
|
|
class SciEngine : public Engine {
|
|
friend class Console;
|
|
public:
|
|
SciEngine(OSystem *syst, const ADGameDescription *desc, SciGameId gameId);
|
|
~SciEngine();
|
|
|
|
// Engine APIs
|
|
virtual Common::Error run();
|
|
bool hasFeature(EngineFeature f) const;
|
|
void pauseEngineIntern(bool pause);
|
|
virtual GUI::Debugger *getDebugger();
|
|
Console *getSciDebugger();
|
|
Common::Error loadGameState(int slot);
|
|
Common::Error saveGameState(int slot, const Common::String &desc);
|
|
bool canLoadGameStateCurrently();
|
|
bool canSaveGameStateCurrently();
|
|
void syncSoundSettings();
|
|
uint32 getTickCount();
|
|
void setTickCount(const uint32 ticks);
|
|
|
|
/**
|
|
* Syncs the audio options of the ScummVM launcher (speech, subtitles or
|
|
* both) with the in-game audio options of certain CD game versions. For
|
|
* some games, this allows simultaneous playing of speech and subtitles,
|
|
* even if the original games didn't support this feature.
|
|
*
|
|
* SCI1.1 games which support simultaneous speech and subtitles:
|
|
* - EcoQuest 1 CD
|
|
* - Leisure Suit Larry 6 CD
|
|
* SCI1.1 games which don't support simultaneous speech and subtitles,
|
|
* and we add this functionality in ScummVM:
|
|
* - Space Quest 4 CD
|
|
* - Freddy Pharkas CD
|
|
* - Laura Bow 2 CD
|
|
* SCI1.1 games which don't support simultaneous speech and subtitles,
|
|
* and we haven't added any extra functionality in ScummVM because extra
|
|
* script patches are needed:
|
|
* - King's Quest 6 CD
|
|
*/
|
|
bool speechAndSubtitlesEnabled();
|
|
void syncIngameAudioOptions();
|
|
void updateScummVMAudioOptions();
|
|
|
|
const SciGameId &getGameId() const { return _gameId; }
|
|
const char *getGameIdStr() const;
|
|
int getResourceVersion() const;
|
|
Common::Language getLanguage() const;
|
|
Common::Platform getPlatform() const;
|
|
bool isDemo() const;
|
|
bool isCD() const;
|
|
bool forceHiresGraphics() const;
|
|
|
|
/** Returns true if the game's original platform is big-endian. */
|
|
bool isBE() const;
|
|
|
|
bool hasMacIconBar() const;
|
|
|
|
inline ResourceManager *getResMan() const { return _resMan; }
|
|
inline ScriptPatcher *getScriptPatcher() const { return _scriptPatcher; }
|
|
inline Kernel *getKernel() const { return _kernel; }
|
|
inline EngineState *getEngineState() const { return _gamestate; }
|
|
inline Vocabulary *getVocabulary() const { return _vocabulary; }
|
|
inline EventManager *getEventManager() const { return _eventMan; }
|
|
inline reg_t getGameObject() const { return _gameObjectAddress; } // Gets the game object VM address
|
|
|
|
Common::RandomSource &getRNG() { return _rng; }
|
|
|
|
Common::String getSavegameName(int nr) const;
|
|
Common::String getSavegamePattern() const;
|
|
|
|
Common::String getFilePrefix() const;
|
|
|
|
/** Prepend 'TARGET-' to the given filename. */
|
|
Common::String wrapFilename(const Common::String &name) const;
|
|
|
|
/** Remove the 'TARGET-' prefix of the given filename, if present. */
|
|
Common::String unwrapFilename(const Common::String &name) const;
|
|
|
|
const char *getGameObjectName(); // Gets the name of the game object (should only be used for identifying fanmade games)
|
|
|
|
/**
|
|
* Checks if we are in a QfG import screen, where special handling
|
|
* of file-listings is performed.
|
|
*/
|
|
int inQfGImportRoom() const;
|
|
|
|
void sleep(uint32 msecs);
|
|
|
|
void scriptDebug();
|
|
bool checkExportBreakpoint(uint16 script, uint16 pubfunct);
|
|
bool checkSelectorBreakpoint(BreakpointType breakpointType, reg_t send_obj, int selector);
|
|
|
|
void patchGameSaveRestore();
|
|
|
|
public:
|
|
|
|
/**
|
|
* Processes a multilanguage string based on the current language settings and
|
|
* returns a string that is ready to be displayed.
|
|
* @param str the multilanguage string
|
|
* @param sep optional seperator between main language and subtitle language,
|
|
* if NULL is passed no subtitle will be added to the returned string
|
|
* @return processed string
|
|
*/
|
|
Common::String strSplitLanguage(const char *str, uint16 *splitLanguage, const char *sep = "\r----------\r");
|
|
Common::String strSplit(const char *str, const char *sep = "\r----------\r") {
|
|
return strSplitLanguage(str, NULL, sep);
|
|
}
|
|
|
|
kLanguage getSciLanguage();
|
|
void setSciLanguage(kLanguage lang);
|
|
void setSciLanguage();
|
|
|
|
Common::String getSciLanguageString(const Common::String &str, kLanguage lang, kLanguage *lang2 = NULL, uint16 *languageSplitter = NULL) const;
|
|
|
|
// Check if vocabulary needs to get switched (in multilingual parser games)
|
|
void checkVocabularySwitch();
|
|
|
|
// Initializes ports and paint16 for non-sci32 games, also sets default palette
|
|
void initGraphics();
|
|
|
|
public:
|
|
GfxAnimate *_gfxAnimate; // Animate for 16-bit gfx
|
|
GfxCache *_gfxCache;
|
|
GfxCompare *_gfxCompare;
|
|
GfxControls16 *_gfxControls16; // Controls for 16-bit gfx
|
|
GfxControls32 *_gfxControls32; // Controls for 32-bit gfx
|
|
GfxCoordAdjuster *_gfxCoordAdjuster;
|
|
GfxCursor *_gfxCursor;
|
|
GfxMenu *_gfxMenu; // Menu for 16-bit gfx
|
|
GfxPalette *_gfxPalette16;
|
|
GfxPalette32 *_gfxPalette32; // Palette for 32-bit gfx
|
|
GfxRemap *_gfxRemap16; // Remapping for the QFG4 demo
|
|
GfxRemap32 *_gfxRemap32; // Remapping for 32-bit gfx
|
|
GfxPaint16 *_gfxPaint16; // Painting in 16-bit gfx
|
|
GfxPaint32 *_gfxPaint32; // Painting in 32-bit gfx
|
|
GfxPorts *_gfxPorts; // Port managment for 16-bit gfx
|
|
GfxScreen *_gfxScreen;
|
|
GfxText16 *_gfxText16;
|
|
GfxText32 *_gfxText32;
|
|
GfxTransitions *_gfxTransitions; // transitions between screens for 16-bit gfx
|
|
GfxMacIconBar *_gfxMacIconBar; // Mac Icon Bar manager
|
|
|
|
#ifdef ENABLE_SCI32
|
|
Audio32 *_audio32;
|
|
Video32 *_video32;
|
|
RobotDecoder *_robotDecoder;
|
|
GfxFrameout *_gfxFrameout; // kFrameout and the like for 32-bit gfx
|
|
GfxTransitions32 *_gfxTransitions32;
|
|
#endif
|
|
|
|
AudioPlayer *_audio;
|
|
Sync *_sync;
|
|
SoundCommandParser *_soundCmd;
|
|
GameFeatures *_features;
|
|
|
|
opcode_format (*_opcode_formats)[4];
|
|
|
|
DebugState _debugState;
|
|
|
|
Common::MacResManager *getMacExecutable() { return &_macExecutable; }
|
|
|
|
private:
|
|
/**
|
|
* Initializes a SCI game
|
|
* This function must be run before script_run() is executed. Graphics data
|
|
* is initialized iff s->gfx_state != NULL.
|
|
* @param[in] s The state to operate on
|
|
* @return true on success, false if an error occurred.
|
|
*/
|
|
bool initGame();
|
|
|
|
/**
|
|
* Runs a SCI game
|
|
* This is the main function for SCI games. It takes a valid state, loads
|
|
* script 0 to it, finds the game object, allocates a stack, and runs the
|
|
* init method of the game object. In layman's terms, this runs a SCI game.
|
|
* @param[in] s Pointer to the pointer of the state to operate on
|
|
*/
|
|
void runGame();
|
|
|
|
/**
|
|
* Uninitializes an initialized SCI game
|
|
* This function should be run after each script_run() call.
|
|
* @param[in] s The state to operate on
|
|
*/
|
|
void exitGame();
|
|
|
|
/**
|
|
* Loads the Mac executable for SCI1 games
|
|
*/
|
|
void loadMacExecutable();
|
|
|
|
void initStackBaseWithSelector(Selector selector);
|
|
|
|
bool gameHasFanMadePatch();
|
|
void setLauncherLanguage();
|
|
|
|
const ADGameDescription *_gameDescription;
|
|
const SciGameId _gameId;
|
|
ResourceManager *_resMan; /**< The resource manager */
|
|
ScriptPatcher *_scriptPatcher; /**< The script patcher */
|
|
EngineState *_gamestate;
|
|
Kernel *_kernel;
|
|
Vocabulary *_vocabulary;
|
|
int16 _vocabularyLanguage;
|
|
EventManager *_eventMan;
|
|
reg_t _gameObjectAddress; /**< Pointer to the game object */
|
|
Console *_console;
|
|
Common::RandomSource _rng;
|
|
Common::MacResManager _macExecutable;
|
|
bool _forceHiresGraphics; // user-option for GK1, KQ6, PQ4
|
|
};
|
|
|
|
|
|
/**
|
|
* Global instance of the SciEngine class, similar to g_engine.
|
|
* This is a hackish way to make all central components available
|
|
* everywhere. Ideally, we would get rid of this again in the future,
|
|
* but for now it's a pragmatic and simple way to achieve the goal.
|
|
*/
|
|
extern SciEngine *g_sci;
|
|
|
|
/**
|
|
* Convenience function to obtain the active SCI version.
|
|
*/
|
|
SciVersion getSciVersion();
|
|
|
|
/**
|
|
* Same as above, but this version doesn't assert on unknown SCI versions.
|
|
* Only used by the fallback detector
|
|
*/
|
|
SciVersion getSciVersionForDetection();
|
|
|
|
/**
|
|
* Convenience function converting an SCI version into a human-readable string.
|
|
*/
|
|
const char *getSciVersionDesc(SciVersion version);
|
|
|
|
} // End of namespace Sci
|
|
|
|
#endif // SCI_SCI_H
|