refactor: 重构前端 UI 组件与后端 AgentScope schemas
This commit is contained in:
@@ -4,6 +4,7 @@ import 'package:go_router/go_router.dart';
|
||||
import '../../../../core/di/injection.dart';
|
||||
import '../../../../core/notifications/local_notification_service.dart';
|
||||
import '../../../../core/theme/design_tokens.dart';
|
||||
import '../../../../shared/widgets/page_header.dart' as widgets;
|
||||
import '../../data/services/calendar_service.dart';
|
||||
import '../../data/models/schedule_item_model.dart';
|
||||
import '../widgets/create_event_sheet.dart';
|
||||
@@ -62,20 +63,22 @@ class _CalendarEventDetailScreenState extends State<CalendarEventDetailScreen> {
|
||||
style: TextStyle(color: AppColors.slate600),
|
||||
),
|
||||
const SizedBox(height: 16),
|
||||
GestureDetector(
|
||||
onTap: () => context.pop(),
|
||||
child: Container(
|
||||
padding: const EdgeInsets.symmetric(
|
||||
horizontal: 16,
|
||||
vertical: 8,
|
||||
),
|
||||
decoration: BoxDecoration(
|
||||
color: AppColors.blue600,
|
||||
borderRadius: BorderRadius.circular(20),
|
||||
SizedBox(
|
||||
height: AppSpacing.xxl * 2,
|
||||
child: TextButton(
|
||||
onPressed: () => context.pop(),
|
||||
style: TextButton.styleFrom(
|
||||
padding: const EdgeInsets.symmetric(
|
||||
horizontal: AppSpacing.lg,
|
||||
),
|
||||
backgroundColor: AppColors.blue600,
|
||||
shape: RoundedRectangleBorder(
|
||||
borderRadius: BorderRadius.circular(AppRadius.full),
|
||||
),
|
||||
),
|
||||
child: const Text(
|
||||
'返回',
|
||||
style: TextStyle(color: Colors.white),
|
||||
style: TextStyle(color: AppColors.white),
|
||||
),
|
||||
),
|
||||
),
|
||||
@@ -108,23 +111,7 @@ class _CalendarEventDetailScreenState extends State<CalendarEventDetailScreen> {
|
||||
padding: const EdgeInsets.only(left: 16, right: 16, top: 12, bottom: 8),
|
||||
child: Row(
|
||||
children: [
|
||||
GestureDetector(
|
||||
onTap: () => Navigator.of(context).pop(),
|
||||
child: Container(
|
||||
width: 36,
|
||||
height: 36,
|
||||
decoration: BoxDecoration(
|
||||
color: const Color(0xFFF8FAFF),
|
||||
borderRadius: BorderRadius.circular(18),
|
||||
border: Border.all(color: const Color(0xFFDEE7F6)),
|
||||
),
|
||||
child: const Icon(
|
||||
LucideIcons.chevronLeft,
|
||||
size: 16,
|
||||
color: AppColors.slate700,
|
||||
),
|
||||
),
|
||||
),
|
||||
widgets.BackButton(onPressed: () => Navigator.of(context).pop()),
|
||||
],
|
||||
),
|
||||
),
|
||||
@@ -241,7 +228,7 @@ class _CalendarEventDetailScreenState extends State<CalendarEventDetailScreen> {
|
||||
Row(
|
||||
children: [
|
||||
if (event.canEdit)
|
||||
GestureDetector(
|
||||
_buildHeaderActionButton(
|
||||
onTap: () => CreateEventSheet.edit(
|
||||
context,
|
||||
event,
|
||||
@@ -251,43 +238,23 @@ class _CalendarEventDetailScreenState extends State<CalendarEventDetailScreen> {
|
||||
});
|
||||
},
|
||||
),
|
||||
child: Container(
|
||||
width: 36,
|
||||
height: 36,
|
||||
decoration: BoxDecoration(
|
||||
color: const Color(0xFFF8FAFF),
|
||||
borderRadius: BorderRadius.circular(12),
|
||||
border: Border.all(color: const Color(0xFFDCE5F4)),
|
||||
),
|
||||
child: const Icon(
|
||||
LucideIcons.pencil,
|
||||
size: 18,
|
||||
color: AppColors.slate600,
|
||||
),
|
||||
),
|
||||
icon: LucideIcons.pencil,
|
||||
iconColor: AppColors.slate600,
|
||||
backgroundColor: AppColors.surfaceTertiary,
|
||||
borderColor: AppColors.borderTertiary,
|
||||
),
|
||||
if (event.canEdit) const SizedBox(width: 8),
|
||||
if (event.canDelete)
|
||||
GestureDetector(
|
||||
_buildHeaderActionButton(
|
||||
onTap: _showDeleteConfirmation,
|
||||
child: Container(
|
||||
width: 36,
|
||||
height: 36,
|
||||
decoration: BoxDecoration(
|
||||
color: const Color(0xFFFFF1F2),
|
||||
borderRadius: BorderRadius.circular(12),
|
||||
border: Border.all(color: const Color(0xFFFECACA)),
|
||||
),
|
||||
child: const Icon(
|
||||
LucideIcons.trash2,
|
||||
size: 18,
|
||||
color: AppColors.red500,
|
||||
),
|
||||
),
|
||||
icon: LucideIcons.trash2,
|
||||
iconColor: AppColors.red500,
|
||||
backgroundColor: AppColors.warningBackground,
|
||||
borderColor: AppColors.messageRejectBorder,
|
||||
),
|
||||
if (event.canInvite) ...[
|
||||
const SizedBox(width: 8),
|
||||
GestureDetector(
|
||||
_buildHeaderActionButton(
|
||||
onTap: () => CalendarShareDialog.show(
|
||||
context,
|
||||
event.id,
|
||||
@@ -295,20 +262,10 @@ class _CalendarEventDetailScreenState extends State<CalendarEventDetailScreen> {
|
||||
canInvite: event.canInvite,
|
||||
canEdit: event.canEdit,
|
||||
),
|
||||
child: Container(
|
||||
width: 36,
|
||||
height: 36,
|
||||
decoration: BoxDecoration(
|
||||
color: const Color(0xFFF0FDF4),
|
||||
borderRadius: BorderRadius.circular(12),
|
||||
border: Border.all(color: const Color(0xFFBBF7D0)),
|
||||
),
|
||||
child: const Icon(
|
||||
LucideIcons.share2,
|
||||
size: 18,
|
||||
color: AppColors.slate600,
|
||||
),
|
||||
),
|
||||
icon: LucideIcons.share2,
|
||||
iconColor: AppColors.slate600,
|
||||
backgroundColor: AppColors.blue50,
|
||||
borderColor: AppColors.blue100,
|
||||
),
|
||||
],
|
||||
],
|
||||
@@ -317,6 +274,35 @@ class _CalendarEventDetailScreenState extends State<CalendarEventDetailScreen> {
|
||||
);
|
||||
}
|
||||
|
||||
Widget _buildHeaderActionButton({
|
||||
required VoidCallback onTap,
|
||||
required IconData icon,
|
||||
required Color iconColor,
|
||||
required Color backgroundColor,
|
||||
required Color borderColor,
|
||||
}) {
|
||||
return SizedBox(
|
||||
width: AppSpacing.xxl * 2,
|
||||
height: AppSpacing.xxl * 2,
|
||||
child: TextButton(
|
||||
onPressed: onTap,
|
||||
style: TextButton.styleFrom(
|
||||
padding: const EdgeInsets.all(AppSpacing.none),
|
||||
backgroundColor: backgroundColor,
|
||||
shape: RoundedRectangleBorder(
|
||||
borderRadius: BorderRadius.circular(AppRadius.md),
|
||||
side: BorderSide(color: borderColor),
|
||||
),
|
||||
),
|
||||
child: Icon(
|
||||
icon,
|
||||
size: AppSpacing.lg + AppSpacing.xs,
|
||||
color: iconColor,
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
void _showDeleteConfirmation() {
|
||||
showDialog(
|
||||
context: context,
|
||||
|
||||
@@ -145,12 +145,22 @@ class _CreateEventSheetState extends State<CreateEventSheet>
|
||||
child: Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
children: [
|
||||
GestureDetector(
|
||||
onTap: () => Navigator.pop(context),
|
||||
child: const Icon(
|
||||
LucideIcons.x,
|
||||
size: 24,
|
||||
color: AppColors.slate700,
|
||||
SizedBox(
|
||||
width: AppSpacing.xxl * 2,
|
||||
height: AppSpacing.xxl * 2,
|
||||
child: TextButton(
|
||||
onPressed: () => Navigator.pop(context),
|
||||
style: TextButton.styleFrom(
|
||||
padding: const EdgeInsets.all(AppSpacing.none),
|
||||
shape: RoundedRectangleBorder(
|
||||
borderRadius: BorderRadius.circular(AppRadius.full),
|
||||
),
|
||||
),
|
||||
child: const Icon(
|
||||
LucideIcons.x,
|
||||
size: AppSpacing.xxl,
|
||||
color: AppColors.slate700,
|
||||
),
|
||||
),
|
||||
),
|
||||
Text(
|
||||
@@ -164,16 +174,25 @@ class _CreateEventSheetState extends State<CreateEventSheet>
|
||||
ValueListenableBuilder<TextEditingValue>(
|
||||
valueListenable: _titleController,
|
||||
builder: (context, value, child) {
|
||||
return GestureDetector(
|
||||
onTap: _saveEvent,
|
||||
child: Text(
|
||||
'保存',
|
||||
style: TextStyle(
|
||||
fontSize: 17,
|
||||
fontWeight: FontWeight.w600,
|
||||
color: value.text.trim().isNotEmpty
|
||||
? AppColors.blue600
|
||||
: AppColors.slate400,
|
||||
final enabled = value.text.trim().isNotEmpty;
|
||||
return SizedBox(
|
||||
height: AppSpacing.xxl * 2,
|
||||
child: TextButton(
|
||||
onPressed: enabled ? _saveEvent : null,
|
||||
style: TextButton.styleFrom(
|
||||
padding: const EdgeInsets.symmetric(
|
||||
horizontal: AppSpacing.md,
|
||||
),
|
||||
minimumSize: const Size(AppSpacing.none, AppSpacing.none),
|
||||
tapTargetSize: MaterialTapTargetSize.shrinkWrap,
|
||||
),
|
||||
child: Text(
|
||||
'保存',
|
||||
style: TextStyle(
|
||||
fontSize: 17,
|
||||
fontWeight: FontWeight.w600,
|
||||
color: enabled ? AppColors.blue600 : AppColors.slate400,
|
||||
),
|
||||
),
|
||||
),
|
||||
);
|
||||
|
||||
@@ -3,6 +3,9 @@ import 'package:go_router/go_router.dart';
|
||||
import '../../../../core/theme/design_tokens.dart';
|
||||
import '../../../../shared/widgets/page_header.dart' as widgets;
|
||||
import '../../../../shared/widgets/app_input.dart';
|
||||
import '../../../../shared/widgets/link_button.dart';
|
||||
import '../../../../shared/widgets/toast/toast.dart';
|
||||
import '../../../../shared/widgets/toast/toast_type.dart';
|
||||
|
||||
class AddContactScreen extends StatefulWidget {
|
||||
final String? contactId;
|
||||
@@ -62,17 +65,24 @@ class _AddContactScreenState extends State<AddContactScreen> {
|
||||
}
|
||||
|
||||
Widget _buildConfirmButton() {
|
||||
return GestureDetector(
|
||||
onTap: _handleConfirm,
|
||||
child: Container(
|
||||
width: 36,
|
||||
height: 36,
|
||||
decoration: BoxDecoration(
|
||||
color: AppColors.surfaceInfo,
|
||||
borderRadius: BorderRadius.circular(18),
|
||||
border: Border.all(color: AppColors.borderQuaternary),
|
||||
return SizedBox(
|
||||
width: AppSpacing.xxl * 2,
|
||||
height: AppSpacing.xxl * 2,
|
||||
child: TextButton(
|
||||
onPressed: _handleConfirm,
|
||||
style: TextButton.styleFrom(
|
||||
padding: const EdgeInsets.all(AppSpacing.none),
|
||||
backgroundColor: AppColors.surfaceInfo,
|
||||
shape: RoundedRectangleBorder(
|
||||
borderRadius: BorderRadius.circular(AppRadius.full),
|
||||
side: const BorderSide(color: AppColors.borderQuaternary),
|
||||
),
|
||||
),
|
||||
child: const Icon(
|
||||
Icons.check,
|
||||
size: AppSpacing.lg,
|
||||
color: AppColors.blue600,
|
||||
),
|
||||
child: const Icon(Icons.check, size: 16, color: AppColors.blue600),
|
||||
),
|
||||
);
|
||||
}
|
||||
@@ -83,7 +93,7 @@ class _AddContactScreenState extends State<AddContactScreen> {
|
||||
width: 72,
|
||||
height: 72,
|
||||
decoration: BoxDecoration(
|
||||
color: const Color(0xFFF3F6FC),
|
||||
color: AppColors.surfaceInfoLight,
|
||||
borderRadius: BorderRadius.circular(36),
|
||||
border: Border.all(color: Colors.transparent),
|
||||
),
|
||||
@@ -102,7 +112,7 @@ class _AddContactScreenState extends State<AddContactScreen> {
|
||||
decoration: BoxDecoration(
|
||||
color: AppColors.white,
|
||||
borderRadius: BorderRadius.circular(16),
|
||||
border: Border.all(color: const Color(0xFFE3EAF6)),
|
||||
border: Border.all(color: AppColors.messageCardBorder),
|
||||
),
|
||||
child: Column(
|
||||
children: [
|
||||
@@ -127,19 +137,12 @@ class _AddContactScreenState extends State<AddContactScreen> {
|
||||
}
|
||||
|
||||
Widget _buildDeleteRow() {
|
||||
return GestureDetector(
|
||||
onTap: _handleDelete,
|
||||
child: Container(
|
||||
padding: const EdgeInsets.only(bottom: 8),
|
||||
alignment: Alignment.center,
|
||||
child: const Text(
|
||||
'删除联系人',
|
||||
style: TextStyle(
|
||||
fontSize: 12,
|
||||
fontWeight: FontWeight.w600,
|
||||
color: AppColors.red600,
|
||||
),
|
||||
),
|
||||
return Padding(
|
||||
padding: const EdgeInsets.only(bottom: AppSpacing.sm),
|
||||
child: LinkButton(
|
||||
text: '删除联系人',
|
||||
onTap: _handleDelete,
|
||||
foregroundColor: AppColors.red600,
|
||||
),
|
||||
);
|
||||
}
|
||||
@@ -149,9 +152,7 @@ class _AddContactScreenState extends State<AddContactScreen> {
|
||||
final email = _emailController.text.trim();
|
||||
|
||||
if (name.isEmpty || email.isEmpty) {
|
||||
ScaffoldMessenger.of(
|
||||
context,
|
||||
).showSnackBar(const SnackBar(content: Text('请填写昵称和邮箱')));
|
||||
Toast.show(context, '请填写昵称和邮箱', type: ToastType.warning);
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
@@ -3,6 +3,7 @@ import 'package:go_router/go_router.dart';
|
||||
import '../../../../core/theme/design_tokens.dart';
|
||||
import '../../../../core/di/injection.dart';
|
||||
import '../../../../shared/widgets/app_button.dart';
|
||||
import '../../../../shared/widgets/page_header.dart' as widgets;
|
||||
import '../../../../shared/widgets/toast/toast.dart';
|
||||
import '../../../../shared/widgets/toast/toast_type.dart';
|
||||
import '../../../users/data/models/user_response.dart';
|
||||
@@ -161,23 +162,7 @@ class _EditProfileScreenState extends State<EditProfileScreen> {
|
||||
padding: const EdgeInsets.symmetric(horizontal: 20),
|
||||
child: Row(
|
||||
children: [
|
||||
GestureDetector(
|
||||
onTap: () => context.pop(),
|
||||
child: Container(
|
||||
width: 36,
|
||||
height: 36,
|
||||
decoration: BoxDecoration(
|
||||
color: const Color(0xFFF8FAFF),
|
||||
borderRadius: BorderRadius.circular(18),
|
||||
border: Border.all(color: const Color(0xFFDEE7F6)),
|
||||
),
|
||||
child: const Icon(
|
||||
Icons.chevron_left,
|
||||
size: 18,
|
||||
color: Color(0xFF334155),
|
||||
),
|
||||
),
|
||||
),
|
||||
widgets.BackButton(onPressed: () => context.pop()),
|
||||
const SizedBox(width: 12),
|
||||
const Text(
|
||||
'编辑资料',
|
||||
|
||||
@@ -3,6 +3,7 @@ import 'package:go_router/go_router.dart';
|
||||
import 'package:lucide_icons/lucide_icons.dart';
|
||||
import '../../../../core/di/injection.dart';
|
||||
import '../../../../core/theme/design_tokens.dart';
|
||||
import '../../../../shared/widgets/page_header.dart' as widgets;
|
||||
import '../../../../shared/widgets/app_button.dart';
|
||||
import '../../../../shared/widgets/toast/toast.dart';
|
||||
import '../../../../shared/widgets/toast/toast_type.dart';
|
||||
@@ -101,26 +102,7 @@ class _TodoDetailScreenState extends State<TodoDetailScreen> {
|
||||
padding: const EdgeInsets.only(left: 16, right: 16, top: 12, bottom: 8),
|
||||
child: Row(
|
||||
children: [
|
||||
GestureDetector(
|
||||
onTap: () => Navigator.of(context).pop(),
|
||||
child: Container(
|
||||
width: 36,
|
||||
height: 36,
|
||||
decoration: BoxDecoration(
|
||||
color: AppColors.messageBtnWrap,
|
||||
borderRadius: BorderRadius.circular(18),
|
||||
border: Border.all(
|
||||
color: AppColors.messageBtnBorder,
|
||||
width: 1,
|
||||
),
|
||||
),
|
||||
child: const Icon(
|
||||
LucideIcons.chevronLeft,
|
||||
size: 16,
|
||||
color: AppColors.slate700,
|
||||
),
|
||||
),
|
||||
),
|
||||
widgets.BackButton(onPressed: () => Navigator.of(context).pop()),
|
||||
const Spacer(),
|
||||
if (_todo != null) ...[
|
||||
IconButton(
|
||||
|
||||
@@ -9,21 +9,25 @@ class LinkButton extends StatelessWidget {
|
||||
required this.onTap,
|
||||
this.enabled = true,
|
||||
this.textAlign = TextAlign.center,
|
||||
this.foregroundColor,
|
||||
});
|
||||
|
||||
final String text;
|
||||
final VoidCallback? onTap;
|
||||
final bool enabled;
|
||||
final TextAlign textAlign;
|
||||
final Color? foregroundColor;
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
final effectiveColor = foregroundColor ?? AppColors.slate500;
|
||||
|
||||
return SizedBox(
|
||||
height: 44,
|
||||
child: TextButton(
|
||||
onPressed: enabled ? onTap : null,
|
||||
style: TextButton.styleFrom(
|
||||
foregroundColor: enabled ? AppColors.slate500 : AppColors.slate300,
|
||||
foregroundColor: enabled ? effectiveColor : AppColors.slate300,
|
||||
padding: const EdgeInsets.symmetric(
|
||||
horizontal: AppSpacing.md,
|
||||
vertical: AppSpacing.sm,
|
||||
|
||||
Reference in New Issue
Block a user