ScummVM API documentation
scumm.h
1 /* ScummVM - Graphic Adventure Engine
2  *
3  * ScummVM is the legal property of its developers, whose names
4  * are too numerous to list here. Please refer to the COPYRIGHT
5  * file distributed with this source distribution.
6  *
7  * This program is free software: you can redistribute it and/or modify
8  * it under the terms of the GNU General Public License as published by
9  * the Free Software Foundation, either version 3 of the License, or
10  * (at your option) any later version.
11  *
12  * This program is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15  * GNU General Public License for more details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with this program. If not, see <http://www.gnu.org/licenses/>.
19  *
20  */
21 
22 #ifndef SCUMM_SCUMM_H
23 #define SCUMM_SCUMM_H
24 
25 #include "engines/engine.h"
26 
27 #include "common/endian.h"
28 #include "common/events.h"
29 #include "common/file.h"
30 #include "common/savefile.h"
31 #include "common/keyboard.h"
32 #include "common/mutex.h"
33 #include "common/random.h"
34 #include "common/rect.h"
35 #include "common/rendermode.h"
36 #include "common/str.h"
37 #include "common/textconsole.h"
38 #include "common/text-to-speech.h"
39 #include "graphics/surface.h"
40 #include "graphics/sjis.h"
41 #include "graphics/palette.h"
42 
43 #include "scumm/file.h"
44 #include "scumm/gfx.h"
45 #include "scumm/detection.h"
46 #include "scumm/script.h"
47 #include "scumm/serializer.h"
48 
49 #ifdef __DS__
50 /* This disables the dual layer mode which is used in FM-Towns versions
51  * of SCUMM games and which emulates the behavior of the original code.
52  * The only purpose is code size reduction for certain backends.
53  * SCUMM 3 (FM-Towns) games will run in English in normal (DOS VGA) mode,
54  * which should work just fine in most situations. Some glitches might
55  * occur. Japanese mode and SCUMM 5 FM-Towns games will not work without
56  * dual layer (and 16 bit color) support.
57  */
58 #define DISABLE_TOWNS_DUAL_LAYER_MODE
59 #endif
60 
61 namespace GUI {
62 class Dialog;
63 }
64 using GUI::Dialog;
65 namespace Common {
66 class SeekableReadStream;
67 class WriteStream;
68 class SeekableWriteStream;
69 }
70 namespace Graphics {
71 class FontSJIS;
72 }
73 
86 namespace Scumm {
87 
88 class Actor;
89 class BaseCostumeLoader;
90 class BaseCostumeRenderer;
91 class BaseScummFile;
92 class CharsetRenderer;
93 class IMuse;
94 class IMuseDigital;
95 class MacGui;
96 class MusicEngine;
97 class Player_Towns;
98 class ScummEngine;
99 class ScummDebugger;
100 class Sound;
101 class Localizer;
102 class GlyphRenderer_v7;
103 
104 struct Box;
105 struct BoxCoords;
106 struct FindObjectInRoom;
107 
108 // Use g_scumm from error() ONLY
109 extern ScummEngine *g_scumm;
110 
111 /* System Wide Constants */
112 enum {
113  NUM_SENTENCE = 6,
114  NUM_SHADOW_PALETTE = 8
115 };
116 
117 /* SCUMM Debug Channels */
118 void debugC(int level, MSVC_PRINTF const char *s, ...) GCC_PRINTF(2, 3);
119 
120 struct VerbSlot;
121 struct ObjectData;
122 
123 enum {
131 
137 
144 
153  //
154 };
155 
156 enum {
157  MBS_LEFT_CLICK = 0x8000,
158  MBS_RIGHT_CLICK = 0x4000,
159  MBS_MOUSE_MASK = (MBS_LEFT_CLICK | MBS_RIGHT_CLICK),
160  MBS_MAX_KEY = 0x0200
161 };
162 
163 struct SentenceTab {
164  byte verb;
165  byte preposition;
166  uint16 objectA;
167  uint16 objectB;
168  uint8 freezeCount;
169 };
170 
171 struct StringSlot {
172  int16 xpos;
173  int16 ypos;
174  int16 right;
175  int16 height;
176  byte color;
177  byte charset;
178  bool center;
179  bool overhead;
180  bool no_talk_anim;
181  bool wrapping;
182 };
183 
185  // The 'default' values for this string slot. This is used so that the
186  // string slot can temporarily be set to different values, and then be
187  // easily reset to a previously set default.
188  StringSlot _default;
189 
190  void saveDefault() {
191  StringSlot &s = *this;
192  _default = s;
193  }
194 
195  void loadDefault() {
196  StringSlot &s = *this;
197  s = _default;
198  }
199 };
200 
202  bool _screenScroll;
203  uint _objectRedrawCount;
204  uint _objectStripRedrawCount;
205  uint _actorRedrawCount;
206  uint _actorLimbRedrawDrawCount;
207 
208 };
209 
210 enum WhereIsObject {
211  WIO_NOT_FOUND = -1,
212  WIO_INVENTORY = 0,
213  WIO_ROOM = 1,
214  WIO_GLOBAL = 2,
215  WIO_LOCAL = 3,
216  WIO_FLOBJECT = 4
217 };
218 
220  uint32 date;
221  uint16 time;
222  uint32 playtime;
223 };
224 
225 enum UserStates {
226  USERSTATE_SET_FREEZE = 0x01, // freeze scripts if USERSTATE_FREEZE_ON is set, unfreeze otherwise
227  USERSTATE_SET_CURSOR = 0x02, // shows cursor if USERSTATE_CURSOR_ON is set, hides it otherwise
228  USERSTATE_SET_IFACE = 0x04, // change user-interface (sentence-line, inventory, verb-area)
229  USERSTATE_FREEZE_ON = 0x08, // only interpreted if USERSTATE_SET_FREEZE is set
230  USERSTATE_CURSOR_ON = 0x10, // only interpreted if USERSTATE_SET_CURSOR is set
231  USERSTATE_IFACE_SENTENCE = 0x20, // only interpreted if USERSTATE_SET_IFACE is set
232  USERSTATE_IFACE_INVENTORY = 0x40, // only interpreted if USERSTATE_SET_IFACE is set
233  USERSTATE_IFACE_VERBS = 0x80 // only interpreted if USERSTATE_SET_IFACE is set
234 };
235 
236 #define USERSTATE_IFACE_ALL (USERSTATE_IFACE_SENTENCE | USERSTATE_IFACE_INVENTORY | USERSTATE_IFACE_VERBS)
237 
243 enum ResType {
244  rtInvalid = 0,
245  rtFirst = 1,
246  rtRoom = 1,
247  rtScript = 2,
248  rtCostume = 3,
249  rtSound = 4,
250  rtInventory = 5,
251  rtCharset = 6,
252  rtString = 7,
253  rtVerb = 8,
254  rtActorName = 9,
255  rtBuffer = 10,
256  rtScaleTable = 11,
257  rtTemp = 12,
258  rtFlObject = 13,
259  rtMatrix = 14,
260  rtBox = 15,
261  rtObjectName = 16,
262  rtRoomScripts = 17,
263  rtRoomImage = 18,
264  rtImage = 19,
265  rtTalkie = 20,
266  rtSpoolBuffer = 21,
267  rtLast = 21
268 };
269 
270 typedef uint16 ResId;
271 
272 class ResourceManager;
273 
314 #define PIT_BASE_FREQUENCY 1193182.0 // In Hz
315 #define PIT_V1_DIVISOR 65536.0
316 #define PIT_V2_4_DIVISOR 5041.0
317 #define PIT_V5_6_ORCHESTRATOR_DIVISOR 4096.0
318 #define PIT_V5_6_SUBTIMER_INC 3433.0
319 #define PIT_V5_SUBTIMER_THRESH 4167.0
320 #define PIT_V6_SAMNMAX_SUBTIMER_THRESH 4167.0
321 #define PIT_V6_DOTT_SUBTIMER_THRESH 4237.0
322 #define PIT_V7_ORCHESTRATOR_DIVISOR 3977.0
323 #define PIT_V7_SUBTIMER_INC 3977.0
324 #define PIT_V7_SUBTIMER_THRESH 4971.0
325 
326 #define PIT_HE_PUTT_PUTT_DIVISOR 9362.0
327 #define PIT_HE_FATTY_BEAR_DIVISOR 21845.0
328 
329 #define LOOM_STEAM_CDDA_RATE 240.0
330 
344 #define AMIGA_NTSC_VBLANK_RATE 240.0
345 #define AMIGA_PAL_VBLANK_RATE 200.0
346 
351 #define GAME_PROPER_SAVE 201
352 #define GAME_FAILED_SAVE 202
353 #define GAME_PROPER_LOAD 203
354 #define GAME_FAILED_LOAD 204
355 
360 #define GUI_PAGE_MAIN 0
361 #define GUI_PAGE_SAVE 1
362 #define GUI_PAGE_LOAD 2
363 #define GUI_PAGE_RESTART 3 // Sega CD
364 #define GUI_PAGE_CODE_CONFIRM 4 // Sega CD
365 #define GUI_PAGE_INVALID_CODE 5 // Sega CD
366 
367 #define GUI_CTRL_FIRST_SG 1
368 #define GUI_CTRL_LAST_SG 9
369 #define GUI_CTRL_SAVE_BUTTON 10
370 #define GUI_CTRL_LOAD_BUTTON 11
371 #define GUI_CTRL_PLAY_BUTTON 12
372 #define GUI_CTRL_QUIT_BUTTON 13
373 #define GUI_CTRL_OK_BUTTON 14
374 #define GUI_CTRL_CANCEL_BUTTON 15
375 #define GUI_CTRL_ARROW_UP_BUTTON 16
376 #define GUI_CTRL_ARROW_DOWN_BUTTON 17
377 #define GUI_CTRL_PATH_BUTTON 18
378 #define GUI_CTRL_MUSIC_SLIDER 19
379 #define GUI_CTRL_SPEECH_SLIDER 20
380 #define GUI_CTRL_SFX_SLIDER 21
381 #define GUI_CTRL_TEXT_SPEED_SLIDER 22
382 #define GUI_CTRL_DISPLAY_TEXT_CHECKBOX 23
383 #define GUI_CTRL_SPOOLED_MUSIC_CHECKBOX 24
384 #define GUI_CTRL_OUTER_BOX 26
385 #define GUI_CTRL_INNER_BOX 27
386 
387 // Sega CD
388 #define GUI_CTRL_NUMPAD_1 1
389 #define GUI_CTRL_NUMPAD_2 2
390 #define GUI_CTRL_NUMPAD_3 3
391 #define GUI_CTRL_NUMPAD_4 4
392 #define GUI_CTRL_NUMPAD_5 5
393 #define GUI_CTRL_NUMPAD_6 6
394 #define GUI_CTRL_NUMPAD_7 7
395 #define GUI_CTRL_NUMPAD_8 8
396 #define GUI_CTRL_NUMPAD_9 9
397 #define GUI_CTRL_NUMPAD_0 10
398 #define GUI_CTRL_RESTART_BUTTON 13
399 #define GUI_CTRL_ARROW_LEFT_BUTTON 16
400 #define GUI_CTRL_ARROW_RIGHT_BUTTON 17
401 #define GUI_CTRL_NUMPAD_BACK 23
402 
403 enum GUIString {
404  gsPause = 0,
405  gsVersion = 1,
406  gsTextSpeedSlider = 2,
407  gsRestart = 3,
408  gsQuitPrompt = 4,
409  gsSave = 5,
410  gsLoad = 6,
411  gsPlay = 7,
412  gsCancel = 8,
413  gsQuit = 9,
414  gsOK = 10,
415  gsMustName = 11,
416  gsGameNotSaved = 12,
417  gsGameNotLoaded = 13,
418  gsSaving = 14,
419  gsLoading = 15,
420  gsNamePrompt = 16,
421  gsSelectLoadPrompt = 17,
422  gsReplacePrompt = 18,
423  gsYes = 20,
424  gsNo = 21,
425  gsIMuseBuffer = 22,
426  gsVoiceAndText = 23,
427  gsTextDisplayOnly = 24,
428  gsVoiceOnly = 25,
429  gsYesKey = 26,
430  gsMusicVolumeSlider = 27,
431  gsVoiceVolumeSlider = 28,
432  gsSfxVolumeSlider = 29,
433  gsHeap = 30,
434  gsSavePath = 31,
435  gsTitle = 32,
436  gsDisabled = 33,
437  gsMusic = 34,
438  gsVoice = 35,
439  gsSfx = 36,
440  gsTextSpeed = 37,
441  gsDisplayText = 38,
442  gsSpooledMusic = 39,
443  gsInsertSaveDisk = 40,
444  gsSnapOn = 41,
445  gsSnapOff = 42,
446  gsRecalJoystick = 43,
447  gsMouseMode = 44,
448  gsMouseOn = 45,
449  gsMouseOff = 46,
450  gsJoystickOn = 47,
451  gsJoystickOff = 48,
452  gsSoundsOn = 49,
453  gsSoundsOff = 50,
454  gsVGAMode = 51,
455  gsEGAMode = 52,
456  gsCGAMode = 53,
457  gsHerculesMode = 54,
458  gsTandyMode = 55,
459  gsCurrentPasscode = 56,
460  gsEnterPasscode = 57,
461  gsConfirmPasscode = 58,
462  gsInvalidPasscode = 59,
463  gsSlowFast = 60,
464  gsRestartGame = 61,
465  gsHeapExt = 62,
466 };
467 
469  int relativeCenterX;
470  int relativeCenterY;
471  int xPos;
472  int yPos;
473  int normalFillColor;
474  int topLineColor;
475  int bottomLineColor;
476  int leftLineColor;
477  int rightLineColor;
478  int normalTextColor;
479  int highlightedTextColor;
480  int highlightedFillColor;
481  bool centerText;
482  Common::String label;
483 #ifdef USE_TTS
484  Common::String alternateTTSLabel;
485 #endif
486  bool doubleLinesFlag;
487 };
488 
489 enum ScummAction {
490  kScummActionNone,
491  kScummActionInsaneDownLeft,
492  kScummActionInsaneDown,
493  kScummActionInsaneDownRight,
494  kScummActionInsaneLeft,
495  kScummActionInsaneRight,
496  kScummActionInsaneUpLeft,
497  kScummActionInsaneUp,
498  kScummActionInsaneUpRight,
499  kScummActionInsaneAttack,
500  kScummActionInsaneSwitch,
501  kScummActionInsaneCheat,
502 
503  kScummActionCount
504 };
505 
506 extern const char *const insaneKeymapId;
507 
511 class ScummEngine : public Engine, public Common::Serializable {
512  friend class ScummDebugger;
513  friend class CharsetRenderer;
514  friend class CharsetRendererClassic;
515  friend class CharsetRendererTownsClassic;
516  friend class ResourceManager;
517  friend class MacGuiImpl;
518  friend class MacIndy3Gui;
519  friend class MacLoomGui;
520  friend class MacV5Gui;
521  friend class MacV6Gui;
522  friend class LogicHEBasketball;
523 
524 public:
525  /* Put often used variables at the top.
526  * That results in a shorter form of the opcode
527  * on some architectures. */
528  IMuse *_imuse = nullptr;
529  IMuseDigital *_imuseDigital = nullptr;
530  MusicEngine *_musicEngine = nullptr;
531  Player_Towns *_townsPlayer = nullptr;
532  Sound *_sound = nullptr;
533 
534  VerbSlot *_verbs = nullptr;
535  ObjectData *_objs = nullptr;
536 
537  // Core variables
538  GameSettings _game;
539  uint8 _gameMD5[16];
540 
543 
545  Gdi *_gdi = nullptr;
546 
548  ResourceManager *_res = nullptr;
549  int _insideCreateResource = 0; // Counter for HE sound
550 
551  bool _useOriginalGUI = true;
552  bool _enableAudioOverride = false;
553  bool _enableCOMISong = false;
554  bool _isAmigaPALSystem = false;
555  bool _quitFromScriptCmd = false;
556  bool _isHE995 = false;
557  bool _enableHECompetitiveOnlineMods = false;
558 
559  Common::Keymap *_insaneKeymap;
560 
561 protected:
563 
564  bool _needsSoundUnpause = false;
565 
566 public:
567  // Constructor / Destructor
568  ScummEngine(OSystem *syst, const DetectorResult &dr);
569  ~ScummEngine() override;
570 
571  // Engine APIs
572  Common::Error init();
573  Common::Error go();
574  Common::Error run() override {
575  Common::Error err;
576  err = init();
577  if (err.getCode() != Common::kNoError)
578  return err;
579  return go();
580  }
581 
582  void errorString(const char *buf_input, char *buf_output, int buf_output_size) override;
583  bool hasFeature(EngineFeature f) const override;
584  bool gameSupportsQuitDialogOverride() const;
585  void syncSoundSettings() override;
586 
587  Common::Error loadGameState(int slot) override;
588  bool canLoadGameStateCurrently(Common::U32String *msg = nullptr) override;
589  Common::Error saveGameState(int slot, const Common::String &desc, bool isAutosave = false) override;
590  bool canSaveGameStateCurrently(Common::U32String *msg = nullptr) override;
591 
592  void pauseEngineIntern(bool pause) override;
593 
594 protected:
595  virtual void setupScumm(const Common::Path &macResourceFile);
596  virtual void resetScumm();
597 
598  virtual void setupScummVars();
599  virtual void resetScummVars();
600  void setVideoModeVarToCurrentConfig();
601  void setSoundCardVarToCurrentConfig();
602 
603  void setupCharsetRenderer(const Common::Path &macFontFile);
604  void setupCostumeRenderer();
605 
606  virtual void loadLanguageBundle();
607  void loadCJKFont();
608  void loadKorFont();
609  void setupMusic(int midi);
610  void setTalkSpeed(int talkspeed);
611  int getTalkSpeed();
612 
613  // Scumm main loop & helper functions.
614  virtual void scummLoop(int delta);
615  virtual void scummLoop_updateScummVars();
616  virtual void scummLoop_handleSaveLoad();
617  virtual void scummLoop_handleDrawing();
618  virtual void scummLoop_handleActors() = 0;
619  virtual void scummLoop_handleEffects();
620  virtual void scummLoop_handleSound();
621 
622  virtual void runBootscript();
623 
624  virtual void terminateSaveMenuScript() {};
625 
626  // Event handling
627 public:
628  void beginTextInput();
629  void endTextInput();
630 
631  void parseEvents(); // Used by IMuseDigital::startSound
632 protected:
633  virtual void parseEvent(Common::Event event);
634 
635  void waitForTimer(int quarterFrames, bool freezeMacGui = false);
636  uint32 _lastWaitTime;
637 
638  void setTimerAndShakeFrequency();
639 
645  uint32 getIntegralTime(double fMsecs);
646  double _msecFractParts = 0.0;
647 
648  virtual void processInput();
649  virtual void processKeyboard(Common::KeyState lastKeyHit);
650  virtual void clearClickedStatus();
651 
652  // Cursor/palette
653  virtual void updateCursor();
654  virtual void animateCursor() {}
655  virtual void updatePalette();
656  virtual void setDefaultCursor() {};
657  virtual void setCursorTransparency(int a) {};
658  virtual void resetCursors() {}
659  virtual void setCursorHotspot(int x, int y) {}
660  virtual void setCursorFromBuffer(const byte *ptr, int width, int height, int pitch, bool preventScale = false) {}
661 
662 public:
663  void pauseGame();
664  void restart();
665  bool isUsingOriginalGUI() const;
666  bool isMessageBannerActive(); // For Indy4 Jap character shadows
667 
668  bool _isIndy4Jap = false;
669 
670 protected:
671  Dialog *_pauseDialog = nullptr;
672  Dialog *_messageDialog = nullptr;
673  Dialog *_versionDialog = nullptr;
674 
675  void confirmExitDialog();
676  void confirmRestartDialog();
677  void pauseDialog();
678  void messageDialog(const Common::U32String &message);
679  void versionDialog();
680 
681  // Original GUI
682  int32 _bannerColors[50]; // Colors for the original GUI
683  byte *_bannerMem = nullptr;
684  uint32 _bannerMemSize = 0;
685  int _bannerSaveYStart = 0;
686 
687  bool _messageBannerActive = false;
688  bool _comiQuitMenuIsOpen = false;
689  bool _closeBannerAndQueryQuitFlag = false;
690 
691  // The followings are needed for MI1 FM-Towns
692  byte *_textSurfBannerMem = nullptr;
693  uint32 _textSurfBannerMemSize = 0;
694 
695  InternalGUIControl _internalGUIControls[30];
696 
697  // Special GUI strings
698  const char _emptyMsg[1] = {'\0'};
699  const char _uncheckedBox[2] = {' ', '\0'};
700  const char _checkedBox[2] = {'x', '\0'};
701  const char _arrowUp[2] = {'\x18', '\0'};
702  const char _arrowDown[2] = {'\x19', '\0'};
703  const char _arrowLeft[2] = {'\x3c', '\0'};
704  const char _arrowRight[2] = {'\x3d', '\0'};
705 
706  Common::StringArray _savegameNames;
707  int _menuPage = 0;
708  int _mainMenuSavegameLabel = 1;
709  int _curDisplayedSaveSlotPage = 0;
710  int _firstSaveStateOfList = 0; // For LOOM VGA
711  bool _mainMenuIsActive = false;
712  bool _quitByGUIPrompt = false;
713  char _mainMenuMusicSlider[17];
714  char _mainMenuSpeechSlider[17];
715  char _mainMenuSfxSlider[17];
716  char _mainMenuTextSpeedSlider[17];
717  char _mainMenuSegaCDPasscode[5];
718  int _spooledMusicIsToBeEnabled = 1;
719  int _saveScriptParam = 0;
720  int _guiCursorAnimCounter = 0;
721  int _v5VoiceMode = 0;
722 
723  // Fake flags just for sub v5 GUIs
724  int _internalSpeakerSoundsAreOn = 1;
725  int _guiMouseFlag = 1;
726  int _guiJoystickFlag = 1;
727 
728  bool _mixerMutedByGUI = false;
729 
730  Graphics::Surface _savegameThumbnail;
731  byte *_tempTextSurface = nullptr;
732  byte *_tempMainSurface = nullptr;
733  byte *_tempVerbSurface = nullptr;
734  bool _postGUICharMask = false;
735 
736  // Saved cursor pre and post GUI
737  byte *_curGrabbedCursor = nullptr;
738  int8 _oldCursorState = 0;
739  int _curCursorState = 0;
740  int _curCursorWidth = 0;
741  int _curCursorHeight = 0;
742  int _curCursorHotspotX = 0;
743  int _curCursorHotspotY = 0;
744 
745  virtual void setSnailCursor() {}
746 
747  void initBanners();
748  Common::KeyState showBannerAndPause(int bannerId, int32 waitTime, const char *msg, ...);
749  Common::KeyState showOldStyleBannerAndPause(const char *msg, int color, int32 waitTime);
750  Common::KeyState printMessageAndPause(const char *msg, int color, int32 waitTime, bool drawOnSentenceLine);
751 
752  void clearBanner();
753  void setBannerColors(int bannerId, byte r, byte g, byte b);
754  virtual int getBannerColor(int bannerId);
755  void setUpInternalGUIControl(int id, int normalFillColor, int normalTextColor,
756  int topLineColor, int bottomLineColor, int leftLineColor, int rightLineColor,
757  int highlightedTextColor, int highlightedFillColor,
758  int anchorPointX, int anchorPointY, int x, int y, const char *label, bool centerFlag, bool unknownFlag);
759  void drawInternalGUIControl(int id, bool highlightColor);
760  int getInternalGUIControlFromCoordinates(int x, int y);
761  virtual bool isSmushActive() { return false; }
762  virtual bool isInsaneActive() { return false; }
763 
764  virtual void queryQuit(bool returnToLauncher);
765  virtual void queryRestart();
766  virtual const char *getGUIString(int stringId);
767  void waitForBannerInput(int32 waitTime, Common::KeyState &ks, bool &leftBtnClicked, bool &rightBtnClicked, bool handleMouseWheel = false);
768  virtual int getGUIStringHeight(const char *str);
769  virtual int getGUIStringWidth(const char *str);
770  virtual void drawGUIText(const char *buttonString, Common::Rect *clipRect, int textXPos, int textYPos, int textColor, bool centerFlag);
771  void getSliderString(int stringId, int value, char *sliderString, int size);
772  virtual int getMusicVolume();
773  virtual int getSpeechVolume();
774  virtual int getSFXVolume();
775  virtual void setMusicVolume(int volume);
776  virtual void setSpeechVolume(int volume);
777  virtual void setSFXVolume(int volume);
778  virtual void toggleVoiceMode();
779  virtual void handleLoadDuringSmush() {}
780  virtual void setSkipVideo(int value) {}
781 
782  void showMainMenu();
783  virtual void setUpMainMenuControls();
784  void setUpMainMenuControlsSegaCD();
785  void setUpMainMenuControlsIndy4Jap();
786  void drawMainMenuControls();
787  void drawMainMenuControlsSegaCD();
788  void updateMainMenuControls();
789  void updateMainMenuControlsSegaCD();
790  void drawMainMenuTitle(const char *title);
791  bool executeMainMenuOperation(int op, int mouseX, int mouseY, bool &hasLoadedState);
792  bool executeMainMenuOperationSegaCD(int op, int mouseX, int mouseY, bool &hasLoadedState);
793  bool shouldHighlightLabelAndWait(int clickedControl);
794  void fillSavegameLabels();
795  bool canWriteGame(int slotId);
796  bool userWriteLabelRoutine(Common::KeyState &ks, bool &leftMsClicked, bool &rightMsClicked);
797  void saveCursorPreMenu();
798  void restoreCursorPostMenu();
799  void saveSurfacesPreGUI();
800  void restoreSurfacesPostGUI();
801  void showDraftsInventory();
802  void setUpDraftsInventory();
803  void drawDraftsInventory();
804 
805 public:
806  char displayMessage(MSVC_PRINTF const char *message, ...) GCC_PRINTF(2, 3);
807  bool displayMessageYesNo(MSVC_PRINTF const char *message, ...) GCC_PRINTF(2, 3);
808  bool displayMessageOKQuit(MSVC_PRINTF const char *message, ...) GCC_PRINTF(2, 3);
809 
810 protected:
811  byte _fastMode = 0;
812 
813  byte _numActors = 0;
814  Actor **_actors = nullptr; // Has _numActors elements
815  Actor **_sortedActors = nullptr;
816 
817  byte *_arraySlot = nullptr;
818  uint16 *_inventory = nullptr;
819  uint16 *_newNames = nullptr;
820 public:
821  // VAR is a wrapper around scummVar, which attempts to include additional
822  // useful information should an illegal var access be detected.
823  #define VAR(x) scummVar(x, #x, __FILE__, __LINE__)
824  int32& scummVar(byte var, const char *varName, const char *file, int line) {
825  if (var == 0xFF) {
826  error("Illegal access to variable %s in file %s, line %d", varName, file, line);
827  }
828  return _scummVars[var];
829  }
830  int32 scummVar(byte var, const char *varName, const char *file, int line) const {
831  if (var == 0xFF) {
832  error("Illegal access to variable %s in file %s, line %d", varName, file, line);
833  }
834  return _scummVars[var];
835  }
836 
837 protected:
838  int16 _varwatch = 0;
839  int32 *_roomVars = nullptr;
840  int32 *_scummVars = nullptr;
841  byte *_bitVars = nullptr;
842 
843  /* Global resource tables */
844  int _numVariables = 0;
845  int _numBitVariables = 0;
846  int _numLocalObjects = 0;
847  int _numGlobalObjects = 0;
848  int _numArray = 0;
849  int _numVerbs = 0;
850  int _numFlObject = 0;
851  int _numInventory = 0;
852  int _numNewNames = 0;
853  int _numGlobalScripts = 0;
854  int _numRoomVariables = 0;
855  int _numPalettes = 0;
856  int _numSprites = 0;
857  int _numTalkies = 0;
858  int _numWindows = 0;
859  int _HEHeapSize = 0;
860 
861 public:
862  int _numLocalScripts = 60, _numImages = 0, _numRooms = 0, _numScripts = 0, _numSounds = 0; // Used by HE games
863  int _numCostumes = 0; // FIXME - should be protected, used by Actor::remapActorPalette
864  int32 _numCharsets = 0; // FIXME - should be protected, used by CharsetRenderer
865 
866  BaseCostumeLoader *_costumeLoader = nullptr;
867  BaseCostumeRenderer *_costumeRenderer = nullptr;
868 
869  int _NESCostumeSet = 0;
870  void NES_loadCostumeSet(int n);
871  byte *_NEScostdesc = nullptr, *_NEScostlens = nullptr, *_NEScostoffs = nullptr, *_NEScostdata = nullptr;
872  byte _NESPatTable[2][4096];
873  byte _NESPalette[2][16];
874  byte _NESBaseTiles = 0;
875 
876  int _NESStartStrip = 0;
877 
878 protected:
879  int _curPalIndex = 0;
880 
881 public:
882  byte _currentRoom = 0; // FIXME - should be protected but Actor::isInCurrentRoom uses it
883  int _roomResource = 0; // FIXME - should be protected but Sound::pauseSounds uses it
884  bool _egoPositioned = false; // Used by Actor::putActor, hence public
885 
886  FilenamePattern _filenamePattern;
887 
888  virtual Common::Path generateFilename(const int room) const;
889 
890 protected:
891  Common::KeyState _keyPressed;
892  bool _keyDownMap[512]; // FIXME - 512 is a guess. it's max(kbd.ascii)
893  bool _actionMap[kScummActionCount];
894 
895  Common::Point _mouse;
896  Common::Point _virtualMouse;
897 
898  uint16 _mouseAndKeyboardStat = 0;
899  byte _leftBtnPressed = 0, _rightBtnPressed = 0;
900 
901  int _mouseWheelFlag = 0; // For original save/load dialog only
902 
903  bool _setupIsComplete = false;
904 
909  uint32 _lastInputScriptTime = 0;
910 
912  int _bootParam = 0;
913 
914  // Various options useful for debugging
915  bool _dumpScripts = false;
916  bool _hexdumpScripts = false;
917  bool _showStack = false;
918  bool _debugMode = false;
919 
920  // Save/Load class - some of this may be GUI
921  byte _saveLoadFlag = 0, _saveLoadSlot = 0;
922  uint32 _lastSaveTime = 0;
923  bool _saveTemporaryState = false;
924  bool _pauseSoundsDuringSave = true;
925  bool _loadFromLauncher = false;
926  bool _videoModeChanged = false;
927  Common::String _saveLoadFileName;
928  Common::String _saveLoadDescription;
929 
930  bool saveState(Common::SeekableWriteStream *out, bool writeHeader = true);
931  bool saveState(int slot, bool compat, Common::String &fileName);
932  bool loadState(int slot, bool compat);
933  bool loadState(int slot, bool compat, Common::String &fileName);
934  void saveLoadWithSerializer(Common::Serializer &s) override;
935  void saveResource(Common::Serializer &ser, ResType type, ResId idx);
936  void loadResource(Common::Serializer &ser, ResType type, ResId idx);
937  void loadResourceOLD(Common::Serializer &ser, ResType type, ResId idx); // "Obsolete"
938 
939  virtual int checkSoundEngineSaveDataSize(Serializer &s);
940 
941  void copyHeapSaveGameToFile(int slot, const char *saveName);
942  bool changeSavegameName(int slot, char *newName);
943  virtual Common::SeekableReadStream *openSaveFileForReading(int slot, bool compat, Common::String &fileName);
944  virtual Common::SeekableWriteStream *openSaveFileForWriting(int slot, bool compat, Common::String &fileName);
945 
946  Common::String makeSavegameName(int slot, bool temporary) const {
947  return makeSavegameName(_targetName, slot, temporary);
948  }
949 
950  int getKeyState(int key);
951  int getActionState(ScummAction action);
952 
953 public:
954  static Common::String makeSavegameName(const Common::String &target, int slot, bool temporary);
955 
956  bool getSavegameName(int slot, Common::String &desc);
957  void listSavegames(bool *marks, int num);
958 
959  void requestSave(int slot, const Common::String &name);
960  void requestLoad(int slot);
961 
962  Common::String getTargetName() const { return _targetName; }
963  bool canPauseSoundsDuringSave() const { return _pauseSoundsDuringSave; }
964 
965 // thumbnail + info stuff
966 public:
967  static bool querySaveMetaInfos(const char *target, int slot, int heversion, Common::String &desc, Graphics::Surface *&thumbnail, SaveStateMetaInfos *&timeInfos);
968 
969 protected:
970  void saveInfos(Common::WriteStream *file);
971  static bool loadInfos(Common::SeekableReadStream *file, SaveStateMetaInfos *stuff);
972 
973  /* Script VM - should be in Script class */
974  uint32 _localScriptOffsets[1024];
975  const byte *_scriptPointer = nullptr;
976  const byte *_scriptOrgPointer = nullptr;
977  const byte * const *_lastCodePtr = nullptr;
978  byte _opcode = 0;
979  bool _debug = false;
980  byte _currentScript = 0xFF; // Let debug() work on init stage
981  int _scummStackPos = 0;
982  int _vmStack[256];
983 
984  char _engineVersionString[50];
985  char _dataFileVersionString[50];
986 
987  OpcodeEntry _opcodes[256];
988 
993  bool currentScriptSlotIs(uint16 script) const {
994  return _currentScript != 0xFF && vm.slot[_currentScript].number == script;
995  }
996 
997  virtual void setupOpcodes() = 0;
998  void executeOpcode(byte i);
999  const char *getOpcodeDesc(byte i);
1000 
1001  void initializeLocals(int slot, int *vars);
1002  int getScriptSlot();
1003 
1004  void startScene(int room, Actor *a, int b);
1005  bool startManiac();
1006 
1007 public:
1008  void runScript(int script, bool freezeResistant, bool recursive, int *lvarptr, int cycle = 0);
1009  void stopScript(int script);
1010  void nukeArrays(byte scriptSlot);
1011 
1012 protected:
1013  void runObjectScript(int script, int entry, bool freezeResistant, bool recursive, int *vars, int slot = -1, int cycle = 0);
1014  void runScriptNested(int script);
1015  void executeScript();
1016  void updateScriptPtr();
1017  virtual void runInventoryScript(int i);
1018  virtual void runInventoryScriptEx(int i);
1019  virtual void checkAndRunSentenceScript();
1020  void runExitScript();
1021  void runEntryScript();
1022  void runQuitScript();
1023  void runAllScripts();
1024  void freezeScripts(int scr);
1025  void unfreezeScripts();
1026 
1027  bool isScriptInUse(int script) const;
1028  bool isRoomScriptRunning(int script) const;
1029  bool isScriptRunning(int script) const;
1030 
1031  void killAllScriptsExceptCurrent();
1032  void killScriptsAndResources();
1033  void decreaseScriptDelay(int amount);
1034 
1035  void stopObjectCode();
1036  void stopObjectScript(int script);
1037 
1038  void getScriptBaseAddress();
1039  void resetScriptPointer();
1040  int getVerbEntrypoint(int obj, int entry);
1041 
1042  void refreshScriptPointer();
1043  byte fetchScriptByte();
1044  virtual uint fetchScriptWord();
1045  virtual int fetchScriptWordSigned();
1046  uint fetchScriptDWord();
1047  int fetchScriptDWordSigned();
1048  void ignoreScriptWord() { fetchScriptWord(); }
1049  void ignoreScriptByte() { fetchScriptByte(); }
1050  void push(int a);
1051  int pop();
1052  virtual int readVar(uint var);
1053  virtual void writeVar(uint var, int value);
1054  // SCUMM 1/2
1055  virtual void resetSentence() {}
1056 
1057 protected:
1058  virtual void beginCutscene(int *args);
1059  virtual void endCutscene();
1060  void abortCutscene();
1061  void beginOverride();
1062  void endOverride();
1063 
1064  void copyScriptString(byte *dst);
1065  int resStrLen(const byte *src);
1066  void doSentence(int c, int b, int a);
1067 
1068  /* Should be in Resource class */
1069  BaseScummFile *_fileHandle = nullptr;
1070  uint32 _fileOffset = 0;
1071 public:
1074  Common::Path _macCursorFile;
1075 
1076  bool openFile(BaseScummFile &file, const Common::Path &filename, bool resourceFile = false);
1077  ScummFile *instantiateScummFile(bool indexPAKFiles = true);
1078 
1079 protected:
1080  int _resourceHeaderSize = 8;
1081  byte _resourceMapper[128];
1082  const byte *_resourceLastSearchBuf; // FIXME: need to put it to savefile?
1083  uint32 _resourceLastSearchSize; // FIXME: need to put it to savefile?
1084 
1085  virtual void allocateArrays();
1086  void openRoom(int room);
1087  void closeRoom();
1088  void deleteRoomOffsets();
1089  virtual void readRoomsOffsets();
1090  void askForDisk(const Common::Path &filename, int disknum);
1091  bool openResourceFile(const Common::Path &filename, byte encByte);
1092 
1093  void loadPtrToResource(ResType type, ResId idx, const byte *ptr);
1094  virtual int readResTypeList(ResType type);
1095 // void allocResTypeData(ResType type, uint32 tag, int num, int mode);
1096 // byte *createResource(int type, int index, uint32 size);
1097  int loadResource(ResType type, ResId idx);
1098 // void nukeResource(ResType type, ResId idx);
1099  int getResourceRoomNr(ResType type, ResId idx);
1100  virtual uint32 getResourceRoomOffset(ResType type, ResId idx);
1101 
1102 public:
1103  int getResourceSize(ResType type, ResId idx);
1104  byte *getResourceAddress(ResType type, ResId idx);
1105  virtual byte *getStringAddress(ResId idx);
1106  byte *getStringAddressVar(int i);
1107  void ensureResourceLoaded(ResType type, ResId idx);
1108 
1109 protected:
1110  Common::Mutex _resourceAccessMutex; // Used in getResourceSize(), getResourceAddress() and findResource()
1111  // to avoid race conditions between the audio thread of Digital iMUSE
1112  // and the main SCUMM thread
1113 
1114  int readSoundResource(ResId idx);
1115  int readSoundResourceSmallHeader(ResId idx);
1116  bool isResourceInUse(ResType type, ResId idx) const;
1117 
1118  virtual void setupRoomSubBlocks();
1119  virtual void resetRoomSubBlocks();
1120 
1121  virtual void clearRoomObjects();
1122  virtual void resetRoomObjects();
1123  virtual void resetRoomObject(ObjectData *od, const byte *room, const byte *searchptr = NULL);
1124 
1125  virtual void readArrayFromIndexFile();
1126  virtual void readMAXS(int blockSize) = 0;
1127  virtual void readGlobalObjects();
1128  virtual void readIndexFile();
1129  virtual void readIndexBlock(uint32 block, uint32 itemsize);
1130  virtual void loadCharset(int i);
1131  void nukeCharset(int i);
1132 
1133  int _lastLoadedRoom = 0;
1134 public:
1135  const byte *findResourceData(uint32 tag, const byte *ptr);
1136  const byte *findResource(uint32 tag, const byte *ptr);
1137  void applyWorkaroundIfNeeded(ResType type, int idx);
1138  bool verifyMI2MacBootScript();
1139  bool verifyMI2MacBootScript(byte *buf, int size);
1140  bool tryPatchMI1CannibalScript(byte *buf, int size);
1141 
1142  int getResourceDataSize(const byte *ptr) const;
1143  void dumpResource(const char *tag, int index, const byte *ptr, int length = -1);
1144 
1145 public:
1146  /* Should be in Object class */
1147  byte OF_OWNER_ROOM = 0;
1148  int getInventorySlot();
1149  int findInventory(int owner, int index);
1150  int getInventoryCount(int owner);
1151 
1152 protected:
1153  byte *_objectOwnerTable = nullptr, *_objectRoomTable = nullptr, *_objectStateTable = nullptr;
1154  int _numObjectsInRoom = 0;
1155 
1156 public:
1157  uint32 *_classData = nullptr;
1158 
1159 protected:
1160  void markObjectRectAsDirty(int obj);
1161  virtual void loadFlObject(uint object, uint room);
1162  void nukeFlObjects(int min, int max);
1163  int findFlObjectSlot();
1164  int findLocalObjectSlot();
1165  void addObjectToInventory(uint obj, uint room);
1166  void updateObjectStates();
1167 public:
1168  bool getClass(int obj, int cls) const; // Used in actor.cpp, hence public
1169 protected:
1170  void putClass(int obj, int cls, bool set);
1171  int getState(int obj);
1172  void putState(int obj, int state);
1173  void setObjectState(int obj, int state, int x, int y);
1174  int getOwner(int obj) const;
1175  void putOwner(int obj, int owner);
1176  void setOwnerOf(int obj, int owner);
1177  void clearOwnerOf(int obj);
1178  int getObjectRoom(int obj) const;
1179  virtual bool objIsActor(int obj);
1180  virtual int objToActor(int obj);
1181  virtual int actorToObj(int actor);
1182  int getObjX(int obj);
1183  int getObjY(int obj);
1184  void getObjectWidth(int object, int &width) { int x, y, dir; getObjectXYPos(object, x, y, dir, width); }
1185  void getObjectXYPos(int object, int &x, int &y) { int dir, width; getObjectXYPos(object, x, y, dir, width); }
1186  void getObjectXYPos(int object, int &x, int &y, int &dir) { int width; getObjectXYPos(object, x, y, dir, width); }
1187  void getObjectXYPos(int object, int &x, int &y, int &dir, int &width);
1188  int getObjOldDir(int obj);
1189  int getObjNewDir(int obj);
1190  int getObjectIndex(int object) const;
1191  int getObjectImageCount(int object);
1192  int whereIsObject(int object) const;
1193  int findObject(int x, int y);
1194  void findObjectInRoom(FindObjectInRoom *fo, byte findWhat, uint object, uint room);
1195 public:
1196  int getObjectOrActorWidth(int object, int &width); // Used in v4 and below
1197  int getObjectOrActorXY(int object, int &x, int &y); // Used in actor.cpp, hence public
1198  int getDist(int x, int y, int x2, int y2); // Also used in actor.cpp
1199 protected:
1200 
1201  int getObjActToObjActDist(int a, int b); // Not sure how to handle
1202  const byte *getObjOrActorName(int obj); // these three..
1203  void setObjectName(int obj);
1204 
1205  void addObjectToDrawQue(int object);
1206  void removeObjectFromDrawQue(int object);
1207  void clearDrawObjectQueue();
1208  void processDrawQue();
1209 
1210  virtual void clearDrawQueues();
1211 
1212  uint32 getOBCDOffs(int object) const;
1213  byte *getOBCDFromObject(int obj, bool v0CheckInventory = true);
1214  const byte *getOBIMFromObjectData(const ObjectData &od);
1215  const byte *getObjectImage(const byte *ptr, int state);
1216  virtual int getObjectIdFromOBIM(const byte *obim);
1217 
1218 protected:
1219  /* Should be in Verb class */
1220  uint16 _verbMouseOver = 0;
1221  int8 _userPut = 0;
1222  uint16 _userState = 0;
1223 
1224  virtual void handleMouseOver(bool updateInventory);
1225  virtual void redrawVerbs();
1226  virtual void checkExecVerbs();
1227 
1228  void verbMouseOver(int verb);
1229  int findVerbAtPos(int x, int y) const;
1230  virtual void drawVerb(int verb, int mode, Common::TextToSpeechManager::Action ttsAction = Common::TextToSpeechManager::INTERRUPT);
1231  virtual void runInputScript(int clickArea, int val, int mode);
1232  void restoreVerbBG(int verb);
1233  void drawVerbBitmap(int verb, int x, int y);
1234  int getVerbSlot(int id, int mode) const;
1235  void killVerb(int slot);
1236  void setVerbObject(uint room, uint object, uint verb);
1237 
1238 public:
1239  bool isValidActor(int id) const;
1240 
1241  /* Should be in Actor class */
1242  Actor *derefActor(int id, const char *errmsg = 0) const;
1243  Actor *derefActorSafe(int id, const char *errmsg) const;
1244 
1245 protected:
1246  void walkActors();
1247  void playActorSounds();
1248  void redrawAllActors();
1249  virtual void setActorRedrawFlags();
1250  void putActors();
1251  void showActors();
1252  void resetV1ActorTalkColor();
1253  virtual void resetActorBgs();
1254  virtual void processActors();
1255  void processUpperActors();
1256  virtual int getActorFromPos(int x, int y);
1257 
1258 public:
1259  /* Actor talking stuff */
1260  byte _actorToPrintStrFor = 0, _V1TalkingActor = 0;
1261  int _sentenceNum = 0;
1262  SentenceTab _sentence[NUM_SENTENCE];
1263  StringTab _string[6];
1264  byte _haveMsg = 0;
1265  int16 _talkDelay = 0;
1266  int _NES_lastTalkingActor = 0;
1267  int _NES_talkColor = 0;
1268 
1269  virtual void actorTalk(const byte *msg);
1270  void stopTalk();
1271  int getTalkingActor(); // Wrapper around VAR_TALK_ACTOR for V1 Maniac
1272  void setTalkingActor(int variable);
1273 
1274  // Generic costume code
1275  bool isCostumeInUse(int i) const;
1276 
1277 protected:
1278  /* Should be in Graphics class? */
1279  uint16 _screenB = 0, _screenH = 0;
1280 public:
1281  int _roomHeight = 0, _roomWidth = 0;
1282  int _screenHeight = 0, _screenWidth = 0;
1283  VirtScreen _virtscr[4]; // Virtual screen areas
1284  CameraData camera; // 'Camera' - viewport
1285  bool _cameraIsFrozen = false;
1286 
1287  int _screenStartStrip = 0, _screenEndStrip = 0;
1288  int _screenTop = 0;
1289  bool _forceBannerVirtScreen = false;
1290 
1291  // For Mac versions of 320x200 games:
1292  // these versions rendered at 640x480 without any aspect ratio correction;
1293  // in order to correctly display the games as they should be, we perform some
1294  // offset corrections within the various rendering pipelines.
1295  //
1296  // The only reason I've made _useMacScreenCorrectHeight toggleable is because
1297  // maybe someday the screen correction can be activated or deactivated from the
1298  // ScummVM GUI; but currently I'm not taking that responsibility, after all the
1299  // work done on ensuring that old savegames translate correctly to the new setting... :-P
1300  bool _useMacScreenCorrectHeight = true;
1301  int _macScreenDrawOffset = 20;
1302 
1303  Common::RenderMode _renderMode;
1304  uint8 _bytesPerPixel = 1;
1305  Graphics::PixelFormat _outputPixelFormat;
1306 
1307 protected:
1308  ColorCycle _colorCycle[16]; // Palette cycles
1309  uint8 _colorUsedByCycle[256];
1310  Graphics::PaletteLookup _pl; // Used by the internal GUI
1311 
1312  uint32 _ENCD_offs = 0, _EXCD_offs = 0;
1313  uint32 _CLUT_offs = 0, _EPAL_offs = 0;
1314  uint32 _IM00_offs = 0, _PALS_offs = 0;
1315 
1316  //ender: fullscreen
1317  bool _fullRedraw = false, _bgNeedsRedraw = false;
1318  bool _screenEffectFlag = false, _completeScreenRedraw = false;
1319  bool _disableFadeInEffect = false;
1320 
1321  struct {
1322  int hotspotX, hotspotY, width, height;
1323  byte animate, animateIndex;
1324  int8 state;
1325  } _cursor;
1326 
1327  // HACK Double the array size to handle 16-bit images.
1328  // this should be dynamically allocated based on game depth instead.
1329  byte _grabbedCursor[16384];
1330  byte _macGrabbedCursor[16384 * 4]; // Double resolution cursor
1331  byte _currentCursor = 0;
1332 
1333  byte _newEffect = 0, _switchRoomEffect2 = 0, _switchRoomEffect = 0;
1334  bool _doEffect = false;
1335 
1336  bool _snapScroll = false;
1337 
1338  virtual void setBuiltinCursor(int index) {}
1339 public:
1340  bool isLightOn() const;
1341 
1342  virtual int getCurrentLights() const;
1343 
1344 protected:
1345  void initScreens(int b, int h);
1346  void initVirtScreen(VirtScreenNumber slot, int top, int width, int height, bool twobufs, bool scrollable);
1347  void initBGBuffers(int height);
1348  void initCycl(const byte *ptr); // Color cycle
1349 
1350  void decodeNESBaseTiles();
1351 
1352  void drawObject(int obj, int scrollType);
1353  void drawRoomObjects(int arg);
1354  void drawRoomObject(int i, int arg);
1355  void drawBox(int x, int y, int x2, int y2, int color);
1356  void drawLine(int x1, int y1, int x2, int y2, int color);
1357  void drawPixel(VirtScreen *vs, int x, int y, int16 color, bool useBackbuffer = false);
1358 
1359  void moveScreen(int dx, int dy, int height);
1360 
1361  void restoreBackground(Common::Rect rect, byte backcolor = 0);
1362  void redrawBGStrip(int start, int num);
1363  virtual void redrawBGAreas();
1364 
1365  void cameraMoved();
1366  void setCameraAtEx(int at);
1367  virtual void setCameraAt(int pos_x, int pos_y);
1368  virtual void setCameraFollows(Actor *a, bool setCamera = false);
1369  virtual void moveCamera();
1370  virtual void panCameraTo(int x, int y);
1371  void clampCameraPos(Common::Point *pt);
1372  void actorFollowCamera(int act);
1373 
1374  const byte *getPalettePtr(int palindex, int room);
1375 
1376  void setPaletteFromTable(const byte *ptr, int numcolor, int firstIndex = 0);
1377  void resetPalette(bool isBootUp = false);
1378 
1379  void setCurrentPalette(int pal);
1380  void setRoomPalette(int pal, int room);
1381  void setPCEPaletteFromPtr(const byte *ptr);
1382  void setAmigaPaletteFromPtr(const byte *ptr);
1383  virtual void setPaletteFromPtr(const byte *ptr, int numcolor = -1);
1384  void setV1ColorTable(int renderMode);
1385 
1386  virtual void setPalColor(int index, int r, int g, int b);
1387  void setDirtyColors(int min, int max);
1388  const byte *findPalInPals(const byte *pal, int index);
1389  void swapPalColors(int a, int b);
1390  virtual void copyPalColor(int dst, int src);
1391  void cyclePalette();
1392  void stopCycle(int i);
1393  virtual void palManipulateInit(int resID, int start, int end, int time);
1394  void palManipulate();
1395  uint32 findClosestPaletteColor(byte *palette, int paletteLength, byte r, byte g, byte b);
1396  void applyGrayscaleToPaletteRange(int min, int max); // For Sam&Max original noir mode
1397  bool haveToApplyMonkey1PaletteFix();
1398 
1399 public:
1400  uint8 *getHEPaletteSlot(uint16 palSlot);
1401  uint16 get16BitColor(uint8 r, uint8 g, uint8 b);
1402  uint32 getPaletteColorFromRGB(byte *palette, byte r, byte g, byte b);
1403  uint32 getPackedRGBColorFromPalette(byte *palette, uint32 color);
1404  void fetchBlackAndWhite(uint32 &black, uint32 &white, byte *palette, int paletteEntries);
1405  int remapPaletteColor(int r, int g, int b, int threshold); // Used by Actor::remapActorPalette
1406  void readPCEPalette(const byte **ptr, byte **dest, int numEntries);
1407  void colorPCEToRGB(uint16 color, byte *r, byte *g, byte *b);
1408  void setPCETextPalette(uint8 color);
1409 protected:
1410  void moveMemInPalRes(int start, int end, byte direction);
1411  void setShadowPalette(int slot, int redScale, int greenScale, int blueScale, int startColor, int endColor);
1412  void setShadowPalette(int redScale, int greenScale, int blueScale, int startColor, int endColor, int start, int end);
1413  virtual void darkenPalette(int redScale, int greenScale, int blueScale, int startColor, int endColor);
1414 
1415 public:
1416  void markRectAsDirty(VirtScreenNumber virt, int left, int right, int top, int bottom, int dirtybit = 0);
1417  void markRectAsDirty(VirtScreenNumber virt, const Common::Rect& rect, int dirtybit = 0) {
1418  markRectAsDirty(virt, rect.left, rect.right, rect.top, rect.bottom, dirtybit);
1419  }
1420 protected:
1421  // Screen rendering
1422  byte *_compositeBuf;
1423  byte *_hercCGAScaleBuf = nullptr;
1424  bool _enableEGADithering = false;
1425  bool _supportsEGADithering = false;
1426  bool _enableSegaShadowMode = false;
1427 
1428  virtual void drawDirtyScreenParts();
1429  void updateDirtyScreen(VirtScreenNumber slot);
1430  void drawStripToScreen(VirtScreen *vs, int x, int width, int top, int bottom);
1431 
1432  void mac_markScreenAsDirty(int x, int y, int w, int h);
1433  void mac_drawStripToScreen(VirtScreen *vs, int top, int x, int y, int width, int height);
1434  void mac_drawIndy3TextBox();
1435  void mac_undrawIndy3TextBox();
1436  void mac_undrawIndy3CreditsText();
1437  void mac_drawBufferToScreen(const byte *buffer, int pitch, int x, int y, int width, int height, bool epxRectangleExpansion = true);
1438  void mac_updateCompositeBuffer(const byte *buffer, int pitch, int x, int y, int width, int height);
1439  void mac_blitDoubleResImage(const byte *buffer, int pitch, int x, int y, int width, int height);
1440  void mac_applyDoubleResToBuffer(const byte *inputBuffer, byte *outputBuffer, int width, int height, int inputPitch, int outputPitch);
1441  void mac_blitEPXImage(const byte *buffer, int pitch, int x, int y, int width, int height, bool epxRectangleExpansion = true);
1442  void mac_applyEPXToBuffer(const byte *inputBuffer, byte *outputBuffer, int width, int height, int inputPitch, int outputPitch, int xOffset, int yOffset, int bufferWidth, int bufferHeight);
1443  void mac_scaleCursor(byte *&outCursor, int &outHotspotX, int &outHotspotY, int &outWidth, int &outHeight);
1444  void mac_toggleSmoothing();
1445 
1446  Common::KeyState mac_showOldStyleBannerAndPause(const char *msg, int32 waitTime);
1447 
1448  const byte *postProcessDOSGraphics(VirtScreen *vs, int &pitch, int &x, int &y, int &width, int &height) const;
1449  const byte *ditherVGAtoEGA(int &pitch, int &x, int &y, int &width, int &height) const;
1450 
1451 public:
1452  VirtScreen *findVirtScreen(int y);
1453  byte *getMaskBuffer(int x, int y, int z);
1454 
1455 protected:
1456  void fadeIn(int effect);
1457  void fadeOut(int effect);
1458 
1459  void dissolveEffectSelector();
1460  void transitionEffect(int a);
1461  void dissolveEffect(int width, int height);
1462  void scrollEffect(int dir);
1463 
1464  void updateScreenShakeEffect();
1465 
1466 public:
1467  double getTimerFrequency();
1468  double getAmigaMusicTimerFrequency(); // For setting up Players v2 and v3
1469 
1470 protected:
1471  bool _shakeEnabled = false;
1472  bool _shakeTempSavedState = false; // For saving and restoring before and after GUI calls
1473  uint _shakeFrame = 0;
1474  uint32 _shakeNextTick = 0;
1475  uint32 _shakeTickCounter = 0;
1476  double _shakeTimerRate;
1477  double _timerFrequency;
1478 
1479  void setShake(int mode);
1480 
1481  int _drawObjectQueNr = 0;
1482  byte _drawObjectQue[200];
1483 
1484  /* For each of the 410 screen strips, gfxUsageBits contains a
1485  * bitmask. The lower 80 bits each correspond to one actor and
1486  * signify if any part of that actor is currently contained in
1487  * that strip.
1488  *
1489  * If the leftmost bit is set, the strip (background) is dirty
1490  * needs to be redrawn.
1491  *
1492  * The second leftmost bit is set by restoreBlastObjectsRect() and
1493  * restoreBackground(), but I'm not yet sure why.
1494  */
1495  uint32 gfxUsageBits[410 * 3];
1496 
1497  void upgradeGfxUsageBits();
1498  void setGfxUsageBit(int strip, int bit);
1499  void clearGfxUsageBit(int strip, int bit);
1500 
1501  // speed optimization: inline due to frequent calling
1502  bool testGfxUsageBit(int strip, int bit) {
1503  assert(strip >= 0 && strip < ARRAYSIZE(gfxUsageBits) / 3);
1504  assert(1 <= bit && bit <= 96);
1505  bit--;
1506  return (gfxUsageBits[3 * strip + bit / 32] & (1 << (bit % 32))) != 0;
1507  }
1508 
1509  bool testGfxAnyUsageBits(int strip);
1510  bool testGfxObjectUsageBits(int strip); // Used for HE actors overlap calculations
1511  bool testGfxOtherUsageBits(int strip, int bit);
1512 
1513 public:
1514  byte _roomPalette[256];
1515  byte *_shadowPalette = nullptr;
1516  bool _skipDrawObject = 0;
1517  int _voiceMode = 0;
1518  int _soundEnabled = 0;
1519 
1520  // HE specific
1521  byte _HEV7ActorPalette[256];
1522  uint8 *_hePalettes = nullptr;
1523  uint16 _hePaletteSlot = 0;
1524  uint16 *_16BitPalette = nullptr;
1525 
1526  // Indy4 Amiga specific
1527  byte *_verbPalette = nullptr;
1528 
1529  ScummEngine_v0_Delays _V0Delay;
1530 
1531 protected:
1532  int _shadowPaletteSize = 0;
1533  byte _currentPalette[3 * 256];
1534  byte _darkenPalette[3 * 256];
1535  int _paletteChangedCounter = 1;
1536 
1537  int _palDirtyMin = 0, _palDirtyMax = 0;
1538 
1539  byte _palManipStart = 0, _palManipEnd = 0;
1540  uint16 _palManipCounter = 0;
1541  byte *_palManipPalette = nullptr;
1542  byte *_palManipIntermediatePal = nullptr;
1543 
1544  bool _haveActorSpeechMsg = false;
1545  bool _useTalkAnims = false;
1546  uint16 _defaultTextSpeed = 0;
1547  int _saveSound = 0;
1548  bool _native_mt32 = false;
1549  bool _copyProtection = false;
1550  bool _shadowPalRemap = false;
1551 
1552  // Indy4 Amiga specific
1553  uint16 _amigaFirstUsedColor = 0;
1554  byte _amigaPalette[3 * 64];
1555  void amigaPaletteFindFirstUsedColor();
1556  void mapRoomPalette(int idx);
1557  int remapRoomPaletteColor(int r, int g, int b);
1558  void mapVerbPalette(int idx);
1559  int remapVerbPaletteColor(int r, int g, int b);
1560 
1561  // EGA dithering mode color tables for certain VGA games like MI2, LOOM Talkie...
1562  byte *_egaColorMap[2];
1563 
1564 public:
1565  uint16 _extraBoxFlags[65];
1566 
1567  byte getNumBoxes();
1568  byte *getBoxMatrixBaseAddr();
1569  byte *getBoxConnectionBase(int box);
1570 
1571  int getNextBox(byte from, byte to);
1572 
1573  void setBoxFlags(int box, int val);
1574  void setBoxScale(int box, int b);
1575 
1576  bool checkXYInBoxBounds(int box, int x, int y);
1577 
1578  BoxCoords getBoxCoordinates(int boxnum);
1579 
1580  byte getMaskFromBox(int box);
1581  Box *getBoxBaseAddr(int box);
1582  byte getBoxFlags(int box);
1583  int getBoxScale(int box);
1584 
1585  int getScale(int box, int x, int y);
1586  int getScaleFromSlot(int slot, int x, int y);
1587 
1588 protected:
1589  // Scaling slots/items
1590  struct ScaleSlot {
1591  int x1, y1, scale1;
1592  int x2, y2, scale2;
1593  };
1594  friend void syncWithSerializer(Common::Serializer &, ScaleSlot &);
1595  ScaleSlot _scaleSlots[20];
1596  void setScaleSlot(int slot, int x1, int y1, int scale1, int x2, int y2, int scale2);
1597  void setBoxScaleSlot(int box, int slot);
1598  void convertScaleTableToScaleSlot(int slot);
1599 
1600  void calcItineraryMatrix(byte *itineraryMatrix, int num);
1601  void createBoxMatrix();
1602  virtual bool areBoxesNeighbors(int i, int j);
1603 
1604  /* String class */
1605 public:
1606  CharsetRenderer *_charset = nullptr;
1607  byte _charsetColorMap[16];
1608 
1614  int _textSurfaceMultiplier = 0;
1615 
1616  bool _isModernMacVersion = false;
1617  bool _useGammaCorrection = true;
1618 
1619  Graphics::Surface *_macScreen = nullptr;
1620  MacGui *_macGui = nullptr;
1621  bool _useMacGraphicsSmoothing = true;
1622  byte _completeScreenBuffer[320 * 200];
1623 
1624 protected:
1625  byte _charsetColor = 0;
1626  byte _charsetData[23][16];
1627 
1628  int _charsetBufPos = 0;
1629  byte _charsetBuffer[512];
1630 
1631  bool _keepText = false;
1632  byte _msgCount = 0;
1633 
1634  int _nextLeft = 0, _nextTop = 0;
1635 
1636  Localizer *_localizer = nullptr;
1637 
1638 #ifdef USE_TTS
1639  bool _voiceNextString = false;
1640  bool _checkPreviousSaid = false;
1641  bool _voicePassHelpButtons = false;
1642  int _previousVerb = -1;
1643  int _previousControl = -1;
1644  Common::String _previousSaid;
1645  Common::String _passHelpButtons[6];
1646 #endif
1647 
1648  void restoreCharsetBg();
1649  void clearCharsetMask();
1650  void clearTextSurface();
1651 
1652  virtual void initCharset(int charset);
1653 
1654  virtual void printString(int m, const byte *msg);
1655 
1656  virtual bool handleNextCharsetCode(Actor *a, int *c);
1657  virtual void drawSentence() {}
1658  virtual void displayDialog();
1659  int countNumberOfWaits(); // For SE speech support, from disasm
1660  bool newLine();
1661  void drawString(int a, const byte *msg, Common::TextToSpeechManager::Action ttsAction = Common::TextToSpeechManager::QUEUE);
1662  virtual void fakeBidiString(byte *ltext, bool ignoreVerb, int ltextSize) const;
1663  void wrapSegaCDText();
1664  void debugMessage(const byte *msg);
1665  virtual void showMessageDialog(const byte *msg);
1666 
1667 #ifdef USE_TTS
1668  void sayText(const Common::String &text, Common::TextToSpeechManager::Action action = Common::TextToSpeechManager::QUEUE) const;
1669  void stopTextToSpeech() const;
1670  void sayButtonText();
1671 #endif
1672 
1673  virtual int convertMessageToString(const byte *msg, byte *dst, int dstSize);
1674  int convertIntMessage(byte *dst, int dstSize, int var);
1675  int convertVerbMessage(byte *dst, int dstSize, int var);
1676  int convertNameMessage(byte *dst, int dstSize, int var);
1677  int convertStringMessage(byte *dst, int dstSize, int var);
1678 
1679 public:
1680  Common::Language _language; // Accessed by a hack in NutRenderer::loadFont
1681 
1682  // Used by class ScummDialog:
1683  virtual void translateText(const byte *text, byte *trans_buff, int transBufferSize);
1684  // Old Hebrew games require reversing the dialog text.
1685  bool reverseIfNeeded(const byte *text, byte *reverseBuf, int reverseBufSize) const;
1686  // Returns codepage that matches the game for languages that require it.
1687  Common::CodePage getDialogCodePage() const;
1688 
1689  // Somewhat hackish stuff for 2 byte support (Chinese/Japanese/Korean)
1690  bool _useCJKMode = false;
1691  bool _useMultiFont = false;
1692  int _numLoadedFont = 0;
1693  int _2byteShadow = 0;
1694  bool _force2ByteCharHeight = false;
1695 
1696  int _2byteHeight = 0;
1697  int _2byteWidth = 0;
1698  int _krStrPost = 0;
1699  byte _newLineCharacter = 0;
1700  byte *get2byteCharPtr(int idx);
1701 
1702  bool isScummvmKorTarget();
1703  bool hasLocalizer();
1704 
1705 //protected:
1706  byte *_2byteFontPtr = nullptr;
1707  byte *_2byteMultiFontPtr[20];
1708  int _2byteMultiHeight[20];
1709  int _2byteMultiWidth[20];
1710  int _2byteMultiShadow[20];
1711 
1712 private:
1713  struct TranslatedLine {
1714  uint32 originalTextOffset;
1715  uint32 translatedTextOffset;
1716  };
1717 
1718  struct TranslationRange {
1719  uint32 left;
1720  uint32 right;
1721 
1722  TranslationRange(uint32 left_, uint32 right_) : left(left_), right(right_) {}
1723  TranslationRange() : left(0), right(0) {}
1724  };
1725 
1726  struct TranslationRoom {
1728  };
1729 
1730  bool _existLanguageFile = false;
1731  bool _isRTL = false;
1732  byte *_languageBuffer = nullptr;
1733  int _numTranslatedLines = 0;
1734  TranslatedLine *_translatedLines = nullptr;
1735  uint16 *_languageLineIndex = nullptr;
1737 
1738  const byte *searchTranslatedLine(const byte *text, const TranslationRange &range, bool useIndex);
1739 
1740  virtual void createTextRenderer(GlyphRenderer_v7 *gr) {}
1741 
1742 public:
1743 
1744  /* Scumm Vars */
1745  byte VAR_KEYPRESS = 0xFF;
1746  byte VAR_SYNC = 0xFF;
1747  byte VAR_EGO = 0xFF;
1748  byte VAR_CAMERA_POS_X = 0xFF;
1749  byte VAR_HAVE_MSG = 0xFF;
1750  byte VAR_ROOM = 0xFF;
1751  byte VAR_OVERRIDE = 0xFF;
1752  byte VAR_MACHINE_SPEED = 0xFF;
1753  byte VAR_ME = 0xFF;
1754  byte VAR_NUM_ACTOR = 0xFF;
1755  byte VAR_CURRENT_LIGHTS = 0xFF;
1756  byte VAR_CURRENTDRIVE = 0xFF; // How about merging this with VAR_CURRENTDISK?
1757  byte VAR_CURRENTDISK = 0xFF;
1758  byte VAR_TMR_1 = 0xFF;
1759  byte VAR_TMR_2 = 0xFF;
1760  byte VAR_TMR_3 = 0xFF;
1761  byte VAR_MUSIC_TIMER = 0xFF;
1762  byte VAR_ACTOR_RANGE_MIN = 0xFF;
1763  byte VAR_ACTOR_RANGE_MAX = 0xFF;
1764  byte VAR_CAMERA_MIN_X = 0xFF;
1765  byte VAR_CAMERA_MAX_X = 0xFF;
1766  byte VAR_TIMER_NEXT = 0xFF;
1767  byte VAR_VIRT_MOUSE_X = 0xFF;
1768  byte VAR_VIRT_MOUSE_Y = 0xFF;
1769  byte VAR_ROOM_RESOURCE = 0xFF;
1770  byte VAR_LAST_SOUND = 0xFF;
1771  byte VAR_CUTSCENEEXIT_KEY = 0xFF;
1772  byte VAR_OPTIONS_KEY = 0xFF;
1773  byte VAR_TALK_ACTOR = 0xFF;
1774  byte VAR_CAMERA_FAST_X = 0xFF;
1775  byte VAR_SCROLL_SCRIPT = 0xFF;
1776  byte VAR_ENTRY_SCRIPT = 0xFF;
1777  byte VAR_ENTRY_SCRIPT2 = 0xFF;
1778  byte VAR_EXIT_SCRIPT = 0xFF;
1779  byte VAR_EXIT_SCRIPT2 = 0xFF;
1780  byte VAR_VERB_SCRIPT = 0xFF;
1781  byte VAR_SENTENCE_SCRIPT = 0xFF;
1782  byte VAR_INVENTORY_SCRIPT = 0xFF;
1783  byte VAR_CUTSCENE_START_SCRIPT = 0xFF;
1784  byte VAR_CUTSCENE_END_SCRIPT = 0xFF;
1785  byte VAR_CHARINC = 0xFF;
1786  byte VAR_WALKTO_OBJ = 0xFF;
1787  byte VAR_DEBUGMODE = 0xFF;
1788  byte VAR_HEAPSPACE = 0xFF;
1789  byte VAR_RESTART_KEY = 0xFF;
1790  byte VAR_PAUSE_KEY = 0xFF;
1791  byte VAR_MOUSE_X = 0xFF;
1792  byte VAR_MOUSE_Y = 0xFF;
1793  byte VAR_TIMER = 0xFF;
1794  byte VAR_TIMER_TOTAL = 0xFF;
1795  byte VAR_SOUNDCARD = 0xFF;
1796  byte VAR_VIDEOMODE = 0xFF;
1797  byte VAR_MAINMENU_KEY = 0xFF;
1798  byte VAR_FIXEDDISK = 0xFF;
1799  byte VAR_CURSORSTATE = 0xFF;
1800  byte VAR_USERPUT = 0xFF;
1801  byte VAR_SOUNDRESULT = 0xFF;
1802  byte VAR_TALKSTOP_KEY = 0xFF;
1803  byte VAR_FADE_DELAY = 0xFF;
1804  byte VAR_NOSUBTITLES = 0xFF;
1805 
1806  // V5+
1807  byte VAR_SOUNDPARAM = 0xFF;
1808  byte VAR_SOUNDPARAM2 = 0xFF;
1809  byte VAR_SOUNDPARAM3 = 0xFF;
1810  byte VAR_INPUTMODE = 0xFF;
1811  byte VAR_MEMORY_PERFORMANCE = 0xFF;
1812  byte VAR_VIDEO_PERFORMANCE = 0xFF;
1813  byte VAR_ROOM_FLAG = 0xFF;
1814  byte VAR_GAME_LOADED = 0xFF;
1815  byte VAR_NEW_ROOM = 0xFF;
1816 
1817  // V4/V5
1818  byte VAR_V5_TALK_STRING_Y = 0xFF;
1819 
1820  // V6+
1821  byte VAR_ROOM_WIDTH = 0xFF;
1822  byte VAR_ROOM_HEIGHT = 0xFF;
1823  byte VAR_SUBTITLES = 0xFF;
1824  byte VAR_V6_EMSSPACE = 0xFF;
1825 
1826  // V7/V8 specific variables
1827  byte VAR_CAMERA_POS_Y = 0xFF;
1828  byte VAR_CAMERA_MIN_Y = 0xFF;
1829  byte VAR_CAMERA_MAX_Y = 0xFF;
1830  byte VAR_CAMERA_THRESHOLD_X = 0xFF;
1831  byte VAR_CAMERA_THRESHOLD_Y = 0xFF;
1832  byte VAR_CAMERA_SPEED_X = 0xFF;
1833  byte VAR_CAMERA_SPEED_Y = 0xFF;
1834  byte VAR_CAMERA_ACCEL_X = 0xFF;
1835  byte VAR_CAMERA_ACCEL_Y = 0xFF;
1836  byte VAR_CAMERA_DEST_X = 0xFF;
1837  byte VAR_CAMERA_DEST_Y = 0xFF;
1838  byte VAR_CAMERA_FOLLOWED_ACTOR = 0xFF;
1839 
1840  // V7/V8 specific variables
1841  byte VAR_VERSION_KEY = 0xFF;
1842  byte VAR_DEFAULT_TALK_DELAY = 0xFF;
1843  byte VAR_CUSTOMSCALETABLE = 0xFF;
1844  byte VAR_BLAST_ABOVE_TEXT = 0xFF;
1845  byte VAR_VOICE_MODE = 0xFF;
1846  byte VAR_MUSIC_BUNDLE_LOADED = 0xFF;
1847  byte VAR_VOICE_BUNDLE_LOADED = 0xFF;
1848 
1849  byte VAR_LEFTBTN_DOWN = 0xFF; // V7/V8
1850  byte VAR_RIGHTBTN_DOWN = 0xFF; // V7/V8
1851  byte VAR_LEFTBTN_HOLD = 0xFF; // V6/V72HE/V7/V8
1852  byte VAR_RIGHTBTN_HOLD = 0xFF; // V6/V72HE/V7/V8
1853  byte VAR_PRE_SAVELOAD_SCRIPT = 0xFF; // V6/V7 (not HE)
1854  byte VAR_POST_SAVELOAD_SCRIPT = 0xFF; // V6/V7 (not HE)
1855  byte VAR_SAVELOAD_PAGE = 0xFF; // V8
1856  byte VAR_OBJECT_LABEL_FLAG = 0xFF; // V8
1857 
1858  // V6/V7 specific variables (FT & Sam & Max specific)
1859  byte VAR_CHARSET_MASK = 0xFF;
1860 
1861  // V6 specific variables
1862  byte VAR_V6_SOUNDMODE = 0xFF;
1863 
1864  // V1/V2 specific variables
1865  byte VAR_CHARCOUNT = 0xFF;
1866  byte VAR_VERB_ALLOWED = 0xFF;
1867  byte VAR_ACTIVE_VERB = 0xFF;
1868  byte VAR_ACTIVE_OBJECT1 = 0xFF;
1869  byte VAR_ACTIVE_OBJECT2 = 0xFF;
1870 
1871  // HE specific variables
1872  byte VAR_ALWAYS_REDRAW_ACTORS = 0xFF; // Used in setActorRedrawFlags()
1873  byte VAR_SKIP_RESET_TALK_ACTOR = 0xFF; // Used in setActorCostume()
1874 
1875  byte VAR_SOUND_CHANNEL = 0xFF; // Used in o_startSound()
1876  byte VAR_TALK_CHANNEL = 0xFF; // Used in playVoice()
1877  byte VAR_SOUND_TOKEN_OFFSET = 0xFF; // Used in handleSoundFrame()
1878  byte VAR_START_DYN_SOUND_CHANNELS = 0xFF; // Used in getNextDynamicChannel()
1879  byte VAR_SOUND_CALLBACK_SCRIPT = 0xFF;
1880 
1881  byte VAR_EARLY_TALKIE_CALLBACK = 0xFF;
1882  byte VAR_EARLY_CHAN_0_CALLBACK = 0xFF;
1883  byte VAR_EARLY_CHAN_1_CALLBACK = 0xFF;
1884  byte VAR_EARLY_CHAN_2_CALLBACK = 0xFF;
1885  byte VAR_EARLY_CHAN_3_CALLBACK = 0xFF;
1886 
1887  byte VAR_MAIN_SCRIPT = 0xFF; // Used in scummLoop()
1888 
1889  byte VAR_DEFAULT_SCRIPT_PRIORITY = 0xFF; // Used in runScript()/runObjectScript()
1890  byte VAR_LAST_SCRIPT_PRIORITY = 0xFF; // Used in runAllScripts()
1891 
1892  byte VAR_QUIT_SCRIPT = 0xFF; // Used in confirmExitDialog()
1893  byte VAR_ERROR_FLAG = 0xFF; // HE70-90
1894  byte VAR_OPERATION_FAILURE = 0xFF; // HE99+
1895 
1896  byte VAR_COLOR_BLACK = 0xFF;
1897 
1898  // Exists both in V7 and in V72HE:
1899  byte VAR_NUM_GLOBAL_OBJS = 0xFF;
1900 
1901  byte VAR_LAST_FRAME_BURN_TIME = 0xFF; // HE90+
1902  byte VAR_LAST_FRAME_SCUMM_TIME = 0xFF; // HE90+
1903 
1904  byte VAR_WINDEX_RUNNING = 0xFF;
1905 
1906 #ifdef USE_RGB_COLOR
1907  // FM-Towns / PC-Engine specific
1908  Graphics::FontSJIS *_cjkFont = nullptr;
1909 #endif
1910 
1911  // FM-Towns specific
1912 #ifndef DISABLE_TOWNS_DUAL_LAYER_MODE
1913 public:
1914  bool towns_isRectInStringBox(int x1, int y1, int x2, int y2);
1915  byte _townsPaletteFlags = 0;
1916  byte _townsCharsetColorMap[16];
1917 
1918 protected:
1919  void towns_drawStripToScreen(VirtScreen *vs, int dstX, int dstY, int srcX, int srcY, int w, int h);
1920  void towns_fillTopLayerRect(int x1, int y1, int x2, int y2, int col);
1921  void towns_swapVirtScreenArea(VirtScreen *vs, int x, int y, int w, int h);
1922  void towns_clearStrip(int strip);
1923 #ifdef USE_RGB_COLOR
1924  void towns_setPaletteFromPtr(const byte *ptr, int numcolor = -1);
1925  void towns_setTextPaletteFromPtr(const byte *ptr);
1926 #endif
1927  void towns_setupPalCycleField(int x1, int y1, int x2, int y2);
1928  void towns_processPalCycleField();
1929  void towns_resetPalCycleFields();
1930  void towns_restoreCharsetBg();
1931  void towns_scriptScrollEffect(int dir);
1932 
1933  void requestScroll(int dir);
1934  void scrollLeft() { requestScroll(-1); }
1935  void scrollRight() { requestScroll(1); }
1936  void towns_waitForScroll(int waitForDirection, int threshold = 0);
1937  void towns_updateGfx();
1938 
1939  Common::Rect _cyclRects[10];
1940  int _numCyclRects = 0;
1941  int _scrollRequest = 0;
1942  int _scrollDeltaAdjust = 0;
1943  bool _scrollNeedDeltaAdjust = 0;
1944  int _refreshDuration[20];
1945  int _refreshArrayPos = 0;
1946  bool _refreshNeedCatchUp = false;
1947  bool _enableSmoothScrolling = false;
1948  bool _forceFMTownsHiResMode = false;
1949  uint32 _scrollTimer = 0;
1950  uint32 _scrollDestOffset = 0;
1951  uint16 _scrollFeedStrips[3];
1952 
1953  Common::Rect _curStringRect;
1954 
1955  byte _townsOverrideShadowColor = 0;
1956  byte _textPalette[48];
1957  byte _townsClearLayerFlag = 1;
1958  byte _townsActiveLayerFlags = 3;
1959  static const uint8 _townsLayer2Mask[];
1960 
1961  TownsScreen *_townsScreen = nullptr;
1962 #else
1963  void scrollLeft() { redrawBGStrip(_gdi->_numStrips - 1, 1); }
1964  void scrollRight() { redrawBGStrip(0, 1); }
1965  void towns_updateGfx() {}
1966  void towns_waitForScroll(int waitForDirection, int threshold = 0) {}
1967  void towns_fillTopLayerRect(int x1, int y1, int x2, int y2, int col) {}
1968  void towns_swapVirtScreenArea(VirtScreen *vs, int x, int y, int w, int h) {}
1969 #endif // DISABLE_TOWNS_DUAL_LAYER_MODE
1970 };
1971 
1972 } // End of namespace Scumm
1973 
1974 #endif
#define ARRAYSIZE(x)
Definition: util.h:112
Definition: charset.h:70
Definition: macgui_impl.h:52
Definition: keymap.h:66
VirtScreenNumber
Definition: gfx.h:161
Definition: gfx.h:563
Definition: str.h:59
Definition: boxes.h:44
Definition: surface.h:67
EngineFeature
Definition: engine.h:258
Definition: stream.h:77
Definition: error.h:81
T left
Definition: rect.h:170
ErrorCode getCode() const
Definition: error.h:112
Definition: detection.h:119
Definition: script.h:31
Definition: gfx.h:138
Definition: pixelformat.h:138
Definition: macgui_v6.h:33
Definition: script.h:128
Definition: random.h:44
Definition: palette.h:189
RenderMode
Definition: rendermode.h:48
No error occurred.
Definition: error.h:48
Definition: rect.h:524
Common::Path _containerFile
Definition: scumm.h:1073
Definition: path.h:52
Definition: scumm.h:171
Definition: resource.h:80
Definition: music.h:40
ResType
Definition: scumm.h:243
Definition: stream.h:745
Definition: macgui_indy3.h:39
Definition: sound.h:59
Definition: system.h:46
void void void void void debugC(int level, uint32 debugChannel, MSVC_PRINTF const char *s,...) GCC_PRINTF(3
Definition: serializer.h:79
Definition: scumm.h:163
Definition: scumm.h:511
Definition: gfx.h:185
Graphics::Surface _textSurface
Definition: scumm.h:1613
Definition: scumm.h:184
int FORCEINLINE GCC_PRINTF(2, 0) int vsprintf_s(T(&dst)[N]
Definition: scumm.h:136
Definition: detection.h:46
T right
Definition: rect.h:171
Definition: ustr.h:57
bool currentScriptSlotIs(uint16 script) const
Definition: scumm.h:993
Definition: scumm.h:219
Definition: scumm.h:152
Definition: player_towns.h:32
Definition: scumm.h:201
Definition: debugger.h:33
Definition: object.h:189
Definition: object.h:64
Definition: imuse.h:50
Definition: events.h:210
Definition: algorithm.h:29
Definition: formatinfo.h:28
Definition: mutex.h:67
Definition: rect.h:144
Definition: macgui_v5.h:33
Definition: serializer.h:308
Definition: charset.h:159
Definition: scumm.h:468
void NORETURN_PRE error(MSVC_PRINTF const char *s,...) GCC_PRINTF(1
Definition: actor.h:100
Definition: localizer.h:31
Definition: dialog.h:49
Definition: gfx.h:292
Definition: stream.h:351
Definition: base-costume.h:68
Definition: scumm.h:1590
Definition: macgui.h:39
Definition: keyboard.h:294
Definition: serializer.h:33
Common::Error run() override
Definition: scumm.h:574
Common::RandomSource _rnd
Definition: scumm.h:542
Definition: macgui_loom.h:33
Definition: system.h:163
Definition: scumm.h:143
Definition: base-costume.h:49
Definition: engine.h:144
Definition: actor.h:30
Definition: gfx.h:279
Definition: verbs.h:47
Definition: detection.h:133
Definition: file.h:36
Language
Definition: language.h:45