回调问题的范围问题

时间:2014-03-19 10:14:34

标签: javascript

我正在尝试创建一个类似角度的范围对象来响应其属性的变化。这是预期的行为:

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"

目前年龄钥匙工作正常。但名字却没有。我怀疑它与以下函数中的作用域有关:

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)
        }
      }
    )
  }
}

问题似乎是将var key传递给此:function(scope) { return scope.data[key] },以下是使用的其他两个函数:

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);
    }
  }
}

有人有任何想法如何解决这个功能?如果我在控制台中初始化观察者它可以完美地工作但我希望它是自动化的,所以你不必在每次定义一个新变量时都定义一个观察者。

1 个答案:

答案 0 :(得分:0)

找到解决方案。方法是使用这个:

Scope.prototype.$createWatcher = function(key) {
  return function(scope) { return scope.data[key] }
}

然后在init函数中:

$$.$watch(
  $$.$createWatcher(key),
  function(newValue, oldValue, scope) {
    if(newValue) {
      console.log ('has been changed from "%s" to "%s"',oldValue, newValue)
    }
  }
)