Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Aurelia observer not firing for array

Tags:

aurelia

I have a custom data grid element simplified like this:

export class DataGrid {

  @bindable data;

  dataChanged(newValue, oldValue) {
    console.log("Sensing new data...", newValue);
  }
}

It's instantiated like this:

<data-grid data.bind="records"></data-grid>

"Sensing new data..." and the array of records is displayed in the console when the data grid appears. However, when I delete a record from the array of objects, the dataChanged() function is not triggered.

let index = this.records.findIndex((r) => { return r.acc_id === this.record.acc_id; });
if (index > -1) {
  console.log("Deleting element..." + index, this.records);
  this.records.splice(index, 1);
}

I get "Deleting element..." in the console but not "Sensing new data...".

Any ideas why dataChanged() is not firing when I splice out a record?

like image 772
LStarky Avatar asked Feb 06 '17 17:02

LStarky


1 Answers

You can not observe an Array for mutations like that. You have to use a collectionObserver instead. Right now, your dataChanged() would only fire if you overwrite the data value (ie data = [1, 2, 3] which overwrites it with a new array).


Example how to use the collectionObserver from the BindingEngine class, for your usecase:

import { BindingEngine } from 'aurelia-framework';

export class DataGrid {
  static inject = [BindingEngine];

  @bindable data;

  constructor(bindingEngine) {
    this._bindingEngine = bindingEngine;
  }

  attached() {
    this._dataObserveSubscription = this._bindingEngine
      .collectionObserver(this.data)
      .subscribe(splices => this.dataArrayChanged(splices));
  }

  detached() {
    // clean up this observer when the associated view is removed
    this._dataObserveSubscription.dispose();
  }


  dataArrayChanged(splices) {
    console.log('Array mutated', splices);
  }
}
like image 120
Tarps Avatar answered Sep 28 '22 08:09

Tarps