UniApp实战之开发一个复杂场景的表格组件

1. 引言

在实际开发中,表格作为常见的数据展示形式,在UniApp的开发中也显得相当重要。而一个复杂的表格组件需要考虑的因素很多,如展示数据的种类、数据的排序、分页等。本文将结合实际项目,介绍如何开发一个复杂场景下的表格组件。

2. 数据的处理

在实际项目中,数据处理是表格组件开发的重点之一。我们需要根据实际业务场景,对数据进行分类、加工等操作。

2.1 分类处理

在实际项目中,数据一般会按照不同的类别分开展示,这就要求我们对数据进行分类处理。比如我们要开发一个学生的成绩表格,数据一般是按照学期、科目进行分类,我们就可以将数据按照学期和科目进行分类,这样展示数据会更加清晰。

// 数据分类处理

const tableData = [

{name: '小明', term: '1', subject: '语文', score: '90'},

{name: '小红', term: '1', subject: '数学', score: '80'},

{name: '小明', term: '1', subject: '数学', score: '85'},

{name: '小红', term: '2', subject: '语文', score: '95'},

{name: '小明', term: '2', subject: '语文', score: '88'},

{name: '小红', term: '2', subject: '数学', score: '93'},

{name: '小明', term: '2', subject: '数学', score: '92'},

]

const classifyData = {} // 初始化分类数据对象

tableData.forEach((item) => {

if (!classifyData[item.term]) {

classifyData[item.term] = {}

}

if (!classifyData[item.term][item.subject]) {

classifyData[item.term][item.subject] = []

}

classifyData[item.term][item.subject].push(item)

})

export default classifyData

2.2 加工处理

数据的加工处理通常是针对特定业务场景进行的。在表格开发中,我们可以将原始数据转换成用于展示的数据格式。比如在一个销售数据分析表格中,我们可以计算出每个销售员的总销售量和销售额,并将这些结果展示在表格中。

// 数据加工处理

const rawSalesData = [

{name: '小明', sales: 10, price: 100},

{name: '小红', sales: 20, price: 200},

{name: '小李', sales: 30, price: 300},

{name: '小张', sales: 40, price: 400},

]

const calcResult = rawSalesData.reduce((result, item) => {

if (!result[item.name]) {

result[item.name] = {

name: item.name,

totalSales: 0,

totalPrice: 0,

}

}

result[item.name].totalSales += item.sales

result[item.name].totalPrice += item.sales * item.price

return result

}, {})

const tableData = Object.values(calcResult)

export default tableData

3. UI组件的实现

在实际项目中,UI组件的实现是一个重点。如何实现UI组件的复用是一个需要考虑的因素。

3.1 基础组件的封装

UniApp内置了很多基础组件,我们可以基于这些基础组件进行封装,实现自己的组件。比如我们需要封装一个表格组件,可以基于UniApp内置的list组件进行封装:

<template>

<view class="table-container">

<list>

<block v-for="(item, index) in tableData" :key="index">

<cell>

<view class="table-row">

<view class="table-cell">{{ item.name }}</view>

<view class="table-cell">{{ item.age }}</view>

</view>

</cell>

</block>

</list>

</view>

</template>

<script>

export default {

props: {

tableData: {

type: Array,

default: () => [],

},

},

}

</script>

<style scoped>

.table-container {

background-color: #fff;

}

.table-row {

display: flex;

}

.table-cell {

flex: 1;

text-align: center;

}

</style>

3.2 复用组件的实现

除了基础组件的封装外,我们还可以实现复用性更高的组件。比如我们需要封装一个表格排序功能,我们可以将排序功能分离出来成为一个单独的组件,这样就可以在不同的表格中复用这个排序组件。

<template>

<view class="table-container">

<view class="header">

<view class="table-header-cell" @click="sort>'name')">姓名</view>

<view class="table-header-cell" @click="sort('age')">年龄</view>

</view>

<list>

<block v-for="(item, index) in tableData" :key="index">

<cell>

<view class="table-row">

<view class="table-cell">{{ item.name }}</view>

<view class="table-cell">{{ item.age }}</view>

</view>

</cell>

</block>

</list>

</view>

<sort-modal :visible="visible" :sortData="sortData" @sort="onSort"></sort-modal>

</template>

<script>

import SortModal from '@/components/SortModal'

export default {

props: {

tableData: {

type: Array,

default: () => [],

},

},

data() {

return {

visible: false,

sortData: [

{label: '姓名', value: 'name'},

{label: '年龄', value: 'age'},

],

}

},

methods: {

sort(field) {

this.visible = true

},

onSort(sortField) {

console.log('sortField: ', sortField)

const sortFieldArr = sortField.split('.')

const key = sortFieldArr[0]

const direction = sortFieldArr[1]

if (direction === 'asc') {

this.tableData.sort((a, b) => a[key] - b[key])

} else {

this.tableData.sort((a, b) => b[key] - a[key])

}

},

},

components: {

SortModal,

},

}

</script>

<style scoped>

.table-container {

background-color: #fff;

}

.header {

display: flex;

}

.table-header-cell {

flex: 1;

text-align: center;

cursor: pointer;

}

.table-row {

display: flex;

}

.table-cell {

flex: 1;

text-align: center;

}

</style>

4. 总结

本文介绍了如何开发一个复杂场景下的表格组件,包括数据的分类、加工处理以及UI组件的实现。对在实际项目中开发表格组件的同学有一定的参考价值。