Javascript 在Ember中使用组件生命周期事件

Javascript 在Ember中使用组件生命周期事件,javascript,ember.js,Javascript,Ember.js,根据最新的Ember文档,不鼓励使用观察者来覆盖组件生命周期挂钩。我不确定的是如何有效地使用这些挂钩。文档中说,您可以使用didUpdateAttrs和didReceiveAttrs作为观察员的替代品 假设我有一个组件,它绘制出一些数据。该组件看起来像: {{my-chart data=data showLabels=showLabels otherProps=otherProps}} didReceiveAttrs() { let data = this.getAttr('data'

根据最新的Ember文档,不鼓励使用观察者来覆盖组件生命周期挂钩。我不确定的是如何有效地使用这些挂钩。文档中说,您可以使用
didUpdateAttrs
didReceiveAttrs
作为观察员的替代品

假设我有一个组件,它绘制出一些数据。该组件看起来像:

{{my-chart data=data showLabels=showLabels otherProps=otherProps}}
didReceiveAttrs() {
    let data = this.getAttr('data');
    this.performAnalytics(data);

    let showLabels = this.get('showLabels');
    this.updateHideLabels(showLabels);
}
当设置了
data
时,它需要对数据执行一些分析,因此只有当
data
是真正的新数据时才会发生这种情况。
showLabels
属性显示/隐藏图表中的标签,并通过
my chart
之外的内容进行切换

我选择在初始和后续渲染时使用
didReceiveAttrs
,并将其编码如下:

{{my-chart data=data showLabels=showLabels otherProps=otherProps}}
didReceiveAttrs() {
    let data = this.getAttr('data');
    this.performAnalytics(data);

    let showLabels = this.get('showLabels');
    this.updateHideLabels(showLabels);
}
问题是每次更改任何属性时,
didReceiveAttrs
中的所有代码都会运行。因此,如果用户重复执行导致
showLabels
更改的操作,则也会调用
performAnalytics
,这是不好的,因为它会导致图表刷新

我的具体问题是,如何使用生命周期事件(如
didReceiveAttrs
)作为观察者,以便只执行已更改的属性的代码路径


我会说,我尝试过存储属性并将其与传入属性进行比较,但我觉得这样做效率很低,尤其是在
数据
这是一个复杂对象数组的情况下。

您可以编写一个实用程序文件,比如
utils/component lifecycle.js

export const attrsHaveChanged=((changes,attr)=>{
const{oldAttrs,newAttrs}=changes;
如果(旧属性){
const oldAttrsValue=JSON.stringify(oldAttrs[attr].value);
const newAttrsValue=JSON.stringify(newAttrs[attr].value);
返回oldAttrsValue!==newAttrsValue;
}否则{
返回true;
}
});
现在在您的组件中,您可以导入它

从'appname/utils/component lifecycle'导入{attrsHaveChanged};
并使用它

didReceiveAttrs(更改){
如果(更改(“图表数据”)){
doSomething();
}
}

函数被传递到两个参数,
(oldAtrs,newAttrs)
。查看更改的内容并查看是否需要更新…我认为它传递了一个参数,
attrs
,其中包含
newAttrs
,可能还包含
oldAttrs
。比较这两种类型的布尔值或字符串很容易,但对象数组似乎并不容易。我刚刚检查了两个数组,它们具有相同的余烬id和相同数量的对象,看起来像完全相同的对象,没有通过测试
attrs.newAttrs.data===attrs.oldAttrs.data
。使用不可变的结构将使比较变得容易。因为这些都是react方法,所以请研究react如何管理这些方法。此外,对于您的用例来说,观察可能更简单,这是一种开放的可能性;react倾向于选择浅和宽,而不是深和窄。您如何使用组件中的数据?您现在描述的内容可以通过计算属性来完成。