Skip to content

Instantly share code, notes, and snippets.

@boxofrox
Last active December 16, 2015 09:39
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save boxofrox/5414640 to your computer and use it in GitHub Desktop.
Save boxofrox/5414640 to your computer and use it in GitHub Desktop.
Lazy stats accessor. Only recomputes value when necessary, but requires managing flags to avoid stale cache.
// need a static local variable here to ensure all new stats have unique'ish ids.
// stacking the same modifier is not possible. create a new object of the same modifier in order
// to apply the same effect twice.
var StatModifier = (function () {
var idCounter = 0;
return Base.extends({
id: 0,
name: '',
affects: '',
offset: 0,
constructor: function (settings) {
settings = settings || {};
// override defaults with settings
this.id = idCounter++;
_.extend(this, settings);
},
toString: function () {
return '[' + name + ', ' + affects + ', ' + offset + ']';
},
},
})();
var Stat = Base.extends({
name: '',
value: 0,
baseValue: 0,
modifiers: null,
constructor: function (name, startingValue) {
this.name = name || '';
this.baseValue = startingValue || 0;
this.value = this.baseValue;
modifiers = {};
},
addModifier: function (mod) {
// ignore this modifier if it's invalid or has no effect
if (!mod || !mod.value) return;
// warning: this modifier affects some other stat
if (this.name == mod.affects) {
console.log('Attempted to add stat modifier ' + mod.toString() + ' to wrong stat, ' + this.name);
return;
}
// ignore this modifier if it's already applied. NOTE: this occurance is a bug. accounting elsewhere has failed D:
if (this.modifiers[mod.id] === mod) {
console.log('Attempting to re-add stat modifier, ' + mod.name + ', to stat, ' + this.name)
return;
}
this.modifiers[mod.id] = mod;
this.addOffset(mod.value);
},
// why addOffset? because maybe some stats should extend and override this function. why?
// maybe some stats may have a floor/ceiling (clipped stat). maybe some can be negative or must be positive, etc.
// maybe some stats cannot change by more than 5 points (clipped offset), etc.
// this should be a private function. never use outside this class.
addOffset = function (offset) {
this.value += offset;
if (this.value < 0) this.value = 0;
},
removeModifier = function (mod) {
if (mod && this.modifiers[mod.id]) {
this.modifiers[mod.id] = null;
}
},
});
// example: creating a stat
Game.player = new Player({
skills: {
botany: new Stat({
name: 'botany'
}),
},
});
// example: creating stat modifier
brownThumb = new StatModifier({
name: 'brown thumb',
affects: 'botany',
offset: -5,
});
// example: applying stat modifier
Game.player.skills.botany.addModifier(brownThumb);
// example: reading the base stat
value = Game.player.skills.botany.baseValue;
// example: reading the modified stat
value = Game.player.skills.botany.value;
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment