因此,我的情况如下:我得到了一个组件,它有两个输入字段,表示联系人,并填充了来自服务的数据:
@service('contact-data') contact;
每个字段代表一个属性,可通过
{{contact.properties.foo}}
我将属性保存为JS对象,以便在使用它们时轻松过滤出空字段,我用@tracked
跟踪它,如下所示:
export default class MyService extends Service {
@tracked properties = {id: 0, foo: "", bar : "abc", };
@action updateProperty(name, value) {
this.properties[name] = value;
}
}
但是,属性无法在组件中正确重新呈现,文本字段也无法更新。
我很感激你能帮我这个忙!谢谢
2条答案
按热度按时间vohkndzv1#
每当你有一堆需要跟踪的嵌套状态时,仅仅跟踪顶级对象不会导致对该对象内部的更新传播出去。您需要跟踪内部属性,或您需要重置正在跟踪的整个对象。
您基本上有两个粗略的选项来处理这些内部属性的更新:
1.如果对象有一个众所周知的形状,请将其提取到一个在字段上使用
@tracked
的实用程序类中,并在创建服务时示例化该实用程序类。然后更新这些字段。1.如果对象真的像哈希Map一样被使用,那么您有两个变体选项:
1.如果不需要IE11支持,请使用https://github.com/pzuraq/tracked-built-ins
1.执行“纯功能更新”,即执行
this.properties = { ...this.properties, foo: newValue };
之类的操作其中,(1)几乎总是最便宜、性能最好的。执行(2.1)会稍微贵一些,因为它需要使用
Proxy
,但还不够您通常会注意到的。执行(2.2)将最终触发应用程序中任何地方使用的properties
中的every属性的重新渲染,即使它没有更改。在您所描述的例子中,字段似乎是众所周知的,这意味着您应该访问该类。解决方案可能如下所示:
请注意,
@tracked
installs getters and setters in place of plain class properties,因此,如果您需要在某个地方或类似的地方将其用于JSON负载,您还需要在实用程序类上实现toJSON
:gj3fmq9x2#
还有另一个add-on,它对数组和对象执行与跟踪内置程序基本相同的操作。
它是一个代理,基本上通知根用户某个地方发生了更新。相对于跟踪内置的优点是嵌套深度不受限制,因为JSON通常具有深度嵌套。
在性能方面,其缺点与跟踪内置程序类似。尽量少用它,并且尽量不要在具有数百行/数千行的表中使用它,因为重新渲染将不会有性能。