248 lines
6.4 KiB
Vue
248 lines
6.4 KiB
Vue
<template>
|
|
<view class="page">
|
|
<custom-navbar title="寺庙活动" />
|
|
<view class="header" :style="{ backgroundColor: CommonEnum.BASE_COLOR }">
|
|
<!-- 状态展示 -->
|
|
<status-display
|
|
v-if="loading"
|
|
type="loading"
|
|
loading-text="加载中..."
|
|
/>
|
|
|
|
<!-- 错误状态 -->
|
|
<status-display
|
|
v-if="error"
|
|
type="error"
|
|
:error-text="error"
|
|
@retry="loadPageData"
|
|
/>
|
|
|
|
<!-- 空状态 -->
|
|
<status-display
|
|
v-if="!loading && !error && activityList.length === 0"
|
|
type="empty"
|
|
empty-text="暂无活动"
|
|
/>
|
|
|
|
<!-- 活动卡片列表 -->
|
|
<view class="activity-list" v-if="!loading && !error && activityList.length > 0">
|
|
<activity-card
|
|
v-for="activity in activityList"
|
|
:key="activity.id"
|
|
:activity="activity"
|
|
:show-title="true"
|
|
@card-click="handleCardClick"
|
|
@register="handleRegister"
|
|
/>
|
|
</view>
|
|
</view>
|
|
</view>
|
|
</template>
|
|
|
|
<script>
|
|
import CommonEnum from "../../enum/common";
|
|
import { ACTIVITY_STATUS, ACTIVITY_TYPE } from "../../enum/activity";
|
|
import StatusDisplay from "../../components/status-display/status-display.vue";
|
|
import ActivityCard from "../../components/activity-card/activity-card.vue";
|
|
import activityApi from "../../api/activity/activity.js";
|
|
import activityFormatter from "../../utils/activity-data-formatter.js";
|
|
|
|
export default {
|
|
components: {
|
|
StatusDisplay,
|
|
ActivityCard
|
|
},
|
|
data() {
|
|
return {
|
|
CommonEnum,
|
|
loading: false,
|
|
error: '',
|
|
activityList: [],
|
|
// 分页参数
|
|
pageNum: 1,
|
|
pageSize: 20,
|
|
hasMore: true
|
|
}
|
|
},
|
|
onLoad() {
|
|
// 页面加载时获取数据
|
|
this.loadPageData()
|
|
},
|
|
// 下拉刷新
|
|
onPullDownRefresh() {
|
|
this.refreshData()
|
|
},
|
|
// 上拉加载更多
|
|
onReachBottom() {
|
|
if (this.hasMore && !this.loading) {
|
|
this.loadMoreData()
|
|
}
|
|
},
|
|
methods: {
|
|
// 加载页面数据
|
|
async loadPageData() {
|
|
this.loading = true
|
|
this.error = ''
|
|
|
|
try {
|
|
const response = await activityApi.getActivityList({
|
|
pageNum: this.pageNum,
|
|
pageSize: this.pageSize
|
|
})
|
|
|
|
if (response.code === 200 && response.data) {
|
|
// 格式化数据
|
|
const formattedData = activityFormatter.formatActivityList(response.data)
|
|
this.activityList = formattedData
|
|
|
|
// 判断是否还有更多数据
|
|
this.hasMore = response.data.length >= this.pageSize
|
|
} else {
|
|
this.error = response.msg || '获取活动列表失败'
|
|
}
|
|
} catch (error) {
|
|
console.error('获取活动列表失败:', error)
|
|
this.error = '网络错误,请稍后重试'
|
|
} finally {
|
|
this.loading = false
|
|
uni.stopPullDownRefresh()
|
|
}
|
|
},
|
|
|
|
// 刷新数据
|
|
async refreshData() {
|
|
this.pageNum = 1
|
|
this.hasMore = true
|
|
await this.loadPageData()
|
|
},
|
|
|
|
// 加载更多数据
|
|
async loadMoreData() {
|
|
if (!this.hasMore || this.loading) return
|
|
|
|
this.loading = true
|
|
try {
|
|
const nextPage = this.pageNum + 1
|
|
const response = await activityApi.getActivityList({
|
|
pageNum: nextPage,
|
|
pageSize: this.pageSize
|
|
})
|
|
|
|
if (response.code === 200 && response.data) {
|
|
const formattedData = activityFormatter.formatActivityList(response.data)
|
|
this.activityList = [...this.activityList, ...formattedData]
|
|
this.pageNum = nextPage
|
|
this.hasMore = response.data.length >= this.pageSize
|
|
} else {
|
|
this.hasMore = false
|
|
}
|
|
} catch (error) {
|
|
console.error('加载更多活动失败:', error)
|
|
this.hasMore = false
|
|
} finally {
|
|
this.loading = false
|
|
}
|
|
},
|
|
|
|
// 处理卡片点击
|
|
handleCardClick(activity) {
|
|
console.log('点击活动卡片:', activity)
|
|
// 跳转到活动详情页
|
|
uni.navigateTo({
|
|
url: `/pages/activity/activityDetail?actId=${activity.id}`
|
|
})
|
|
},
|
|
|
|
// 处理报名
|
|
async handleRegister(activity) {
|
|
console.log('报名活动:', activity)
|
|
|
|
// 检查用户是否登录
|
|
const userInfo = uni.getStorageSync('userInfo')
|
|
if (!userInfo) {
|
|
uni.showModal({
|
|
title: '提示',
|
|
content: '请先登录后再报名活动',
|
|
confirmText: '去登录',
|
|
success: (res) => {
|
|
if (res.confirm) {
|
|
// 跳转到登录页
|
|
uni.navigateTo({
|
|
url: '/pages/login/login'
|
|
})
|
|
}
|
|
}
|
|
})
|
|
return
|
|
}
|
|
|
|
// 确认报名
|
|
uni.showModal({
|
|
title: '确认报名',
|
|
content: `确定要报名参加"${activity.name}"活动吗?`,
|
|
success: async (res) => {
|
|
if (res.confirm) {
|
|
try {
|
|
const response = await activityApi.registerActivity({
|
|
activityId: activity.id,
|
|
userId: userInfo.id,
|
|
userName: userInfo.userName || userInfo.nickName,
|
|
phone: userInfo.phone
|
|
})
|
|
|
|
if (response.code === 200) {
|
|
uni.showToast({
|
|
title: '报名成功',
|
|
icon: 'success'
|
|
})
|
|
|
|
// 刷新活动列表以更新报名状态
|
|
this.refreshData()
|
|
} else {
|
|
uni.showToast({
|
|
title: response.msg || '报名失败',
|
|
icon: 'none'
|
|
})
|
|
}
|
|
} catch (error) {
|
|
console.error('报名失败:', error)
|
|
uni.showToast({
|
|
title: '报名失败,请稍后重试',
|
|
icon: 'none'
|
|
})
|
|
}
|
|
}
|
|
}
|
|
})
|
|
}
|
|
}
|
|
}
|
|
</script>
|
|
|
|
<style lang="scss">
|
|
page {
|
|
background: #FAF8F3;
|
|
align-items: center;
|
|
justify-content: center;
|
|
flex-direction: column;
|
|
}
|
|
|
|
|
|
.header {
|
|
width: 100%;
|
|
min-height: 100vh;
|
|
display: flex;
|
|
align-items: center;
|
|
justify-content: center;
|
|
flex-direction: column;
|
|
padding: 0 34rpx;
|
|
padding-bottom: 40rpx;
|
|
}
|
|
|
|
.activity-list {
|
|
margin-top: 40rpx;
|
|
width: 100%;
|
|
align-items: center;
|
|
flex-direction: column;
|
|
}
|
|
</style> |