我有一个JSON文件,该文件将后端的数据馈入表中(内置的Bootstrap-Vue)。在该表中,我希望VueJS创建一个在特定条件下生成的按钮,如果单击该按钮,则将生成一个包含其他详细信息的新页面。
以下是JSON输出的示例:
{"driver_id":2,"driver_name":"{driver_first_name}, {driver_last_name}","driver_truck":"58","driver_trailer":"37","driver_status":"sleeping","has_violations":true},
因此,如果“ has_violations”为true,则将生成按钮,使onclick会通过JSON向后端请求其他数据,然后基于该数据生成一个新页面。
类似于event.target.closest('tr').dataset.userId
的普通js
但是如何在VueJS中做到这一点?
在表格代码中进行了编辑(按请求):
<template>
<b-container fluid>
<!--Search Controls-->
<b-row>
<b-col md="6" class="my-1">
<b-form-group horizontal label="Filter" class="mb-0">
<b-input-group>
<b-form-input v-model="filter" placeholder="Type to Search" />
<b-input-group-append>
<b-btn :disabled="!filter" @click="filter = ''">Clear</b-btn>
</b-input-group-append>
</b-input-group>
</b-form-group>
</b-col>
<b-col md="6" class="my-1">
<b-form-group horizontal label="Sort" class="mb-0">
<b-input-group>
<b-form-select v-model="sortBy" :options="sortOptions">
<option slot="first" :value="null">-- none --</option>
</b-form-select>
<b-form-select :disabled="!sortBy" v-model="sortDesc" slot="append">
<option :value="false">Asc</option>
<option :value="true">Desc</option>
</b-form-select>
</b-input-group>
</b-form-group>
</b-col>
<b-col md="6" class="my-1">
<b-form-group horizontal label="Sort direction" class="mb-0">
<b-input-group>
<b-form-select v-model="sortDirection" slot="append">
<option value="asc">Asc</option>
<option value="desc">Desc</option>
<option value="last">Last</option>
</b-form-select>
</b-input-group>
</b-form-group>
</b-col>
<b-col md="6" class="my-1">
<b-form-group horizontal label="Per page" class="mb-0">
<b-form-select :options="pageOptions" v-model="perPage" />
</b-form-group>
</b-col>
</b-row>
<!--Search Controls-->
<!-- Main table element -->
<b-table show-empty
stacked="md"
:items="items"
:fields="fields"
:current-page="currentPage"
:per-page="perPage"
:filter="filter"
:sort-by.sync="sortBy"
:sort-desc.sync="sortDesc"
:sort-direction="sortDirection"
@filtered="onFiltered"
>
<template slot="driverName" slot-scope="row">{{row.value.driver_first_name}} {{row.value.driver_last_name}}</template>
<template slot="truckNumber" slot-scope="row">{{row.value.driver_truck}}</template>
<template slot="truckNumber" slot-scope="row">{{row.value.driver_trailer}}</template>
<template slot="status" slot-scope="row">{{row.value.driver_status}}</template>
<template slot="violations" slot-scope="row">{{row.value?'Yes':'No'}}</template>
<template slot="actions" slot-scope="row">
<router-link :to="{name: 'driver_violations_list'}">
<b-button id="driverLogs">View Driver Logs</b-button>
</router-link>
</template>
</b-table>
<b-row>
<b-col md="6" class="my-1">
<b-pagination :total-rows="totalRows" :per-page="perPage" v-model="currentPage" class="my-0" />
</b-col>
</b-row>
</b-container>
</template>
<script>
export default {
data () {
return {
items: items,
fields: [
{ key: 'driver_name', label: 'Driver Name', sortable: true, sortDirection: 'desc' },
{ key: 'truck_number', label: 'Truck Number', sortable: true, 'class': 'text-center' },
{ key: 'trailer_number', label: 'Trailer Number', sortable: true, 'class': 'text-center' },
{ key: 'has_violations', label: 'Violations' },
{ key: 'driver_status', label: 'Status' },
{ key: 'actions', label: 'Actions' }
],
currentPage: 1,
perPage: 5,
totalRows: items.length,
pageOptions: [ 5, 10, 15 ],
sortBy: null,
sortDesc: false,
sortDirection: 'asc',
filter: null,
}
},
computed: {
sortOptions () {
return this.fields
.filter(f => f.sortable)
.map(f => { return { text: f.label, value: f.key } })
}
},
methods: {
onFiltered (filteredItems) {
// Trigger pagination to update the number of buttons/pages due to filtering
this.totalRows = filteredItems.length
this.currentPage = 1
}
//Get JSON
getDriverStatus: function () {
const url = 'driver_status_data.json'
axios.get(url, {
dataType: 'json',
headers: {
'Accept': 'application/json',
'Content-Type': 'application/json'
},
mode: 'no-cors',
credentials: 'include'
})
.then(function (response) {
console.log(JSON.stringify(response.data))
this.courses = JSON.stringify(response.data)
})
.catch(function (error) {
console.log(error)
})
}
}
}
</script>
答案 0 :(得分:0)
使用here中记载的表格插槽有条件地呈现按钮。
这是一个例子:
new Vue({
el: '#app',
computed: {
driverName () {
return this.driver ? `${this.driver.driver_name.driver_first_name} ${this.driver.driver_name.driver_last_name}` : 'N / A'
}
},
methods: {
showViolations (driver) {
this.driver = driver
this.loading = true
// Simulate an async api call with setInterval and setTimeout
let interval = setInterval(() => {
this.progress += 10
}, 250)
setTimeout(() => {
this.loading = false
this.progress = 0
clearInterval(interval)
}, 2500)
}
},
data () {
return {
progress: 0,
driver: null,
loading: false,
violations: [
'Violation 1',
'Violation 2',
'Violation 3'
],
fields: {
driver_id: {
label: 'ID',
sortable: true
},
first_name: {
key: 'driver_name.driver_first_name',
label: 'First Name',
sortable: true
},
last_name: {
key: 'driver_name.driver_last_name',
label: 'Last Name',
sortable: true
},
driver_truck: {
label: 'Truck',
sortable: true
},
driver_trailer: {
label: 'Trailer',
sortable: true
},
driver_status: {
label: 'Status',
sortable: true
},
has_violations: {
label: 'Violations',
sortable: true
}
},
items: [
{
driver_id:2,
driver_name: {
driver_first_name: 'Bob',
driver_last_name: 'Dole'
},
driver_truck: 58,
driver_trailer: 37,
driver_status: 'Sleeping',
has_violations: true
},
{
driver_id:3,
driver_name: {
driver_first_name: 'John',
driver_last_name: 'Lennon'
},
driver_truck: 69,
driver_trailer: 34,
driver_status: 'Deep Sleeping',
has_violations: false
}
]
}
}
})
<!-- Add this to <head> -->
<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="https://cdnjs.cloudflare.com/ajax/libs/vue/2.5.17/vue.js"></script>
<!-- Add this after vue.js -->
<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-table striped hover :fields="fields" :items="items">
<template slot="has_violations" slot-scope="data">
<template v-if="data.item.has_violations">
<b-button size="md" variant="primary" v-b-modal.violations @click="showViolations(data.item)">
See Violations
</b-button>
</template>
</template>
</b-table>
<b-modal id="violations" :title="`Violations By: ${driverName}`">
<b-progress v-show="loading" :value="progress" :max="100" animated></b-progress>
<p v-if="!loading" class="my-4" v-for="violation in violations" :key="violation">{{ violation }}</p>
</b-modal>
</div>