Reputation: 115
I have an EmberJS controller that has the following computed property:
hasSelectedRequirements: Ember.computed('selectedRequirements.[]', function() {
console.log("this should get printed but it doesn't");
return this.get('selectedRequirements').length > 0;
}),
which sets a boolean flag I am using in a template to conditionally display html.
I also have a button, that, when clicked, takes the form data and pushes an element onto the selectedRequirements array by calling the addRequirement action
actions: {
addRequirement() {
...
// extract data from form and create the requirement variable
var selectedRequirements = this.get('selectedRequirements');
selectedRequirements.push(requirement);
this.set('selectedRequirements', selectedRequirements);
console.log(this.get('selectedRequirements')); // does print as expected
}
}
If I change the addRequirement function to this instead, then the hasSelectedRequirements computed property's function handler is run as expected, and the console.log statement works:
actions: {
addRequirement() {
...
// extract data from form and create the requirement variable
var selectedRequirements = this.get('selectedRequirements');
selectedRequirements.push(requirement);
// create a new, local array
var arr = new Array();
arr.push(1);
this.set('selectedRequirements', arr);
console.log(this.get('selectedRequirements')); // does print as expected
}
}
It seems as though Ember's computed properties rely upon the array that is being observed being a completely different array?
The problem is that the computed property is not recognizing that an element was added to the selectedRequirements array, and the computed property function never gets called (the console.log statement never runs). Why does the computed property not recognize that the selectedRequirements array has been modified and how can I fix the computed property code?
Upvotes: 0
Views: 1406
Reputation: 1
using pushObject
instead of push
and removeObject
instead of splice
will trigger the computed
property.
Upvotes: 0
Reputation: 115
It seems that Ember's computed properties (at least observing using the array.[] syntax) require a new array in order to recognize changes. Thus, the best solution I have found is to create a copy of the array using slice:
actions: {
addRequirement() {
...
// extract data from form and create the requirement variable
var selectedRequirements = this.get('selectedRequirements');
selectedRequirements.push(requirement);
this.set('selectedRequirements', selectedRequirements.slice(0));
console.log(this.get('selectedRequirements')); // does print as expected
}
}
This guarantees that the hasSelectedRequirements computed property is set appropriately each time the addRequirement action is called
Upvotes: 1
Reputation: 9396
Use pushObject
like this.get('selectedRequirements').pushObject(obj);
Upvotes: 3