131 lines
6.1 KiB
Vue
131 lines
6.1 KiB
Vue
<template>
|
|
<view class="threshold-list-page">
|
|
<view class="page-head">
|
|
<text class="page-title">{{ mode === 'history' ? '往期裂变活动' : '拉新裂变活动' }}</text>
|
|
<text class="page-subtitle">{{ mode === 'history' ? '查看历史开奖与流产活动' : '完成消费或邀请门槛即可参与' }}</text>
|
|
</view>
|
|
|
|
<view class="toolbar">
|
|
<view class="toolbar-btn" :class="{ active: mode === 'active' }" @tap="switchMode('active')">进行中</view>
|
|
<view class="toolbar-btn" :class="{ active: mode === 'history' }" @tap="switchMode('history')">往期</view>
|
|
</view>
|
|
|
|
<view v-if="loading" class="state">加载中...</view>
|
|
<view v-else-if="activities.length === 0" class="state">{{ mode === 'history' ? '暂无往期活动' : '暂无进行中的活动' }}</view>
|
|
|
|
<view v-else class="activity-grid">
|
|
<view v-for="item in activities" :key="item.id" class="activity-card" @tap="goDetail(item.id)">
|
|
<image v-if="item.cover_image" class="activity-cover" :src="item.cover_image" mode="aspectFill" />
|
|
<view v-else class="activity-cover empty">暂无图片</view>
|
|
<view class="activity-meta">
|
|
<view class="title-row">
|
|
<text class="activity-name">{{ item.title }}</text>
|
|
<text class="activity-status" :class="statusClass(item.status)">{{ statusLabel(item.status) }}</text>
|
|
</view>
|
|
<view class="tag-row">
|
|
<text class="activity-type" :class="typeClass(item.type)">{{ typeLabel(item.type) }}</text>
|
|
<text class="activity-mode">{{ qualificationModeLabel(item.qualification_mode) }}</text>
|
|
</view>
|
|
<view class="stat-row">
|
|
<text>消费门槛 {{ money(item.spend_threshold_amount) }}</text>
|
|
<text>最低开奖 {{ item.min_participants || 0 }} 人</text>
|
|
</view>
|
|
<view class="stat-row" v-if="Number(item.invite_threshold_count || 0) > 0">
|
|
<text>邀请门槛 {{ item.invite_threshold_count || 0 }} 人</text>
|
|
<text>有效消费 {{ money(item.invite_effective_amount) }}</text>
|
|
</view>
|
|
</view>
|
|
</view>
|
|
</view>
|
|
</view>
|
|
</template>
|
|
|
|
<script>
|
|
import { listThresholdActivities } from '@/api/thresholdActivity'
|
|
|
|
export default {
|
|
data() {
|
|
return {
|
|
loading: false,
|
|
mode: 'active',
|
|
activities: []
|
|
}
|
|
},
|
|
onLoad(options) {
|
|
this.mode = options?.mode === 'history' ? 'history' : 'active'
|
|
this.loadData()
|
|
},
|
|
methods: {
|
|
async loadData() {
|
|
this.loading = true
|
|
try {
|
|
const params = { page: 1, page_size: 50 }
|
|
if (this.mode === 'active') params.status = 'active'
|
|
const res = await listThresholdActivities(params)
|
|
const list = Array.isArray(res?.list) ? res.list : []
|
|
this.activities = this.mode === 'history' ? list.filter(item => item.status !== 'active') : list
|
|
} catch (e) {
|
|
uni.showToast({ title: e.message || '加载失败', icon: 'none' })
|
|
} finally {
|
|
this.loading = false
|
|
}
|
|
},
|
|
switchMode(mode) {
|
|
if (this.mode === mode) return
|
|
this.mode = mode
|
|
this.loadData()
|
|
},
|
|
goDetail(id) {
|
|
uni.navigateTo({ url: `/pages-activity/activity/threshold/detail?id=${id}` })
|
|
},
|
|
typeLabel(type) {
|
|
return { daily: '每日裂变', weekly: '每周裂变', monthly: '每月裂变' }[type] || '裂变活动'
|
|
},
|
|
typeClass(type) {
|
|
return { daily: 'type-daily', weekly: 'type-weekly', monthly: 'type-monthly' }[type] || 'type-default'
|
|
},
|
|
qualificationModeLabel(mode) {
|
|
return { spend_only: '消费达标', invite_only: '邀请达标', either: '任一达标' }[mode] || '门槛活动'
|
|
},
|
|
statusLabel(status) {
|
|
return { active: '进行中', finished: '已结束', aborted: '已流产' }[status] || status || '-'
|
|
},
|
|
statusClass(status) {
|
|
return { active: 'status-active', finished: 'status-finished', aborted: 'status-aborted' }[status] || 'status-finished'
|
|
},
|
|
money(v) {
|
|
return `¥${(Number(v || 0) / 100).toFixed(2)}`
|
|
}
|
|
}
|
|
}
|
|
</script>
|
|
|
|
<style lang="scss">
|
|
.threshold-list-page { min-height: 100vh; padding: 28rpx; background: #fff7ed; }
|
|
.page-head { margin-bottom: 28rpx; }
|
|
.page-title { display: block; font-size: 46rpx; font-weight: 900; color: #1f2937; }
|
|
.page-subtitle { display: block; margin-top: 10rpx; font-size: 24rpx; color: #9ca3af; }
|
|
.toolbar { display: flex; gap: 16rpx; margin-bottom: 28rpx; }
|
|
.toolbar-btn { flex: 1; text-align: center; padding: 20rpx 0; background: #fff; border-radius: 999rpx; color: #9a5b24; font-weight: 800; }
|
|
.toolbar-btn.active { background: #ff8a3d; color: #fff; }
|
|
.state { padding: 120rpx 0; text-align: center; color: #9ca3af; }
|
|
.activity-grid { display: flex; flex-direction: column; gap: 24rpx; }
|
|
.activity-card { overflow: hidden; border-radius: 28rpx; background: #fff; box-shadow: 0 12rpx 30rpx rgba(0,0,0,.06); }
|
|
.activity-cover { width: 100%; height: 260rpx; display: block; background: #f3f4f6; }
|
|
.activity-cover.empty { display: flex; align-items: center; justify-content: center; color: #9ca3af; }
|
|
.activity-meta { padding: 24rpx 22rpx; display: flex; flex-direction: column; gap: 14rpx; }
|
|
.title-row, .tag-row, .stat-row { display: flex; align-items: center; justify-content: space-between; gap: 16rpx; flex-wrap: wrap; }
|
|
.activity-name { flex: 1; min-width: 0; font-size: 30rpx; font-weight: 800; color: #1f2937; }
|
|
.activity-status { font-size: 22rpx; font-weight: 800; }
|
|
.status-active { color: #10b981; }
|
|
.status-finished { color: #94a3b8; }
|
|
.status-aborted { color: #ef4444; }
|
|
.activity-type, .activity-mode { display: inline-flex; align-items: center; padding: 8rpx 18rpx; border-radius: 999rpx; font-size: 22rpx; font-weight: 800; }
|
|
.type-daily { background: rgba(249, 115, 22, .12); color: #f97316; }
|
|
.type-weekly { background: rgba(239, 68, 68, .12); color: #ef4444; }
|
|
.type-monthly { background: linear-gradient(135deg, #a855f7, #ec4899, #f59e0b); color: #fff; }
|
|
.type-default { background: rgba(148, 163, 184, .12); color: #64748b; }
|
|
.activity-mode { background: rgba(14, 165, 233, .12); color: #0284c7; }
|
|
.stat-row { font-size: 22rpx; color: #6b7280; }
|
|
</style>
|