在脚手架中使用动画在 PageView 页面上使用 Flutter 切换 FAB

Flutter Switching FAB on PageView Pages with animation in Scaffold

因此,我已经查看了几个地方以了解应该如何实现它,我确定我遗漏了一些微不足道的东西,但我有一个 flutter 应用程序,其主体是一个 PageView 的脚手架。我需要为某些页面设置不同的 FAB,目前的设置方式是将脚手架的 floatingActionButton 属性设置为访问 FloatingActionButtons 数组,索引为 _currentPageIndex(由 bottomNavBar 和 _pageController 共享的私有变量。

这会突然更改 FAB,这不是所需的行为。

我正在尝试让 FAB 在页面发生变化(如 material spec:

时动画化(扩展和缩减)

Tabbed Screens When tabs are present, the FAB should briefly disappear, then >reappear when the new content moves into place. This expresses >that the FAB is not connected to any particular tab.

对于如何简单地实施它的任何建议,我将不胜感激(我很确定我遗漏了一些微不足道的东西)。另一种方法是通过将 FAB 包裹在某种东西中来手动制作 FAB 的进出动画。

您可以尝试使用像这样的 AnimatedCrossFade 小部件:

        class TestingNewWidgetState extends State<TestingNewWidget> {
          int currentIndex = 0;

          @override
          Widget build(BuildContext context) {
            return Scaffold(
              floatingActionButton: AnimatedCrossFade(
                crossFadeState: currentIndex == 0
                    ? CrossFadeState.showFirst
                    : CrossFadeState.showSecond,
                duration: Duration(seconds: 1),
                firstChild: FloatingActionButton(
                  onPressed: () => null,
                  child: Icon(Icons.arrow_left),
                  backgroundColor: Colors.red,
                ),
                secondChild: FloatingActionButton(
                  onPressed: () => null,
                  child: Icon(Icons.arrow_right),
                  backgroundColor: Colors.blue,
                ),
              ),
              body: PageView(
                onPageChanged: (index) {
                  setState(() {
                    currentIndex = index;
                  });
                },
                children: <Widget>[
                  Scaffold(
                    body: Center(
                      child: Text("page 1"),
                    ),
                  ),
                  Scaffold(
                    body: Center(
                      child: Text("page 2"),
                    ),
                  ),
                ],
              ),
            );
          }
        }

更新

请记住,您可以创建自己的小部件,这是一个使用自定义 FloatingActionButton 的示例:

        class TestingNewWidgetState extends State<TestingNewWidget> {
          int currentIndex = 0;

          @override
          Widget build(BuildContext context) {
            var customFabButton;
            if (currentIndex == 0) {
              customFabButton = CustomFabButton(
                color: Colors.red,
                onPressed: () => null,
                icon: Icons.alarm,
              );
            } else if (currentIndex == 1) {
              customFabButton = CustomFabButton(
                color: Colors.blue,
                onPressed: () => null,
                icon: Icons.satellite,
              );
            } else {
              customFabButton = CustomFabButton(
                color: Colors.green,
                onPressed: () => null,
                icon: Icons.verified_user,
              );
            }

            return Scaffold(
              floatingActionButton: customFabButton,
              body: PageView(
                onPageChanged: (index) {
                  setState(() {
                    currentIndex = index;
                  });
                },
                children: <Widget>[
                  Scaffold(
                    body: Center(
                      child: Text("page 1"),
                    ),
                  ),
                  Scaffold(
                    body: Center(
                      child: Text("page 2"),
                    ),
                  ),
                  Scaffold(
                    body: Center(
                      child: Text("page 3"),
                    ),
                  ),
                ],
              ),
            );
          }
        }

        class CustomFabButton extends StatelessWidget {
          final IconData icon;
          final Color color;
          final VoidCallback onPressed;

          const CustomFabButton({Key key, this.icon, this.color, this.onPressed})
              : super(key: key);

          @override
          Widget build(BuildContext context) {
            return GestureDetector(
              onTap: onPressed,
              child: AnimatedContainer(
                decoration: BoxDecoration(
                  shape: BoxShape.circle,
                  color: color,
                ),
                duration: Duration(seconds: 1),
                height: 50.0,
                width: 50.0,
                child: Icon(icon),
              ),
            );
          }
        }