Module Pattern And This
Solution 1:
In that case every new instance of Seat
will share the newest Self
object since it is set in the constructor. You should avoid doing this.
Solution 2:
A more practical demo example might be something like this, where you want to make sure this
is the instance of the class.
functionFoo() {
var _this = this;
_this.someItem = {};
_this.go = function() {
doSomethingElse(function(result) {
_this.someItem.something = result; // _this and this are different
});
};
};
functiondoSomethingElse(callback) {
callback('asdf');
}
var foo = newFoo();
foo.go();
For your example using that pattern, you can define the _this
in each method if it would be any benefit (this one wouldn't, but a more complex example might):
Seat.prototype.moveTo = function(newX, newY) {
var _this = this;
if(newX >= 0 && newY >= 0) {
_this.x = newX; _this.y = newY;
}
};
Solution 3:
Yes, by doing it this way, all instances of Seat
will have the same this
, causing problems all over the place. Just remove the var self
and use this
in all places where you were using self
. In the code you've given, there's no point where you will lose reference to this
.
(@added example) Now your question makes more sense.
Instead of trying to handle this for all methods at once, you'll have to handle it at each point where you're using a function that has a different this
(any function that isn't on the prototype or instance).
If you don't need this
inside the callback, I would just use .bind
to make the instance this
available inside. Note however that .bind
isn't supported in some (very)old versions of IE, so you'll either need a polyfil to work for those, or store this
in a var.
SeatingChartView.prototype.addSeat = function(newSeat) {
var newCircle = new createjs.Shape();
newCircle.graphics.beginFill("black").drawCircle(0, 0, 10);
newCircle.x = newSeat.x;
newCircle.y = newSeat.y;
newCircle.seat = newSeat;
newCircle.on('click', function(event) {
if(event.nativeEvent.button == 2) {
this.seatForm.open(event.currentTarget.seat);
}
}.bind(this)); // modified here, added `.bind(this)`
newCircle.on('pressmove', this.controller.moveSeat)
this.stage.addChild(newCircle);
}
Solution 4:
This would totally negate the purpose of "classing". But in JS it's called prototyping.
Principally you want the base prototype to be "copied" when creating new instances. The base prototype should be shielded from changes when extended.
Suppose you have done what you did, all instances of Seat
will have the same properties. Even worst, when creating new "copies" of Seat
, all other previously created copies will have their values changed.
Since you want this
to maintain reference to Seat
, I would recommend using the following pattern:
var Base = {
init: function(arg) {
this.name = arg;
},
getName: function() {
returnthis.name;
}
}
Base.init('foo');
Base.getName(); // returns 'foo'
Your transformed code:
var Seat = {
init: function(startX, startY, inputSeatNumber, inputTableNumber) {
this.radius = 10;
this.x = startX;
this.y = startY;
this.seatNumber = inputSeatNumber;
this.tableNumber = inputTableNumber;
},
moveTo: function(newX, newY) {
if (newX >= 0 && newY >= 0) {
this.x = newX; this.y = newY;
}
},
setBackground: function(imageLocation) {
var self = this;
this.background = new createjs.Bitmap(imageLocation);
setTimeout(function() {
self.stage.canvas.width = self.background.image.width;
self.stage.canvas.height = self.background.image.height;
self.stage.addChild(self.background);
self.stage.update();
}, 500);
}
}
Extend the prototype:
var vipSeat = Object.create(Seat);
vipSeat.init( //your init values )
You can also not create an init method and simply use Object.create's second argument to assignment initial values to the prototype: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/create#Example:_Using_propertiesObject_argument_with_Object.create
Post a Comment for "Module Pattern And This"