mirror of
https://github.com/tusen-ai/naive-ui.git
synced 2025-03-07 13:48:31 +08:00
feat(table): refractor table unfinished,fixed bug,remove only custom trigger onchange,change onchange params,add demo with ajax,fixed header,filter and sorter
This commit is contained in:
parent
28ddaa8d48
commit
f9c7ae76bf
135
demo/documentation/components/table/enUS/ajaxUsage.md
Normal file
135
demo/documentation/components/table/enUS/ajaxUsage.md
Normal file
@ -0,0 +1,135 @@
|
||||
# Ajax
|
||||
|
||||
```html
|
||||
<n-button @click="sortName" style="margin-right:5px;">sort name</n-button>
|
||||
<n-button @click="clearFilters" style="margin-right:5px;"
|
||||
>clear filters</n-button
|
||||
>
|
||||
<n-button @click="clearFiltersAndSorters">clear filters and sorters</n-button>
|
||||
|
||||
<n-advanced-table
|
||||
style="margin-top:10px;"
|
||||
ref="table"
|
||||
:columns="columns"
|
||||
:data="data"
|
||||
:loading="loading"
|
||||
:pagination="pagination"
|
||||
@on-change="onChange"
|
||||
>
|
||||
</n-advanced-table>
|
||||
```
|
||||
|
||||
```js
|
||||
const _columns = $this => {
|
||||
return [
|
||||
{
|
||||
title: "Name",
|
||||
key: "name",
|
||||
sortable: true,
|
||||
sorter: "custom",
|
||||
render(h, params) {
|
||||
return (
|
||||
<span>
|
||||
{params.row.name.first} {params.row.name.last}
|
||||
</span>
|
||||
);
|
||||
}
|
||||
},
|
||||
{
|
||||
title: "Gender",
|
||||
key: "gender",
|
||||
filterable: true,
|
||||
filterItems: [
|
||||
{ label: "Male", value: "male" },
|
||||
{ label: "Female", value: "female" }
|
||||
]
|
||||
},
|
||||
{
|
||||
title: "Email",
|
||||
key: "email"
|
||||
}
|
||||
];
|
||||
};
|
||||
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
data: [],
|
||||
columns: _columns(this),
|
||||
loading: false,
|
||||
total: 0
|
||||
};
|
||||
},
|
||||
mounted() {
|
||||
this.getData().then(data => {
|
||||
this.data = data.results;
|
||||
this.total = 100;
|
||||
});
|
||||
},
|
||||
computed: {
|
||||
pagination() {
|
||||
return { total: this.total, limit: 5, custom: true };
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
getData(params = {}) {
|
||||
this.loading = true;
|
||||
if (!params.results) {
|
||||
params.results = this.pagination.limit;
|
||||
}
|
||||
if (!params.page) {
|
||||
params.page = this.pagination.currentPage;
|
||||
}
|
||||
let url = "https://randomuser.me/api";
|
||||
let paramsArr = [];
|
||||
Object.keys(params).forEach(key => {
|
||||
if (Array.isArray(params[key])) {
|
||||
params[key].forEach(value => {
|
||||
paramsArr.push(`${key}[]=${value}`);
|
||||
});
|
||||
} else paramsArr.push(`${key}=${params[key]}`);
|
||||
});
|
||||
if (paramsArr.length) {
|
||||
url = url + "?" + paramsArr.join("&");
|
||||
}
|
||||
console.log("TCL: fetch -> url", url);
|
||||
|
||||
return fetch(url)
|
||||
.then(res => res.json())
|
||||
.finally(() => {
|
||||
this.loading = false;
|
||||
});
|
||||
},
|
||||
onChange({ filter, sorter, pagination }) {
|
||||
let params = {
|
||||
page: pagination.currentPage
|
||||
};
|
||||
if (sorter) {
|
||||
Object.assign(params, {
|
||||
sortField: sorter.field,
|
||||
sortOrder: sorter.order
|
||||
});
|
||||
}
|
||||
if (filter) {
|
||||
Object.assign(params, {
|
||||
...filter
|
||||
});
|
||||
}
|
||||
this.getData(params).then(data => {
|
||||
this.data = data.results;
|
||||
});
|
||||
console.log(filter, sorter, pagination);
|
||||
},
|
||||
sortName() {
|
||||
this.$refs.table.sort("name", "ascend");
|
||||
},
|
||||
clearFilters() {
|
||||
this.$refs.table.filter(null);
|
||||
},
|
||||
clearFiltersAndSorters() {
|
||||
this.$refs.table.filter(null);
|
||||
this.$refs.table.sort(null);
|
||||
}
|
||||
}
|
||||
};
|
||||
```
|
@ -1,12 +1,19 @@
|
||||
# Filter and sorter
|
||||
|
||||
```html
|
||||
<n-button @click="sortName" style="margin-right:5px;">sort name</n-button>
|
||||
<n-button @click="clearFilters" style="margin-right:5px;"
|
||||
>clear filters</n-button
|
||||
>
|
||||
<n-button @click="clearFiltersAndSorters">clear filters and sorters</n-button>
|
||||
|
||||
<n-advanced-table
|
||||
style="margin-top:10px;"
|
||||
ref="table"
|
||||
:columns="columns"
|
||||
:data="data"
|
||||
:pagination="pagination"
|
||||
@on-selected-change="onSelectedChange"
|
||||
@on-change="onChange"
|
||||
>
|
||||
</n-advanced-table>
|
||||
```
|
||||
@ -16,11 +23,16 @@ const _columns = $this => {
|
||||
return [
|
||||
{
|
||||
title: "Name",
|
||||
key: "name"
|
||||
key: "name",
|
||||
sortable: true,
|
||||
sorter(rowA, rowB) {
|
||||
return rowA.name.length - rowB.name.length;
|
||||
}
|
||||
},
|
||||
{
|
||||
title: "Age",
|
||||
key: "age",
|
||||
defaultSortOrder: "ascend",
|
||||
sortable: true,
|
||||
sorter(rowA, rowB) {
|
||||
return rowA.age - rowB.age;
|
||||
@ -86,6 +98,20 @@ export default {
|
||||
return { total: this.data.length, limit: 5 };
|
||||
}
|
||||
},
|
||||
methods: {}
|
||||
methods: {
|
||||
onChange({ filter, sorter, pagination }) {
|
||||
console.log(filter, sorter, pagination);
|
||||
},
|
||||
sortName() {
|
||||
this.$refs.table.sort("name", "ascend");
|
||||
},
|
||||
clearFilters() {
|
||||
this.$refs.table.filter(null);
|
||||
},
|
||||
clearFiltersAndSorters() {
|
||||
this.$refs.table.filter(null);
|
||||
this.$refs.table.sort(null);
|
||||
}
|
||||
}
|
||||
};
|
||||
```
|
||||
|
66
demo/documentation/components/table/enUS/fixedHeader.md
Normal file
66
demo/documentation/components/table/enUS/fixedHeader.md
Normal file
@ -0,0 +1,66 @@
|
||||
# Fixed Header
|
||||
|
||||
Display large amounts of data in scrollable view.
|
||||
|
||||
```html
|
||||
<n-advanced-table
|
||||
ref="table"
|
||||
:columns="columns"
|
||||
:data="data"
|
||||
:pagination="pagination"
|
||||
max-height="250px"
|
||||
@on-selected-change="onSelectedChange"
|
||||
>
|
||||
</n-advanced-table>
|
||||
```
|
||||
|
||||
```js
|
||||
const _columns = $this => {
|
||||
return [
|
||||
{
|
||||
title: "Name",
|
||||
key: "name"
|
||||
},
|
||||
{
|
||||
title: "Age",
|
||||
key: "age"
|
||||
},
|
||||
{
|
||||
title: "Address",
|
||||
key: "address"
|
||||
}
|
||||
];
|
||||
};
|
||||
|
||||
const data = [];
|
||||
for (let i = 0; i < 46; i++) {
|
||||
data.push({
|
||||
key: i,
|
||||
name: `Edward King ${i}`,
|
||||
age: 32,
|
||||
address: `London, Park Lane no. ${i}`
|
||||
});
|
||||
}
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
data: data,
|
||||
columns: _columns(this),
|
||||
selectedData: []
|
||||
};
|
||||
},
|
||||
computed: {
|
||||
pagination() {
|
||||
return { total: this.data.length, limit: 10 };
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
sendMail(rowData) {
|
||||
this.$NMessage.info("send mail to " + rowData.name);
|
||||
},
|
||||
onSelectedChange(selectedData) {
|
||||
this.selectedData = selectedData;
|
||||
}
|
||||
}
|
||||
};
|
||||
```
|
@ -13,6 +13,8 @@ Table is used to displays rows of data.
|
||||
basic
|
||||
select
|
||||
filterAndSorter
|
||||
ajaxUsage
|
||||
fixedHeader
|
||||
```
|
||||
|
||||
## API
|
||||
|
@ -124,7 +124,7 @@
|
||||
</div>
|
||||
<!-- 分页 -->
|
||||
<div
|
||||
v-if="pagination !== false && showingData.length"
|
||||
v-if="pagination !== false"
|
||||
:style="tableWrapperStl"
|
||||
class="n-advance-table__pagination"
|
||||
>
|
||||
@ -147,6 +147,17 @@ import themeable from '../../../mixins/themeable'
|
||||
import { Store, storageMixin } from '../store'
|
||||
import BaseTable from '../baseTable/baseTable'
|
||||
|
||||
const sortOrderMap = {
|
||||
ascend: -1,
|
||||
descend: 1,
|
||||
unset: 0
|
||||
}
|
||||
const sortOrderReverseMap = {
|
||||
'-1': 'descend',
|
||||
'1': 'ascend',
|
||||
'0': 'unset'
|
||||
}
|
||||
|
||||
export default {
|
||||
store () {
|
||||
return new Store()
|
||||
@ -334,9 +345,9 @@ export default {
|
||||
if (this.pagination) {
|
||||
// TODO: check count limit is exisit
|
||||
let total = this.pagination.total
|
||||
if (this.pagination.custom !== true) {
|
||||
total = this.data.length
|
||||
}
|
||||
// if (this.pagination.custom !== true) {
|
||||
// total = this.data.length
|
||||
// }
|
||||
return Math.ceil(total / this.pagination.limit) || 1
|
||||
}
|
||||
return 1
|
||||
@ -348,7 +359,9 @@ export default {
|
||||
} else if (!this.processedData.length) {
|
||||
data = this.copyData
|
||||
}
|
||||
data = this.computePageDivideData(data)
|
||||
if (this.pagination.custom !== true) {
|
||||
data = this.computePageDivideData(data)
|
||||
}
|
||||
return data
|
||||
},
|
||||
tableStl () {
|
||||
@ -442,9 +455,10 @@ export default {
|
||||
// },
|
||||
currentPage () {
|
||||
this.computeCurrentPageSelection()
|
||||
if (this.pagination.custom === true) {
|
||||
this.useRemoteChange()
|
||||
}
|
||||
// if (this.pagination.custom === true) {
|
||||
this.useRemoteChange()
|
||||
this.mainTBodyEl.scrollTo(0, 0)
|
||||
// }
|
||||
|
||||
// this.currentPageAllSelect = this.allCheckboxesSelect
|
||||
this.$emit('on-page-change', this.paginationer)
|
||||
@ -465,12 +479,13 @@ export default {
|
||||
currentSortColumn (sorter, oldSorter) {
|
||||
this.processedData = this.computeShowingData()
|
||||
// 上次的若是为custom,本次为locale sort那么也需要触发useRemoteChange
|
||||
if (
|
||||
sorter.sorter === 'custom' ||
|
||||
(oldSorter && oldSorter.sorter === 'custom')
|
||||
) {
|
||||
this.useRemoteChange()
|
||||
}
|
||||
// if (
|
||||
// sorter.sorter === 'custom' ||
|
||||
// (oldSorter && oldSorter.sorter === 'custom')
|
||||
// ) {
|
||||
// this.useRemoteChange()
|
||||
// }
|
||||
this.useRemoteChange()
|
||||
this.$emit('on-sort-change', this.currentSortColumn)
|
||||
},
|
||||
checkBoxes () {
|
||||
@ -518,6 +533,15 @@ export default {
|
||||
},
|
||||
mounted () {
|
||||
// console.log(this.wrapperWidth, this.tbodyWidth)
|
||||
this.columns.forEach((column, i) => {
|
||||
if (column.defaultSortOrder) {
|
||||
this.$set(
|
||||
this.sortIndexs,
|
||||
column.key || i,
|
||||
sortOrderMap[column.defaultSortOrder]
|
||||
)
|
||||
}
|
||||
})
|
||||
|
||||
this.init()
|
||||
|
||||
@ -546,7 +570,7 @@ export default {
|
||||
item => item !== currentEl && item !== null && item !== undefined
|
||||
)
|
||||
.forEach(el => {
|
||||
el.scrollTop = currentEl.scrollTop
|
||||
if (currentEl) el.scrollTop = currentEl.scrollTop
|
||||
})
|
||||
})
|
||||
|
||||
@ -595,21 +619,29 @@ export default {
|
||||
this.currentPage = pageNum
|
||||
},
|
||||
sort (columnKey, order) {
|
||||
this.$set(this.sortIndexs, columnKey, order)
|
||||
if (columnKey == null) {
|
||||
this.clearSort()
|
||||
return
|
||||
}
|
||||
this.$set(this.sortIndexs, columnKey, sortOrderMap[order])
|
||||
},
|
||||
filter (filterOptions) {
|
||||
// ---- TODO: 未来版本将会去除这段代码,为了兼容老版本
|
||||
Object.keys(filterOptions).forEach(key => {
|
||||
let column = this.columns.find(item => item.key === key)
|
||||
if (column && !column.filterMultiple) {
|
||||
if (filterOptions[key].length) {
|
||||
filterOptions[key] = filterOptions[key][0]
|
||||
} else {
|
||||
delete filterOptions[key]
|
||||
}
|
||||
}
|
||||
})
|
||||
// ----
|
||||
// // ---- TODO: 未来版本将会去除这段代码,为了兼容老版本
|
||||
// Object.keys(filterOptions).forEach(key => {
|
||||
// let column = this.columns.find(item => item.key === key)
|
||||
// if (column && !column.filterMultiple) {
|
||||
// if (filterOptions[key].length) {
|
||||
// filterOptions[key] = filterOptions[key][0]
|
||||
// } else {
|
||||
// delete filterOptions[key]
|
||||
// }
|
||||
// }
|
||||
// })
|
||||
// // ----
|
||||
if (filterOptions === null) {
|
||||
this.selectedFilter = {}
|
||||
return
|
||||
}
|
||||
this.selectedFilter = filterOptions
|
||||
},
|
||||
// search (columnKey,word) {
|
||||
@ -651,7 +683,6 @@ export default {
|
||||
Object.keys(this.sortIndexs).forEach(key => {
|
||||
this.sortIndexs[key] = 0
|
||||
})
|
||||
this.currentSortColumn = null
|
||||
},
|
||||
computeHorizontalScrollBarHeight () {
|
||||
const tbody = this.mainTBodyEl
|
||||
@ -756,45 +787,44 @@ export default {
|
||||
|
||||
keys.forEach(key => {
|
||||
let val = this.currentFilterColumn[key].value
|
||||
let filterFn = this.currentFilterColumn[key].filterFn
|
||||
let filterMultiple = this.currentFilterColumn[key].filterMultiple
|
||||
if (option === 'custom' && filterFn === 'custom') {
|
||||
currentFilterColumn[key] = {
|
||||
value: filterMultiple ? val : val[0]
|
||||
}
|
||||
} else if (option !== 'custom') {
|
||||
currentFilterColumn[key] = {
|
||||
value: filterMultiple ? val : val[0]
|
||||
}
|
||||
}
|
||||
// let filterFn = this.currentFilterColumn[key].filterFn
|
||||
// let filterMultiple = this.currentFilterColumn[key].filterMultiple
|
||||
currentFilterColumn[key] = val
|
||||
})
|
||||
if (Object.keys(currentFilterColumn).length === 0) {
|
||||
currentFilterColumn = null
|
||||
}
|
||||
return currentFilterColumn
|
||||
},
|
||||
getCustomSorterData () {
|
||||
if (!this.currentSortColumn) {
|
||||
return null
|
||||
}
|
||||
const isCustom =
|
||||
this.currentSortColumn.sorter === 'custom' &&
|
||||
this.currentSortColumn.type !== null
|
||||
return isCustom ? this.currentSortColumn : null
|
||||
},
|
||||
// getCustomSorterData () {
|
||||
// if (!this.currentSortColumn) {
|
||||
// return null
|
||||
// }
|
||||
// const isCustom =
|
||||
// this.currentSortColumn.sorter === 'custom' &&
|
||||
// this.currentSortColumn.type !== null
|
||||
// return isCustom ? this.currentSortColumn : null
|
||||
// },
|
||||
useRemoteChange () {
|
||||
clearTimeout(this.remoteTimter)
|
||||
|
||||
this.remoteTimter = setTimeout(() => {
|
||||
const currentFilterColumn = this.getFilterData('custom')
|
||||
const currentSortColumn = this.getCustomSorterData()
|
||||
const currentSortColumn = this.currentSortColumn
|
||||
|
||||
const sortType =
|
||||
currentSortColumn && Number(currentSortColumn.type).toString()
|
||||
const emitData = {
|
||||
filter: currentFilterColumn,
|
||||
sorter: {
|
||||
key: currentSortColumn.key,
|
||||
order: currentSortColumn.type
|
||||
},
|
||||
pagination: this.paginationer
|
||||
filter: currentFilterColumn || null,
|
||||
sorter:
|
||||
currentSortColumn && currentSortColumn.type !== 0
|
||||
? {
|
||||
field: currentSortColumn.key,
|
||||
order: sortOrderReverseMap[sortType],
|
||||
column: currentSortColumn.column
|
||||
}
|
||||
: null,
|
||||
pagination: this.paginationer || null
|
||||
// search: this.currentSearchColumn
|
||||
}
|
||||
this.$emit('on-change', emitData)
|
||||
@ -868,9 +898,9 @@ export default {
|
||||
return data
|
||||
},
|
||||
onFilter (value, column) {
|
||||
if (column.filter === 'custom') {
|
||||
this.useRemoteChange()
|
||||
}
|
||||
// if (column.filter === 'custom') {
|
||||
this.useRemoteChange()
|
||||
// }
|
||||
},
|
||||
onSortChange (sortIndexs) {
|
||||
this.sortIndexs = sortIndexs
|
||||
|
@ -226,6 +226,8 @@
|
||||
border-radius: 2.5px;
|
||||
background: $--table-scrollbar-color;
|
||||
}
|
||||
scroll-behavior: smooth;
|
||||
|
||||
tr.n-table__tr--hover {
|
||||
background-color: $--table-row-hover;
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user