I'm trying to make an angular-like scope object that responds to changes in its properties. This is the intended behavior:
x = new Scope('a', 'b');
x.data = {
name: 'Jim',
age : 19
}
x.$init();
x.$digest();
x.data.name = 'Bob';
x.$digest();
// name has been changed from "Jim" to "Bob"
x.data.age = 200;
x.$digest();
// age has been changed from "19" to "200"
The age key works fine at the moment. But the name doesn't. I suspect it's to do with scoping in the following function:
Scope.prototype.$init = function() {
$$ = this;
$$.keys = Object.keys($$.data);
for(var i=0; i<$$.keys.length; i++) {
var key = $$.keys[i];
$$.$watch(
function(scope) { return scope.data[key] },
function(newValue, oldValue, scope) {
if(newValue) {
console.log ('%s has been changed from "%s" to "%s"',key,oldValue, newValue)
}
}
)
}
}
The problem seems to be passing the var key
into this: function(scope) { return scope.data[key] },
Here are the other two functions used:
Scope.prototype.$watch = function(watchFunction, listenerFunction) {
var watcher = {
watchFunction: watchFunction,
listenerFunction: listenerFunction
}
this.watchers.unshift(watcher)
}
Scope.prototype.$digest = function() {
var length = this.watchers.length;
var watcher, newValue, oldValue
while(length--) {
watcher = this.watchers[length];
newValue = watcher.watchFunction(this);
oldValue = watcher.last;
if(newValue !== oldValue) {
watcher.last = newValue;
watcher.listenerFunction(newValue, oldValue, this);
}
}
}
Has anybody got any ideas how to solve that function? If I initialise the watcher in the console it works perfectly but I want it automated so you don't have to define a watcher everytime you define a new variable.