diff --git a/components/pagination/pagination.vue b/components/pagination/pagination.vue new file mode 100644 index 0000000..120cbd4 --- /dev/null +++ b/components/pagination/pagination.vue @@ -0,0 +1,308 @@ + + + + + \ No newline at end of file diff --git a/composables/usePagination.js b/composables/usePagination.js new file mode 100644 index 0000000..c1b2f1c --- /dev/null +++ b/composables/usePagination.js @@ -0,0 +1,190 @@ +import { ref, computed } from 'vue' + +/** + * 分页管理组合式函数 + * @param {Object} options - 配置选项 + * @param {Function} options.fetchData - 获取数据的API函数 + * @param {Object} options.defaultParams - 默认查询参数 + * @param {string} options.mode - 分页模式:'loadMore' 或 'pager' + * @param {number} options.pageSize - 每页数量 + * @returns {Object} 分页相关的状态和方法 + */ +export function usePagination(options = {}) { + const { + fetchData, + defaultParams = {}, + mode = 'loadMore', + pageSize = 10 + } = options + + // 基础状态 + const list = ref([]) + const loading = ref(false) + const error = ref(null) + + // 分页参数 + const queryParams = ref({ + pageNum: 1, + pageSize, + ...defaultParams + }) + + // 分页信息 + const pagination = ref({ + total: 0, + currentPage: 1, + pageSize, + totalPages: 0 + }) + + // 上拉加载相关 + const noMore = ref(false) + + // 计算属性 + const hasData = computed(() => list.value.length > 0) + const isEmpty = computed(() => !loading.value && list.value.length === 0) + const canLoadMore = computed(() => mode === 'loadMore' && !noMore.value && !loading.value) + + /** + * 获取数据列表 + * @param {boolean} isRefresh - 是否为刷新操作 + */ + const getList = async (isRefresh = false) => { + if (loading.value) return + + try { + loading.value = true + error.value = null + + // 如果是刷新,重置页码 + if (isRefresh) { + queryParams.value.pageNum = 1 + noMore.value = false + } + + const res = await fetchData(queryParams.value) + + // 处理响应数据 + const newData = res?.rows || [] + const total = res?.total || 0 + + // 更新分页信息 + pagination.value = { + total, + currentPage: queryParams.value.pageNum, + pageSize, + totalPages: Math.ceil(total / pageSize) + } + + // 更新数据列表 + if (isRefresh || queryParams.value.pageNum === 1) { + list.value = newData + } else { + list.value = [...list.value, ...newData] + } + + // 检查是否还有更多数据 + if (mode === 'loadMore') { + noMore.value = queryParams.value.pageNum * pageSize >= total + } + + console.log(`获取数据成功: 第${queryParams.value.pageNum}页,共${newData.length}条`) + + } catch (err) { + console.error('获取数据失败:', err) + error.value = err + + // 显示错误提示 + uni.showToast({ + title: '数据加载失败', + icon: 'none' + }) + } finally { + loading.value = false + } + } + + /** + * 刷新数据 + */ + const refresh = () => { + getList(true) + } + + /** + * 加载下一页(上拉加载模式) + */ + const loadMore = () => { + if (!canLoadMore.value) return + + queryParams.value.pageNum++ + getList() + } + + /** + * 跳转到指定页(分页器模式) + * @param {number} page - 目标页码 + */ + const goToPage = (page) => { + if (page < 1 || page > pagination.value.totalPages || page === queryParams.value.pageNum) { + return + } + + queryParams.value.pageNum = page + getList(true) + } + + /** + * 重置分页状态 + */ + const reset = () => { + list.value = [] + loading.value = false + error.value = null + noMore.value = false + queryParams.value.pageNum = 1 + pagination.value = { + total: 0, + currentPage: 1, + pageSize, + totalPages: 0 + } + } + + /** + * 更新查询参数 + * @param {Object} newParams - 新的查询参数 + */ + const updateParams = (newParams) => { + queryParams.value = { + ...queryParams.value, + ...newParams, + pageNum: 1 // 重置页码 + } + reset() + getList() + } + + return { + // 状态 + list, + loading, + error, + noMore, + pagination, + queryParams, + + // 计算属性 + hasData, + isEmpty, + canLoadMore, + + // 方法 + getList, + refresh, + loadMore, + goToPage, + reset, + updateParams + } +} \ No newline at end of file diff --git a/pages/myOrder/myOrder.vue b/pages/myOrder/myOrder.vue index 1ad9898..350d43c 100644 --- a/pages/myOrder/myOrder.vue +++ b/pages/myOrder/myOrder.vue @@ -1,12 +1,12 @@