Skip to content

Commit 0dfd287

Browse files
committed
fix(change_detection): handle locals when invoking a method
Closes angular#660
1 parent 7f31036 commit 0dfd287

File tree

3 files changed

+34
-3
lines changed

3 files changed

+34
-3
lines changed

modules/angular2/src/change_detection/change_detection_jit_generator.es6

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -203,6 +203,17 @@ if (${TEMP_LOCAL} instanceof ContextWithVariableBindings) {
203203
`;
204204
}
205205

206+
function invokeMethodTemplate(name:string, args:string, context:string, newValue:string) {
207+
return `
208+
${TEMP_LOCAL} = ${UTIL}.findContext("${name}", ${context});
209+
if (${TEMP_LOCAL} instanceof ContextWithVariableBindings) {
210+
${newValue} = ${TEMP_LOCAL}.get('${name}').apply(null, [${args}]);
211+
} else {
212+
${newValue} = ${context}.${name}(${args});
213+
}
214+
`;
215+
}
216+
206217
function localDefinitionsTemplate(names:List):string {
207218
return names.map((n) => `var ${n};`).join("\n");
208219
}
@@ -366,7 +377,11 @@ export class ChangeDetectorJITGenerator {
366377
}
367378
368379
case RECORD_TYPE_INVOKE_METHOD:
369-
return assignmentTemplate(newValue, `${context}.${r.name}(${args})`);
380+
if (r.contextIndex == 0) { // only the first property read can be a local
381+
return invokeMethodTemplate(r.name, args, context, newValue);
382+
} else {
383+
return assignmentTemplate(newValue, `${context}.${r.name}(${args})`);
384+
}
370385
371386
case RECORD_TYPE_INVOKE_CLOSURE:
372387
return assignmentTemplate(newValue, `${context}(${args})`);

modules/angular2/src/change_detection/dynamic_change_detector.js

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -132,8 +132,16 @@ export class DynamicChangeDetector extends AbstractChangeDetector {
132132
break;
133133

134134
case RECORD_TYPE_INVOKE_METHOD:
135-
var methodInvoker:Function = proto.funcOrValue;
136-
return methodInvoker(this._readContext(proto), this._readArgs(proto));
135+
var context = this._readContext(proto);
136+
var args = this._readArgs(proto);
137+
var c = ChangeDetectionUtil.findContext(proto.name, context);
138+
if (c instanceof ContextWithVariableBindings) {
139+
return FunctionWrapper.apply(c.get(proto.name), args);
140+
} else {
141+
var methodInvoker:Function = proto.funcOrValue;
142+
return methodInvoker(c, args);
143+
}
144+
break;
137145

138146
case RECORD_TYPE_KEYED_ACCESS:
139147
var arg = this._readArgs(proto)[0];

modules/angular2/test/change_detection/change_detection_spec.js

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -318,6 +318,14 @@ export function main() {
318318
.toEqual(['key=value']);
319319
});
320320

321+
it('should invoke a function from ContextWithVariableBindings', () => {
322+
var locals = new ContextWithVariableBindings(null,
323+
MapWrapper.createFromPairs([["key", () => "value"]]));
324+
325+
expect(executeWatch('key', 'key()', locals))
326+
.toEqual(['key=value']);
327+
});
328+
321329
it('should handle nested ContextWithVariableBindings', () => {
322330
var nested = new ContextWithVariableBindings(null,
323331
MapWrapper.createFromPairs([["key", "value"]]));

0 commit comments

Comments
 (0)