ylj20011123 d7aa326d2e update
2025-10-20 18:45:14 +08:00

552 lines
15 KiB
Vue
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

<template>
<view class="invoice-management-page">
<!-- 头部统计区域 -->
<view class="header-section">
<view class="stats-card">
<view class="stats-item">
<text class="stats-number">{{ totalInvoices }}</text>
<text class="stats-label">总发票数</text>
</view>
<view class="stats-divider"></view>
<view class="stats-item">
<text class="stats-number">{{ totalAmount }}</text>
<text class="stats-label">开票金额()</text>
</view>
</view>
</view>
<!-- 搜索和筛选区域 -->
<view class="filter-section">
<view class="search-box">
<view class="search-icon">🔍</view>
<input class="search-input" v-model="searchText" placeholder="请输入发票号码" @input="handleSearch" />
</view>
<view class="filter-tabs">
<view class="filter-tab" v-for="(item, index) in statusTabs" :key="index"
:class="{ 'tab-active': currentStatus === item.value }" @click="switchStatus(item.value)">
{{ item.label }}
</view>
</view>
</view>
<!-- 发票列表 -->
<view class="invoice-list">
<view class="invoice-item" v-for="(invoice, key) in filteredInvoices" :key="invoice.id"
@click="goToDetail(invoice)">
<view class="item-header">
<view class="invoice-title">{{ invoice.title }}</view>
<view class="invoice-status" :class="'status-' + invoice.status">
{{ statusText[invoice.status] || '未知' }}
</view>
</view>
<view class="item-content">
<view class="info-row">
<text class="info-label">发票号码</text>
<text class="info-value">{{ invoice.invoiceNumber }}</text>
</view>
<view class="info-row">
<text class="info-label">开票金额</text>
<text class="info-value amount">¥{{ invoice.amount }}</text>
</view>
<view class="info-row">
<text class="info-label">开票日期</text>
<text class="info-value">{{ invoice.createTime }}</text>
</view>
</view>
<view class="item-footer">
<view class="invoice-type">{{ invoice.type }}</view>
<view class="view-detail">
<text>查看详情</text>
<text class="arrow"></text>
</view>
</view>
</view>
</view>
<!-- 空状态 -->
<view class="empty-state" v-if="filteredInvoices.length === 0">
<view class="empty-icon">📄</view>
<text class="empty-text">暂无发票记录</text>
<text class="empty-desc">您还没有申请过发票</text>
</view>
<!-- 加载更多 -->
<view class="load-more" v-if="hasMore && filteredInvoices.length > 0">
<text class="load-text">{{ loading ? '加载中...' : '上拉加载更多' }}</text>
</view>
</view>
</template>
<script>
export default {
data() {
return {
menu: {}, // 手机配置信息
searchText: '', // 搜索关键词
currentStatus: 'all', // 当前筛选状态
loading: false,
hasMore: true,
page: 1,
pageSize: 10,
// 统计数据
totalInvoices: 0,
totalAmount: '0.00',
// 状态筛选标签
statusTabs: [
{ label: '全部', value: 'all' },
{ label: '已开票', value: 'issued' },
{ label: '申请中', value: 'applying' },
{ label: '已驳回', value: 'rejected' }
],
// 发票列表数据
invoiceList: [],
// 状态文本映射
statusText: {
'issued': '已开票',
'applying': '申请中',
'rejected': '已驳回'
},
// 模拟数据
mockData: [
{
id: 1,
title: '云南高速公路服务区有限公司',
invoiceNumber: 'FP202401001',
amount: '1000.00',
status: 'issued',
type: '增值税普通发票',
createTime: '2024-01-15 14:30:00',
email: 'zhangsan@example.com',
phone: '13800138000',
taxNumber: '91530100MA6KXXXXXX',
bankName: '中国银行昆明分行',
bankAccount: '6217 9027 0000 1234 567'
},
{
id: 2,
title: '个人用户',
invoiceNumber: 'FP202401002',
amount: '500.00',
status: 'applying',
type: '增值税普通发票',
createTime: '2024-01-16 09:15:00',
email: 'lisi@example.com',
phone: '13900139000'
},
{
id: 3,
title: '商贸有限公司',
invoiceNumber: 'FP202401003',
amount: '3000.00',
status: 'rejected',
type: '增值税专用发票',
createTime: '2024-01-14 16:45:00',
email: 'wangwu@example.com',
phone: '13700137000',
taxNumber: '91530100MA6KXXXXXX',
bankName: '工商银行昆明分行',
bankAccount: '6222 0227 0000 1234 567',
rejectReason: '税号信息有误,请核对后重新申请'
}
]
}
},
computed: {
// 筛选后的发票列表
filteredInvoices() {
var list = this.invoiceList;
var _this = this;
// 按状态筛选
if (this.currentStatus !== 'all') {
var currentStatus = this.currentStatus;
list = list.filter(function (item) {
return item.status === currentStatus;
});
}
// 按搜索关键词筛选
if (this.searchText) {
var keyword = this.searchText.toLowerCase();
list = list.filter(function (item) {
return item.title.toLowerCase().indexOf(keyword) !== -1 ||
item.invoiceNumber.toLowerCase().indexOf(keyword) !== -1;
});
}
return list;
}
},
onLoad() {
this.menu = uni.getMenuButtonBoundingClientRect();
this.loadInvoiceList();
this.calculateStats();
},
onReachBottom() {
if (this.hasMore && !this.loading) {
this.loadMore();
}
},
onPullDownRefresh() {
this.refresh();
},
methods: {
// 加载发票列表
loadInvoiceList() {
var _this = this;
try {
this.loading = true;
// 模拟API调用
setTimeout(function () {
// 使用模拟数据
if (_this.page === 1) {
_this.invoiceList = _this.mockData;
} else {
// 模拟分页
_this.invoiceList = _this.invoiceList.concat(_this.mockData);
}
// 模拟分页逻辑
_this.hasMore = _this.page < 3;
_this.loading = false;
_this.calculateStats();
uni.stopPullDownRefresh();
}, 1000);
} catch (error) {
console.error('加载发票列表失败:', error);
uni.showToast({
title: '加载失败,请重试',
icon: 'none'
});
this.loading = false;
uni.stopPullDownRefresh();
}
},
// 加载更多
loadMore() {
this.page++;
this.loadInvoiceList();
},
// 刷新
refresh() {
this.page = 1;
this.hasMore = true;
this.loadInvoiceList();
},
// 计算统计数据
calculateStats() {
this.totalInvoices = this.invoiceList.length;
var total = this.invoiceList.reduce(function (sum, item) {
return sum + parseFloat(item.amount || 0);
}, 0);
this.totalAmount = total.toFixed(2);
},
// 搜索处理
handleSearch() {
// 搜索时重置分页
this.page = 1;
},
// 切换状态筛选
switchStatus(status) {
this.currentStatus = status;
},
// 跳转到详情页
goToDetail(invoice) {
uni.navigateTo({
url: '/pages/InvoiceManagement/detail?id=' + invoice.id + '&invoice=' + encodeURIComponent(JSON.stringify(invoice))
});
}
}
}
</script>
<style lang="less" scoped>
.invoice-management-page {
min-height: 100vh;
background: linear-gradient(135deg, #E8F5E8 0%, #F8F9FA 50%, #FFFFFF 100%);
}
.mainTop {
width: 100%;
background-color: #f8f8f8;
box-sizing: border-box;
position: fixed;
left: 0;
top: 0;
z-index: 999;
.pageTitle {
width: 100%;
display: flex;
align-items: center;
justify-content: center;
font-size: 14px;
}
}
/* 头部统计区域 */
.header-section {
padding: 40rpx 24rpx 44rpx;
background: linear-gradient(135deg, #22c55e 0%, #16a34a 100%);
position: relative;
border-bottom-left-radius: 40rpx;
border-bottom-right-radius: 40rpx;
margin-bottom: 20rpx;
}
.stats-card {
background: rgba(255, 255, 255, 0.15);
backdrop-filter: blur(10rpx);
border-radius: 24rpx;
padding: 32rpx;
display: flex;
align-items: center;
border: 2rpx solid rgba(255, 255, 255, 0.2);
.stats-item {
flex: 1;
text-align: center;
color: white;
.stats-number {
display: block;
font-size: 30rpx;
font-weight: 600;
}
.stats-label {
font-size: 24rpx;
opacity: 0.9;
}
}
.stats-divider {
width: 2rpx;
height: 60rpx;
background: rgba(255, 255, 255, 0.3);
margin: 0 32rpx;
}
}
/* 搜索和筛选区域 */
.filter-section {
padding: 40rpx 24rpx 24rpx;
background: white;
}
.search-box {
display: flex;
align-items: center;
background: #f5f5f5;
border-radius: 40rpx;
padding: 16rpx 24rpx;
margin-bottom: 24rpx;
.search-icon {
font-size: 28rpx;
margin-right: 16rpx;
opacity: 0.6;
}
.search-input {
flex: 1;
font-size: 24rpx;
background: transparent;
border: none;
outline: none;
&::placeholder {
color: #999;
}
}
}
.filter-tabs {
display: flex;
gap: 16rpx;
.filter-tab {
flex: 1;
text-align: center;
padding: 12rpx 16rpx;
background: #f5f5f5;
border-radius: 40rpx;
font-size: 24rpx;
color: #666;
transition: all 0.3s ease;
&.tab-active {
background: linear-gradient(135deg, #22c55e, #16a34a);
color: white;
font-weight: 600;
}
}
}
/* 发票列表 */
.invoice-list {
padding: 0 24rpx 40rpx;
}
.invoice-item {
background: white;
border-radius: 24rpx;
padding: 24rpx;
margin-bottom: 24rpx;
box-shadow: 0 8rpx 32rpx rgba(0, 0, 0, 0.08);
border: 1rpx solid #f0f0f0;
transition: all 0.3s ease;
&:active {
transform: scale(0.98);
box-shadow: 0 4rpx 16rpx rgba(0, 0, 0, 0.12);
}
}
.item-header {
display: flex;
justify-content: space-between;
align-items: flex-start;
margin-bottom: 24rpx;
.invoice-title {
flex: 1;
font-size: 30rpx;
font-weight: 600;
color: #333;
margin-right: 16rpx;
line-height: 1.4;
}
.invoice-status {
padding: 8rpx 16rpx;
border-radius: 20rpx;
font-size: 24rpx;
font-weight: 500;
white-space: nowrap;
&.status-issued {
background: #d4edda;
color: #155724;
}
&.status-applying {
background: #fff3cd;
color: #856404;
}
&.status-rejected {
background: #f8d7da;
color: #721c24;
}
}
}
.item-content {
margin-bottom: 24rpx;
.info-row {
display: flex;
align-items: center;
margin-bottom: 12rpx;
.info-label {
font-size: 24rpx;
color: #666;
width: 140rpx;
flex-shrink: 0;
}
.info-value {
flex: 1;
font-size: 24rpx;
color: #333;
&.amount {
color: #22c55e;
font-weight: 600;
font-size: 24rpx;
}
}
}
}
.item-footer {
display: flex;
justify-content: space-between;
align-items: center;
padding-top: 20rpx;
border-top: 1rpx solid #f0f0f0;
.invoice-type {
font-size: 24rpx;
color: #666;
background: #f5f5f5;
padding: 8rpx 16rpx;
border-radius: 16rpx;
}
.view-detail {
display: flex;
align-items: center;
color: #22c55e;
font-size: 24rpx;
.arrow {
margin-left: 8rpx;
font-size: 24rpx;
}
}
}
/* 空状态 */
.empty-state {
text-align: center;
padding: 120rpx 40rpx;
.empty-icon {
font-size: 120rpx;
margin-bottom: 32rpx;
opacity: 0.3;
}
.empty-text {
display: block;
font-size: 32rpx;
color: #666;
margin-bottom: 16rpx;
}
.empty-desc {
display: block;
font-size: 26rpx;
color: #999;
}
}
/* 加载更多 */
.load-more {
text-align: center;
padding: 40rpx;
.load-text {
font-size: 26rpx;
color: #999;
}
}
</style>