This commit is contained in:
2026-03-27 20:40:51 +08:00
parent af0a879a17
commit a1cec2bc34
130 changed files with 756 additions and 294 deletions

View File

@@ -10,6 +10,7 @@ import '../../shared/ui_constants.dart';
import '../../components/glass_panel.dart';
import '../../components/neon_glow.dart';
import '../orders/fund_orders_page.dart';
import 'transfer_page.dart';
/// 资产页面 - Material Design 3 风格
class AssetPage extends StatefulWidget {
@@ -314,7 +315,7 @@ class _FundAccountCard extends StatelessWidget {
text: '划转',
type: NeonButtonType.outline,
icon: Icons.swap_horiz,
onPressed: () => _showTransferDialog(context),
onPressed: () => _navigateToTransfer(context),
height: 44,
showGlow: false,
),
@@ -1084,170 +1085,14 @@ void _showWithdrawDialog(BuildContext context, String? balance) {
);
}
void _showTransferDialog(BuildContext context) {
final controller = TextEditingController();
final formKey = GlobalKey<ShadFormState>();
int direction = 1;
final colorScheme = Theme.of(context).colorScheme;
showShadDialog(
context: context,
builder: (ctx) => StatefulBuilder(
builder: (ctx, setState) => Dialog(
backgroundColor: Colors.transparent,
child: GlassPanel(
borderRadius: BorderRadius.circular(AppRadius.xxl),
padding: EdgeInsets.all(AppSpacing.lg),
child: Column(
mainAxisSize: MainAxisSize.min,
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Text(
'划转',
style: GoogleFonts.spaceGrotesk(
fontSize: 20,
fontWeight: FontWeight.bold,
color: colorScheme.onSurface,
),
),
SizedBox(height: AppSpacing.lg),
Row(
children: [
Expanded(
child: _DirectionButton(
label: '资金→交易',
isSelected: direction == 1,
onTap: () => setState(() => direction = 1),
),
),
SizedBox(width: AppSpacing.sm),
Expanded(
child: _DirectionButton(
label: '交易→资金',
isSelected: direction == 2,
onTap: () => setState(() => direction = 2),
),
),
],
),
SizedBox(height: AppSpacing.lg),
ShadForm(
key: formKey,
child: ShadInputFormField(
id: 'amount',
controller: controller,
label: const Text('划转金额'),
placeholder: const Text('请输入划转金额(USDT)'),
keyboardType: const TextInputType.numberWithOptions(decimal: true),
validator: Validators.amount,
),
),
SizedBox(height: AppSpacing.lg),
Row(
children: [
Expanded(
child: NeonButton(
text: '取消',
type: NeonButtonType.outline,
onPressed: () => Navigator.of(ctx).pop(),
height: 44,
showGlow: false,
),
),
SizedBox(width: AppSpacing.sm),
Expanded(
child: NeonButton(
text: '确认',
type: NeonButtonType.primary,
onPressed: () async {
if (formKey.currentState!.saveAndValidate()) {
Navigator.of(ctx).pop();
final response = await context.read<AssetProvider>().transfer(
direction: direction,
amount: controller.text,
);
if (context.mounted) {
_showResultDialog(
context,
response.success ? '划转成功' : '划转失败',
response.message,
);
}
}
},
height: 44,
showGlow: true,
),
),
],
),
],
),
),
),
),
void _navigateToTransfer(BuildContext context) async {
final result = await Navigator.push<bool>(
context,
MaterialPageRoute(builder: (_) => const TransferPage()),
);
}
class _DirectionButton extends StatelessWidget {
final String label;
final bool isSelected;
final VoidCallback onTap;
const _DirectionButton({
required this.label,
required this.isSelected,
required this.onTap,
});
@override
Widget build(BuildContext context) {
final colorScheme = Theme.of(context).colorScheme;
return GestureDetector(
onTap: onTap,
child: AnimatedContainer(
duration: const Duration(milliseconds: 200),
padding: EdgeInsets.symmetric(vertical: AppSpacing.sm + AppSpacing.xs),
decoration: BoxDecoration(
color: isSelected
? colorScheme.primary.withOpacity(0.15)
: colorScheme.surfaceContainerHigh,
borderRadius: BorderRadius.circular(AppRadius.md),
border: isSelected
? Border.all(
color: colorScheme.primary.withOpacity(0.3),
)
: null,
),
child: Center(
child: Row(
mainAxisSize: MainAxisSize.min,
children: [
if (isSelected)
Icon(
LucideIcons.check,
size: 14,
color: colorScheme.primary,
)
else
SizedBox(width: 14),
SizedBox(width: AppSpacing.xs),
Text(
label,
style: TextStyle(
color: isSelected
? colorScheme.primary
: colorScheme.onSurfaceVariant,
fontWeight: isSelected ? FontWeight.w600 : FontWeight.normal,
fontSize: 12,
),
),
],
),
),
),
);
// 如果划转成功,刷新数据
if (result == true && context.mounted) {
context.read<AssetProvider>().refreshAll(force: true);
}
}