编程技术是改变世界的力量。
本站
当前位置:网站首页 > HTML/CSS > 正文

vue-pro-table:包含搜索/列表/分页的页面级组件

gowuye 2023-10-18 04:08 595 浏览 4 评论

vue-pro-table

一个基于 ElementUI 封装的 table 列表页组件,将包含搜索、列表、分页等功能的页面封装成一个组件

特性

?将搜索、列表、分页三者的交互逻辑封装到组件中,节省开发者代码量

?配置化的请求函数,自动发送请求,自动获取请求参数,自动显示 loading 效果

?配置化的表格项,跟 el-table-column 的配置属性类似

?配置化的搜索表单,支持大部分表单元素

?配置化的分页,跟 el-pagination 的配置属性类似

?自定义是否显示搜索和分页

?自定义标题栏和工具栏

?丰富的插槽提供功能扩展

使用

安装和引入

安装

// npm
npm install vue-pro-table
// yarn
yarn add vue-pro-table

引入

该组件依赖 element-ui,需要自行引入

import ElementUI from "element-ui";
import "element-ui/lib/theme-chalk/index.css";
Vue.use(ElementUI);

// 引入vue-pro-table
import VueProTable from "vue-pro-table";
Vue.use(VueProTable);

快速使用

<template>
  <vue-pro-table title="列表" :request="getList" :columns="columns">
    <template #operate="scope">
      <el-button size="mini" type="primary">编辑</el-button>
      <el-button size="mini" type="danger">删除</el-button>
    </template>
  </vue-pro-table>
</template>

<script>
import {getUserList} from 'src/api/xxx';
export default {
  data() {
    // 表格列配置,大部分属性跟el-table-column配置一样
    columns: [
      { label: '序号', type: 'index' },
      { label: '名称', prop: 'nickName', width: 180 },
      { label: '邮箱', prop: 'userEmail' },
      {
        label: '操作',
        fixed: 'right',
        width: 180,
        align: 'center',
        tdSlot: 'operate', // 自定义单元格内容的插槽名称
      },
    ],
  },
  methods: {
    // 请求函数
    async getList(params) {
      // params是从组件接收的,包含分页和搜索字段。
      const { data } = await getUserList(params)

      // 必须要返回一个对象,包含data数组和total总数
      return {
        data: data.list,
        total: +data.total,
      }
    },
  }
}
</script>

预览效果

默认不包含搜索表单

请求函数配置

?request,请求列表数据的函数

组件加载的时候会自动执行 request 函数,并在加载过程中显示 loading 效果

  • 函数接收参数:包含搜索表单的所有字段和分页的 pageNum 和 pageSize
  • 函数必须返回一个对象,包含:

? data: 列表数据的数组

? total:总数,用于分页

表格配置

?columns 属性的配置,是一个数组

参数

说明

类型

可选值

默认值

label

对应 el-table-column 的 label

string

-

-

type

对应 el-table-column 的 type

string

selection/index/expand

-

prop

对应 el-table-column 的 prop

string

-

-

width

对应 el-table-column 的 width

string,number

-

-

minWidth

对应 el-table-column 的 min-width

string,number

-

-

align

对应 el-table-column 的 align

string

left/center/right

left

fixed

对应 el-table-column 的 fixed

string, boolean

true, left, right

-

sortable

对应 el-table-column 的 sortable

boolean

false/true

false

filters

对应 el-table-column 的 filters

Array[{ text, value }]

-

-

tdSlot

单元格要自定义内容时,可以通过此属性配置一个插槽名称,并且是作用域插槽,可以接收 scope 数据

string

-

-

labelSlot

表头要自定义内容时,可以通过此属性配置一个插槽名称,并且是作用域插槽,可以接收 scope 数据

string

-

-

?row-key 属性配置

对应 el-table 的 row-key,默认值是'id'

搜索配置

?search 属性的配置,是一个对象

如果不想显示搜索表单,可以不配置 search 或者 search 设置为 false

参数

说明

类型

可选值

默认值

labelWidth

label 文字长度

string

-

-

inputWidth

表单项长度

string

-

-

fields

表单字段列表,包含 text,select,radio,checkbox,datetime 等类型,所有字段类型配置见下表

Array[{字段类型}]

-

-

?fields 列表的字段类型配置

参数

说明

类型

可选值

默认值

type

字段类型

string

text,textarea,select,radio,radio-button,checkbox,checkbox-button,number,date,daterange,datetime,datetimerange

text

label

label 文本

string

-

-

name

搜索时的提交的参数名称

string

-

-

style

额外的样式

object

-

-

defaultValue

默认值

-

-


options

当 type 是 select,radio,radio-button,checkbox,checkbox-button 时的枚举选项

Array[{name, value}]

-

-

transform

搜索前对表单数据进行转换,比如表单数据是数组,但是搜索的时候需要传递字符串。它是一个函数,默认参数是字段的 value,需要返回转换后的结果

function(value)

-

-

trueNames

当 type 是 daterange,datetimerange 时,开始时间和结束时间是在一个数组里面,但是搜索时可能需要两个字段,这时就需要把开始时间和结束时间分别赋值给两个字段,这两个字段的名称就是通过 trueNames 配置,它是一个数组,例如:trueNames: ['startTime', 'endTime']

Array[string]



min

当 type 是 number 时的最小值

number

-

-

max

当 type 是 number 时的最大值

number

-

-

分页配置

?

pagination 属性的配置,是一个对象

如果不想显示分页,将 pagination 设置为 false

参数

说明

类型

可选值

默认值

layout

组件布局

string

total, sizes, prev, pager, next, jumper

total, sizes, prev, pager, next, jumper

pageSize

每页显示条目个数

number

-

10

pageSizes

每页显示个数选择器的选项设置

Array[number]

-

[10, 20, 30, 40, 50, 100]

标题栏配置

表格上方有一个标题栏,标题栏左侧显示一个标题,右侧是一个可自定义的工具栏

?hide-title-bar

是否隐藏标题栏,布尔值

?title

表格标题

?自定义表格标题

提供一个具名插槽title,来自定义标题的内容

?工具栏

工具栏默认是空的,提供一个具名插槽 toolbar,来自定义工具栏的内容

事件

?selectionChange

如果columns中配置了type为selection的列,可以通过该事件得到已选择的行,参数是一个数组

组件内部方法

?refresh

配置 ref 属性,可以通过 ref 获取组件后调用组件内部的refresh方法刷新列表

完整用法

<template>
  <vue-pro-table
    ref="proTable"
    title="用户列表"
    :request="getList"
    :columns="columns"
    :search="searchConfig"
    :pagination="paginationConfig"
    @selectionChange="handleSelectionChange"
  >
      <!-- 工具栏 -->
      <template #toolbar>
        <el-button
          type="primary"
          icon="el-icon-plus"
          @click="$router.push({name: 'userAdd'})"
        >创建账号</el-button>
        <el-button
          type="danger"
          icon="el-icon-refresh"
          @click="$refs.pageBox.refresh()"
        >刷新</el-button>
      </template>

      <!-- 展开行 -->
      <template #expand="{row}">
        {{row.userEmail}}
      </template>

      <!-- 状态 -->
      <template #status="{row}">
        <el-tag :type="+row.status === 1 ? 'success' : 'info'">{{+row.status === 1 ? '启用' : '停用'}}</el-tag>
      </template>

      <!-- 表格操作栏 -->
      <template #page-operate="{row}">

        <el-button
          type="text"
          @click="$router.push({name: 'userEdit', params: {
                id: row.id
              }})"
        >编辑</el-button>

        <el-button
          v-if="+row.status === 1"
          type="text"
          @click="setUserStatus(row, 0)"
        >停用</el-button>

        <el-button
          v-else
          type="text"
          @click="setUserStatus(row, 1)"
        >启用</el-button>

      </template>

      <!-- 操作栏头部 -->
      <template #th-operate>
        <el-input />
      </template>

  </vue-pro-table>
</template>

<script>
import {getUserList} from 'src/api/xxx';
export default {
  data() {
    // 表格列配置,大部分属性跟el-table-column配置一样
    columns: [
        { label: '', type: 'expand', tdSlot: 'expand' },
        { label: '全选', type: 'selection' },
        { label: '序号', type: 'index' },
        { label: '账户名称', prop: 'nickName', sortable: true },
        { label: '账号', prop: 'userEmail', width: 80 },
        {
          label: '状态',
          prop: 'status',
          tdSlot: 'status',
          filters: [
            { text: '启用', value: 1 },
            { text: '禁用', value: 0 },
          ],
        },
        { label: '创建时间', prop: 'createTime', align: 'right' },
        { label: '最后修改时间', prop: 'updateTime' },
        {
          label: '操作',
          labelSlot: 'th-operate',
          fixed: 'right',
          width: 180,
          align: 'center',
          tdSlot: 'page-operate',
        },
    ],
    // 搜索配置
    searchConfig: {
        labelWidth: '90px',
        inputWidth: '360px',
        fields: [
          {
            type: 'text',
            label: '账户名称',
            name: 'nickName',
            defaultValue: 'abc',
          },
          {
            type: 'textarea',
            label: '描述',
            name: 'description',
          },
          {
            label: '状态',
            name: 'status',
            type: 'select',
            defaultValue: 1,
            options: [
              {
                name: '已发布',
                value: 1,
              },
              {
                name: '未发布',
                value: 0,
              },
            ],
          },
          {
            label: '性别',
            name: 'sex',
            type: 'radio',
            options: [
              {
                name: '男',
                value: 1,
              },
              {
                name: '女',
                value: 0,
              },
            ],
          },
          {
            label: '城市',
            name: 'city',
            type: 'radio-button',
            options: [
              {
                name: '北京',
                value: 'bj',
              },
              {
                name: '上海',
                value: 'sh',
              },
              {
                name: '广州',
                value: 'gz',
              },
              {
                name: '深圳',
                value: 'sz',
              },
            ],
          },
          {
            label: '爱好',
            name: 'hobby',
            type: 'checkbox',
            defaultValue: ['吃饭'],
            options: [
              {
                name: '吃饭',
                value: '吃饭',
              },
              {
                name: '睡觉',
                value: '睡觉',
              },
              {
                name: '打豆豆',
                value: '打豆豆',
              },
            ],
            transform: (val) => val.join(','),
          },
          {
            label: '水果',
            name: 'fruit',
            type: 'checkbox-button',
            options: [
              {
                name: '苹果',
                value: '苹果',
              },
              {
                name: '香蕉',
                value: '香蕉',
              },
              {
                name: '橘子',
                value: '橘子',
              },
              {
                name: '葡萄',
                value: '葡萄',
              },
            ],
            transform: (val) => val.join(','),
          },
          {
            label: '日期',
            name: 'date',
            type: 'date',
          },
          {
            label: '时间',
            name: 'datetime',
            type: 'datetime',
            defaultValue: '2020-10-10 8:00:00',
          },
          {
            label: '日期范围',
            name: 'daterange',
            type: 'daterange',
            trueNames: ['startDate', 'endDate'],
            style: { width: '360px' },
          },
          {
            label: '时间范围',
            name: 'datetimerange',
            type: 'datetimerange',
            trueNames: ['startTime', 'endTime'],
            style: { width: '360px' },
            defaultValue: ['2020-10-10 9:00:00', '2020-10-11 18:30:00'],
          },
          {
            label: '数量',
            name: 'num',
            type: 'number',
            min: 0,
            max: 10,
          },
        ],
    },
    // 分页配置
    paginationConfig: {
      layout: 'total, prev, pager, next, sizes', // 分页组件显示哪些功能
      pageSize: 5, // 每页条数
      pageSizes: [5, 10, 20, 50],
    }
  },
  methods: {
    // 请求函数
    async getList(params) {
      // params是从组件接收的,包含分页和搜索字段。
      const { data } = await getUserList(params)

      // 必须要返回一个对象,包含data数组和total总数
      return {
        data: data.list,
        total: +data.total,
      }
    },
    // 选择
    handleSelectionChange(arr) {
      console.log(arr)
    },
  }
}
</script>

效果:

相关推荐

python中调试pdb_python怎么调试
python中调试pdb_python怎么调试

当你的Python程序出现错误或行为不符合预期时,调试工具是一种非常有用的方式来帮助你找到问题所在。Python内置了一个强大的调试器模块,称为pdb(Pyth...

2023-10-22 12:21 gowuye

vue3+tsx开发语法详解_vue3+typescript
vue3+tsx开发语法详解_vue3+typescript

很多组件库都使用了TSX的方式开发,主要因为其灵活性比较高,TSX和SFC开发的优缺点就不介绍了,这里主要说一下将SFC项目改造为TSX的过程。安装JSX库pn...

2023-10-22 12:20 gowuye

对前端初学者的一些帮助(常见名词解释)
对前端初学者的一些帮助(常见名词解释)

1.HTML:HTML是超文本标记语言,“超文本”就是指页面内可以包含图片、链接,甚至音乐、程序等非文字元素。2.CSS:主要用来设计网页的样式,美化网页;...

2023-10-22 12:20 gowuye

JAVA多线程详解(超详细)_java多线程菜鸟教程
JAVA多线程详解(超详细)_java多线程菜鸟教程

一、线程简介1、进程、线程程序:开发写的代码称之为程序。程序就是一堆代码,一组数据和指令集,是一个静态的概念。进程(Process):将程序运行起来,我们称之...

2023-10-22 12:19 gowuye

一文搞懂什么时候用 Runnable?什么时候用 Callable ?

今天我们看一道leetcodehard难度题目:统计可以被K整除的下标对数目。题目给你一个下标从0开始、长度为n的整数数组nums和一个整数k,返回满足下述条件的下标对(i...

优化重复冗余代码的8种方式_优化重复冗余代码的8种方式是什么

日常开发中,我们经常会遇到一些重复代码。大家都知道重复代码不好,它主要有这些缺点:可维护性差、可读性差、增加错误风险等等。最近呢,我优化了一些系统中的重复代码,用了好几种的方式。感觉挺有用的,所以本文...

高级 CSS 和 Sass:Flexbox、网格、动画等等!
高级 CSS 和 Sass:Flexbox、网格、动画等等!

Udemy-高级CSS和Sass:Flexbox、网格、动画等等!讲师:JonasSchmedtmann下载:口袋资源网高级CSS和Sass:...

2023-10-22 12:19 gowuye

我们现在正处于 JavaScript 消亡的边缘?
我们现在正处于 JavaScript 消亡的边缘?

每10年JavaScript都会发生一次改朝换代式的变革。在我看来,JavaScript当前正处于一次快速变革的开始,而这段时期未来可能会被称为Ja...

2023-10-22 12:19 gowuye

CSS预编译器三剑客及PostCSS_前端预编译css有哪几种
CSS预编译器三剑客及PostCSS_前端预编译css有哪几种

这篇文章包含两个部分,第一部分是个CSS预编译器:Sass、Less、Stylus,他们之间的对比,第二部分是现在大火的PostCSS。为什么会出现CSS预编译...

2023-10-22 12:18 gowuye

CSS预处理语言Sass入门_css3预处理器
CSS预处理语言Sass入门_css3预处理器

1.引言CSS3之前的CSS都大都是枚举属性样式,而编程语言强大的变量、函数、循环、分支等功能基本都不能在CSS中使用,让CSS的编程黯淡无光,Sass就是一...

2023-10-22 12:18 gowuye

“金三银四”,让我们愉快的开始准备Web面经吧:CSS篇
“金三银四”,让我们愉快的开始准备Web面经吧:CSS篇

前言又到了一年一度的“金三银四的季节了”。不过恐怕大家都有感觉,当下,正面临着近几年来的最严重的互联网寒冬,因此今天的“金三银四”肯定又是一场更为惨烈的江湖厮杀...

2023-10-22 12:18 gowuye

sass @extend(继承)指令详解_sass内置函数总结

在设计网页的时候常常遇到这种情况:一个元素使用的样式与另一个元素完全相同,但又添加了额外的样式。通常会在HTML中给元素定义两个class,一个通用样式,一个特殊样式。普通CSS的实现接下来以警...

Sass混合的使用_sas中如何合并两组数据

本节我们学习Sass中的混合,Sass中的混合是通过@mixin指令来定义的,混合允许我们定义可以在整个样式表中重复使用的样式,避免使用无语意的类。混合可以包含所有的CSS规则和任何其他...

css代码规范工具stylelint_代码规范

css样式的书写顺序及原理——很重要!很重要!很重要!为什么重要???概括讲就是,它涉及了浏览器的渲染原理:reflow和repaint还想知道更多为什么可以参考:https://blog.csdn....

CSS-in-JS 是恶魔还是天使?_天启四骑士是恶魔还是天使
CSS-in-JS 是恶魔还是天使?_天启四骑士是恶魔还是天使

有些人极为讨厌CSS-in-JS,单单提起这个名字都会让他们反感,总之就是拒绝二字。他们认为样式不属于JavaScript,而是属于CSS,并且CSS...

2023-10-22 12:17 gowuye

已有4位网友发表了看法:

  • 编程站

    编程站  评论于 [2023-11-11 19:51:21]  回复

    vue proTable官网

取消回复欢迎 发表评论: