diff --git a/components/table/SelectionCheckboxAll.jsx b/components/table/SelectionCheckboxAll.jsx index de584ebda..7cb3fa8de 100644 --- a/components/table/SelectionCheckboxAll.jsx +++ b/components/table/SelectionCheckboxAll.jsx @@ -50,12 +50,12 @@ export default { subscribe () { const { store } = this this.unsubscribe = store.subscribe(() => { - this.setCheckState() + this.setCheckState(this.$props) }) }, - checkSelection (data, type, byDefaultChecked) { - const { store, getCheckboxPropsByItem, getRecordKey } = this + checkSelection (props, data, type, byDefaultChecked) { + const { store, getCheckboxPropsByItem, getRecordKey } = props || this.$props // type should be 'every' | 'some' if (type === 'every' || type === 'some') { return ( @@ -68,9 +68,9 @@ export default { return false }, - setCheckState () { - const checked = this.getCheckState() - const indeterminate = this.getIndeterminateState() + setCheckState (props) { + const checked = this.getCheckState(props) + const indeterminate = this.getIndeterminateState(props) this.setState((prevState) => { const newState = {} if (indeterminate !== prevState.indeterminate) { @@ -83,23 +83,23 @@ export default { }) }, - getCheckState () { + getCheckState (props) { const { store, data } = this let checked if (!data.length) { checked = false } else { checked = store.getState().selectionDirty - ? this.checkSelection(data, 'every', false) + ? this.checkSelection(props, data, 'every', false) : ( - this.checkSelection(data, 'every', false) || - this.checkSelection(data, 'every', true) + this.checkSelection(props, data, 'every', false) || + this.checkSelection(props, data, 'every', true) ) } return checked }, - getIndeterminateState () { + getIndeterminateState (props) { const { store, data } = this let indeterminate if (!data.length) { @@ -107,19 +107,19 @@ export default { } else { indeterminate = store.getState().selectionDirty ? ( - this.checkSelection(data, 'some', false) && - !this.checkSelection(data, 'every', false) + this.checkSelection(props, data, 'some', false) && + !this.checkSelection(props, data, 'every', false) ) - : ((this.checkSelection(data, 'some', false) && - !this.checkSelection(data, 'every', false)) || - (this.checkSelection(data, 'some', true) && - !this.checkSelection(data, 'every', true)) + : ((this.checkSelection(props, data, 'some', false) && + !this.checkSelection(props, data, 'every', false)) || + (this.checkSelection(props, data, 'some', true) && + !this.checkSelection(props, data, 'every', true)) ) } return indeterminate }, - handleSelectAllChagne (e) { + handleSelectAllChange (e) { const checked = e.target.checked this.$emit('select', checked ? 'all' : 'removeAll', 0, null) }, @@ -182,7 +182,7 @@ export default { checked={checked} indeterminate={indeterminate} disabled={disabled} - onChange={this.handleSelectAllChagne} + onChange={this.handleSelectAllChange} /> {customSelections} diff --git a/components/table/Table.jsx b/components/table/Table.jsx index 7bdb7e9c4..a81b2a719 100755 --- a/components/table/Table.jsx +++ b/components/table/Table.jsx @@ -16,7 +16,7 @@ import Column from './Column' import ColumnGroup from './ColumnGroup' import createBodyRow from './createBodyRow' import { flatArray, treeMap, flatFilter } from './util' -import { initDefaultProps, mergeProps, getOptionProps } from '../_util/props-util' +import { initDefaultProps, mergeProps, getOptionProps, getComponentFromProp, isValidElement } from '../_util/props-util' import BaseMixin from '../_util/BaseMixin' import { TableProps, @@ -437,7 +437,7 @@ export default { let selectedRowKeys = this.store.getState().selectedRowKeys.concat(defaultSelection) const key = this.getRecordKey(record, rowIndex) const { pivot } = this.$data - const rows = this.getFlatCurrentPageData() + const rows = this.getFlatCurrentPageData(this.$props.childrenColumnName) let realIndex = rowIndex if (this.$props.expandedRowRender) { realIndex = rows.findIndex(row => this.getRecordKey(row, rowIndex) === key) @@ -500,10 +500,8 @@ export default { handleRadioSelect (record, rowIndex, e) { const checked = e.target.checked const nativeEvent = e.nativeEvent - const defaultSelection = this.store.getState().selectionDirty ? [] : this.getDefaultSelection() - let selectedRowKeys = this.store.getState().selectedRowKeys.concat(defaultSelection) const key = this.getRecordKey(record, rowIndex) - selectedRowKeys = [key] + const selectedRowKeys = [key] this.store.setState({ selectionDirty: true, }) @@ -517,7 +515,7 @@ export default { }, handleSelectRow (selectionKey, index, onSelectFunc) { - const data = this.getFlatCurrentPageData() + const data = this.getFlatCurrentPageData(this.$props.childrenColumnName) const defaultSelection = this.store.getState().selectionDirty ? [] : this.getDefaultSelection() const selectedRowKeys = this.store.getState().selectedRowKeys.concat(defaultSelection) const changeableRowKeys = data @@ -662,10 +660,10 @@ export default { }, renderRowSelection (locale) { - const { prefixCls, rowSelection } = this + const { prefixCls, rowSelection, childrenColumnName } = this const columns = this.columns.concat() if (rowSelection) { - const data = this.getFlatCurrentPageData().filter((item, index) => { + const data = this.getFlatCurrentPageData(childrenColumnName).filter((item, index) => { if (rowSelection.getCheckboxProps) { return !this.getCheckboxPropsByItem(item, index).props.disabled } @@ -741,6 +739,14 @@ export default { const key = this.getColumnKey(column, i) let filterDropdown let sortButton + let customHeaderCell = column.customHeaderCell + const { slots } = column + let title = column.title + if (title === undefined && slots && slots.title) { + title = this.$slots[slots.title] + title = title && title[0] + } + const sortTitle = this.getColumnTitle(title, {}) || locale.sortTitle const isSortColumn = this.isSortColumn(column) if ((column.filters && column.filters.length > 0) || column.filterDropdown) { const colFilters = key in filters ? filters[key] : [] @@ -759,12 +765,6 @@ export default { ) } if (column.sorter) { - // const isSortColumn = this.isSortColumn(column) - // if (isSortColumn) { - // column.className = classNames(column.className, { - // [`${prefixCls}-column-sort`]: sortOrder, - // }) - // } const isAscend = isSortColumn && sortOrder === 'ascend' const isDescend = isSortColumn && sortOrder === 'descend' sortButton = ( @@ -781,7 +781,27 @@ export default { /> ) + customHeaderCell = (col) => { + let colProps = {} + // Get original first + if (column.customHeaderCell) { + colProps = { + ...column.customHeaderCell(col), + } + } + colProps.on = colProps.on || {} + // Add sorter logic + const onHeaderCellClick = colProps.on.click + colProps.on.click = (...args) => { + this.toggleSortOrder(column) + if (onHeaderCellClick) { + onHeaderCellClick(...args) + } + } + return colProps + } } + const sortTitleString = sortButton && typeof sortTitle === 'string' ? sortTitle : undefined return { ...column, className: classNames(column.className, { @@ -793,29 +813,16 @@ export default { title: [
this.toggleSortOrder(column)} > {this.renderColumnTitle(column.title)} {sortButton}
, filterDropdown, ], + customHeaderCell, } - // column.title = ( - // - // {column.title} - // {sortButton} - // {filterDropdown} - // - // ) - - // if (sortButton || filterDropdown) { - // column.className = classNames(`${prefixCls}-column-has-filters`, column.className) - // } - - // return column }) }, renderColumnTitle (title) { @@ -829,6 +836,23 @@ export default { } return title }, + + getColumnTitle (title, parentNode) { + if (!title) { + return + } + if (isValidElement(title)) { + debugger + const props = title.props + if (props && props.children) { + const { children } = props + return this.getColumnTitle(children, props) + } + } else { + return parentNode.title || title + } + }, + handleShowSizeChange (current, pageSize) { const pagination = this.sPagination pagination.onShowSizeChange(current, pageSize) @@ -939,11 +963,11 @@ export default { }, getFlatData () { - return flatArray(this.getLocalData()) + return flatArray(this.getLocalData(null, false)) }, - getFlatCurrentPageData () { - return flatArray(this.getCurrentPageData()) + getFlatCurrentPageData (childrenColumnName) { + return flatArray(this.getCurrentPageData(), childrenColumnName) }, recursiveSort (data, sorterFn) { @@ -954,7 +978,7 @@ export default { } : item)) }, - getLocalData (state) { + getLocalData (state, filter = true) { const currentState = state || this.$data const { sFilters: filters } = currentState const { dataSource } = this.$props @@ -966,7 +990,7 @@ export default { data = this.recursiveSort(data, sorterFn) } // 筛选 - if (filters) { + if (filter && filters) { Object.keys(filters).forEach((columnKey) => { const col = this.findColumn(columnKey) if (!col) { diff --git a/components/table/demo/index.vue b/components/table/demo/index.vue index ea92dd7db..5155ad260 100644 --- a/components/table/demo/index.vue +++ b/components/table/demo/index.vue @@ -49,7 +49,7 @@ const md = { ## How To Use Specify \`dataSource\` of Table as an array of data. -## Examples +## Examples `, } export default { diff --git a/components/table/index.en-US.md b/components/table/index.en-US.md index 2df59fd2e..81f2e8ad9 100644 --- a/components/table/index.en-US.md +++ b/components/table/index.en-US.md @@ -44,6 +44,7 @@ const columns = [{ | defaultExpandedRowKeys | Initial expanded row keys | string\[] | - | | expandedRowKeys | Current expanded row keys | string\[] | - | | expandedRowRender | Expanded container render for each row | Function(record, index, indent, expanded):VNode\|slot-scope | - | +| expandIcon | Customize row expand Icon. | Function(props):VNode \| slot="expandIcon" slot-scope="props" | - | | expandRowByClick | Whether to expand row by clicking anywhere in the whole row | boolean | `false` | | footer | Table footer renderer | Function(currentPageData)\|slot-scope | | | indentSize | Indent size in pixels of tree data | number | 15 | @@ -120,7 +121,7 @@ One of the Table `columns` prop for describing the table's columns, Column has t | sortOrder | Order of sorted values: `'ascend'` `'descend'` `false` | boolean\|string | - | | title | Title of this column | string\|slot | - | | width | Width of this column | string\|number | - | -| customCell | Set props on per cell | Function(record) | - | +| customCell | Set props on per cell | Function(record, rowIndex) | - | | customHeaderCell | Set props on per header cell | Function(column) | - | | onFilter | Callback executed when the confirm filter button is clicked, Use as a `filter` event when using template or jsx | Function | - | | onFilterDropdownVisibleChange | Callback executed when `filterDropdownVisible` is changed, Use as a `filterDropdownVisible` event when using template or jsx | function(visible) {} | - | diff --git a/components/table/index.zh-CN.md b/components/table/index.zh-CN.md index 86733ad73..48c02c13f 100644 --- a/components/table/index.zh-CN.md +++ b/components/table/index.zh-CN.md @@ -43,7 +43,8 @@ const columns = [{ | defaultExpandAllRows | 初始时,是否展开所有行 | boolean | false | | defaultExpandedRowKeys | 默认展开的行 | string\[] | - | | expandedRowKeys | 展开的行,控制属性 | string\[] | - | -| expandedRowRender | 额外的展开行 | Function(record, index, indent, expanded):VNode\|slot-scope| - | +| expandedRowRender | 额外的展开行 | Function(record, index, indent, expanded):VNode \| slot="expandedRowRender" slot-scope="record, index, indent, expanded" | - | +| expandIcon | 自定义展开图标 | Function(props):VNode \| slot="expandIcon" slot-scope="props" | - | | expandRowByClick | 通过点击行来展开子行 | boolean | `false` | | footer | 表格尾部 | Function(currentPageData)\|slot-scope | | | indentSize | 展示树形数据时,每层缩进的宽度,以 px 为单位 | number | 15 | @@ -122,7 +123,7 @@ const columns = [{ | title | 列头显示文字 | string\|slot | - | | width | 列宽度 | string\|number | - | | customCell | 设置单元格属性 | Function(record) | - | -| customHeaderCell | 设置头部单元格属性 | Function(column) | - | +| customHeaderCell | 设置头部单元格属性 | Function(column, rowIndex) | - | | onFilter | 本地模式下,确定筛选的运行函数, 使用template或jsx时作为`filter`事件使用 | Function | - | | onFilterDropdownVisibleChange | 自定义筛选菜单可见变化时调用,使用template或jsx时作为`filterDropdownVisibleChange`事件使用 | function(visible) {} | - | | slots | 使用columns时,可以通过该属性配置支持slot的属性,如 `slots: { filterIcon: 'XXX'}` | object | - | diff --git a/types/table/column.d.ts b/types/table/column.d.ts index 0fd087f6a..e2fb09010 100644 --- a/types/table/column.d.ts +++ b/types/table/column.d.ts @@ -133,7 +133,8 @@ export declare class Column extends AntdComponent { * @type Function */ customCell: ( - record: any + record: any, + rowIndex: number, ) => { props: object; attrs: object; diff --git a/types/table/table.d.ts b/types/table/table.d.ts index 0d372307a..e222583c2 100644 --- a/types/table/table.d.ts +++ b/types/table/table.d.ts @@ -193,6 +193,12 @@ export declare class Table extends AntdComponent { expanded: boolean ) => any; + /** + * Customize row expand Icon. + * @type Function | ScopedSlot + */ + expandIcon: Function | ScopedSlot; + /** * Whether to expand row by clicking anywhere in the whole row * @default false