2 回答

TA贡献1772条经验 获得超6个赞
查看您的问题,我会立即看到两个问题,第一个是有关丢失的问题this.set()
,第二个是您需要显式定义一个setter以便按您希望的方式工作。我将在下面详细介绍。
至于您关于在Ember 2.x和Ember 3.x之间进行此更改的问题,我不记得有任何更改可以更改此行为changes,但是@Lux在他们对您的评论中100%正确,这种行为从未得到支持,因此您可能曾经做过一些意外的事?
因此,首先让我们谈谈使用this.set()
。Ember有一个对象模型,要求您使用它this.set()
来更新属性,以便可以将更改通知系统的其他部分(例如模板或计算的属性)。您可以在Ember的官方文档中了解有关此对象的更多信息。
值得一提的第二件事是,不建议您覆盖未定义setter的计算属性。对于新开发人员而言,这已经是一个足够大的问题,因为从Ember 3.8开始正式弃用没有getter的计算属性设置,这意味着在Ember的下一个主要版本(Ember 4.0)中,默认行为将发生变化。
如果您想设置计算属性,则可以阅读Ember中定义setter的文档,但我还将在下面提供示例。
假设您有一个fullName()
组合了firstName
和的计算属性lastName
fullName: computed('firstName', 'lastName', function() {
return `${this.firstName} ${this.lastName}`;
}),
如果要设置此计算属性(例如,在操作中)
this.set('fullName', 'Chris Manson');
那么您将覆盖计算属性的行为,并且如果更改firstName或,它将停止更新lastName。
如果你想实现一些实际的字符串分割业务逻辑Chris Manson和设定Chris为firstName和Manson作为lastName,那么你会更新您的计算机属性是这样的:
fullName: computed('firstName', 'lastName', {
get() {
return `${this.firstName} ${this.lastName}`;
},
set(propertyName, newValue) {
// propertyName is not used - if you logged it then it would say `fullName`
let pieces = newValue.split(' ');
this.set('firstName', pieces[0]);
this.set('lastName', pieces[1]);
return newValue;
}
}),
这使您可以在不删除计算属性的情况下更新计算属性property

TA贡献1951条经验 获得超3个赞
defineProperty
如果需要动态定义计算属性,则应使用:
import { defineProperty, computed } from '@ember/object';
export default Component.extend({
init() {
defineProperty(this, 'myComputedProperty', computed('someDependentKey', function() {
return null;
});
}
});
添加回答
举报