[ogs-changes] dist/c++/ogs/core Abilities.cpp,1.4,1.5 Abilities.h,1.3,1.4 Ability.cpp,1.5,1.6 Abilit
Status: Alpha
Brought to you by:
elemings
Update of /cvsroot/ogs/dist/c++/ogs/core
In directory sc8-pr-cvs1:/tmp/cvs-serv21226/c++/ogs/core
Modified Files:
Abilities.cpp Abilities.h Ability.cpp Ability.h Character.cpp
Creature.cpp Modifier.cpp Modifier.h Modifiers.cpp Modifiers.h
Log Message:
See C++ ChangeLog (Apr 5 and 8) for details.
Index: Abilities.cpp
===================================================================
RCS file: /cvsroot/ogs/dist/c++/ogs/core/Abilities.cpp,v
retrieving revision 1.4
retrieving revision 1.5
diff -C2 -d -r1.4 -r1.5
*** Abilities.cpp 4 Apr 2003 20:22:43 -0000 1.4
--- Abilities.cpp 8 Apr 2003 21:43:06 -0000 1.5
***************
*** 29,32 ****
--- 29,37 ----
using ogs::core::Strength;
+ static Ability::Type types [] = {
+ Ability::CHA, Ability::CON, Ability::DEX,
+ Ability::INT, Ability::STR, Ability::WIS
+ };
+
/**
* Create a complete set of abilities. The ability scores are generated
***************
*** 34,44 ****
*/
Abilities::Abilities () {
! Map& map = *this;
! map [Ability::CHA] = new Ability (Ability::CHA);
! map [Ability::CON] = new Ability (Ability::CON);
! map [Ability::DEX] = new Ability (Ability::DEX);
! map [Ability::INT] = new Ability (Ability::INT);
! map [Ability::STR] = new Strength ();
! map [Ability::WIS] = new Ability (Ability::WIS);
}
--- 39,49 ----
*/
Abilities::Abilities () {
! PtrMap& map = *this;
! map [Ability::CHA] = AbilityPtr (new Ability (Ability::CHA));
! map [Ability::CON] = AbilityPtr (new Ability (Ability::CON));
! map [Ability::DEX] = AbilityPtr (new Ability (Ability::DEX));
! map [Ability::INT] = AbilityPtr (new Ability (Ability::INT));
! map [Ability::STR] = AbilityPtr (new Strength ());
! map [Ability::WIS] = AbilityPtr (new Ability (Ability::WIS));
}
***************
*** 49,70 ****
*/
Abilities::Abilities (Ability::Method& method) {
! Map& map = *this;
! map [Ability::CHA] = new Ability (Ability::CHA, method);
! map [Ability::CON] = new Ability (Ability::CON, method);
! map [Ability::DEX] = new Ability (Ability::DEX, method);
! map [Ability::INT] = new Ability (Ability::INT, method);
! map [Ability::STR] = new Strength (method);
! map [Ability::WIS] = new Ability (Ability::WIS, method);
}
- struct Abilities::Delete {
- void operator() (ValueType value) { delete value.second; }
- };
-
/**
! * Destroy this set of abilities.
*/
! Abilities::~Abilities () {
! std::for_each (this->begin (), this->end (), Delete ());
}
--- 54,84 ----
*/
Abilities::Abilities (Ability::Method& method) {
! PtrMap& map = *this;
! map [Ability::CHA] = AbilityPtr (new Ability (Ability::CHA, method));
! map [Ability::CON] = AbilityPtr (new Ability (Ability::CON, method));
! map [Ability::DEX] = AbilityPtr (new Ability (Ability::DEX, method));
! map [Ability::INT] = AbilityPtr (new Ability (Ability::INT, method));
! map [Ability::STR] = AbilityPtr (new Strength (method));
! map [Ability::WIS] = AbilityPtr (new Ability (Ability::WIS, method));
}
/**
! * Cteate a set of abilities using a direct method.
! *
! * @param directMethod A direct method.
*/
! Abilities::Abilities (PartialMethod& directMethod) {
! PtrMap& map = *this;
!
! for (int i = 0; i < Ability::NUM; ++i) {
! Ability::Type type = types [i];
!
! if (directMethod.hasAbility (type)) {
! Ability* ability = type == Ability::STR?
! new Strength (directMethod):
! new Ability (type, directMethod);
! map [type] = AbilityPtr (ability);
! }
! }
}
***************
*** 84,98 ****
if (isComplete ()) {
! Map& map = *this;
Modifier::Value total = 0;
Ability* ability = NULL;
Ability::Score highest = 0;
- Ability::Type types [] = {
- Ability::CHA, Ability::CON, Ability::DEX,
- Ability::INT, Ability::STR, Ability::WIS
- };
for (int i = 0; i < Ability::NUM; ++i) {
! ability = map [types [i]];
total += (ability->getModifier ()).getValue ();
if (ability->getOriginalScore () > highest) {
--- 98,108 ----
if (isComplete ()) {
! PtrMap& map = *this;
Modifier::Value total = 0;
Ability* ability = NULL;
Ability::Score highest = 0;
for (int i = 0; i < Ability::NUM; ++i) {
! ability = (map [types [i]]).get ();
total += (ability->getModifier ()).getValue ();
if (ability->getOriginalScore () > highest) {
Index: Abilities.h
===================================================================
RCS file: /cvsroot/ogs/dist/c++/ogs/core/Abilities.h,v
retrieving revision 1.3
retrieving revision 1.4
diff -C2 -d -r1.3 -r1.4
*** Abilities.h 4 Apr 2003 20:22:43 -0000 1.3
--- Abilities.h 8 Apr 2003 21:43:08 -0000 1.4
***************
*** 28,55 ****
# include <map>
# include <ogs/core/Ability.h>
OGS_BEGIN_CORE_NAMESPACE
/**
! * A set of ability scores. A set of ability scores normally consists
! * of one score for each ability. Some entities however may not possess
! * all six abilities. Certain creatures for example may lack
! * Intelligence, Constitution, Strength, or some other ability by their
! * very nature.
*/
! class Abilities: private std::map<Ability::Type, Ability*> {
public:
! // TODO: Change this to a smart pointer.
! typedef std::map<Ability::Type, Ability*>::iterator Iterator;
Abilities ();
Abilities (Ability::Method& method);
! ~Abilities ();
Iterator getBegin ();
Iterator getEnd ();
! Ability* operator[] (Ability::Type abilityType);
! void removeAbility (Ability::Type abilityType);
bool isComplete () const;
--- 28,67 ----
# include <map>
+ # include <boost/shared_ptr.hpp>
+
# include <ogs/core/Ability.h>
OGS_BEGIN_CORE_NAMESPACE
+ /** A smart pointer that holds a dynamically allocated ability score. */
+ typedef boost::shared_ptr<Ability> AbilityPtr;
+
/**
! * A set of ability scores. Abilities are normally complete sets. A
! * complete set of ability scores consists of one score for each type of
! * ability. Some entities however may not possess all six abilities.
! * Certain creatures for example may lack Intelligence, Constitution,
! * Strength, or some other ability by their very nature. Sentient items
! * also do not have physical abilities. These entities have partial
! * sets of ability scores.
*/
! class Abilities: private std::map<Ability::Type, AbilityPtr> {
! private:
! typedef std::map<Ability::Type, Ability::Score> ScoreMap;
! typedef std::map<Ability::Type, AbilityPtr> PtrMap;
!
public:
! /** An iterator for each ability in this set. */
! typedef PtrMap::iterator Iterator;
!
! struct PartialMethod;
Abilities ();
Abilities (Ability::Method& method);
! Abilities (PartialMethod& directMethod);
Iterator getBegin ();
Iterator getEnd ();
! AbilityPtr operator[] (Ability::Type abilityType);
bool isComplete () const;
***************
*** 59,73 ****
private:
! typedef std::map<Ability::Type, Ability*> Map;
! typedef Map::value_type ValueType;
! struct Delete;
! Abilities (const Abilities& abilities);
! Abilities& operator= (const Abilities& abilities);
! bool canReroll (Modifier::Value modifier, Ability::Score score);
};
/**
* Determine the iterator for the beginning of these abilities.
*
--- 71,134 ----
private:
! bool canReroll (Modifier::Value modifier, Ability::Score score);
! };
! /**
! * A method that directly maps ability types to ability scores. The
! * partial method can be used to directly create a set of abilities with
! * preset scores. It can also be used to create partial sets of
! * abilities.
! */
! struct Abilities::PartialMethod: public Ability::Method,
! private Abilities::ScoreMap {
! /** A pair of ability type and ability score. */
! typedef Abilities::ScoreMap::value_type Value;
! /** An iterator of values. */
! typedef Abilities::ScoreMap::iterator Iterator;
! PartialMethod (Iterator first, Iterator last);
! bool hasAbility (Ability::Type type);
! Ability::Score operator() (Ability::Type type);
};
/**
+ * Create a new direct method. A direct method is created from a
+ * sequence of pairs of ability types and ability scores. The iterators
+ * point to the first and last element of this sequence. The sequence
+ * may describe a partial set of ability scores: all six ability pairs
+ * need not be present.
+ *
+ * @param first Iterator to first pair of ability type and score.
+ * @param first Iterator to last pair of ability type and score.
+ */
+ inline
+ Abilities::PartialMethod::PartialMethod (Iterator first, Iterator last):
+ ScoreMap (first, last) {
+ // empty constructor body
+ }
+
+ /**
+ * Determine if this method provides a score for an ability type.
+ *
+ * @param type An ability type.
+ * @return True if this method provides a score for the type.
+ */
+ inline bool
+ Abilities::PartialMethod::hasAbility (Ability::Type type) {
+ return (this->find (type) != this->end ());
+ }
+
+ /**
+ * Determine the score for an ability type.
+ *
+ * @param type An ability type.
+ * @return An ability score.
+ */
+ inline Ability::Score
+ Abilities::PartialMethod::operator() (Ability::Type type) {
+ return ((*this) [type]);
+ }
+
+ /**
* Determine the iterator for the beginning of these abilities.
*
***************
*** 96,115 ****
* @return An ability or null if the ability does not exist.
*/
! inline Ability*
Abilities::operator[] (Ability::Type abilityType) {
// The map::operator[] inserts the key if not found so this operator
// cannot use it. It has to check first and return NULL if not found.
Iterator itor = find (abilityType);
! return (itor == end ()? NULL: itor->second);
! }
!
! /**
! * Remove an ability from this set of abilities.
! *
! * @param abilityType Type of ability to be removed.
! */
! inline void
! Abilities::removeAbility (Ability::Type abilityType) {
! this->erase (abilityType);
}
--- 157,166 ----
* @return An ability or null if the ability does not exist.
*/
! inline AbilityPtr
Abilities::operator[] (Ability::Type abilityType) {
// The map::operator[] inserts the key if not found so this operator
// cannot use it. It has to check first and return NULL if not found.
Iterator itor = find (abilityType);
! return (itor == end ()? AbilityPtr (): itor->second);
}
Index: Ability.cpp
===================================================================
RCS file: /cvsroot/ogs/dist/c++/ogs/core/Ability.cpp,v
retrieving revision 1.5
retrieving revision 1.6
diff -C2 -d -r1.5 -r1.6
*** Ability.cpp 4 Apr 2003 20:22:43 -0000 1.5
--- Ability.cpp 8 Apr 2003 21:43:08 -0000 1.6
***************
*** 116,120 ****
_type (type),
_originalScore (rollStandard ()),
! _currentScore (_originalScore),
_modifier (getModifier (_originalScore)) {
if (! isValidType (type)) {
--- 116,120 ----
_type (type),
_originalScore (rollStandard ()),
! _modifiers (),
_modifier (getModifier (_originalScore)) {
if (! isValidType (type)) {
***************
*** 124,127 ****
--- 124,129 ----
throw std::invalid_argument (ostr.str ());
}
+
+ this->_modifiers.addObserver (*this);
}
***************
*** 137,141 ****
_type (type),
_originalScore (method (type)),
! _currentScore (_originalScore),
_modifier (getModifier (_originalScore)) {
if (! isValidType (type)) {
--- 139,143 ----
_type (type),
_originalScore (method (type)),
! _modifiers (),
_modifier (getModifier (_originalScore)) {
if (! isValidType (type)) {
***************
*** 145,148 ****
--- 147,152 ----
throw std::invalid_argument (ostr.str ());
}
+
+ this->_modifiers.addObserver (*this);
}
***************
*** 155,173 ****
void Ability::handleEvent (Event& event) {
try {
! Modifier::Event& modEvent = dynamic_cast<Modifier::Event&> (event);
! Modifier& modifier = dynamic_cast<Modifier&> (event.getSource ());
!
! this->_currentScore -= modEvent.getPreviousValue ();
! this->_currentScore += modifier.getValue ();
! // Update ability modifier only when neccessary.
! if (this->_modifier.getValue () != getModifier (this->_currentScore)) {
! this->_modifier.setValue (getModifier (this->_currentScore));
}
- Event event (*this);
notifyObservers (event);
} catch (...) {
! // Observed object was not a modifier. Ignore it.
}
}
--- 159,177 ----
void Ability::handleEvent (Event& event) {
try {
! //Modifiers::Event& realEvent = dynamic_cast<Modifiers::Event&> (event);
! Event event (*this);
! //Event event (*this, realEvent.getPreviousValue ());
! // The current score may change without the modifier value needing
! // to be updated. So update it only when neccessary.
! Score currentScore = getCurrentScore ();
! Modifier::Value value = getModifier (currentScore);
! if (this->_modifier.getValue () != value) {
! this->_modifier.setValue (value);
}
notifyObservers (event);
} catch (...) {
! // Observed object was not a modifiers list. Ignore it.
}
}
Index: Ability.h
===================================================================
RCS file: /cvsroot/ogs/dist/c++/ogs/core/Ability.h,v
retrieving revision 1.4
retrieving revision 1.5
diff -C2 -d -r1.4 -r1.5
*** Ability.h 4 Apr 2003 20:22:43 -0000 1.4
--- Ability.h 8 Apr 2003 21:43:08 -0000 1.5
***************
*** 105,174 ****
typedef unsigned short Score;
! /**
! * A function object that generates an ability score. The argument
! * of a method is the type of ability score to generate. A method
! * may ignore this parameter.
! */
! struct Method {
! virtual Score operator() (Type type) = 0;
! virtual ~Method () { }
! };
!
! /**
! * A method that generates above-average ability scores. The
! * standard method rolls 4d6 and adds the highest three rolls to
! * generate an ability score. The standard method is normally used
! * to generate ability scores for player characters.
! */
! struct StandardMethod: public Method {
! /**
! * Generate a score using the standard method. The type parameter
! * is not used.
! *
! * @return An ability score.
! */
! Score operator() (Type) {
! return (rollStandard ());
! }
! };
!
! /**
! * A method that generates average ability scores. The average
! * method rolls 3d6 to generate an ability score. The average
! * method is nnormally used to generate ability scores for
! * nonplayer characters.
! */
! struct AverageMethod: public Method {
! /**
! * Generate a score using the average method. The type parameter
! * is not used.
! *
! * @return An ability score.
! */
! Score operator() (Type) {
! return (rollAverage ());
! }
! };
!
! /**
! * A method that generates "high-powered" ability scores. The
! * high-powered method rolls 5d6 and adds the highest three rolls to
! * generate an ability score. The high-powered method is nnormally
! * used to generate ability scores for high-level player characters
! */
! struct HighPoweredMethod: public Method {
! /**
! * Generate a score using the high-powered method. The type
! * parameter is not used.
! *
! * @return An ability score.
! */
! Score operator() (Type) {
! return (rollHighPowered ());
! }
! };
static bool isValidType (int i);
- static Modifier::Value getModifier (Score score);
static unsigned getIncreaseCount (Experience::Level xpLevel);
static Experience::Level getIncreaseCountLevel (unsigned count);
--- 105,115 ----
typedef unsigned short Score;
! struct Method;
! struct StandardMethod;
! struct AverageMethod;
! struct HighPoweredMethod;
! struct DirectMethod;
static bool isValidType (int i);
static unsigned getIncreaseCount (Experience::Level xpLevel);
static Experience::Level getIncreaseCountLevel (unsigned count);
***************
*** 189,193 ****
Score _originalScore;
Modifiers _modifiers;
- Score _currentScore;
Modifier _modifier;
--- 130,133 ----
***************
*** 195,198 ****
--- 135,232 ----
static Score rollAverage ();
static Score rollHighPowered ();
+
+ static Modifier::Value getModifier (Score score);
+ };
+
+ /**
+ * A function object that generates an ability score. The argument of a
+ * method is the type of ability score to generate. A method may ignore
+ * this parameter.
+ */
+ struct Ability::Method {
+ virtual Ability::Score operator() (Ability::Type type) = 0;
+ virtual ~Method () { }
+ };
+
+ /**
+ * A method that generates above-average ability scores. The standard
+ * method rolls 4d6 and adds the highest three rolls to generate an
+ * ability score. The standard method is normally used to generate
+ * ability scores for player characters.
+ */
+ struct Ability::StandardMethod: public Ability::Method {
+ /**
+ * Generate a score using the standard method. The type parameter
+ * is not used.
+ *
+ * @return An ability score.
+ */
+ Ability::Score operator() (Ability::Type) {
+ return (Ability::rollStandard ());
+ }
+ };
+
+ /**
+ * A method that generates average ability scores. The average method
+ * rolls 3d6 to generate an ability score. The average method is
+ * normally used to generate ability scores for nonplayer characters.
+ */
+ struct Ability::AverageMethod: public Ability::Method {
+ /**
+ * Generate a score using the average method. The type parameter
+ * is not used.
+ *
+ * @return An ability score.
+ */
+ Ability::Score operator() (Ability::Type) {
+ return (Ability::rollAverage ());
+ }
+ };
+
+ /**
+ * A method that generates "high-powered" ability scores. The
+ * high-powered method rolls 5d6 and adds the highest three rolls to
+ * generate an ability score. The high-powered method is nnormally
+ * used to generate ability scores for high-level player characters
+ */
+ struct Ability::HighPoweredMethod: public Ability::Method {
+ /**
+ * Generate a score using the high-powered method. The type
+ * parameter is not used.
+ *
+ * @return An ability score.
+ */
+ Ability::Score operator() (Ability::Type) {
+ return (Ability::rollHighPowered ());
+ }
+ };
+
+ /**
+ * A method that generates a direct ability score. The direct method is
+ * used to initialize an ability with a fixed score. This method is
+ * normally used by referees and players who are allowed to choose
+ * ability scores.
+ */
+ struct Ability::DirectMethod: public Ability::Method {
+ Ability::Score score;
+
+ /**
+ * Create a new direct method.
+ *
+ * @param score A score to be generated by this method.
+ */
+ DirectMethod (Ability::Score score) {
+ this->score = score;
+ }
+
+ /**
+ * Generate a score using the direct method. This method simply
+ * returns the score contained in the direct method.
+ *
+ * @return An ability score.
+ */
+ Ability::Score operator() (Ability::Type) {
+ return (score);
+ }
};
***************
*** 274,278 ****
inline Ability::Score
Ability::getCurrentScore () const {
! return (this->_currentScore);
}
--- 308,312 ----
inline Ability::Score
Ability::getCurrentScore () const {
! return (this->_originalScore + this->_modifiers.getValue ());
}
Index: Character.cpp
===================================================================
RCS file: /cvsroot/ogs/dist/c++/ogs/core/Character.cpp,v
retrieving revision 1.5
retrieving revision 1.6
diff -C2 -d -r1.5 -r1.6
*** Character.cpp 29 Mar 2003 02:10:29 -0000 1.5
--- Character.cpp 8 Apr 2003 21:43:09 -0000 1.6
***************
*** 77,82 ****
// Add Ingelligence bonus if any.
Abilities& abilities = _creature.getAbilities ();
! Ability* intl = abilities [Ability::INT];
! if (intl != NULL) {
Modifier& modifier = intl->getModifier ();
Modifier::Value value = modifier.getValue ();
--- 77,82 ----
// Add Ingelligence bonus if any.
Abilities& abilities = _creature.getAbilities ();
! AbilityPtr intl = abilities [Ability::INT];
! if (intl) {
Modifier& modifier = intl->getModifier ();
Modifier::Value value = modifier.getValue ();
Index: Creature.cpp
===================================================================
RCS file: /cvsroot/ogs/dist/c++/ogs/core/Creature.cpp,v
retrieving revision 1.8
retrieving revision 1.9
diff -C2 -d -r1.8 -r1.9
*** Creature.cpp 29 Mar 2003 02:10:29 -0000 1.8
--- Creature.cpp 8 Apr 2003 21:43:09 -0000 1.9
***************
*** 41,45 ****
_skills (), _feats (), _body (body), _character (NULL) {
// Add Dexterity modifier to Reflex save, initiative, and defense.
! Ability* ability = this->_abilities [Ability::DEX];
Modifier& modifier = ability->getModifier ();
this->_saves.ref.addModifier (modifier);
--- 41,45 ----
_skills (), _feats (), _body (body), _character (NULL) {
// Add Dexterity modifier to Reflex save, initiative, and defense.
! AbilityPtr ability = this->_abilities [Ability::DEX];
Modifier& modifier = ability->getModifier ();
this->_saves.ref.addModifier (modifier);
Index: Modifier.cpp
===================================================================
RCS file: /cvsroot/ogs/dist/c++/ogs/core/Modifier.cpp,v
retrieving revision 1.2
retrieving revision 1.3
diff -C2 -d -r1.2 -r1.3
*** Modifier.cpp 25 Mar 2003 06:13:11 -0000 1.2
--- Modifier.cpp 8 Apr 2003 21:43:09 -0000 1.3
***************
*** 25,32 ****
#include <typeinfo>
! #include "ogs/Support.h"
#include "ogs/core/Modifier.h"
! using namespace ogs::support;
using ogs::core::Modifier;
--- 25,32 ----
#include <typeinfo>
! #include "ogs/support/Object.h"
#include "ogs/core/Modifier.h"
! using ogs::support::Object;
using ogs::core::Modifier;
***************
*** 39,44 ****
// Let event store previous value before it is changed.
Modifier::Event event (*this);
!
! this->value = value;
notifyObservers (event);
}
--- 39,43 ----
// Let event store previous value before it is changed.
Modifier::Event event (*this);
! this->_value = value;
notifyObservers (event);
}
***************
*** 52,68 ****
std::string Modifier::toString () const {
std::ostringstream ostr;
! ostr << (typeid (this)).name () << "@" << this;
! ostr << " [value " << value << "]";
return (ostr.str ());
- }
-
- /**
- * Create a new modifier event.
- *
- * @param modifier Modifier causing this event.
- */
- Modifier::Event::Event (Modifier& modifier):
- ogs::support::Event (modifier) {
- this->value = modifier.getValue ();
}
--- 51,57 ----
std::string Modifier::toString () const {
std::ostringstream ostr;
! ostr << Object::toString ();
! ostr << " [value " << this->_value << "]";
return (ostr.str ());
}
Index: Modifier.h
===================================================================
RCS file: /cvsroot/ogs/dist/c++/ogs/core/Modifier.h,v
retrieving revision 1.1
retrieving revision 1.2
diff -C2 -d -r1.1 -r1.2
*** Modifier.h 7 Jan 2003 07:41:33 -0000 1.1
--- Modifier.h 8 Apr 2003 21:43:09 -0000 1.2
***************
*** 36,41 ****
/**
! * A modifier is an integer value added to (or subtracted from if
! * negative) another integer value.
*/
class Modifier: public ogs::support::Object {
--- 36,45 ----
/**
! * An integer value added to another integer value. If the value of the
! * modifier is negative, the value of the modifier is subtracted from
! * the other value. The "other" value may be an objects that has a
! * modifiable integer attribute. The integer value is encapsulated in
! * a class to allow modifier objects to notify observers of events that
! * cause the value of the modifier to change.
*/
class Modifier: public ogs::support::Object {
***************
*** 44,50 ****
* A signed integer type representing the value of a modifier. This
* type is explicitly named in case the underlying type should
! * changes in the future.
*/
! typedef int Value;
class Event;
--- 48,54 ----
* A signed integer type representing the value of a modifier. This
* type is explicitly named in case the underlying type should
! * change in the future.
*/
! typedef short Value;
class Event;
***************
*** 58,71 ****
private:
! Value value;
};
/**
! * Create a modifier with a specified value.
*
* @param value Value of the modifier.
*/
! inline Modifier::Modifier (Value value) {
! this->value = value;
}
--- 62,77 ----
private:
! Value _value;
};
/**
! * Create a new modifier. The default value of the modifier is zero (0).
*
* @param value Value of the modifier.
*/
! inline
! Modifier::Modifier (Value value):
! _value (value) {
! // empty constructor body
}
***************
*** 75,102 ****
* @return Value of the modifier.
*/
! inline Modifier::Value Modifier::getValue () const {
! return (this->value);
}
/**
* An event that allows observers to determine the previous value of
! * the modifier.
*/
class Modifier::Event: public ogs::support::Event {
public:
- Event (Modifier& modifier);
Value getPreviousValue () const;
private:
! Value value;
};
/**
* Determine previous value of this modifier.
*
* @return Previous value of this modifier.
*/
! inline Modifier::Value Modifier::Event::getPreviousValue () const {
! return (this->value);
}
--- 81,123 ----
* @return Value of the modifier.
*/
! inline Modifier::Value
! Modifier::getValue () const {
! return (this->_value);
}
/**
* An event that allows observers to determine the previous value of
! * the modifier. Modifier events must be created before the modifier
! * value is changed so the event can store the preivous value!
*/
class Modifier::Event: public ogs::support::Event {
public:
Value getPreviousValue () const;
private:
! Value _value;
! Event (Modifier& modifier);
! friend void Modifier::setValue (Value value);
};
/**
+ * Create a new modifier event.
+ *
+ * @param modifier Modifier causing this event.
+ */
+ inline
+ Modifier::Event::Event (Modifier& modifier):
+ ogs::support::Event (modifier), _value (modifier.getValue ()) {
+ // empty constructor body
+ }
+
+ /**
* Determine previous value of this modifier.
*
* @return Previous value of this modifier.
*/
! inline Modifier::Value
! Modifier::Event::getPreviousValue () const {
! return (this->_value);
}
Index: Modifiers.cpp
===================================================================
RCS file: /cvsroot/ogs/dist/c++/ogs/core/Modifiers.cpp,v
retrieving revision 1.2
retrieving revision 1.3
diff -C2 -d -r1.2 -r1.3
*** Modifiers.cpp 25 Mar 2003 06:13:11 -0000 1.2
--- Modifiers.cpp 8 Apr 2003 21:43:10 -0000 1.3
***************
*** 21,24 ****
--- 21,25 ----
*/
+ #include "ogs/support/Event.h"
#include "ogs/core/Modifiers.h"
***************
*** 27,35 ****
/**
- * Create an empty list of modifiers.
- */
- Modifiers::Modifiers (): list (), value (0) { }
-
- /**
* Add a modifier to this list of modifiers. The total value is
* updated accordingly and observers are notified.
--- 28,31 ----
***************
*** 39,46 ****
void Modifiers::addModifier (Modifier& modifier) {
modifier.addObserver (*this);
! list.push_front (&modifier);
! Event event (*this);
! this->value += modifier.getValue ();
notifyObservers (event);
}
--- 35,42 ----
void Modifiers::addModifier (Modifier& modifier) {
modifier.addObserver (*this);
! this->_list.push_front (&modifier);
! Event event (*this, Event::ADDED, modifier);
! this->_value += modifier.getValue ();
notifyObservers (event);
}
***************
*** 54,61 ****
void Modifiers::removeModifier (Modifier& modifier) {
modifier.removeObserver (*this);
! list.remove (&modifier);
! Event event (*this);
! value -= modifier.getValue ();
notifyObservers (event);
}
--- 50,57 ----
void Modifiers::removeModifier (Modifier& modifier) {
modifier.removeObserver (*this);
! this->_list.remove (&modifier);
! Event event (*this, Event::REMOVED, modifier);
! this->_value -= modifier.getValue ();
notifyObservers (event);
}
***************
*** 68,80 ****
* @param event Event that occured.
*/
! void Modifiers::handleEvent (Event& event) {
try {
! Modifier::Event& modEvent = dynamic_cast<Modifier::Event&> (event);
Modifier& modifier = dynamic_cast<Modifier&> (event.getSource ());
! Event event (*this);
! this->value -= modEvent.getPreviousValue ();
! this->value += modifier.getValue ();
! notifyObservers (event);
} catch (...) {
// Observed object was not a modifier. Ignore it.
--- 64,81 ----
* @param event Event that occured.
*/
! void Modifiers::handleEvent (ogs::support::Event& event) {
try {
! Modifier::Event& oldEvent = dynamic_cast<Modifier::Event&> (event);
Modifier& modifier = dynamic_cast<Modifier&> (event.getSource ());
! /* The cached value is updated by subtracting the previous value of
! * the modifier that changed and then adding its new value. The
! * only other way to update the cached value would be to reset it to
! * zero (0), then add every modifier in the list.
! */
! Event newEvent (*this, Event::CHANGED, modifier);
! this->_value -= oldEvent.getPreviousValue ();
! this->_value += modifier.getValue ();
! notifyObservers (newEvent);
} catch (...) {
// Observed object was not a modifier. Ignore it.
Index: Modifiers.h
===================================================================
RCS file: /cvsroot/ogs/dist/c++/ogs/core/Modifiers.h,v
retrieving revision 1.1
retrieving revision 1.2
diff -C2 -d -r1.1 -r1.2
*** Modifiers.h 7 Jan 2003 07:41:33 -0000 1.1
--- Modifiers.h 8 Apr 2003 21:43:10 -0000 1.2
***************
*** 26,29 ****
--- 26,30 ----
# define OGS_CORE_MODIFIERS_H
+ # include <cassert>
# include <list>
***************
*** 35,43 ****
/**
! * A list of modifiers.
*/
class Modifiers: public ogs::support::Object,
public ogs::support::Observer {
public:
Modifiers ();
--- 36,54 ----
/**
! * A list of modifiers. A modifier list allows objects to observe a
! * single object rather than each modifier in the list. A modifier list
! * intercepts events caused by each modifier in the list. It also
! * generates its own events when a modifier is added or removed from the
! * list. In either case, the list updates a total value, cached
! * internally, and transmits an event to observers of the list. Note
! * that a modifier list behaves just like an STL list. If dynamically
! * allocated modifiers are added to it, they must be deallocated by the
! * caller.
*/
class Modifiers: public ogs::support::Object,
public ogs::support::Observer {
public:
+ class Event;
+
Modifiers ();
***************
*** 49,67 ****
void handleEvent (ogs::support::Event& event);
! protected:
typedef std::list<Modifier*> List;
! private:
! List list;
! Modifier::Value value;
};
/**
* Determine the total value of all modifiers in this list.
*
* @return Total value of all modifiers in this list.
*/
! inline Modifier::Value Modifiers::getValue () const {
! return (this->value);
}
--- 60,168 ----
void handleEvent (ogs::support::Event& event);
! private:
typedef std::list<Modifier*> List;
! List _list;
! Modifier::Value _value;
};
/**
+ * Create an empty list of modifiers.
+ */
+ inline
+ Modifiers::Modifiers ():
+ _list (), _value (0) {
+ // empty constructor body
+ }
+
+ /**
* Determine the total value of all modifiers in this list.
*
* @return Total value of all modifiers in this list.
*/
! inline Modifier::Value
! Modifiers::getValue () const {
! return (this->_value);
! }
!
! /**
! * An event that allows observers to determine the previous value of a
! * list of modifiers. Modifier list events must be created before the
! * list is changed so the event can store the preivous value!
! */
! class Modifiers::Event: public ogs::support::Event {
! public:
! /** The type of event that happened. */
! enum Type {
! /** A modifier was added to the list. */
! ADDED,
! /** A modifier was removed from the list. */
! REMOVED,
! /** The value of a modifier in the list changed. */
! CHANGED
! };
!
! Modifier::Value getPreviousValue () const;
! Type getType () const;
! Modifier& getModifier () const;
!
! private:
! Modifier::Value _value;
! Type _type;
! Modifier* _modifier;
!
! Event (Modifiers& modifiers, Type type, Modifier& modifier);
!
! friend void Modifiers::addModifier (Modifier& modifier);
! friend void Modifiers::removeModifier (Modifier& modifier);
! friend void Modifiers::handleEvent (ogs::support::Event& event);
! };
!
! /**
! * Create a new modifier list event.
! *
! * @param modifiers Modifier list causing this event.
! */
! inline
! Modifiers::Event::Event (Modifiers& modifiers,
! Type type,
! Modifier& modifier):
! ogs::support::Event (modifiers),
! _value (modifiers.getValue ()),
! _type (type),
! _modifier (&modifier) {
! // empty constructor body
! }
!
! /**
! * Determine previous value of this list of modifiers.
! *
! * @return Previous value of this list of modifiers.
! */
! inline Modifier::Value
! Modifiers::Event::getPreviousValue () const {
! return (this->_value);
! }
!
! /**
! * Determine the type of this event. A modifier list event has three
! * types: added, removed, or changed.
! *
! * @return Type of this event.
! */
! inline Modifiers::Event::Type
! Modifiers::Event::getType () const {
! return (this->_type);
! }
!
! /**
! * Determine the modifier described by the type of this event.
! *
! * @return Modifier described by the type of this event.
! */
! inline Modifier&
! Modifiers::Event::getModifier () const {
! assert (this->_modifier != NULL);
! return (*(this->_modifier));
}
|