问题
I get reference from here :
https://bootstrap-vue.js.org/docs/components/card/#card-groups
https://bootstrap-vue.js.org/docs/components/button/#pressed-state-and-toggling
My vue component like this :
<template>
...
<b-card-group deck v-for="row in formattedItems">
<b-card :title="item.title"
img-src="http://placehold.it/140?text=No image"
img-alt="Img"
img-top
v-for="item in row">
<p class="card-text">
{{item.price}}
</p>
<p class="card-text">
{{item.country}}
</p>
<div slot="footer">
<b-button-group size="sm">
<b-button :pressed.sync="oriPress" variant="outline-primary">Original</b-button>
<b-button :pressed.sync="kwPress" variant="outline-primary">Kw</b-button>
</b-button-group>
<b-btn variant="primary" block>Add</b-btn>
</div>
</b-card>
</b-card-group>
....
</template>
<script>
export default {
..
data () {
return{
items: [
{id:1, title:'chelsea', price:900, country: 'england'},
{id:2, title:'liverpool', price:800, country: 'england'},
{id:3, title:'mu', price:700, country: 'england'},
{id:4, title:'city', price:600, country: 'england'},
{id:5, title:'arsenal', price:500, country: 'england'},
{id:6, title:'tottenham', price:400, country: 'england'},
{id:7, title:'juventus', price:300, country: 'italy'},
{id:8, title:'madrid', price:200, country: 'span'},
{id:9, title:'barcelona', price:100, country: 'span'},
{id:10, title:'psg', price:50, country: 'france'}
],
oriPress: true,
kwPress: false
}
},
mounted: function () {
this.getItems()
},
computed: {
formattedItems() {
return this.items.reduce((c, n, i) => {
if (i % 4 === 0) c.push([]);
c[c.length - 1].push(n);
return c;
}, []);
}
}
}
</script>
If the script executed, button original in all box active and button kw in all box inactive
That is what I expected. But my problem is when I click the kw button or the original button, all buttons are active or inacive. I want it active only on the button selected on each box
For example there are 10 box boxes. When I click the original button in the third box, the original button in the third box will be active and the kw button will be inactive. When I click the button kw in the ninth box, the button kw in the ninth box will be active and the button original will be inactive. So do the others
How can I do it?
回答1:
The problem is the same oriPress and kwPress data properties are used for all items. You could move those properties into items[] so that they're unique to each item:
// script
data() {
return {
items: [
{id: 1, oriPress: true, kwPress: false, ...},
{id: 2, oriPress: true, kwPress: false, ...},
]
}
}
//template
<b-card-group v-for="row in formattedItems">
<b-card v-for="item in row">
<b-button :pressed.sync="item.oriPress">Original</b-button>
<b-button :pressed.sync="item.kwPress">Kw</b-button>
</b-card>
</b-card-group>
...but I assume the shape of items[] cannot be changed. The alternative is to create a map of oriPress and kwPress properties (one per item). This could be done with a watcher on items[] that initializes oriPress and kwPress each to a map of item IDs to Booleans:
// script
data() {
return {
items: [...],
oriPress: {},
kwPress: {},
}
},
watch: {
items: {
immediate: true,
handler(value) {
this.oriPress = value.reduce((p,c) => {
p[c.id] = true;
return p;
}, {});
this.kwPress = value.reduce((p,c) => {
p[c.id] = false;
return p;
}, {});
}
}
},
//template
<b-card-group v-for="row in formattedItems">
<b-card v-for="item in row">
<b-button :pressed.sync="oriPress[item.id]">Original</b-button>
<b-button :pressed.sync="kwPress[item.id]">Kw</b-button>
</b-card>
</b-card-group>
new Vue({
el: '#app',
data() {
return{
items: [
{id:1, title:'chelsea', price:900, country: 'england'},
{id:2, title:'liverpool', price:800, country: 'england'},
{id:3, title:'mu', price:700, country: 'england'},
{id:4, title:'city', price:600, country: 'england'},
{id:5, title:'arsenal', price:500, country: 'england'},
{id:6, title:'tottenham', price:400, country: 'england'},
{id:7, title:'juventus', price:300, country: 'italy'},
{id:8, title:'madrid', price:200, country: 'span'},
{id:9, title:'barcelona', price:100, country: 'span'},
{id:10, title:'psg', price:50, country: 'france'}
],
oriPress: {},
kwPress: {}
}
},
watch: {
items: {
immediate: true,
handler(value) {
this.oriPress = value.reduce((p,c) => {
p[c.id] = true;
return p;
}, {});
this.kwPress = value.reduce((p,c) => {
p[c.id] = false;
return p;
}, {});
}
}
},
computed: {
formattedItems() {
return this.items.reduce((c, n, i) => {
if (i % 4 === 0) c.push([]);
c[c.length - 1].push(n);
return c;
}, []);
}
}
})
<script src="https://unpkg.com/vue@2.5.17"></script>
<link type="text/css" rel="stylesheet" href="//unpkg.com/bootstrap/dist/css/bootstrap.min.css"/>
<link type="text/css" rel="stylesheet" href="//unpkg.com/bootstrap-vue@latest/dist/bootstrap-vue.css"/>
<script src="//unpkg.com/babel-polyfill@latest/dist/polyfill.min.js"></script>
<script src="//unpkg.com/bootstrap-vue@latest/dist/bootstrap-vue.js"></script>
<div id="app">
<b-card-group deck v-for="row in formattedItems">
<b-card :title="item.title"
img-src="http://placehold.it/140?text=No image"
img-alt="Img"
img-top
v-for="item in row">
<p class="card-text">
{{item.price}}
</p>
<p class="card-text">
{{item.country}}
</p>
<div slot="footer">
<b-button-group size="sm">
<b-button :pressed.sync="oriPress[item.id]" variant="outline-primary">Original</b-button>
<b-button :pressed.sync="kwPress[item.id]" variant="outline-primary">Kw</b-button>
</b-button-group>
<b-btn variant="primary" block>Add</b-btn>
</div>
</b-card>
</b-card-group>
</div>
来源:https://stackoverflow.com/questions/52566362/how-can-i-add-button-selected-if-clicked-on-the-box-list