1

I have an Angular2 Project (IntelliJ IDEA) in witch I use two-way-binding according to this example:

child.component.ts:

  counterValue = 0;
  @Output() counterChange = new EventEmitter();

  @Input()
  get counter() {
    return this.counterValue;
  }

  set counter(val) {
    this.counterValue = val;
    this.counterChange.emit(this.counterValue);
  }

  decrement() {
    this.counter--;
  }

  increment() {
    this.counter++;
  }

child.component.html:

<button (click)="decrement()">-</button>
<span>{{counter}}</span>
<button (click)="increment()">+</button>

parent.component.html:

<child-component [(counter)]="co"></child-component>
co: {{co}}

parent.component.ts:

co = 4;

The code works as expected - unless I change some variable names (both ways: using refactor aswell as manually - looking up all references).

I can change the name of counterValue (even change the variable type through the whole code) but as soon as either refactoring counterChange (2 occurences, as far as I can tell) or counter(...) (4 in child.component.ts, 2 in child.component.html, 1 in parent.html) the output-binding to the parent stops working. The child-component however always works as expected; just the co variable of the parent-component doesn't update anymore.

I went as far as restarting IntelliJ & npm, clearing the caches of IntelliJ and browser: didn't help.

By changing the names back to the ones from the example the output-binding works again.

I'm running out of ideas now and have the terrible feeling of overlooking something fundamental...

B748
  • 35
  • 5
  • 2
    Please show us how the changed variable names look like? I suspect know what the error could be ;) – AT82 Nov 08 '17 at 18:47
  • I tried dozens of variations from `temp` over `onTest` to `visible` and `onVisibilityChange` (which was the main purpose: to mimic the visibility-behaviour of a dialog). Nothing worked until I tried the following on a hunch: the emitter had to be the getter and setter function-name suffixed with `Change`. So `cat123` as getter and setter in conjunction with `cat123Change` worked... – B748 Nov 08 '17 at 21:29
  • 2
    Yes, that is why I asked for the changed variable names, the output needs to be the input variable name + the suffix `Change` – AT82 Nov 09 '17 at 05:11
  • 1
    OK. So this IS indeed fundamental (and - to be honest - a little bit annoying). With this information I found some other threads pointing to the same mistake, e.g. this one: [Angular 2 two way data binding not working](https://stackoverflow.com/questions/45039472/angular-2-two-way-data-binding-not-working). Thanks a lot, guys! You saved me from going nuts. – B748 Nov 09 '17 at 07:42

1 Answers1

1

A condition you have to keep in mind is that the @output variable name is always the input one + "change";

Ex.

@Input() newName: number;
@Output() newNameChange = new EventEmitter();
  • Reference here: [Angular Fundamentals: Two-way binding](https://angular.io/guide/template-syntax#two-way-binding---). Quote: "the element has a settable property called `x` and a corresponding event named `xChange`". – B748 Nov 09 '17 at 07:45