问题
我经常使用这种计算属性,setter只返回新值:
@computed('args.myValue')
get myValue() {
return this.args.myValue;
}
set myValue(newValue) {
return newValue; // <==== this is no longer valid with native setter
}
这几乎没有什么作用:
1.将初始值设置为args.myValue
1.允许更改值(通常通过<Input @value={{this.myValue}} />
)
1.args.myValue
更改时恢复默认值
问题是本地setter不能return
任何值。
请注意,我可能会找到一个“hackish”解决方案,但我希望代码遵循新的EmberJS约定,以避免以后痛苦的更新。
我尝试过的事情
手动缓存
@tracked _myValue = null;
get myValue() {
return this._myValue || this.args.myValue;
}
set myValue(newValue) {
this._myValue = newValue;
}
这不起作用,因为_myValue
总是在第一个myValue=(newValue)
之后设置。为了使其工作,应该有某种观察员在args.myValue
更改时将其重置为null
。
可悲的是,observers are no longer part of EmberJS with native classes。
{{unbound}}
助手
<Input @value={{unbound this.myValue}} />
正如预期的那样,它不起作用,因为它只是不更新myValue
。
{{unbound}}
助手与event.target.value
处理相结合
<Input @value={{unbound this.myValue}} {{on "keyup" this.keyPressed}} />
get myValue() {
return this.args.myValue;
}
@action keyPressed(event) {
this.doStuffThatWillUpdateAtSomeTimeMyValue(event.target.value);
}
但当args.myValue
更改时,Input
仍未更新。
初始代码
下面是一个更具体的使用示例:
组件
// app/components/my-component.js
export default class MyComponent extends Component {
@computed('args.projectName')
get projectName() {
return this.args.projectName;
}
set projectName(newValue) {
return newValue; // <==== this is no longer valid with native setter
}
@action
searchProjects() {
/* event key stuff omitted */
const query = this.projectName;
this.args.queryProjects(query);
}
}
{{! app/components/my-component.hbs }}
<Input @value={{this.projectName}} {{on "keyup" this.searchProjects}} />
控制器
// app/controllers/index.js
export default class IndexController extends Controller {
get entry() {
return this.model.entry;
}
get entryProjectName() {
return this.entry.get('project.name');
}
@tracked queriedProjects = null;
@action queryProjects(query) {
this.store.query('project', { filter: { query: query } })
.then((projects) => this.queriedProjects = projects);
}
@action setEntryProject(project) {
this.entry.project = project;
}
}
{{! app/templates/index.hbs }}
<MyComponent
@projectName={{this.entryProjectName}}
@searchProjects={{this.queryProjects}} />
当在控制器中设置queriedProjects
时,组件会显示它们。
单击其中一个搜索结果时,控制器会更新setEntryProject
。
2条答案
按热度按时间nfeuvbwi1#
根据this Ember.js discussion:
Net,我个人的观点是,正是由于这个原因,通常最好使用常规
<input>
而不是e1d1e组件,并连接您自己的事件侦听器。这将使您负责设置项目。动作中的数量值,但它也消除了使用两种不同的方法设置相同值的最后一个问题,并且它还为您提供了一个机会来处理其他事件。我通过使用标准
<input>
找到了解决这个问题的方法,这似乎是解决问题的“正确方法”(我非常感谢任何能告诉我更好方法的评论):如果我需要将输入值保留为属性,我可以这样做:
编辑
请注意,以下解决方案有一个缺点:它没有提供一种简单的方法来在输入值不变时将其重置为
this.projectName
,例如在焦点输出后。为了解决这个问题,我添加了一些代码:
fcy6dtqo2#
对于这个2源绑定场景,有一种非常通用和简洁的方法,可以使用任何交互式输入元素及其他元素。
考虑到您的第一次尝试(»手动缓存«):
https://ember-twiddle.com/a72fa70c472dfc54d03d040f0d849d17