You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Flutter自定义Floating Action Button:实现点击唤起居中滑入容器求助

解决Flutter容器从下方滑入屏幕中央的问题

要实现点击悬浮按钮后容器从下方滑入屏幕中央的效果,你可以通过精确计算居中位置结合AnimatedPositioned和AnimatedOpacity调整现有代码,核心是让容器初始位置在屏幕外下方,目标位置为屏幕正中央。以下是结合Riverpod状态管理的完整实现方案:

代码实现

import 'package:flutter/material.dart';
import 'package:flutter_riverpod/flutter_riverpod.dart';

// Riverpod状态管理:控制容器显示/隐藏
final showContainerProvider = StateProvider<bool>((ref) => false);

class SlideInContainerPage extends ConsumerWidget {
  const SlideInContainerPage({super.key});

  @override
  Widget build(BuildContext context, WidgetRef ref) {
    final isContainerVisible = ref.watch(showContainerProvider);
    final screenSize = MediaQuery.of(context).size;
    
    // 自定义容器尺寸
    const containerWidth = 320.0;
    const containerHeight = 240.0;

    // 计算容器居中时的坐标
    final centerLeft = (screenSize.width - containerWidth) / 2;
    final centerTop = (screenSize.height - containerHeight) / 2;

    return Scaffold(
      floatingActionButton: FloatingActionButton(
        onPressed: () {
          // 切换容器显示状态
          ref.read(showContainerProvider.notifier).state = !isContainerVisible;
        },
        child: const Icon(Icons.add),
      ),
      body: Stack(
        children: [
          // 页面主内容
          const Center(child: Text('应用主界面')),
          // 带动画的容器
          AnimatedPositioned(
            duration: const Duration(milliseconds: 350),
            curve: Curves.easeOutCubic, // 更自然的滑动曲线
            // 初始位置:完全在屏幕下方外;目标位置:屏幕中央
            left: isContainerVisible ? centerLeft : centerLeft, // 保持水平居中,仅垂直滑动
            top: isContainerVisible ? centerTop : screenSize.height,
            width: containerWidth,
            height: containerHeight,
            child: AnimatedOpacity(
              duration: const Duration(milliseconds: 300),
              opacity: isContainerVisible ? 1.0 : 0.0,
              child: Container(
                decoration: BoxDecoration(
                  color: Colors.white,
                  borderRadius: BorderRadius.circular(16),
                  boxShadow: const [
                    BoxShadow(
                      color: Colors.black38,
                      blurRadius: 10,
                      offset: Offset(0, 4),
                    )
                  ],
                ),
                child: const Center(child: Text('滑入的弹窗容器')),
              ),
            ),
          ),
        ],
      ),
    );
  }
}

关键调整说明

  1. 居中位置计算:通过MediaQuery获取屏幕宽高,减去容器自身尺寸后取一半,得到容器左上角的坐标,确保容器完全居中。
  2. 初始位置设置:将容器初始top值设为screenSize.height,让容器完全隐藏在屏幕下方,滑入时移动到计算好的居中top值。
  3. 水平位置固定:初始和目标状态的left值都设为居中坐标,保证容器仅做垂直方向的滑动,符合“从下方滑入”的需求。
  4. 动画曲线优化:使用Curves.easeOutCubic让滑动动画更流畅自然,避免生硬的线性运动。

内容的提问来源于stack exchange,提问作者Thushan Isuru

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.09 20:50:07