废话不多讲,先上代码。
<template>
<v-container>
<v-card>
<v-card-text>
<v-data-table :items="books" :headers="headers">
<template v-slot:item.name="{ item }">
<v-chip :color="item.color">{{ item.name }}</v-chip>
</template>
<template v-slot:item.actions="{ item }">
<v-btn icon @click="move(item, -1)">
<v-icon>mdi-arrow-up</v-icon>
</v-btn>
<v-btn icon @click="move(item, +1)">
<v-icon>mdi-arrow-down</v-icon>
</v-btn>
</template>
</v-data-table>
</v-card-text>
</v-card>
</v-container>
</template>
<script>
export default {
name: 'MoveUpAndDown',
data() {
return {
books: [],
headers: [
{ text: 'Name', value: 'name' },
{ text: 'Price', value: 'price' },
{ text: 'Actions', value: 'actions', width: '50%', align: 'end' },
],
};
},
methods: {
async getBooks() {
await new Promise((resolve) => {
setTimeout(() => {
resolve();
}, 0);
});
this.books = [
{ name: 'Book1', price: 100, color: 'primary' },
{ name: 'Book2', price: 120, color: 'secondary' },
{ name: 'Book3', price: 60, color: 'warn' },
{ name: 'Book4', price: 90, color: 'error' },
];
},
move(item, n) {
let i = this.books.indexOf(item);
console.log(
'before: ',
this.books.map((x) => {
return x.name;
})
);
let j = i + n;
if (j >= 0 && j < this.books.length) {
let tmp = this.books[j];
this.$set(this.books, j, this.books[i]);
this.$set(this.books, i, tmp);
}
console.log(
'after: ',
this.books.map((x) => x.name)
);
},
},
beforeMount() {
this.getBooks();
},
};
</script>
主要的问题就是Array变化后的数据不刷新问题,需要用vue.set()
方法设置。设置数组使用vue.set(array, index, item)
。