Sí, es un problema de inicialización. this
no se refiere a su objeto SizeManager
en el punto en que lo está utilizando. (Los inicializadores de objeto no cambian el valor de this
). this
se establece por la forma en que llama a una función y tiene el mismo valor a lo largo de esa llamada de función. No está llamando al ninguna función allí, por lo que this
tiene el valor que tenía antes del comienzo de ese código.
(he señalado algo sobre ratio
de su ejemplo específico al final de este, pero primero vamos a caminar a través de algunas opciones para el caso general se eleva.)
Daniel's given you un buen novillo en hacer ratio
una función, excepto que no parece haberse dado cuenta de que desea variar el ancho. Alternativamente, si width
y height
no van a cambiar, simplemente calcularlo después:
var SizeManager = {
width : 800,
height : 600,
resize : function (newWidth) {
this.width = newWidth;
this.height = newWidth/this.ratio;
}
};
SizeManager.ratio = SizeManager.width/SizeManager.height;
(Nota al margen: He añadido this.
a las propiedades que se está haciendo referencia en resize
Ellos habían desaparecido de su original. ., pero son requeridos sin ellos, que está tratando con el horror of implicit globals, que es una mala cosa (tm))
Por supuesto, es posible encapsular todo eso en una fábrica:.
function makeSizeManager(width, height) {
return {
width : width,
height : height,
ratio : width/height,
resize : function (newWidth) {
this.width = newWidth;
this.height = newWidth/this.ratio;
}
};
}
var SizeManager = makeSizeManager(800, 600);
... pero que también podría hacer que sea una función constructora de real para que no se crea un montón de duplicado (pero idéntico) resize
funciones:
function SizeManager(width, height) {
this.width = width;
this.height = height;
this.ratio = width/height;
}
SizeManager.prototype.resize = function (newWidth) {
this.width = newWidth;
this.height = newWidth/this.ratio;
};
var aSizeManagerInstance = new SizeManager(800, 600);
(tenga en cuenta que los nombres cambian un poco en este último.)
Y como una última nota final: En el ejemplo específico, que en realidad no tienen que almacenar ratio
en absoluto, usted puede hacer esto:
var SizeManager = {
width : 800,
height : 600,
resize : function (newWidth) {
var ratio = this.width/this.height;
this.width = newWidth;
this.height = newWidth/ratio;
}
};
Pero eso es sólo para ese ejemplo específico, por lo tanto, la discusión anterior para hablar sobre el caso general.
Si lo está cambiando de un objeto literal a una función, debe cambiar la forma en que especifica las propiedades (en el tercer bloque de código). es decir. 'this.width = width' en lugar de' this.width: width' –
@Daniel: ¡Gracias! parece que solo edité a medias esas líneas después de pegarlas. Fijo. –