Files
front-pc/pages/sign-content/index.vue

283 lines
7.4 KiB
Vue

<template>
<KlNavTab />
<div class="sign-content">
<!-- 顶部统计 -->
<div class="sign-header">
<div class="sign-icon">
<div class="icon-text"></div>
</div>
<div class="sign-info">
<div class="search-container">
<div class="search-group">
<span class="search-label">积分标题</span>
<el-input v-model="query.title" placeholder="请输入关键词" class="search-input" clearable>
<template #prefix>
<el-icon><Search /></el-icon>
</template>
</el-input>
<el-button type="primary" class="search-btn" @click="handleSearch">搜索</el-button>
</div>
<div class="sign-center ml-10px">
<el-button type="success" class="sign-btn" @click="handleClickSign"> 立即签到 </el-button>
</div>
</div>
</div>
</div>
<!-- Tab切换 -->
<!-- <div class="sign-tabs">
<div class="tab" @click="handleClickTab('today')" :class="{ active: sign_status_tab === 'today' }">今日签到</div>
<div class="tab" @click="handleClickTab('allRanking')" :class="{ active: sign_status_tab === 'allRanking' }">总排行</div>
<div class="tab" @click="handleClickTab('rewardRanking')" :class="{ active: sign_status_tab === 'rewardRanking' }">奖励排行</div>
</div> -->
<!-- 签到列表 -->
<div class="sign-table">
<div class="table-header">
<!-- <div>昵称</div> -->
<div>积分标题</div>
<div>积分描述</div>
<div>积分</div>
<div>发生时间</div>
</div>
<div v-for="item in result.list" :key="item.id" class="table-row">
<!-- <div class="avatar"> -->
<!-- <img :src="item.avatar" alt="avatar" /> -->
<!-- <span>{{ item.nickname }}</span> -->
<!-- </div> -->
<div>{{ item.title }}</div>
<div>{{ item.description }}</div>
<div>{{ item.point }}</div>
<div>{{ dayjs(item.createTime).format('YYYY-MM-DD HH:mm:ss') }}</div>
</div>
</div>
<!-- 分页组件 -->
<div class="mt-10px flex justify-center">
<el-pagination
v-model:current-page="query.pageNo"
:page-size="query.pageSize"
layout="prev, pager, next"
:total="result.total"
@current-change="handleCurrentChange"
/>
</div>
</div>
</template>
<script setup lang="ts">
import { reactive } from 'vue'
import { Search } from '@element-plus/icons-vue'
import { signIn, getUserPointPage } from '~/api/personal-center/index'
import type { PageResultMemberPointRecordRespVO } from '~/api/personal-center/types'
import useUserStore from '~/store/user'
import dayjs from 'dayjs'
const userStore = useUserStore()
const query = reactive({
pageNo: 1,
pageSize: 10,
userId: userStore.userId,
title: '',
})
const result = reactive<PageResultMemberPointRecordRespVO>({
total: 0,
list: [],
})
// const signList = ref([
// {
// avatar: 'https://dummyimage.com/40x40/ccc/fff.png&text=美',
// name: '头街',
// totalDays: 756,
// continuousDays: 33,
// lastSignTime: '2025-05-11 09:22:13',
// reward: '3积分',
// },
// {
// avatar: 'https://dummyimage.com/40x40/ccc/fff.png&text=小',
// name: 'xiaoy94',
// totalDays: 648,
// continuousDays: 21,
// lastSignTime: '2025-05-11 09:21:15',
// reward: '3积分',
// },
// // ... 其余数据
// ])
// const sign_status_tab = ref('today') // today allRanking rewardRanking
// const handleClickTab = (val: string) => {
// sign_status_tab.value = val
// }
const handleCurrentChange = (val: number) => {
console.log(1)
query.pageNo = val // 更新当前页
getUserPointPageList()
}
const getUserPointPageList = async () => {
const res = await getUserPointPage(query)
if (res.code === 0) {
result.list = res.data.list
result.total = res.data.total
}
}
getUserPointPageList()
const handleClickSign = async () => {
const res = await signIn()
if (res.code === 0) {
ElMessage.success(res.msg)
query.pageNo = 1
getUserPointPageList()
}
console.log(res)
}
const handleSearch = () => {
query.pageNo = 1
getUserPointPageList()
}
</script>
<style lang="scss" scoped>
.sign-content {
// background: #f5f5f5;
padding: 24px;
.sign-header {
display: flex;
align-items: center;
background: linear-gradient(135deg, #f8f9fa 0%, #ffffff 100%);
border-radius: 12px;
padding: 24px;
margin-bottom: 24px;
box-shadow: 0 4px 6px rgba(0, 0, 0, 0.05);
border: 1px solid #e9ecef;
.sign-icon {
.icon-text {
font-size: 32px;
color: #fff;
background: linear-gradient(45deg, #4f46e5, #8b5cf6);
width: 60px;
height: 60px;
display: flex;
align-items: center;
justify-content: center;
border-radius: 8px;
box-shadow: 0 2px 4px rgba(79, 70, 229, 0.2);
}
}
.search-container {
flex: 1;
display: flex;
align-items: center;
justify-content: space-between;
margin-left: 32px;
.search-group {
flex: 1;
display: flex;
align-items: center;
max-width: 600px;
.search-label {
font-size: 14px;
color: #495057;
margin-right: 12px;
white-space: nowrap;
}
.search-input {
flex: 1;
margin-right: 12px;
.el-input__inner {
height: 40px;
border-radius: 8px;
border-color: #dee2e6;
}
}
.search-btn {
height: 40px;
padding: 0 24px;
border-radius: 8px;
font-weight: 500;
}
}
.sign-btn {
height: 40px;
padding: 0 24px;
border-radius: 8px;
font-weight: 500;
background: linear-gradient(45deg, #10b981, #34d399);
border: none;
&:hover {
opacity: 0.9;
}
.el-icon {
margin-right: 8px;
}
}
}
}
.sign-tabs {
display: flex;
background: #fff;
border-radius: 8px 8px 0 0;
overflow: hidden;
border: 1px solid #eee;
.tab {
flex: 1;
text-align: center;
padding: 16px 0;
font-size: 16px;
cursor: pointer;
&.active {
background: #f44336;
color: #fff;
font-weight: bold;
}
}
}
.sign-table {
background: #fff;
border-radius: 0 0 8px 8px;
border: 1px solid #eee;
.table-header,
.table-row {
display: flex;
padding: 12px 0;
border-bottom: 1px solid #eee;
div {
flex: 1;
text-align: center;
}
.avatar {
display: flex;
align-items: center;
justify-content: center;
img {
width: 32px;
height: 32px;
border-radius: 50%;
margin-right: 8px;
}
}
}
.table-header {
background: #fafafa;
font-weight: bold;
}
.table-row:last-child {
border-bottom: none;
}
}
}
</style>