在 Vue 3 中,随着 Composition API 的引入,组件的封装和复用变得更加灵活和强大。同时本人也是注意到前一个组件在使用时存在的诸多小问题,本文将介绍如何将组件升级同时使用到到 Vue 3新版本的全新内容,并利用 Vue 3 的 Composition API 进行重构,使其更加符合现代 Vue 应用的开发模式。
原始组件回顾
原始的分页器组件使用了 ref
和 defineEmits
来管理状态和事件。主要通过覆盖ref变量来完成逻辑,但是这样后期开发会遇到很多隐患
<template>
<!-- 分页 -->
<el-pagination class="custom_page" :currentPage="currentPage" :page-size="pageSize"
:page-sizes="pageSizes" :disabled="disabled" :background="background" :total="total" :pager-count="pagerCount"
@size-change="handleSizeChange" @current-change="handleCurrentChange" />
</template>
<script setup>
import { ref, defineEmits } from 'vue';
const currentPage = ref(3);
const pageSize = ref(10);
const pageSizes = [10, 20, 30, 40];
const background = ref(true);
const disabled = ref(false);
const total = ref(100)
const pagerCount = ref(7)
const emit = defineEmits(['update:currentPage', 'update:pageSize']);
const handleSizeChange = (val) => {
console.log(`${val} items per page`)
emit('update:pageSize', val);
}
const handleCurrentChange = (val) => {
console.log(`current page: ${val}`)
emit('update:currentPage', val)
}
</script>
<style>
//这里可以添加子组件的其他样式....
</style>
Vue 3 升级后的组件
新版本采用了defineModel()进行双向绑定,对于不需要双向绑定的变量采用defineProps()只允许父传子值,并在父级调用的时候将数据传入子组件。
这里直接奉上改良后的子组件代码:
<template>
<!-- 分页 -->
<el-pagination class="custom_page" :currentPage="currentPage" :page-size="pageSize" :page-sizes="props.pageSizes"
:background="props.background" :total="props.total" :pager-count="props.pagerCount" @size-change="handleSizeChange"
@current-change="handleCurrentChange" />
</template>
<script setup>
const currentPage = defineModel("currentPage", { type: Number, default: 4 })
const pageSize = defineModel("pageSize", { type: Number, default: 10 })
const emits = defineEmits(["handleSizeChange", "handleCurrentChange"])
const props = defineProps({
total: {
type: Number,
default: 0
},
background: {
type: Boolean,
default: true
},
pageSizes: {
type: Array,
default: [10, 20, 30, 40]
},
pagerCount: {
type: Number,
default: 9
},
})
function handleSizeChange(val) {
// 在被修改时,触发 "update:count" 事件
console.log(`${val} items per page`)
pageSize.value = val
emits('handleSizeChange', val);
}
function handleCurrentChange(val) {
currentPage.value = val
console.log(`current page: ${val}`)
emits('handleCurrentChange', val);
}
</script>
<style lang="less" scoped>
//这里可以自定义样式
</style>
- 使用
<el-pagination>
组件来展示分页控件。这个组件是Element Plus库提供的,用于实现分页功能。 :currentPage
、:page-size
、:page-sizes
、:background
、:total
、:pager-count
是传递给<el-pagination>
组件的props,分别控制当前页码、每页显示条目个数、可选择的每页显示个数、背景色、总条目数、分页器大小内按钮的个数。@size-change
和@current-change
是监听分页器页大小变化和当前页变化的事件,分别绑定了handleSizeChange
和handleCurrentChange
方法。- 属性(Props):定义了传递给组件的props,包括
total
(总条目数)、background
(是否显示背景色)、pageSizes
(每页显示条目的选择数组)、pagerCount
(分页器大小内按钮的个数)。 - 事件(Emits):定义了组件可以触发的自定义事件,这里是
handleSizeChange
和handleCurrentChange
,用于在页大小或当前页变化时通知父组件。 - 方法
: -handleSizeChange
:当页大小变化时调用,更新pageSize``的值并触发
handleSizeChange`事件。handleCurrentChange
:当当前页变化时调用,更新currentPage
的值并触发handleCurrentChange`事件。
父组件引用如下:
<template>
<!-- 父组件引用 -->
<Paginations :total="total" :currentPage="currentPage" :pageSize="pageSize"
layout=" prev, pager, next,sizes,jumper" @handleSizeChange="handleSizeChange"
@handleCurrentChange="handleCurrentChange" />
</template>
<script setup>
import { ref } from 'vue';
import Paginations from '@web/views/components/paginations.vue';
const currentPage = ref(8)
const total = ref(1000)
const pageSize = ref(11)
const handleSizeChange = (ref) => {
console.log(ref, '父组调用Size方法')
pageSize.value = ref
}
const handleCurrentChange = (ref) => {
console.log(ref, '父组件调用Current方法')
currentPage.value = ref
}
</script>
-
Props 的使用:通过
defineProps
接收外部传入的属性,如total
、background
、pageSizes
和pagerCount
。 -
内部状态管理:使用
ref
来管理内部状态,如currentPage
和pageSize
。 -
模板绑定:在模板中,通过
v-bind
或简写:
将 props 和内部状态绑定到el-pagination
组件上。 -
样式作用域:在
<style>
标签中使用scoped
属性,确保样式只应用于当前组件。 -
导入和注册组件:导入了自定义的分页组件
Paginations
,并在模板中进行了引用。 -
响应式数据:使用
ref
函数创建了三个响应式数据total
、currentPage
和pageSize
,分别用于存储总条目数、当前页码和每页显示的条目数。 -
方法定义:
handleSizeChange
:处理页大小变化的事件。当分页组件的页大小发生变化时,会触发这个事件,并将新的页大小作为参数传递给这个方法。方法内部更新了pageSize
的值,并打印了相关信息。handleCurrentChange
:处理当前页变化的事件。当分页组件的当前页发生变化时,会触发这个事件,并将新的当前页码作为参数传递给这个方法。方法内部更新了currentPage
的值,并打印了相关信息。
总结
以上就是所有代码,在前文的基础上进行了更新,用到了最新的方法。这里直接复制粘贴即可。