在这里插入图片描述

项目详情页是项目管理系统的核心页面,需要展示项目的完整信息、进度统计、活动记录等。本文将详细介绍如何在Flutter for OpenHarmony应用中实现一个功能丰富的项目详情页。

页面结构设计

项目详情页接收项目对象作为参数,展示项目的详细信息:

class ProjectDetailPage extends StatelessWidget {
  final Project project;

  const ProjectDetailPage({Key? key, required this.project}) : super(key: key);

  
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text(project.name),
        backgroundColor: Theme.of(context).primaryColor,
        foregroundColor: Colors.white,
        actions: [
          IconButton(
            icon: const Icon(Icons.edit),
            onPressed: () {
              // TODO: 编辑项目
            },
          ),

页面使用StatelessWidget实现,因为项目信息相对静态。应用栏显示项目名称,并提供编辑和分享功能按钮。

项目基本信息卡片

页面顶部展示项目的基本信息,包括图标、名称、语言等:

Card(
  child: Padding(
    padding: EdgeInsets.all(16.w),
    child: Column(
      crossAxisAlignment: CrossAxisAlignment.start,
      children: [
        Row(
          children: [
            Container(
              width: 60.w,
              height: 60.h,
              decoration: BoxDecoration(
                color: _getLanguageColor(project.language).withOpacity(0.1),
                borderRadius: BorderRadius.circular(12),
              ),
              child: Icon(
                _getLanguageIcon(project.language),
                color: _getLanguageColor(project.language),
                size: 30.sp,
              ),
            ),

项目图标使用较大尺寸显示,背景色根据编程语言动态设置。图标容器采用圆角设计,提供现代化的视觉效果。

项目名称和语言展示

项目名称和编程语言信息紧邻图标显示:

SizedBox(width: 16.w),
Expanded(
  child: Column(
    crossAxisAlignment: CrossAxisAlignment.start,
    children: [
      Text(
        project.name,
        style: TextStyle(
          fontSize: 24.sp,
          fontWeight: FontWeight.bold,
        ),
      ),
      SizedBox(height: 4.h),
      Text(
        project.language,
        style: TextStyle(
          fontSize: 16.sp,
          color: _getLanguageColor(project.language),
          fontWeight: FontWeight.w500,
        ),
      ),
    ],
  ),
),

项目名称使用大字号粗体显示,编程语言使用对应的主题色显示,增强视觉识别度。

项目描述和标签

基本信息卡片还包含项目描述和标签信息:

SizedBox(height: 16.h),
Text(
  project.description,
  style: TextStyle(
    fontSize: 16.sp,
    color: Colors.grey[700],
    height: 1.5,
  ),
),
SizedBox(height: 16.h),
Wrap(
  spacing: 8.w,
  runSpacing: 8.h,
  children: project.tags.map((tag) => Chip(
    label: Text(tag),
    backgroundColor: Colors.grey[200],
  )).toList(),
),

项目描述使用适中的行高提高可读性,标签使用Wrap组件自动换行排列,每个标签都是一个Chip组件。

项目进度展示

项目进度使用圆形进度指示器展示,更加直观:

Card(
  child: Padding(
    padding: EdgeInsets.all(16.w),
    child: Column(
      crossAxisAlignment: CrossAxisAlignment.start,
      children: [
        Text(
          '项目进度',
          style: TextStyle(
            fontSize: 20.sp,
            fontWeight: FontWeight.bold,
          ),
        ),
        SizedBox(height: 16.h),
        CircularPercentIndicator(
          radius: 80.w,
          lineWidth: 12.w,
          percent: project.progress,
          center: Text(
            '${(project.progress * 100).toInt()}%',
            style: TextStyle(
              fontSize: 24.sp,
              fontWeight: FontWeight.bold,
            ),
          ),
          progressColor: _getLanguageColor(project.language),
          backgroundColor: Colors.grey[300]!,
        ),

圆形进度条中央显示百分比数值,进度条颜色与项目语言颜色保持一致,提供视觉统一性。

项目统计信息

进度卡片下方展示项目的关键统计信息:

SizedBox(height: 16.h),
Row(
  mainAxisAlignment: MainAxisAlignment.spaceAround,
  children: [
    _buildStatItem('开始时间', '2024-01-15'),
    _buildStatItem('预计完成', '2024-03-30'),
    _buildStatItem('状态', project.status),
  ],
),

统计信息使用三列布局,包含项目开始时间、预计完成时间和当前状态。这些信息帮助用户了解项目的时间安排。

统计项构建方法

统计项使用统一的构建方法确保样式一致:

Widget _buildStatItem(String label, String value) {
  return Column(
    children: [
      Text(
        value,
        style: TextStyle(
          fontSize: 18.sp,
          fontWeight: FontWeight.bold,
        ),
      ),
      SizedBox(height: 4.h),
      Text(
        label,
        style: TextStyle(
          fontSize: 12.sp,
          color: Colors.grey[600],
        ),
      ),
    ],
  );
}

每个统计项包含数值和标签,数值使用粗体显示,标签使用较小字号和灰色。

任务统计展示

任务统计卡片展示不同状态任务的数量:

Card(
  child: Padding(
    padding: EdgeInsets.all(16.w),
    child: Column(
      crossAxisAlignment: CrossAxisAlignment.start,
      children: [
        Text(
          '任务统计',
          style: TextStyle(
            fontSize: 20.sp,
            fontWeight: FontWeight.bold,
          ),
        ),
        SizedBox(height: 16.h),
        Row(
          children: [
            Expanded(
              child: _buildTaskStatCard('待开始', 5, Colors.grey),
            ),
            SizedBox(width: 12.w),
            Expanded(
              child: _buildTaskStatCard('进行中', 8, Colors.blue),
            ),
            SizedBox(width: 12.w),
            Expanded(
              child: _buildTaskStatCard('已完成', 12, Colors.green),
            ),
          ],
        ),

任务统计使用三列网格布局,每种任务状态使用不同颜色区分,便于用户快速了解任务分布。

任务统计卡片构建

任务统计卡片使用统一的构建方法:

Widget _buildTaskStatCard(String title, int count, Color color) {
  return Container(
    padding: EdgeInsets.all(12.w),
    decoration: BoxDecoration(
      color: color.withOpacity(0.1),
      borderRadius: BorderRadius.circular(8),
    ),
    child: Column(
      children: [
        Text(
          count.toString(),
          style: TextStyle(
            fontSize: 24.sp,
            fontWeight: FontWeight.bold,
            color: color,
          ),
        ),
        SizedBox(height: 4.h),
        Text(
          title,
          style: TextStyle(
            fontSize: 12.sp,
            color: color,
          ),
        ),
      ],
    ),
  );
}

每个统计卡片使用对应状态的颜色作为背景和文字颜色,数量使用大字号显示,标题使用小字号。

提交活动图表

项目详情页包含提交活动的可视化图表:

Card(
  child: Padding(
    padding: EdgeInsets.all(16.w),
    child: Column(
      crossAxisAlignment: CrossAxisAlignment.start,
      children: [
        Text(
          '提交活动',
          style: TextStyle(
            fontSize: 20.sp,
            fontWeight: FontWeight.bold,
          ),
        ),
        SizedBox(height: 16.h),
        SizedBox(
          height: 200.h,
          child: LineChart(
            LineChartData(
              gridData: FlGridData(show: false),
              titlesData: FlTitlesData(show: false),
              borderData: FlBorderData(show: false),

图表使用fl_chart库的LineChart组件,隐藏网格线、标题和边框,保持简洁的视觉效果。

图表数据配置

图表数据使用FlSpot对象定义坐标点:

lineBarsData: [
  LineChartBarData(
    spots: [
      FlSpot(0, 3),
      FlSpot(1, 1),
      FlSpot(2, 4),
      FlSpot(3, 2),
      FlSpot(4, 5),
      FlSpot(5, 3),
      FlSpot(6, 4),
    ],
    isCurved: true,
    color: _getLanguageColor(project.language),
    barWidth: 3,
    dotData: FlDotData(show: false),
    belowBarData: BarAreaData(
      show: true,
      color: _getLanguageColor(project.language).withOpacity(0.3),
    ),
  ),
],

图表使用曲线连接数据点,颜色与项目语言颜色一致。线条下方填充半透明颜色,增强视觉效果。

最近活动列表

页面底部展示项目的最近活动记录:

Card(
  child: Padding(
    padding: EdgeInsets.all(16.w),
    child: Column(
      crossAxisAlignment: CrossAxisAlignment.start,
      children: [
        Text(
          '最近活动',
          style: TextStyle(
            fontSize: 20.sp,
            fontWeight: FontWeight.bold,
          ),
        ),
        SizedBox(height: 16.h),
        ListView.separated(
          shrinkWrap: true,
          physics: const NeverScrollableScrollPhysics(),
          itemCount: 5,
          separatorBuilder: (context, index) => Divider(),

活动列表使用ListView.separated组件,自动在列表项之间添加分隔线。

活动项展示

每个活动项包含图标、描述和时间信息:

itemBuilder: (context, index) {
  return ListTile(
    leading: CircleAvatar(
      backgroundColor: _getLanguageColor(project.language).withOpacity(0.1),
      child: Icon(
        Icons.commit,
        color: _getLanguageColor(project.language),
      ),
    ),
    title: Text('修复了登录页面的UI问题'),
    subtitle: Text('2小时前 • main分支'),
    trailing: Icon(Icons.chevron_right),
  );
},

活动项使用ListTile组件,左侧显示圆形头像图标,中间显示活动描述和时间,右侧显示箭头图标表示可点击。

语言颜色映射

页面复用了语言颜色映射逻辑:

Color _getLanguageColor(String language) {
  switch (language.toLowerCase()) {
    case 'dart':
      return Colors.blue;
    case 'javascript':
      return Colors.yellow[700]!;
    case 'python':
      return Colors.green;
    case 'java':
      return Colors.orange;
    case 'swift':
      return Colors.orange[800]!;
    case 'kotlin':
      return Colors.purple;
    default:
      return Colors.grey;
  }
}

这个方法确保整个页面的颜色主题与项目的编程语言保持一致。

语言图标映射

同样复用了语言图标映射逻辑:

IconData _getLanguageIcon(String language) {
  switch (language.toLowerCase()) {
    case 'dart':
      return Icons.flutter_dash;
    case 'javascript':
      return Icons.javascript;
    case 'python':
      return Icons.code;
    case 'java':
      return Icons.coffee;
    default:
      return Icons.code;
  }
}

图标选择与项目列表页面保持一致,提供统一的用户体验。

总结

通过以上实现,我们创建了一个信息丰富的项目详情页,包含项目基本信息、进度展示、任务统计、活动图表等功能。页面设计注重信息的层次化展示,通过卡片布局将不同类型的信息分组显示。颜色主题与项目的编程语言关联,提供个性化的视觉体验。在Flutter for OpenHarmony平台上,这样的详情页能够为开发者提供全面的项目信息视图。

欢迎加入开源鸿蒙跨平台社区:https://openharmonycrossplatform.csdn.net

Logo

开源鸿蒙跨平台开发社区汇聚开发者与厂商,共建“一次开发,多端部署”的开源生态,致力于降低跨端开发门槛,推动万物智联创新。

更多推荐