Vue secondary encapsulates the Table component of ElementUI
- For rapid development and convenient writing
Introduction of the configuration
- Directly to data and config to display data
- To paging, and paging interface method, can be configured without a key, the current paging parameters are fixed, can be modified according to specific projects
- If you have additional request criteria, or a search after display, you need to give queryParams
- For now, only select Input link has built-in type, you can use render to customize, or you can add additional case
config
- Key column prop, label list header display
- Render can be custom render body, he accompany type: custom use
- Renderheaders can be customized
- Type is used to configure editable tables, such as input and select, which can be added later
- Disable props, show the editable for function, parameter is the scope and returns a Boolean
- Props is an additional attribute to use after setting type. This attribute is reserved for dom edits, such as input size, placeholder, and select options
- Support all other attributes and methods of the EL-table, support all attributes of the el-table-column, method is not done
height
- This optional property, if not passed, defaults to the parent component’s parent level of 100%. The height of the table is minus the height of the paging component
Config = [{key: 'name', label: 'name', type: 'custom', renderHeader: (h, data) = > {return ` name ${data. Row. $index} `}, render: (h, data) = > {return ` zhang SAN ${data. Row. $index} `}, {key: 'age', label: 'age', type: 'input', props: {size: 'mini'}}, {key: 'sex', label: 'gender ', type: 'select', props: {size: 'mini'}, key: 'sex', label:' gender ', type: 'select', props: {options: [{value: label: 'male', '1'}, {label: 'nv, value:' 2 '}]}}, {key: 'status', label:' state ', the formatter: (row, column, cellValue, index) => {// native method return index%2? 'enabled' : 'disabled'}}}]Copy the code
Component code
<script> export default { name: 'PTable', model: { prop: 'data', event: 'change' }, props: { config: {// Table configuration type: Array, required: true}, data: {// Table data type: Array, required: true}, editable: Type: Boolean, default: true}, height: {// table height type: Number}, hasPagination: Type: Boolean, default: false}, queryParams: {// Search parameters, need to attach additional parameters to the table type: Object, default: Type: Function}}, data() {return {loading: false, currentData: JSON.parse(JSON.stringify(this.data)), pageSizes: [10, 25, 30, 50], currentPageSize: 10, currentPage: 4, pageLayout: 'total, sizes, prev, pager, next, jumper', pageTotal: 400 } }, created() { this.getTableData() }, mounted() { }, methods: { handleTableChange(key, eventType, value) { this.$emit('change', JSON.parse(JSON.stringify(this.currentData))) this.$emit('table-change', key, eventType, value) }, HandleSizeChange (val) {console.log(' ${val} bars per page '); this.currentPageSize = val; this.getTableData(); }, handleCurrentChange(val) {console.log(' current page: ${val} '); this.currentPage = val; this.getTableData(); }, getTableData() { if (! this.queryApi) return let params = {}; params.pageNum = this.currentPage; params.pageSize = this.currentPageSize; Object.assign(params, this.queryParams); this.loading = true; this.queryApi(params).then(response => { this.currentData = response.result_data; this.pageTotal = response.count; }).finally((error)=>{ this.loading = false; }) } }, render(h) { const renderItem = (scope, data) => { const { key, label, type, width, props, render, ... prop } = data const canEdit = this.editable === false ? this.editable : (props.editable ? props.editable(scope) : true) const isShow = props.show ? Props. Show (scope) : true // Const isDisable = props. Disable? props.disable(scope) : false let ItemTemplate = '' if (canEdit) { switch (type) { case 'input': ItemTemplate = < el - - the model input v = {scope. Row [key]} placeholder = {props. The placeholder | | 'please enter'} size = "mini" rows = {props. Rows} {... {props}} disabled={isDisable} onInput={() => this.handleTableChange(key, 'input', scope.row[key])} onBlur={() => this.handleTableChange(key, 'blur', scope.row[key])}></el-input> break; case 'link': ItemTemplate = <el-link {... {props: props}} disabled={isDisable} onClick={() => props.click(scope)}> {scope.row[key]} </el-link> break; case 'select': ItemTemplate = < el - select v - model = {scope. Row [key]} disabled = {isDisable} placeholder = {props. The placeholder | | 'please enter'} size="mini" {... {props}} onChange={() => this.handleTableChange(key, 'change', scope.row[key])}> { props.options.map((item, index) => { return <el-option key={index} label={item.label} value={item.value}> </el-option> }) } </el-select> break; case 'custom': ItemTemplate = render(h, scope) break; default: ItemTemplate = <span>{scope.row[key]}</span> break; } } else { ItemTemplate = <span>{scope.row[key]}</span> } return ItemTemplate } const renderChildren = (data) => { const { key, label, type, width, props, children, ... prop } = data let PROPS = {} PROPS.type = type; PROPS.prop = key; PROPS.width = width; PROPS.label = label; PROPS.headerAlign = prop.headerAlign || 'center'; let ScopeS = {} if (type === 'selection' || type === 'index') { PROPS.align = 'center' } else if (! type) { Object.assign(PROPS, prop) } else { Object.assign(PROPS, prop) ScopeS = { scopedSlots: { default: (scope) => { return renderItem(scope, data) } } } if (prop.renderHeader) { ScopeS.scopedSlots.header = (scope) => { return prop.renderHeader(h, scope) } } } for (let [key, value] of Object.entries(PROPS)) { (value == undefined) && delete PROPS[key] } return <el-table-column {... {props: PROPS}} {... ScopeS}> { children && children.length ? children.map(item => renderChildren(item)) : '' } </el-table-column> } const tableHeight = this.height ? (this.height - (this.hasPagination ? 60 : 0) + 'px') : '0'; return(<div class="p-table-area" loading={this.loading}> <section class="table-area" style={{ 'height': tableHeight }}> <el-table height="100%" {... {props: this.$attrs}} {... {on: this.$listeners}} data={this.currentData}> { this.config.map((item) => { return renderChildren(item) }) } </el-table> </section> { this.hasPagination && <section class="page-area"> <el-pagination onSizeChange={this.handleSizeChange} OnCurrentChange={this.handleCurrentChange} currentPage={this.currentPage} pageSizes={this.pageSizes} pageSize={this.currentPageSize} layout={this.pageLayout} total={this.pageTotal}> </el-pagination> </section> } </div>) } } </script> <style lang="scss" scoped> .p-table-area { flex: 1; display: flex; flex-direction: column; width: 100%; .table-area { flex: 1; } .page-area { height: 60px; display: flex; align-items: center; justify-content: flex-end; } } /deep/.el-table td { padding: 4px 0; } /deep/.el-table th { padding: 8px 0; } </style>Copy the code