1 /* 2 * Copyright (C) 2011-2013 Me and My Shadow 3 * 4 * This file is part of Me and My Shadow. 5 * 6 * Me and My Shadow is free software: you can redistribute it and/or modify 7 * it under the terms of the GNU General Public License as published by 8 * the Free Software Foundation, either version 3 of the License, or 9 * (at your option) any later version. 10 * 11 * Me and My Shadow is distributed in the hope that it will be useful, 12 * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 * GNU General Public License for more details. 15 * 16 * You should have received a copy of the GNU General Public License 17 * along with Me and My Shadow. If not, see <http://www.gnu.org/licenses/>. 18 */ 19 20 #ifndef GAME_H 21 #define GAME_H 22 23 #include <SDL.h> 24 #include <array> 25 #include <vector> 26 #include <map> 27 #include <string> 28 29 #include "CachedTexture.h" 30 #include "GameState.h" 31 #include "GUIObject.h" 32 #include "GameObjects.h" 33 #include "Scenery.h" 34 #include "SceneryLayer.h" 35 #include "Player.h" 36 #include "Render.h" 37 #include "Shadow.h" 38 39 //This structure contains variables that make a GameObjectEvent. 40 struct typeGameObjectEvent{ 41 //The type of event. 42 int eventType; 43 //The type of object that should react to the event. 44 int objectType; 45 //Flags, 0x1 means use the id. 46 int flags; 47 //Blocks with this id should react to the event. 48 std::string id; 49 50 //Optional pointer to the block the event should be called on. 51 GameObject* target; 52 }; 53 54 class ThemeManager; 55 class ThemeBackground; 56 class TreeStorageNode; 57 class ScriptExecutor; 58 59 //The different level events. 60 enum LevelEventType{ 61 //Event called when the level is created or the game is reset. This happens after all the blocks are created and their onCreate is called. 62 LevelEvent_OnCreate=1, 63 //Event called when the game is saved. 64 LevelEvent_OnSave, 65 //Event called when the game is loaded. 66 LevelEvent_OnLoad, 67 }; 68 69 class Game : public GameState,public GUIEventCallback{ 70 private: 71 //Boolean if the game should reset. This happens when player press 'R' button. 72 bool isReset; 73 74 //The script executor. 75 ScriptExecutor *scriptExecutor; 76 77 protected: 78 //contains currently played level. 79 TreeStorageNode* currentLevelNode; 80 81 //Array containing "tooltips" for certain block types. 82 //It will be shown in the topleft corner of the screen. 83 std::array<TexturePtr, TYPE_MAX> bmTips; 84 85 //Texture containing the action images (record, play, etc..) 86 SharedTexture action; 87 //Texture containing the medal image. 88 SharedTexture medals; 89 90 //ThemeBlockInstance containing the collectable image. 91 ThemeBlockInstance collectable; 92 93 //The name of the current level. 94 std::string levelName; 95 //The path + file of the current level. 96 std::string levelFile; 97 98 //Editor data containing information like name, size, etc... 99 std::map<std::string,std::string> editorData; 100 101 //Vector used to queue the gameObjectEvents. 102 std::vector<typeGameObjectEvent> eventQueue; 103 104 //The themeManager. 105 ThemeManager* customTheme; 106 //The themeBackground. 107 ThemeBackground* background; 108 109 CachedTexture<int> collectablesTexture; 110 CachedTexture<int> recordingsTexture; 111 CachedTexture<int> timeTexture; 112 CachedTexture<Block*> notificationTexture; 113 114 //Load a level from node. 115 //After calling this function the ownership of 116 //node will transfer to Game class. So don't delete 117 //the node after calling this function! 118 virtual void loadLevelFromNode(ImageManager& imageManager, SDL_Renderer& renderer, TreeStorageNode* obj, const std::string& fileName); 119 120 //(internal function) Reload the music according to level music and level pack music. 121 //This is mainly used in level editor. 122 void reloadMusic(); 123 124 public: 125 //Array used to convert GameObject type->string. 126 static const char* blockName[TYPE_MAX]; 127 //Map used to convert GameObject string->type. 128 static std::map<std::string,int> blockNameMap; 129 130 //Map used to convert GameObjectEventType type->string. 131 static std::map<int,std::string> gameObjectEventTypeMap; 132 //Map used to convert GameObjectEventType string->type. 133 static std::map<std::string,int> gameObjectEventNameMap; 134 135 //Map used to convert LevelEventType type->string. 136 static std::map<int,std::string> levelEventTypeMap; 137 //Map used to convert LevelEventType string->type. 138 static std::map<std::string,int> levelEventNameMap; 139 140 //Boolean that is set to true when a game is won. 141 bool won; 142 143 //Boolean that is set to true when we should save game on next logic update. 144 bool saveStateNextTime; 145 146 //Boolean that is set to true when we should load game on next logic update. 147 bool loadStateNextTime; 148 149 //Boolean if the replaying currently done is for the interlevel screen. 150 bool interlevel; 151 152 //Integer containing the current tip index. 153 int gameTipIndex; 154 155 //Integer containing the number of ticks passed since the start of the level. 156 int time; 157 //Integer containing the stored value of time. 158 int timeSaved; 159 160 //Integer containing the number of recordings it took to finish. 161 int recordings; 162 //Integer containing the stored value of recordings. 163 int recordingsSaved; 164 165 //Integer keeping track of currently obtained collectables 166 int currentCollectables; 167 //Integer keeping track of total colletables in the level 168 int totalCollectables; 169 //Integer containing the stored value of current collectables 170 int currentCollectablesSaved; 171 172 //Time of recent swap, for achievements. (in game-ticks) 173 int recentSwap,recentSwapSaved; 174 175 //Store time of recent save/load for achievements (in millisecond) 176 Uint32 recentLoad,recentSave; 177 178 //Enumeration with the different camera modes. 179 enum CameraMode{ 180 CAMERA_PLAYER, 181 CAMERA_SHADOW, 182 CAMERA_CUSTOM 183 }; 184 //The current camera mode. 185 CameraMode cameraMode; 186 //Rectangle containing the target for the camera. 187 SDL_Rect cameraTarget; 188 189 //The saved cameraMode. 190 CameraMode cameraModeSaved; 191 SDL_Rect cameraTargetSaved; 192 193 //Level scripts. 194 std::map<int,std::string> scripts; 195 196 //Compiled scripts. Use lua_rawgeti(L, LUA_REGISTRYINDEX, r) to get the function. 197 std::map<int, int> compiledScripts, savedCompiledScripts, initialCompiledScripts; 198 199 //Vector containing all the levelObjects in the current game. 200 std::vector<Block*> levelObjects; 201 202 //The layers for the scenery. 203 // We utilize the fact that std::map is sorted, and we compare the layer name with "f", 204 // If name<"f" then it's background layer, if name>="f" then it's foreground layer. 205 // NOTE: the layer name is case sensitive, in particular if the name start with capital "F" 206 // then it is still background layer. 207 std::map<std::string,SceneryLayer*> sceneryLayers; 208 209 //The player... 210 Player player; 211 //... and his shadow. 212 Shadow shadow; 213 214 //warning: weak reference only, may point to invalid location 215 Block* objLastCheckPoint; 216 217 //Constructor. 218 Game(SDL_Renderer& renderer, ImageManager& imageManager); 219 //If this is not empty then when next Game class is created 220 //it will play this record file. 221 static std::string recordFile; 222 //Destructor. 223 //It will call destroy(); 224 ~Game(); 225 226 //Method used to clean up the GameState. 227 void destroy(); 228 229 //Inherited from GameState. 230 void handleEvents(ImageManager&imageManager, SDL_Renderer&renderer) override; 231 void logic(ImageManager& imageManager, SDL_Renderer& renderer) override; 232 void render(ImageManager&,SDL_Renderer& renderer) override; 233 void resize(ImageManager& imageManager, SDL_Renderer& renderer) override; 234 235 //This method will load a level. 236 //fileName: The fileName of the level. 237 virtual void loadLevel(ImageManager& imageManager, SDL_Renderer& renderer, std::string fileName); 238 239 //Method used to broadcast a GameObjectEvent. 240 //eventType: The type of event. 241 //objectType: The type of object that should react to the event. 242 //id: The id of the blocks that should react. 243 //target: Pointer to the object 244 void broadcastObjectEvent(int eventType,int objectType=-1,const char* id=NULL,GameObject* target=NULL); 245 246 //Compile all scripts and run onCreate script. 247 //NOTE: Call this function only after script state reset, or there will be some memory leaks. 248 void compileScript(); 249 250 //Method that will check if a script for a given levelEvent is present. 251 //If that's the case the script will be executed. 252 //eventType: The level event type to execute. 253 void inline executeScript(int eventType); 254 255 256 //Returns if the player and shadow can save the current state. 257 bool canSaveState(); 258 259 //Method used to store the current state. 260 //This is used for checkpoints. 261 //Returns: True if it succeeds without problems. 262 bool saveState(); 263 //Method used to load the stored state. 264 //This is used for checkpoints. 265 //Returns: True if it succeeds without problems. 266 bool loadState(); 267 //Method that will reset the GameState to it's initial state. 268 //save: Boolean if the saved state should also be deleted. This also means recreate the Lua context. 269 //noScript: Boolean if we should not compile the script at all. This is used by level editor when exiting test play. 270 void reset(bool save,bool noScript); 271 272 //Save current game record to the file. 273 //fileName: The filename of the destination file. 274 void saveRecord(const char* fileName); 275 //Load game record (and its level) from file and play it. 276 //fileName: The filename of the recording file. 277 void loadRecord(ImageManager& imageManager, SDL_Renderer& renderer, const char* fileName); 278 279 //Method called by the player (or shadow) when he finished. 280 void replayPlay(ImageManager& imageManager, SDL_Renderer &renderer); 281 //Method that gets called when the recording has ended. 282 void recordingEnded(ImageManager& imageManager, SDL_Renderer& renderer); 283 284 //get current level's auto-save record path, 285 //using current level's MD5, file name and other information. 286 void getCurrentLevelAutoSaveRecordPath(std::string &bestTimeFilePath,std::string &bestRecordingFilePath,bool createPath); 287 288 //Method that will prepare the gamestate for the next level and start it. 289 //If it's the last level it will show the congratulations text and return to the level select screen. 290 void gotoNextLevel(ImageManager& imageManager, SDL_Renderer& renderer); 291 292 //Get the name of the current level. getLevelName()293 const std::string& getLevelName(){ 294 return levelName; 295 } 296 297 //GUI event handling is done here. 298 void GUIEventCallback_OnEvent(ImageManager&imageManager, SDL_Renderer&renderer, std::string name, GUIObject* obj, int eventType) override; 299 300 //Get the script executor. getScriptExecutor()301 ScriptExecutor* getScriptExecutor() { 302 return scriptExecutor; 303 } 304 }; 305 306 #endif 307