import 'package:flutter/material.dart'; import 'package:flutter_screenutil/flutter_screenutil.dart'; import 'package:nomo/app/widgets/ix_image.dart'; import 'package:nomo/config/theme/dark_theme_colors.dart'; /// 信息卡片组件 - 用于显示带图标的信息列表 /// 常用于订阅说明、功能介绍等场景 class InfoCard extends StatelessWidget { final String? title; final List items; final Color? backgroundColor; final EdgeInsets? padding; const InfoCard({ super.key, this.title, required this.items, this.backgroundColor, this.padding, }); @override Widget build(BuildContext context) { return Column( crossAxisAlignment: CrossAxisAlignment.start, children: [ if (title != null) ...[ Text( title!, style: TextStyle( fontSize: 16.sp, color: DarkThemeColors.hintTextColor, fontWeight: FontWeight.w500, ), ), 16.verticalSpace, ], Container( padding: padding ?? EdgeInsets.all(16.w), decoration: BoxDecoration( color: backgroundColor ?? DarkThemeColors.bgDisable, borderRadius: BorderRadius.circular(12.r), ), child: Column( children: items .asMap() .entries .map( (entry) => _InfoItemWidget( item: entry.value, isLast: entry.key == items.length - 1, ), ) .toList(), ), ), ], ); } } /// 信息项数据模型 class InfoItem { final IconData? icon; final String? imageSource; final String title; final String description; final Color? iconColor; final Gradient? iconGradient; final double? iconSize; final double? imageWidth; final double? imageHeight; const InfoItem({ this.icon, this.imageSource, required this.title, required this.description, this.iconColor, this.iconGradient, this.iconSize, this.imageWidth, this.imageHeight, }) : assert( icon != null || imageSource != null, 'Either icon or imageSource must be provided', ); } /// 信息项组件(内部使用) class _InfoItemWidget extends StatelessWidget { final InfoItem item; final bool isLast; const _InfoItemWidget({required this.item, this.isLast = false}); @override Widget build(BuildContext context) { return IntrinsicHeight( child: Row( crossAxisAlignment: CrossAxisAlignment.start, children: [ // 左侧时间线(图标/图片 + 竖线) Column( children: [ // 图标或图片容器 _buildIconOrImage(), // 连接线(最后一个不显示) if (!isLast) Expanded( child: Container( width: 1, margin: EdgeInsets.only(top: 8.h, bottom: 8.h), color: Colors.white.withValues(alpha: 0.1), ), ), ], ), 12.horizontalSpace, // 文本内容 Expanded( child: Padding( padding: EdgeInsets.only(bottom: isLast ? 0 : 10.w), child: Column( crossAxisAlignment: CrossAxisAlignment.start, children: [ Text( item.title, style: TextStyle( fontSize: 14.sp, height: 1.6, color: DarkThemeColors.bodyTextColor, fontWeight: FontWeight.w500, ), ), 4.verticalSpace, Text( item.description, style: TextStyle( fontSize: 12.sp, color: DarkThemeColors.hintTextColor, height: 1.7, ), ), ], ), ), ), ], ), ); } /// 构建图标或图片 Widget _buildIconOrImage() { if (item.imageSource != null) { // 显示图片 return IXImage( source: item.imageSource!, width: item.imageWidth ?? 20.w, height: item.imageHeight ?? 20.w, sourceType: _getImageSourceType(item.imageSource!), ); } else { // 显示图标 return Icon( item.icon, size: item.iconSize ?? 20.w, color: item.iconColor ?? Colors.white, ); } } /// 判断图片资源类型 ImageSourceType _getImageSourceType(String source) { if (source.startsWith('http://') || source.startsWith('https://')) { return ImageSourceType.network; } else if (source.startsWith('assets/')) { return ImageSourceType.asset; } else { return ImageSourceType.asset; } } }