Files
wushu/lib/views/profile/components/bug_list_page.dart
2026-03-30 21:30:11 +08:00

501 lines
16 KiB
Dart
Raw 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.
/// 时间: 2026-03-30
/// 功能: 已知bug列表页面
/// 介绍: 显示应用已知bug、解决方法和解决时间的底部弹窗页面
/// 最新变化: 新增bug列表页面支持下拉刷新和滚动查看
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import '../../../constants/app_constants.dart';
class BugListPage extends StatefulWidget {
const BugListPage({super.key});
@override
State<BugListPage> createState() => _BugListPageState();
}
class _BugListPageState extends State<BugListPage> {
// 模拟bug数据
final List<Map<String, dynamic>> _bugs = [
{
'id': 1,
'title': '诗词答题页面偶现卡顿',
'description': '在快速切换诗词题目时,页面可能出现短暂卡顿现象',
'severity': 'medium', // high, medium, low
'status': 'pending', // pending, in_progress, resolved
'solution': '优化页面渲染逻辑减少不必要的widget重建',
'resolveTime': '2026-04-15',
'reportTime': '2026-03-25',
'affectedUsers': '部分用户',
'expanded': false, // 添加展开状态
},
{
'id': 2,
'title': '历史记录加载缓慢',
'description': '当历史记录数量较多时,加载速度较慢',
'severity': 'high',
'status': 'in_progress',
'solution': '实现分页加载和本地缓存优化',
'resolveTime': '2026-04-10',
'reportTime': '2026-03-20',
'affectedUsers': '大量用户',
'expanded': false, // 添加展开状态
},
{
'id': 3,
'title': '主题切换不生效',
'description': '在某些设备上切换主题后,界面颜色没有立即更新',
'severity': 'low',
'status': 'resolved',
'solution': '修复主题状态管理问题,强制刷新界面',
'resolveTime': '2026-03-28',
'reportTime': '2026-03-15',
'affectedUsers': '少数用户',
'expanded': false, // 添加展开状态
},
{
'id': 4,
'title': '收藏夹同步失败',
'description': '网络不稳定时,收藏夹数据同步可能失败',
'severity': 'medium',
'status': 'pending',
'solution': '增加重试机制和离线缓存功能',
'resolveTime': '2026-04-20',
'reportTime': '2026-03-22',
'affectedUsers': '部分用户',
'expanded': false, // 添加展开状态
},
{
'id': 5,
'title': '字体大小设置异常',
'description': '调整字体大小后,部分页面文字显示不完整',
'severity': 'low',
'status': 'resolved',
'solution': '优化字体大小适配逻辑,确保所有页面正确显示',
'resolveTime': '2026-03-26',
'reportTime': '2026-03-18',
'affectedUsers': '少数用户',
'expanded': false, // 添加展开状态
},
];
final ScrollController _scrollController = ScrollController();
bool _isRefreshing = false;
// 切换bug展开状态
void _toggleBugExpanded(int bugId) {
setState(() {
final bugIndex = _bugs.indexWhere((bug) => bug['id'] == bugId);
if (bugIndex != -1) {
_bugs[bugIndex]['expanded'] = !_bugs[bugIndex]['expanded'];
}
});
HapticFeedback.lightImpact();
}
@override
void dispose() {
_scrollController.dispose();
super.dispose();
}
Color _getSeverityColor(String severity) {
switch (severity) {
case 'high':
return Colors.red;
case 'medium':
return Colors.orange;
case 'low':
return Colors.green;
default:
return Colors.grey;
}
}
String _getSeverityText(String severity) {
switch (severity) {
case 'high':
return '';
case 'medium':
return '';
case 'low':
return '';
default:
return '未知';
}
}
Color _getStatusColor(String status) {
switch (status) {
case 'resolved':
return Colors.green;
case 'in_progress':
return Colors.blue;
case 'pending':
return Colors.orange;
default:
return Colors.grey;
}
}
String _getStatusText(String status) {
switch (status) {
case 'resolved':
return '已解决';
case 'in_progress':
return '解决中';
case 'pending':
return '待解决';
default:
return '未知';
}
}
Future<void> _refresh() async {
setState(() {
_isRefreshing = true;
});
// 模拟网络请求延迟
await Future.delayed(const Duration(seconds: 1));
setState(() {
_isRefreshing = false;
});
HapticFeedback.lightImpact();
}
@override
Widget build(BuildContext context) {
return Container(
decoration: const BoxDecoration(
color: Colors.white,
borderRadius: BorderRadius.vertical(top: Radius.circular(20)),
),
child: Column(
children: [
// 顶部拖拽条和标题
_buildHeader(),
// bug列表
Expanded(
child: RefreshIndicator(
onRefresh: _refresh,
color: AppConstants.primaryColor,
child: ListView.builder(
controller: _scrollController,
physics: const AlwaysScrollableScrollPhysics(),
padding: const EdgeInsets.all(16),
itemCount: _bugs.length,
itemBuilder: (context, index) {
final bug = _bugs[index];
return _buildBugItem(bug);
},
),
),
),
],
),
);
}
Widget _buildHeader() {
return Column(
children: [
// 拖拽条
Container(
width: 40,
height: 4,
margin: const EdgeInsets.only(top: 8),
decoration: BoxDecoration(
color: Colors.grey[300],
borderRadius: BorderRadius.circular(2),
),
),
// 标题栏
Container(
padding: const EdgeInsets.all(16),
child: Row(
children: [
Icon(
Icons.bug_report,
color: AppConstants.primaryColor,
size: 24,
),
const SizedBox(width: 12),
Expanded(
child: Text(
'已知问题列表',
style: TextStyle(
fontSize: 18,
fontWeight: FontWeight.bold,
color: AppConstants.primaryColor,
),
),
),
TextButton(
onPressed: () => Navigator.pop(context),
child: const Text('关闭'),
),
],
),
),
const Divider(height: 1),
],
);
}
Widget _buildBugItem(Map<String, dynamic> bug) {
final bool isExpanded = bug['expanded'] ?? false;
return Container(
margin: const EdgeInsets.only(bottom: 16),
decoration: BoxDecoration(
color: Colors.white,
borderRadius: BorderRadius.circular(12),
border: Border.all(color: Colors.grey[200]!),
boxShadow: [
BoxShadow(
color: Colors.black.withValues(alpha: 0.05),
blurRadius: 5,
offset: const Offset(0, 2),
),
],
),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
// 顶部信息行
Container(
padding: const EdgeInsets.all(16),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
// 标题和状态标签
Row(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Expanded(
child: Text(
bug['title'] ?? '未知问题',
style: const TextStyle(
fontSize: 16,
fontWeight: FontWeight.bold,
color: Colors.black87,
),
),
),
const SizedBox(width: 8),
Container(
padding: const EdgeInsets.symmetric(
horizontal: 8,
vertical: 4,
),
decoration: BoxDecoration(
color: _getStatusColor(bug['status']).withValues(alpha: 0.1),
borderRadius: BorderRadius.circular(12),
border: Border.all(
color: _getStatusColor(bug['status']),
width: 1,
),
),
child: Text(
_getStatusText(bug['status']),
style: TextStyle(
fontSize: 12,
color: _getStatusColor(bug['status']),
fontWeight: FontWeight.w500,
),
),
),
],
),
const SizedBox(height: 8),
// 问题描述
Text(
bug['description'] ?? '暂无描述',
style: const TextStyle(
fontSize: 14,
color: Colors.black54,
height: 1.4,
),
),
const SizedBox(height: 12),
// 严重程度和影响用户
Row(
children: [
Container(
padding: const EdgeInsets.symmetric(
horizontal: 6,
vertical: 2,
),
decoration: BoxDecoration(
color: _getSeverityColor(bug['severity']).withValues(alpha: 0.1),
borderRadius: BorderRadius.circular(8),
),
child: Row(
mainAxisSize: MainAxisSize.min,
children: [
Icon(
Icons.priority_high,
size: 12,
color: _getSeverityColor(bug['severity']),
),
const SizedBox(width: 4),
Text(
'${_getSeverityText(bug['severity'])}优先级',
style: TextStyle(
fontSize: 11,
color: _getSeverityColor(bug['severity']),
fontWeight: FontWeight.w500,
),
),
],
),
),
const SizedBox(width: 12),
Icon(
Icons.people,
size: 14,
color: Colors.grey[600],
),
const SizedBox(width: 4),
Text(
bug['affectedUsers'] ?? '未知用户',
style: TextStyle(
fontSize: 12,
color: Colors.grey[600],
),
),
],
),
const SizedBox(height: 12),
// 解决方案按钮
Container(
width: double.infinity,
child: ElevatedButton.icon(
onPressed: () => _toggleBugExpanded(bug['id']),
icon: Icon(
isExpanded ? Icons.expand_less : Icons.expand_more,
size: 18,
),
label: Text(
isExpanded ? '收起解决方案' : '查看解决方案',
style: const TextStyle(fontSize: 14),
),
style: ElevatedButton.styleFrom(
backgroundColor: AppConstants.primaryColor.withValues(alpha: 0.1),
foregroundColor: AppConstants.primaryColor,
elevation: 0,
padding: const EdgeInsets.symmetric(vertical: 8),
shape: RoundedRectangleBorder(
borderRadius: BorderRadius.circular(8),
side: BorderSide(
color: AppConstants.primaryColor.withValues(alpha: 0.3),
),
),
),
),
),
],
),
),
// 解决方案区域(可展开/收起)
if (isExpanded) ...[
const Divider(height: 1),
Container(
padding: const EdgeInsets.all(16),
decoration: BoxDecoration(
color: Colors.grey[50],
borderRadius: const BorderRadius.only(
bottomLeft: Radius.circular(12),
bottomRight: Radius.circular(12),
),
),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Row(
children: [
Icon(
Icons.lightbulb_outline,
color: AppConstants.primaryColor,
size: 16,
),
const SizedBox(width: 8),
Text(
'解决方案',
style: TextStyle(
fontSize: 14,
fontWeight: FontWeight.w600,
color: AppConstants.primaryColor,
),
),
],
),
const SizedBox(height: 8),
Text(
bug['solution'] ?? '暂无解决方案',
style: const TextStyle(
fontSize: 13,
color: Colors.black54,
height: 1.4,
),
),
const SizedBox(height: 12),
// 时间信息
Row(
children: [
Icon(
Icons.schedule,
size: 14,
color: Colors.grey[600],
),
const SizedBox(width: 4),
Text(
'预计解决: ${bug['resolveTime'] ?? '待定'}',
style: TextStyle(
fontSize: 12,
color: Colors.grey[600],
),
),
const SizedBox(width: 16),
Icon(
Icons.report,
size: 14,
color: Colors.grey[600],
),
const SizedBox(width: 4),
Text(
'报告时间: ${bug['reportTime'] ?? '未知'}',
style: TextStyle(
fontSize: 12,
color: Colors.grey[600],
),
),
],
),
],
),
),
],
],
),
);
}
}
// 显示bug列表的底部弹窗方法
void showBugListBottomSheet(BuildContext context) {
showModalBottomSheet(
context: context,
backgroundColor: Colors.transparent,
isScrollControlled: true, // 允许弹窗占据全屏高度
builder: (context) => Container(
height: MediaQuery.of(context).size.height * 0.85, // 设置弹窗高度为屏幕的85%
child: const BugListPage(),
),
);
}