vue.js管理后台table组件封装的方法

我来为你讲解 “Vue.js管理后台table组件封装的方法”的完整攻略。

一、背景介绍

在管理后台开发中,表格展示是必不可少的控件,但是我们往往还需要对表格做各种处理,例如支持多选、排序等等,因此将表格进行封装,可以提高开发效率,简化代码复杂度。

二、封装思路

我们将 Table 的一些常用功能进行封装,例如:

  • 支持多选/单选
  • 支持数据的增删改查操作
  • 支持行样式/列样式的自定义
  • 支持排序/筛选功能

具体实现方法有很多,下面我将提供一种比较常见的封装思路。

1. 创建基础 Table 组件

首先,我们需要创建一个基础的 Table 组件,包含了最基本的展示数据功能。在组件中,我们可以通过 props 的方式传入表格的列数据和行数据,然后通过 v-for 指令进行渲染。

<template>
  <table>
    <thead>
      <tr>
        <th v-for="column in columns" :key="column.field">{{ column.label }}</th>
      </tr>
    </thead>
    <tbody>
      <tr v-for="(row, index) in rows" :key="index">
        <td v-for="column in columns" :key="column.field">{{row[column.field]}}</td>
      </tr>
    </tbody>
  </table>
</template>

<script>
export default {
  props: {
    columns: {
      type: Array,
      default: () => []
    },
    rows: {
      type: Array,
      default: () => []
    }
  }
}
</script>

2. 增加多选/单选功能

为了支持多选/单选功能,我们需要添加一个复选框,以及对应的选中状态。我们可以在组件的 data 中添加一个 selectedRows 属性,用于存储当前选中的行数据。然后在表格中添加一个选择列,通过 v-model 双向绑定实现选择状态的控制。

<template>
  <table>
    <thead>
      <tr>
        <th>
          <input type="checkbox"
            v-model="allSelected"
            @change="selectAll($event)"/>
        </th>
        <th v-for="column in columns" :key="column.field">{{ column.label }}</th>
      </tr>
    </thead>
    <tbody>
      <tr v-for="(row, index) in rows" :key="index">
        <td>
          <input type="checkbox"
            v-model="selectedRows"
            :value="row"/>
        </td>
        <td v-for="column in columns" :key="column.field">{{row[column.field]}}</td>
      </tr>
    </tbody>
  </table>
</template>

<script>
export default {
  props: {
    columns: {
      type: Array,
      default: () => []
    },
    rows: {
      type: Array,
      default: () => []
    }
  },
  data() {
    return {
      allSelected: false,
      selectedRows: []
    }
  },
  methods: {
    selectAll(event) {
      this.selectedRows = event.target.checked ? this.rows : []
    }
  }
}
</script>

3. 增加数据的增删改查功能

为了支持数据的增删改查功能,我们需要在 Table 组件中添加一些按钮,用于操作数据。例如,添加按钮、编辑按钮、删除按钮等等。然后我们可以提取一个 Dialog 组件,用于添加和编辑数据,并使用 slot 的方式将表单内容传入,相当于将弹窗的内容进行了封装。在 Dialog 中,我们可以通过 $emit 方式触发表格的 update 和 create 事件,数据更新后再更新表格即可。

<template>
  <div>
    <button @click="create">添加</button>
    <table>
      <!-- 表头 -->
      <thead>
        <tr>
          <th>
            <input type="checkbox"
              v-model="allSelected"
              @change="selectAll($event)"/>
          </th>
          <th v-for="column in columns" :key="column.field">{{ column.label }}</th>
          <th>操作</th>
        </tr>
      </thead>
      <!-- 数据 -->
      <tbody>
        <tr v-for="(row, index) in rows" :key="index">
          <td>
            <input type="checkbox"
              v-model="selectedRows"
              :value="row"/>
          </td>
          <td v-for="column in columns" :key="column.field">{{row[column.field]}}</td>
          <td>
            <button @click="edit(row)">编辑</button>
            <button @click="remove(row)">删除</button>
          </td>
        </tr>
      </tbody>
    </table>
    <Dialog v-model="dialogVisible"
      @update="update"
      @create="create">
      <!-- 插槽,用于传递弹窗中的表单数据 -->
      <slot name="form"></slot>
    </Dialog>
  </div>
</template>

<script>
import Dialog from '@/components/Dialog.vue'

export default {
  components: {
    Dialog
  },
  props: {
    columns: {
      type: Array,
      default: () => []
    },
    rows: {
      type: Array,
      default: () => []
    }
  },
  data() {
    return {
      allSelected: false,
      selectedRows: [],
      dialogVisible: false,
      currentRow: {}
    }
  },
  methods: {
    create() {
      this.currentRow = {}
      this.dialogVisible = true
    },
    update(row) {
      // 更新数据
      this.rows = this.rows.map(item => item.id === row.id ? row : item)
    },
    remove(row) {
      // 删除数据
      this.rows = this.rows.filter(item => item.id !== row.id)
    },
    selectAll(event) {
      this.selectedRows = event.target.checked ? this.rows : []
    },
    edit(row) {
      // 编辑数据
      this.currentRow = {...row}
      this.dialogVisible = true
    }
  }
}
</script>

4. 增加样式的自定义

为了支持样式的自定义,我们可以在 Table 中定义 slot,用于传入行样式和列样式。例如,我们可以在 tr 中添加一个 row-class 的属性,用于设置行的样式名,然后在表格中添加一个名为 row 的 slot,并根据传递的 row 数据设置样式。列样式的自定义也类似。

<template>
  <table>
    <!-- 表头 -->
    <thead>
      <tr>
        <th>
          <input type="checkbox"
            v-model="allSelected"
            @change="selectAll($event)"/>
        </th>
        <th v-for="column in columns" :key="column.field">{{ column.label }}</th>
        <th>操作</th>
      </tr>
    </thead>
    <!-- 数据 -->
    <tbody>
      <tr v-for="(row, index) in rows" :key="index"
        :class="getRowClass(row)">
        <td>
          <input type="checkbox"
            v-model="selectedRows"
            :value="row"/>
        </td>
        <td v-for="column in columns" :key="column.field"
          :class="getColumnClass(row, column.field)">{{row[column.field]}}</td>
        <td>
          <button @click="edit(row)">编辑</button>
          <button @click="remove(row)">删除</button>
        </td>
      </tr>
    </tbody>
    <!-- 插槽,用于传递行样式和列样式 -->
    <slot name="row" :row="rows"></slot>
    <slot name="column"></slot>
  </table>
</template>

<script>
import Dialog from '@/components/Dialog.vue'

export default {
  components: {
    Dialog
  },
  props: {
    columns: {
      type: Array,
      default: () => []
    },
    rows: {
      type: Array,
      default: () => []
    }
  },
  data() {
    return {
      allSelected: false,
      selectedRows: [],
      dialogVisible: false,
      currentRow: {}
    }
  },
  methods: {
    create() {
      this.currentRow = {}
      this.dialogVisible = true
    },
    update(row) {
      // 更新数据
      this.rows = this.rows.map(item => item.id === row.id ? row : item)
    },
    remove(row) {
      // 删除数据
      this.rows = this.rows.filter(item => item.id !== row.id)
    },
    selectAll(event) {
      this.selectedRows = event.target.checked ? this.rows : []
    },
    edit(row) {
      // 编辑数据
      this.currentRow = {...row}
      this.dialogVisible = true
    },
    // 获取行样式,在插槽中使用
    getRowClass(row) {
      // todo: 实现根据不同的条件返回不同的 class 名称
      return 'row-class'
    },
    // 获取列样式,在插槽中使用
    getColumnClass(row, field) {
      // todo: 实现根据不同的条件返回不同的 class 名称
      return 'column-class'
    }
  }
}
</script>

5. 增加排序/筛选功能

为了支持排序/筛选功能,我们可以在表头的列上添加一个排序/筛选图标,然后监听点击事件,通过排序/筛选算法对数据进行操作即可。例如,我们可以在 Table 中定义一个 sortField 和 sortType 属性,用于存储当前的排序字段和排序类型,然后在点击表头列时根据当前的排序状态修改 sortField 和 sortType,最后使用 Array.sort 方法对数据进行排序。

<template>
  <table>
    <!-- 表头 -->
    <thead>
      <tr>
        <th>
          <input type="checkbox"
            v-model="allSelected"
            @change="selectAll($event)"/>
        </th>
        <th v-for="column in columns" :key="column.field"
          @click="handleSort(column.field)">
          {{ column.label }}
          <span class="sort-icon"
            :class="{
              'sort-asc': sortField === column.field && sortType === 'asc',
              'sort-desc': sortField === column.field && sortType === 'desc'
            }"></span>
        </th>
        <th>操作</th>
      </tr>
    </thead>
    <!-- 数据 -->
    <tbody>
      <tr v-for="(row, index) in rows" :key="index"
        :class="getRowClass(row)">
        <td>
          <input type="checkbox"
            v-model="selectedRows"
            :value="row"/>
        </td>
        <td v-for="column in columns" :key="column.field"
          :class="getColumnClass(row, column.field)">{{row[column.field]}}</td>
        <td>
          <button @click="edit(row)">编辑</button>
          <button @click="remove(row)">删除</button>
        </td>
      </tr>
    </tbody>
    <!-- 插槽,用于传递行样式和列样式 -->
    <slot name="row" :row="rows"></slot>
    <slot name="column"></slot>
  </table>
</template>

<script>
import Dialog from '@/components/Dialog.vue'

export default {
  components: {
    Dialog
  },
  props: {
    columns: {
      type: Array,
      default: () => []
    },
    rows: {
      type: Array,
      default: () => []
    }
  },
  data() {
    return {
      allSelected: false,
      selectedRows: [],
      dialogVisible: false,
      currentRow: {},
      sortField: '',
      sortType: ''
    }
  },
  methods: {
    create() {
      this.currentRow = {}
      this.dialogVisible = true
    },
    update(row) {
      // 更新数据
      this.rows = this.rows.map(item => item.id === row.id ? row : item)
    },
    remove(row) {
      // 删除数据
      this.rows = this.rows.filter(item => item.id !== row.id)
    },
    selectAll(event) {
      this.selectedRows = event.target.checked ? this.rows : []
    },
    edit(row) {
      // 编辑数据
      this.currentRow = {...row}
      this.dialogVisible = true
    },
    // 获取行样式,在插槽中使用
    getRowClass(row) {
      // todo: 实现根据不同的条件返回不同的 class 名称
      return 'row-class'
    },
    // 获取列样式,在插槽中使用
    getColumnClass(row, field) {
      // todo: 实现根据不同的条件返回不同的 class 名称
      return 'column-class'
    },
    // 排序
    sort() {
      // 从小到大排序
      if (this.sortType === 'asc') {
        this.rows.sort((a, b) => a[this.sortField] - b[this.sortField])
      }
      // 从大到小排序
      if (this.sortType === 'desc') {
        this.rows.sort((a, b) => b[this.sortField] - a[this.sortField])
      }
    },
    // 点击表头排序
    handleSort(field) {
      // 默认为从小到大排序
      let type = 'asc'
      // 如果当前点击的就是排序的列,那么将排序类型翻转
      if (this.sortField === field) {
        type = this.sortType === 'asc' ? 'desc' : 'asc'
      }
      // 更新排序状态
      this.sortField = field
      this.sortType = type
      // 对数据进行重新排序
      this.sort()
    }
  }
}
</script>

三、总结

以上就是 Vue.js 管理后台 Table 组件的封装方法。通过封装 Table 组件,我们可以提高开发效率,优化代码结构,降低维护成本。当然,以上示例中的实现方式还有很多需要改进的地方,可以根据需求进行相应的调整和改动。

阅读剩余 89%

本站文章如无特殊说明,均为本站原创,如若转载,请注明出处:vue.js管理后台table组件封装的方法 - Python技术站

(0)
上一篇 2023年6月25日
下一篇 2023年6月25日

相关文章

  • html5-canvas入门(六)

    当然,我很乐意为您提供HTML5 Canvas入门的完整攻略。以下是详细的步骤和示例: 步骤一:创建Canvas元素 首先,需要在HTML文档中创建Canvas元素。以下是一个示例Canvas元素: <canvas id="Canvas" width="500" height="500"&gt…

    other 2023年5月9日
    00
  • 每个程序员需掌握的20个代码命名小贴士

    每个程序员需掌握的20个代码命名小贴士 在编写程序的过程中,良好的代码命名是非常重要的,它能够使你的代码更加可读、可维护和易于理解。下面是20个代码命名小贴士,让你写出更好的代码。 1. 命名应具有描述性 代码命名应该具有表现力和描述性,这样阅读代码的人就可以通过代码名称短暂的理解代码的功能。 示例: # 不好的命名风格 a = 5 # 好的命名风格 num…

    other 2023年6月27日
    00
  • python基础教程之基本数据类型和变量声明介绍

    Python基础教程之基本数据类型和变量声明介绍 本攻略将详细介绍Python中的基本数据类型和变量声明。在Python中,有多种基本数据类型可供使用,包括整数、浮点数、字符串、布尔值和列表等。同时,我们还将学习如何声明和使用变量来存储和操作这些数据类型。 基本数据类型 1. 整数(int) 整数是Python中最基本的数据类型之一,用于表示没有小数部分的数…

    other 2023年8月9日
    00
  • fastDFS文件服务器迁移

    FastDFS是一个开源的轻量级分布式文件系统,它具有高性能、高可靠性、易部署等特点。在实际应用中,可能需要将FastDFS文件服务器迁移到新的服务器上。本文将提供一个完整的攻略,包括备份数据、安装配置新服务器、迁移数据等步骤,并提供两个示例说明。 备份数据 在迁移FastDFS文件服务器之前,需要备份数据以防止数据丢失。可以使用FastDFS提供的工具进行…

    other 2023年5月5日
    00
  • WindowsXP系统 CMD常用命令大全

    Windows XP系统CMD常用命令大全 简介 CMD,全称为Windows Command Prompt,是Windows操作系统中的命令行工具,可以在不使用图形化界面的情况下,通过命令来操作系统。本文介绍了Windows XP系统下CMD常用命令,包括常用的文件管理、网络连接、系统配置等命令,方便用户更好地使用Windows XP系统。 常用命令 文件…

    other 2023年6月26日
    00
  • html-标签左对齐

    以下是关于“HTML标签左对齐”的完整攻略,包括定义、方法、示例说明和注意事项。 定义 在HTML中,标签默认是左对齐的,这意味着标签的左侧边缘与其父元的左侧边缘对齐。如果需要将标签居中或右对齐,需要使用CSS样式来实现。 方法 以下是HTML标签对齐的方法: 使用默认样式 在HTML中,标签默认是左对齐的。如果不需要改变标签的对齐方式可以直接使用默认样式。…

    other 2023年5月8日
    00
  • 分享25段shell脚本代码 日常工作基本够用

    分享25段shell脚本代码日常工作基本够用 Shell脚本是一种非常强大的工具,可以帮助我们自动化完成各种日常工作。本攻略将分享25段Shell脚本代码,涵盖了日常工作中常用的各种场景,包括文件操作、文本处理、系统管理等。每段代码都附有详细的注释,方便理解和修改。 文件操作 1. 创建目录 #!/bin/bash # 创建目录 mkdir /path/to…

    other 2023年5月7日
    00
  • java 自定义注解的实例详解

    下面是关于“Java自定义注解的实例详解”的完整攻略: 1. 什么是Java自定义注解 Java自定义注解是一种注解工具,它可以在编写代码时增加代码的可读性和可维护性。注解是一种语言级别的元数据,它可以与代码元素(类、方法、成员变量等)进行关联并提供额外的信息。 Java自定义注解也称为元注解,在Java语言中已经内置了一些常用的注解,例如 @Overrid…

    other 2023年6月25日
    00
合作推广
合作推广
分享本页
返回顶部