fix(change_detection): handle locals when invoking a method

Closes #660
This commit is contained in:
vsavkin
2015-02-20 15:50:12 -08:00
parent 7f31036427
commit 0dfd287ec3
3 changed files with 34 additions and 3 deletions

View File

@ -203,6 +203,17 @@ if (${TEMP_LOCAL} instanceof ContextWithVariableBindings) {
`;
}
function invokeMethodTemplate(name:string, args:string, context:string, newValue:string) {
return `
${TEMP_LOCAL} = ${UTIL}.findContext("${name}", ${context});
if (${TEMP_LOCAL} instanceof ContextWithVariableBindings) {
${newValue} = ${TEMP_LOCAL}.get('${name}').apply(null, [${args}]);
} else {
${newValue} = ${context}.${name}(${args});
}
`;
}
function localDefinitionsTemplate(names:List):string {
return names.map((n) => `var ${n};`).join("\n");
}
@ -366,7 +377,11 @@ export class ChangeDetectorJITGenerator {
}
case RECORD_TYPE_INVOKE_METHOD:
return assignmentTemplate(newValue, `${context}.${r.name}(${args})`);
if (r.contextIndex == 0) { // only the first property read can be a local
return invokeMethodTemplate(r.name, args, context, newValue);
} else {
return assignmentTemplate(newValue, `${context}.${r.name}(${args})`);
}
case RECORD_TYPE_INVOKE_CLOSURE:
return assignmentTemplate(newValue, `${context}(${args})`);

View File

@ -132,8 +132,16 @@ export class DynamicChangeDetector extends AbstractChangeDetector {
break;
case RECORD_TYPE_INVOKE_METHOD:
var methodInvoker:Function = proto.funcOrValue;
return methodInvoker(this._readContext(proto), this._readArgs(proto));
var context = this._readContext(proto);
var args = this._readArgs(proto);
var c = ChangeDetectionUtil.findContext(proto.name, context);
if (c instanceof ContextWithVariableBindings) {
return FunctionWrapper.apply(c.get(proto.name), args);
} else {
var methodInvoker:Function = proto.funcOrValue;
return methodInvoker(c, args);
}
break;
case RECORD_TYPE_KEYED_ACCESS:
var arg = this._readArgs(proto)[0];