背景
我正在将一系列对象传递给可以自动here找到的材料自动完成功能。
当我第一次在列表中选择一个项目时,它会引发错误,然后如果我再次单击该项目,它将按预期选择它。每次我单击自动完成中的项目时,都会重复相同的过程。
示例错误
[Vue警告]:事件处理程序中“输入”的错误:“ TypeError:无法 读取未定义的属性“构造函数”
示例代码
<template>
<md-autocomplete
v-model="customer"
:md-options="customers"
@md-changed="getCustomers"
@md-opened="getCustomers"
@md-selected="getSelected"
>
</md-autocomplete>
</template>
<script>
data: () => ({
customers: [],
customer: "", // I also tried making this a {}
}),
methods: {
getCustomers(searchTerm) {
this.customers = new Promise(resolve => {
if (!searchTerm) {
resolve(this.GET_CUSTOMERS);
} else {
const term = searchTerm.toLowerCase();
this.customers = this.GET_CUSTOMERS.filter(({ email }) => {
email.toLowerCase().includes(term);
});
resolve(this.customers);
}
});
},
getSelected() {
console.log(this.customer);
},
}
</script>
数据示例
GET_CUSOTMERS: [
{ client_id: 1, email: "example@example.com" },
{ client_id: 2, email: "example@example.com" }
];
问题
此错误是什么意思,我该如何解决?我已经读到,使用材料的自动完成功能在角度上存在一个错误,几年前通过此错误可以解决这个问题,但我对此表示乐观,因为它目前是可修复的,而不是实质性错误。
答案 0 :(得分:1)
根据MdAutocomplete
的{{3}}源代码,searchTerm
在您的情况下为undefined
(因此,访问{{1 }}):
constructor
undefined
通常是input
-handler:
// MdAutocomplete.vue: onInput()
if (this.searchTerm.constructor.toString().match(/function (\w*)/)[1].toLowerCase() !== 'inputevent') {
^^^^^^^^^^
...除非项目是equal to its value
prop:
searchTerm
因此,当发生错误时,data () {
return {
searchTerm: this.value,
//...
}
},
watch: {
value (val) {
this.searchTerm = val
},
//...
},
的{{1}}可能是selectItem (item, $event) {
const content = $event.target.textContent.trim()
this.searchTerm = content
//...
}
(来自您的value
),导致MdAutocomplete
也是undefined
。选择项目时,v-model
会重置为所选内容的文本内容,并且不会发生错误。
我无法使用OP中的代码段重现这些确切的症状,但似乎发生了不相关的错误:selected。也许这个问题缺少重现该问题的重要细节。
searchTerm
(即此处的undefined
)必须返回字符串数组,因此您必须将对象数组转换为期望的格式(使用{{3} }):
searchTerm
md-options
回调必须返回布尔值,以进行任何过滤。以下demo用作回调,不返回任何内容:
this.customers
您可以删除箭头功能的括号:
this.customers = new Promise(resolve => {
if (!searchTerm) {
resolve(GET_CUSTOMERS.map(x => x.email)); // <-- map to `email` property
} else {
const term = searchTerm.toLowerCase();
this.customers = GET_CUSTOMERS.filter(/*...*/).map(x => x.email); // <-- map to `email` property
resolve(this.customers);
}
}
或使用Array.prototype.filter
语句:
GET_CUSTOMERS.filter(({ email }) => {
email.toLowerCase().includes(term);
});