ant design vue table二次封装

<template>
  <div>
    <a-table
      class="k-table"
      :columns="columns"
      :data-source="origninData"
      :loading="loading"
      :bordered="bordered"
      :pagination="false"
      :size="size"
      :rowKey="(record, index) => index + 1"
      :row-selection="rowSelection"
      :scroll="{ x: 'max-content', y: maxY }"
    >
      <template class="k-table-slot" v-for="(item, i) in columns" v-slot:[item.builder]="slotProps">
        <KBuilder v-if="item.builder" class="builder" :name="item.builder" :row="slotProps" :column="item" />
        <!-- 加下面这行才会渲染,也不知啥原因 -->
        <span v-else>{{ slotProps }}</span>
      </template>
    </a-table>
    <a-pagination
      class="k-pagination"
      show-quick-jumper
      showSizeChanger
      :pageSizeOptions="paginationData.pageSizeOptions"
      :current="current"
      :pageSize="paginationData.pageSize"
      :total="pageTotal"
      :showTotal="paginationData.showTotal"
      :size="pageSizes"
      @change="paginationData.onChange"
      @showSizeChange="paginationData.onShowSizeChange"
    />
  </div>
</template>

<script>
import KBuilder from './KBuilder'
// import { findParentComponents } from '@/utils/KUtils/getData'
/**
 * @origninColumns Table表头
 * @data    Table表格数据
 * @loading 表格懒加载
 * @bordered 是否展示外边框和列边框
 * @size    表格尺寸,可选值为 large、small、default 或者不填
 * @rowKey 序号:使用方法在columns配置中加入 { title: "序号", customRender: (text, record, index) => index + 1 },
 * @pageTotal 分页条数
 * @pageSizes 分页尺寸
 */

export default {
  name: 'KTable',
  components: {
    KBuilder
  },
  props: {
    origninColumns: {
      type: Array,
      default: () => []
    },
    origninData: {
      type: Array,
      default: () => []
    },
    loading: {
      type: Boolean,
      default: false
    },
    bordered: {
      type: Boolean,
      default: true
    },
    size: {
      type: [String, Number],
      default: 'default'
    },
    pageTotal: {
      type: Number,
      default: 0
    },
    pageSizes: {
      type: [String, Number],
      default: 'default'
    },
    pageNo: {
      type: Number,
      default: 0
    }
  },
  mounted() {
    // this.PVM = findParentComponents(this, 'domcumentName')[0]
  },
  data() {
    return {
      selectedRowKeys: [], // 选中key
      selectedRows: [], // 选中数组
      maxY: 0,
      paginationData: {
        current: 1,
        pageSize: 10,
        showTotal: (total, range) => {
          return ' 共' + total + '条'
        },
        pageSizeOptions: ['10', '20', '30', '50', '100'],
        onChange: (pageNo, pageSize) => {
          this.paginationData.current = pageNo
          this.paginationData.pageSize = pageSize
          this.$emit('pagination', { pageSize, pageNo })
          // this.PVM.getPageData({ ...this.PVM.queryParams, pageSize, pageNo })
        },
        // 改变每页数量时更新显示
        onShowSizeChange: (current, pageSize) => {
          this.paginationData.current = 1
          this.paginationData.pageSize = pageSize
          this.$emit('pagination', { pageSize, pageNo: current })
          // this.PVM.getPageData({ ...this.PVM.queryParams, pageSize, pageNo: current })
        }
      }
    }
  },
  created() {
    this.maxY = (document.documentElement.clientHeight / 100) * 55
  },
  methods: {
    onCellClick(record) {
      this.$emit('CellClick', record)
    }
  },
  computed: {
    current({ pageNo, paginationData }) {
      return pageNo || paginationData.current
    },
    columns({ origninColumns }) {
      return origninColumns?.map(item => {
        return {
          ...item,
          scopedSlots: {
            customRender: item.builder
          }
        }
      })
    },
    rowSelection() {
      return {
        selectedRowKeys: this.selectedRowKeys,
        onChange: (selectedRowKeys, selectedRows) => {
          this.selectedRowKeys = selectedRowKeys
          this.selectedRows = selectedRows
          this.$emit('onChange')
          console.log(`selectedRowKeys: ${selectedRowKeys}`, 'selectedRows: ', selectedRows)
        },
        onSelect: (record, selected, selectedRows) => {
          this.$emit('onSelect')

          console.log(record, selected, selectedRows)
        },
        onSelectAll: (selected, selectedRows, changeRows) => {
          this.$emit('onSelectAll')
          console.log(selected, selectedRows, changeRows)
        }
      }
    }
  },
  watch: {}
}
</script>

<style lang="less" scoped>
.k-table {
  margin-top: 24px;
  word-break: break-all !important;
}
.k-table-slot {
  cursor: pointer;
}
.k-pagination {
  display: flex;
  margin-top: 12px;
  justify-content: flex-end;
}

/deep/.ant-table-tbody tr:nth-child(2n) {
  background-color: #f7f9fc !important;
}
/deep/.ant-table-column-title {
  font-size: 14px;
  font-family: PingFang SC, PingFang SC;
  font-weight: 600;
  color: #909399;
}
/deep/.ant-table-content {
  font-size: 14px;
  font-family: PingFang SC, PingFang SC;
  font-weight: 400;
  color: #303133;
}
/deep/.ant-table-tbody > tr > td {
  padding: 16px 12px;
}
</style>

1.重写表头 ------- KBuilder.js

function isFunction(value) {
  return typeof value === 'function'
}

function isVnode(ctx, scope) {
  return scope.constructor.name == ctx.parent.$vnode.constructor.name
}

function findSlot(ctx, slotName) {
  const ctxSlot = ctx.scopedSlots[slotName.toLowerCase()]
  if (isFunction(ctxSlot)) {
    return ctxSlot
  }
  let parent = ctx.parent
  while (parent) {
    if (isFunction(parent.$scopedSlots?.[slotName])) {
      return parent.$scopedSlots[slotName]
    } else {
      parent = parent.$parent
    }
  }
  return null
}

export default {
  name: 'KBuilder',
  functional: true,
  props: {
    name: {
      type: [Function, String, Object],
      default: ''
    }
  },
  render: (h, ctx) => {
    const scope = ctx.props.name
    if (isVnode(ctx, scope)) return scope
    if (isFunction(scope)) {
      return scope(h, ctx.data.attrs, ctx.listeners)
    }
    if (scope && typeof scope === 'string') {
      ctx._slot = ctx._slot || findSlot(ctx, scope)
      if (ctx._slot) {
        return ctx._slot(ctx.data.attrs)
      }
    }
    return h(null)
  }
}

2.目录结构 

3.项目使用

<KTable
      :origninColumns="[{
    title: '序号',
    align: 'left',
    fixed: 'left',
    width: 75,
    key: 'index',
    customRender: (text, record, index) => index + 1
  },
  {
    title: '合同编号',
    align: 'left',
    dataIndex: 'contractNo',
    width: 135,
    sortable: false,
    key: 'contractNo'
  }]"
      :origninData="dataSource"
      :loading="loading"
      :pageTotal="total"
      :current="pages.pageNo"
      @pagination="onPagination"
    >
      <template #action="{row}">
        <a-icon class="action-icon" type="form" title="编辑" @click="onEdit(row)" />
        <a-popconfirm title="确定删除吗?" @confirm="() => onDelet(row)">
          <a-icon class="action-icon" type="delete" title="删除" />
        </a-popconfirm>
      </template>
    </KTable>

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

韩召华

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值