1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340
|
/* 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 3 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, see <http://www.gnu.org/licenses/>.
*
*
* Based on the original sources
* Faery Tale II -- The Halls of the Dead
* (c) 1993-1996 The Wyrmkeep Entertainment Co.
*/
#ifndef SAGA2_PLAYER_H
#define SAGA2_PLAYER_H
#include "saga2/actor.h"
namespace Saga2 {
#define FTA_JULIAN (PlayerActorID)0
#define FTA_PHILIP (PlayerActorID)1
#define FTA_KEVIN (PlayerActorID)2
/* ======================================================================= *
PlayerActor -- data specific to possible center actors
* ======================================================================= */
class ContainerNode;
class PlayerActor {
friend class Actor;
friend void initPlayerActors();
friend void cleanupPlayerActors();
ObjectID _actorID; // ID of player's actor
public:
int16 _portraitType; // Integer representing portrait state
// for this player actor
uint16 _flags; // various flags
ActorAttributes _baseStats; // Base stats for this actor
enum PlayerActorFlags {
kPlayerAggressive = (1 << 0), // Player is in aggressive mode
kPlayerBanded = (1 << 1), // Player is banded
kPlayerHasCartography = (1 << 2) // Player has ability to map
};
// recovery information
enum Recovery {
kBaseManaRec = 1,
kAttribPointsPerUpdate = 1,
kAttribPointsPerValue = 10
};
enum {
kVitalityLevelBump = 50
};
// Container node for ready containers
ContainerNode *_readyNode;
// mana 'experience' pool
int16 _manaMemory[kNumManas];
// attrib recovery pools
uint8 _attribRecPools[kNumSkills];
// skills 'expericene' pool
uint8 _attribMemPools[kNumSkills];
// vitality pool
uint8 _vitalityMemory;
// Flag indicating whether the user has been notified that this player
// actor has been attacked since the last combat
bool _notifiedOfAttack;
// Constructor
PlayerActor(ObjectID a) : _actorID(a), _portraitType(0), _flags(0), _readyNode(NULL),
_vitalityMemory(0), _notifiedOfAttack(false) {
assert(ActorAttributes::kSkillFracPointsPerLevel > 0); // this is used in a divide
memset(&_baseStats, 0, sizeof(_baseStats));
for (int i = 0; i < kNumManas; i++)
_manaMemory[i] = 0;
for (int i = 0; i < kNumSkills; i++) {
_attribRecPools[i] = 0;
_attribMemPools[i] = 0;
}
}
// gets level of skill
int8 getSkillLevel(SkillProto *, bool base = false);
// get the actorAttributes allskills index from proto
uint8 getStatIndex(SkillProto *);
// get the effective stats of this player actor
ActorAttributes *getEffStats();
// these update a players baseStat skills
void skillAdvance(uint8 stat,
uint8 advanceChance,
uint8 points,
uint8 useMult = 1);
void skillAdvance(SkillProto *proto,
uint8 points,
uint8 useMult = 1);
void skillAdvance(ActorSkillID stat,
uint8 points,
uint8 useMult = 1);
void vitalityAdvance(uint8 points);
// Return Actor structure pointer
Actor *getActor() {
return (Actor *)GameObject::objectAddress(_actorID);
}
// Return Actor's object ID
ObjectID getActorID() {
return _actorID;
}
// Set player to be aggressive
void setAggression() {
_flags |= kPlayerAggressive;
}
// Set player to not aggressive
void clearAggression() {
_flags &= ~kPlayerAggressive;
}
// Determine if actor is in aggressive state
bool isAggressive() {
return (_flags & kPlayerAggressive) != 0;
}
// Set the player to be banded
void setBanded() {
_flags |= kPlayerBanded;
}
// Set the player to not be banded
void clearBanded() {
_flags &= ~kPlayerBanded;
}
// Determine if this player actor is banded
bool isBanded() {
return (_flags & kPlayerBanded) != 0;
}
// Resolve the banding state of this actor
void resolveBanding();
// Re-evaluate the portrait type for this player actor
void recalcPortraitType();
// Return the integer representing the portrait type for this
// player actor
int16 getPortraitType() {
return _portraitType;
}
// figures out what what ( if any ) changes are required to
// the charaters vitality
void recoveryUpdate();
void manaUpdate();
void AttribUpdate();
void stdAttribUpdate(uint8 &stat, uint8 baseStat, int16 index);
// get this player actor's base stats
ActorAttributes &getBaseStats() {
return _baseStats;
}
// Notify the user of attack if necessary
void handleAttacked();
// Simply reset the attack notification flag
void resetAttackNotification() {
_notifiedOfAttack = false;
}
};
// Return a pointer to a PlayerActor given it's ID
PlayerActor *getPlayerActorAddress(PlayerActorID id);
// Return a PlayerActor ID given it's address
PlayerActorID getPlayerActorID(PlayerActor *p);
// Return a pointer to the center actor
Actor *getCenterActor();
// Return the center actor's object ID
ObjectID getCenterActorID();
// Return the center actor's player actor ID
PlayerActorID getCenterActorPlayerID();
// Set a new center actor based upon the PlayerActor ID
void setCenterActor(PlayerActorID newCenter);
// Set a new center actor based upon the address of the actor's struct
void setCenterActor(Actor *newCenter);
// Set a new center actor based upon the address of the PlayerActor
// struct
void setCenterActor(PlayerActor *newCenter);
// Get the coordinates of the center actor
TilePoint centerActorCoords();
// Set a player actor's aggression
void setAggression(PlayerActorID player, bool aggression);
// Set the center actor's aggression
inline void setCenterActorAggression(bool aggression) {
setAggression(getCenterActorPlayerID(), aggression);
}
// Determine the state of a player actor's aggression
bool isAggressive(PlayerActorID player);
// Determine if center actor is aggressive
inline bool isCenterActorAggressive() {
return isAggressive(getCenterActorPlayerID());
}
// Set a player actor's banding
void setBanded(PlayerActorID player, bool banded);
// Determine if a player actor is banded
bool isBanded(PlayerActorID player);
// Globally enable or disable player actor banding
void setBrotherBanding(bool enabled);
// Adjust the player actors aggression setting based upon their
// proximity to enemies
void autoAdjustAggression();
// Calculate the portrait for this brother's current state.
void recalcPortraitType(PlayerActorID id);
// Returns an integer value representing this player actor's portrait
// state
int16 getPortraitType(PlayerActorID id);
bool actorToPlayerID(Actor *a, PlayerActorID &result);
bool actorIDToPlayerID(ObjectID id, PlayerActorID &result);
void handlePlayerActorDeath(PlayerActorID id);
// Transport the center actor and the banded brothers who have a path
// the center actor
void transportCenterBand(const Location &loc);
void handlePlayerActorAttacked(PlayerActorID id);
void handleEndOfCombat();
/* ======================================================================= *
PlayerActor list management function prototypes
* ======================================================================= */
// Initialize the player actor list
void initPlayerActors();
void savePlayerActors(Common::OutSaveFile *out);
void loadPlayerActors(Common::InSaveFile *in);
// Cleanup the player actor list
void cleanupPlayerActors();
/* ======================================================================= *
CenterActor management function prototypes
* ======================================================================= */
// Initialize the center actor ID and view object ID
void initCenterActor();
void saveCenterActor(Common::OutSaveFile *outS);
void loadCenterActor(Common::InSaveFile *in);
// Do nothing
inline void cleanupCenterActor() {}
/* ======================================================================= *
PlayerActor iteration class
* ======================================================================= */
class PlayerActorIterator {
protected:
int16 _index;
public:
PlayerActorIterator() {
_index = 0;
}
PlayerActor *first();
PlayerActor *next();
};
// Iterates through all player actors that are not dead.
class LivingPlayerActorIterator : public PlayerActorIterator {
public:
LivingPlayerActorIterator() {}
PlayerActor *first();
PlayerActor *next();
};
} // end of namespace Saga2
#endif
|