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
8  * modify it under the terms of the GNU General Public License
9  * as published by the Free Software Foundation; either version 2
10  * of the License, or (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, write to the Free Software
19  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
20  *
21  */
22 
23 #ifndef ULTIMA4_FILESYS_SAVEGAME_H
24 #define ULTIMA4_FILESYS_SAVEGAME_H
25 
26 #include "common/array.h"
27 #include "common/rect.h"
28 #include "common/stream.h"
29 #include "common/serializer.h"
30 #include "ultima/ultima4/core/coords.h"
31 #include "ultima/ultima4/core/types.h"
32 
33 namespace Ultima {
34 namespace Ultima4 {
35 
36 #define PARTY_SAV_BASE_FILENAME         "party.sav"
37 #define MONSTERS_SAV_BASE_FILENAME      "monsters.sav"
38 #define OUTMONST_SAV_BASE_FILENAME      "outmonst.sav"
39 
40 #define MONSTERTABLE_SIZE                32
41 #define MONSTERTABLE_CREATURES_SIZE        8
42 #define MONSTERTABLE_OBJECTS_SIZE        (MONSTERTABLE_SIZE - MONSTERTABLE_CREATURES_SIZE)
43 
44 class Object;
45 
46 /**
47  * The list of all weapons.  These values are used in both the
48  * inventory fields and character records of the savegame.
49  */
50 enum WeaponType {
51 	WEAP_HANDS,
52 	WEAP_STAFF,
53 	WEAP_DAGGER,
54 	WEAP_SLING,
55 	WEAP_MACE,
56 	WEAP_AXE,
57 	WEAP_SWORD,
58 	WEAP_BOW,
59 	WEAP_CROSSBOW,
60 	WEAP_OIL,
61 	WEAP_HALBERD,
62 	WEAP_MAGICAXE,
63 	WEAP_MAGICSWORD,
64 	WEAP_MAGICBOW,
65 	WEAP_MAGICWAND,
66 	WEAP_MYSTICSWORD,
67 	WEAP_MAX
68 };
69 
70 /**
71  * The list of all armor types.  These values are used in both the
72  * inventory fields and character records of the savegame.
73  */
74 enum ArmorType {
75 	ARMR_NONE,
76 	ARMR_CLOTH,
77 	ARMR_LEATHER,
78 	ARMR_CHAIN,
79 	ARMR_PLATE,
80 	ARMR_MAGICCHAIN,
81 	ARMR_MAGICPLATE,
82 	ARMR_MYSTICROBES,
83 	ARMR_MAX
84 };
85 
86 /**
87  * The list of sex values for the savegame character records.  The
88  * values match the male and female symbols in the character set.
89  */
90 enum SexType {
91 	SEX_MALE = 0xb,
92 	SEX_FEMALE = 0xc
93 };
94 
95 /**
96  * The list of class types for the savegame character records.
97  */
98 enum ClassType {
99 	CLASS_MAGE,
100 	CLASS_BARD,
101 	CLASS_FIGHTER,
102 	CLASS_DRUID,
103 	CLASS_TINKER,
104 	CLASS_PALADIN,
105 	CLASS_RANGER,
106 	CLASS_SHEPHERD
107 };
108 
109 /**
110  * The list of status values for the savegame character records.  The
111  * values match the letter thats appear in the ztats area.
112  */
113 enum StatusType {
114 	STAT_GOOD = 'G',
115 	STAT_POISONED = 'P',
116 	STAT_SLEEPING = 'S',
117 	STAT_DEAD = 'D'
118 };
119 
120 enum Virtue {
121 	VIRT_HONESTY,
122 	VIRT_COMPASSION,
123 	VIRT_VALOR,
124 	VIRT_JUSTICE,
125 	VIRT_SACRIFICE,
126 	VIRT_HONOR,
127 	VIRT_SPIRITUALITY,
128 	VIRT_HUMILITY,
129 	VIRT_MAX
130 };
131 
132 enum BaseVirtue {
133 	VIRT_NONE       = 0x00,
134 	VIRT_TRUTH      = 0x01,
135 	VIRT_LOVE       = 0x02,
136 	VIRT_COURAGE    = 0x04
137 };
138 
139 enum Reagent {
140 	REAG_ASH,
141 	REAG_GINSENG,
142 	REAG_GARLIC,
143 	REAG_SILK,
144 	REAG_MOSS,
145 	REAG_PEARL,
146 	REAG_NIGHTSHADE,
147 	REAG_MANDRAKE,
148 	REAG_MAX
149 };
150 
151 #define SPELL_MAX 26
152 
153 enum Item {
154 	ITEM_SKULL  = 0x01,
155 	ITEM_SKULL_DESTROYED = 0x02,
156 	ITEM_CANDLE = 0x04,
157 	ITEM_BOOK   = 0x08,
158 	ITEM_BELL   = 0x10,
159 	ITEM_KEY_C  = 0x20,
160 	ITEM_KEY_L  = 0x40,
161 	ITEM_KEY_T  = 0x80,
162 	ITEM_HORN   = 0x100,
163 	ITEM_WHEEL  = 0x200,
164 	ITEM_CANDLE_USED = 0x400,
165 	ITEM_BOOK_USED = 0x800,
166 	ITEM_BELL_USED = 0x1000
167 };
168 
169 enum Stone {
170 	STONE_BLUE   = 0x01,
171 	STONE_YELLOW = 0x02,
172 	STONE_RED    = 0x04,
173 	STONE_GREEN  = 0x08,
174 	STONE_ORANGE = 0x10,
175 	STONE_PURPLE = 0x20,
176 	STONE_WHITE  = 0x40,
177 	STONE_BLACK  = 0x80
178 };
179 
180 enum Rune {
181 	RUNE_HONESTY      = 0x01,
182 	RUNE_COMPASSION   = 0x02,
183 	RUNE_VALOR        = 0x04,
184 	RUNE_JUSTICE      = 0x08,
185 	RUNE_SACRIFICE    = 0x10,
186 	RUNE_HONOR        = 0x20,
187 	RUNE_SPIRITUALITY = 0x40,
188 	RUNE_HUMILITY     = 0x80
189 };
190 
191 /**
192  * The Ultima IV savegame player record data.
193  */
194 struct SaveGamePlayerRecord {
195 	void synchronize(Common::Serializer &s);
196 	void init();
197 
198 	unsigned short _hp;
199 	unsigned short _hpMax;
200 	unsigned short _xp;
201 	unsigned short _str, _dex, _intel;
202 	unsigned short _mp;
203 	unsigned short _unknown;
204 	WeaponType _weapon;
205 	ArmorType _armor;
206 	char _name[16];
207 	SexType _sex;
208 	ClassType _class;
209 	StatusType _status;
210 };
211 
212 /**
213  * How Ultima IV stores monster information
214  */
215 struct SaveGameMonsterRecord {
216 	byte _tile;
217 	byte _x;
218 	byte _y;
219 	byte _prevTile;
220 	byte _prevX;
221 	byte _prevY;
222 	byte _unused1;
223 	byte _unused2;
224 
SaveGameMonsterRecordSaveGameMonsterRecord225 	SaveGameMonsterRecord() {
226 		clear();
227 	}
228 
clearSaveGameMonsterRecord229 	void clear() {
230 		_tile = _x = _y = 0;
231 		_prevTile = _prevX = _prevY = 0;
232 		_unused1 = _unused2 = 0;
233 	}
234 
235 	static void synchronize(SaveGameMonsterRecord *monsterTable, Common::Serializer &s);
236 };
237 
238 class LocationCoords : public Coords {
239 public:
240 	MapId _map;
241 
LocationCoords()242 	LocationCoords() : Coords(), _map(0xff) {}
LocationCoords(MapId map,int x_,int y_,int z_)243 	LocationCoords(MapId map, int x_, int y_, int z_) :
244 		Coords(x_, y_, z_), _map(map) {}
LocationCoords(MapId map,const Coords & pos)245 	LocationCoords(MapId map, const Coords &pos) :
246 		Coords(pos), _map(map) {}
247 
248 	/**
249 	 * Synchronize to/from a savegame
250 	 */
251 	void synchronize(Common::Serializer &s);
252 };
253 
254 class LocationCoordsArray : public Common::Array<LocationCoords> {
255 public:
256 
257 	/**
258 	 * Loads the list of map & coordinates from the game context
259 	 */
260 	void load();
261 
262 	/**
263 	 * Synchronize to/from a savegame
264 	 */
265 	void synchronize(Common::Serializer &s);
266 };
267 
268 /**
269  * Represents the on-disk contents of PARTY.SAV.
270  */
271 struct SaveGame {
272 	/**
273 	 * Initialize a new savegame structure
274 	 */
275 	void init(const SaveGamePlayerRecord *avatarInfo);
276 
277 	/**
278 	 * Load an entire savegame, including monsters
279 	 */
280 	void save(Common::WriteStream *stream);
281 
282 	/**
283 	 * Save an entire savegame, including monsters
284 	 */
285 	void load(Common::SeekableReadStream *stream);
286 
287 	/**
288 	 * Called when a new game is started without loading an existing
289 	 * savegame from launcher.
290 	 */
291 	void newGame();
292 
293 	/**
294 	 * Synchronizes data for the savegame structure
295 	 */
296 	void synchronize(Common::Serializer &s);
297 
298 	uint _unknown1;
299 	uint _moves;
300 	SaveGamePlayerRecord _players[8];
301 	int _food;
302 	short _gold;
303 	short _karma[VIRT_MAX];
304 	short _torches;
305 	short _gems;
306 	short _keys;
307 	short _sextants;
308 	short _armor[ARMR_MAX];
309 	short _weapons[WEAP_MAX];
310 	short _reagents[REAG_MAX];
311 	short _mixtures[SPELL_MAX];
312 	unsigned short _items;
313 	LocationCoordsArray _positions;
314 	unsigned short _orientation;
315 
316 	byte _stones;
317 	byte _runes;
318 	unsigned short _members;
319 	unsigned short _transport;
320 	union {
321 		unsigned short _balloonState;
322 		unsigned short _torchDuration;
323 	};
324 	unsigned short _trammelPhase;
325 	unsigned short _feluccaPhase;
326 	unsigned short _shipHull;
327 	unsigned short _lbIntro;
328 	unsigned short _lastCamp;
329 	unsigned short _lastReagent;
330 	unsigned short _lastMeditation;
331 	unsigned short _lastVirtue;
332 };
333 
334 } // End of namespace Ultima4
335 } // End of namespace Ultima
336 
337 #endif
338