好的,我有一些Vue代码和HTML。
例如:
Vue.component('area-selectors-box', {
template: `
<div class="area-selectors-box">
<area-selector v-for="(select, index) in selects" :select="select" :key="index"></area-selector>
</div>
`,
props:['selects']
});
在我的页面中:
<div is="area-selectors-box" v-bind:selects="selects"></div>
这一切都有效,但是如果我阅读页面源代码,我会看到v-bind:selects="selects"
部分,这不符合标准,我猜。
组件具有其他对象属性,例如:
Vue.component('area-option', {
template: `<option :area="area" :value="area.term_id">{{area.name}}<slot></slot></option>`
,props: ['area']
});
在页面源上的计算结果如下:
<option area="[object Object]" value="82">Europa</option>
这显然是不可取的。
如何绑定这些属性而不将它们作为属性显示在 DOM 中?
默认情况下,当v-bind
遇到未与目标上的属性关联的绑定名称时,该值将转换为字符串并分配为属性。由于<option>
没有名为 area
的属性,因此该对象被指定为字符串属性,您在 DOM 中观察到了这一点。
您可以使用 v-bind
的 .prop
修饰符始终将其指定为属性:
<option :area.prop="area" ...>
Vue.component('area-selectors-box', {
template: `
<div class="area-selectors-box">
<area-selector v-for="(select, index) in selects" :select="select" :key="index"></area-selector>
</div>
`,
props:['selects']
});
Vue.component('area-selector', {
template: `<div>
<select v-model="selection">
<area-option
v-for="option in select.options"
:key="option.id"
:area="option.area" />
</select>
<pre>{{selection}}</pre>
</div>`,
props: ['select'],
data() {
return {
selection: null,
}
}
})
Vue.component('area-option', {
template: `<option :area.prop="area" :value="area.term_id">{{area.name}}<slot></slot></option>`
,props: ['area']
});
new Vue({
el: '#app',
data: () => ({
selects: [
{ id: 1, options: [
{ id: 10, area: { term_id: 100, name: 'Europe' } },
{ id: 11, area: { term_id: 101, name: 'Asia' } },
]
},
{ id: 2, options: [
{ id: 20, area: { term_id: 200, name: 'North America' } },
{ id: 21, area: { term_id: 201, name: 'South America' } },
]
},
]
}),
})
<script src="https://unpkg.com/vue@2.6.10"></script>
<div id="app">
<area-selectors-box :selects="selects"></area-selectors-box>
</div>
我自己的答案是:在调用组件时传递 props,而不是在组件本身中传递 props。此代码将起作用并生成干净的 html:
页内 HTML:
<!-- pass selects to area-selectors-box -->
<div is="area-selectors-box" :selects="selects"></div>
.JS:
Vue.component('area-selectors-box', { // pass select to area-selector
template: `
<div class="area-selectors-box">
<area-selector v-for="(select, index) in selects" :select="select" :key="index"></area-selector>
</div>
`,
props:['selects']
});
Vue.component('area-selector', { // pass area to area-option
template: `
<select @change="selected" >
<option disabled selected value="">Seleziona continente</option>
<area-option v-for="area in select.areas" :area="area" :key="area.term_id"></area-option>
</select>
`
,props:['select']
});
Vue.component('area-option', { // pass nothing
template: `<option :value="area.term_id">{{area.name}}<slot></slot></option>`
,props: ['area']
});