Better Living Through JavaScript Closures, An Example

function ConfigObject(){
	var vowels = ["a","e","i","o","u"];
	var consonants = ["b","d","f","g","h","k","l","m","n","p","r","s","t","v","w","z"];
	var minimumNameLength = 3;
	var maximumNameLength = 10;
	var islandCount = 1000;
	var minimumIslandX = 0;
	var minimumIslandY = 0;
	var maximumIslandX = 1000;
	var maximumIslandY = 1000;
	var minimumIslandDistance = 10;
	var maximumDockingDistance = 2;
	var currencyCommodity = "gold";
	var unknownIslandName = "an unknown island";

	this.getVowelCount = function(){return vowels.length;};
	this.getVowel=function(index){return vowels[index];};
	this.getConsonantCount = function(){return consonants.length;};
	this.getConsonant = function(index){return consonants[index];};
	this.getMinimumNameLength = function(){return minimumNameLength;};
	this.getMaximumNameLength = function(){return maximumNameLength;};
	this.getIslandCount = function(){return islandCount;};
	this.getMinimumIslandX = function(){return minimumIslandX;};
	this.getMinimumIslandY = function(){return minimumIslandY;};
	this.getMaximumIslandX = function(){return maximumIslandX;};
	this.getMaximumIslandY = function(){return maximumIslandY;};
	this.getCenterIslandX = function(){return this.getMaximumIslandX()/2+this.getMinimumIslandX()/2;};
	this.getCenterIslandY = function(){return this.getMaximumIslandY()/2+this.getMinimumIslandY()/2;};
	this.getMinimumIslandDistance = function(){return minimumIslandDistance;};
	this.getCurrencyCommodity = function(){return currencyCommodity;};
	this.getUnknownIslandName = function(){return unknownIslandName;};
}
ConfigObject.prototype = new Unserializable();

The above is a good example of what I was talking about in my last post.  Previous to my work today, all of the items that are now preceded by “var” were preceded by “this.”, which means if I were careless, I would be able to clobber the values if I used them as raw properties.  Now I can’t, as the only way to access them is to use the various getter functions.

I’ve also found other areas where I don’t want to expose certain variables to serialization, like the following:

function AvatarCommodityObject(theCommodity){
	var commodity = theCommodity;
	this.units = Game.Commodities.getCommodity(commodity).rollInventory();

	this.getCommodity = function(){
		return commodity;
	}
	this.getUnits = function(){
		return this.units;
	};
	this.setUnits = function(units){
		this.units = units;
	};
	this.buyUnits = function(unitCount){
		this.setUnits(this.getUnits()+unitCount);
	};
	this.sellUnits = function(unitCount){
		this.setUnits(this.getUnits()-unitCount);
	};
}
AvatarCommodityObject.prototype = new Serializable();

Here I have put commodity as a var within the function, and the getter of getCommodity will retrieve it. I cannot be set after construction.  The variable this.units will still get serialized as usual.  Functions never get serialized, and so are a non-problem.

My one remaining issue is the call to Game.Commodities.getCommodity().  I should not have to rely upon a global Game object, nor its subobject Commodities.  Indeed, the Commodities object should be passed in to this constructor.  This I’ll be refactoring shortly.

I feel as though I’ve “leveled up” my JavaScript.

Advertisements

Tags: , ,

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s


%d bloggers like this: