Aurelia 2 and @bindable

Hi.

I’ve got a bindable property in a view-model like this: @bindable tabtexts : any. The view-model is marked as a custom element and in the view using said custom element I have:

<div>
    <my-custom-element tabtexts.bind="subjectAreas"></my-custom-element>
</div>

where subjectAreas is a property of type Array<SubjectArea>which (for demonstration purposes) is initialised in the constructor of the view’s view model.

The above set up is similar to how I’ve done this in the past in applications based on Aurelia 1.

The problem is that when my-custom-elementis created nothing is bound to the tabtexts property. I’ve tried changing the type of tabtexts to Array<SubjectAreasto no avail. In Chrome’s debug view the bindable property does not show up (don’t know if it should). Also, tabtextsChanged(...) is not called but that’s probably not particularly strange since nothing gets bound.

So my question is: has the binding mechanism changed in Aurelia 2? If so, what is the correct way to achieve what I’m trying to do? If it hasn’t changed, what am I doing wrong?

TIA

Just a follow up. I added this to my view (as a debugging aid):

<p repeat.for="tt of tabtexts">${tt.name}</p>

and the expected values are actually available. Now I’m left with the issue of why tabtextsChanged(newValue: Array<SubjectArea>) doesn’t get triggered. The function is rather simple for the time being:

    tabtextsChanged(newValue: any) : void {
        alert('Woo-hoo!');
    }

No Woo-hoo! message gets displayed.

From Au2 documentation in https://docs.aurelia.io/components/bindable-properties#calling-a-change-function-when-bindable-is-modified:

Due to the way the Aurelia binding system works, change callbacks will not be fired upon initial component initialization. If you worked with Aurelia 1, this behavior differs from what you might expect.

If you would like to call your change handler functions when the component is initially bound (like v1), you can achieve this the following way:

import { bindable } from 'aurelia'; 

export class NameComponent {
    @bindable firstName = '';
    @bindable lastName  = '';
    
    bound() {
        this.firstNameChanged(this.firstName, undefined);
    }
    
    firstNameChanged(newVal, oldVal) {
        console.log('Value changed');
    }
}
1 Like

I found that out just before reading your reply. Anyway, thank you for replying. Hopefully it might help someone else in the future. :slight_smile: