修改Flutter Snackbar的位置

32
我想在按钮上方显示一个简单的错误消息,当某些条件不满足时。似乎Flutter的Snackbar非常适合这种用途。
然而,我很难改变Snackbar的位置,使其不是在屏幕底部。这种情况可能吗?如果不行,是否有更适合此目的的Widget?
我当前的Snackbar代码:
class ContinueButton extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Container(
      margin: const EdgeInsets.only(
          bottom: 24.0, top: 24.0),
      child: Align(
        alignment: FractionalOffset.bottomCenter,
        child: MaterialButton(
          onPressed: () {
            final snackBar = SnackBar(
              content: Text('Yay! A SnackBar!'),
            );
            Scaffold.of(context).showSnackBar(snackBar);
          },

          child: Text('Continue'),
          height: 40.0,
          minWidth: 300.0,
          color: Colors.greenAccent,
        ),
      ),
    );
  }
}
8个回答

25

您可以尝试通过将行为设置为SnackBarBehavior.floating并根据需要设置边距来实现。

SnackBar(
  behavior: SnackBarBehavior.floating,
  margin: EdgeInsets.only(bottom: 100.0),
  content: Text("Hello World!"),
);

这种解决方案唯一的问题是,下面的所有内容都不可点击

为了解决这个可点击的问题,请将 dismissDirection 属性设置为 DismissDirection.none。 这也意味着 snackbar 的默认属性可以通过向下拖动来解除消失已经丢失。(默认是DismissDirection.down

SnackBar(
  behavior: SnackBarBehavior.floating,
  margin: EdgeInsets.only(bottom: 100.0),
  content: Text("Hello World!"),
  dismissDirection: DismissDirection.none
);

8
这个解决方案唯一的问题是,下面的所有内容都无法点击。 - Alberto M
1
这是一个大问题... - genericUser

7
您可以通过在Snackbar内放置一个容器来实现这一点。由于Snackbar可以使用任何小部件并且您可以将其背景颜色更改为透明,因此您可以使用具有自定义填充和边框的容器来提供定位的假象。
SnackBar(content: Container(
  //color: Colors.white,
  decoration: BoxDecoration(color: Colors.white, border: Border.all(width: 2.0, color: Colors.black), borderRadius: BorderRadius.circular(20)),
  margin: EdgeInsets.fromLTRB(0, 0, 0, 75),
  child: Padding(
    padding: const EdgeInsets.all(8.0),
    child: Text('Yay! A SnackBar!'),
  ),
), backgroundColor: Colors.transparent, elevation: 1000, behavior: SnackBarBehavior.floating,);

3


1
你可以使用Flushbar代替SnackBar 查看更多详细信息,请访问flushbar 注意:它已在2022年停止使用

2
由于该插件已停止更新,您可能需要查看another_flushbar - Osman

1

这对我很有用:

您可以使用“Align”来包装您的容器。

SnackBar(
    content: GestureDetector(
      onTap: () {
        controller?.close();
      },
      child: Align(
        alignment: Alignment.topCenter,
        child: Container( ........

1
我需要在屏幕顶部添加SnackBar,经过了很多搜索,我终于在这里找到了一个,并且会分享给其他需要在顶部添加SnackBar的人。
我是这样做的:
final snackBar = SnackBar(
      showCloseIcon: true,
      closeIconColor: Colors.white,
      content: Text('your text', textAlign: TextAlign.center),
      dismissDirection: DismissDirection.up,
      behavior: SnackBarBehavior.floating,
      shape: RoundedRectangleBorder(
        borderRadius: BorderRadius.circular(10.0),
      ),
      margin: EdgeInsets.only(
          bottom: MediaQuery.of(context).size.height - 70, left: 10, right: 10),
    );
    ScaffoldMessenger.of(context).showSnackBar(snackBar);

一个重要的注意事项是,这个 SnackBar 将出现在所有屏幕的顶部,意味着下面的屏幕将无法点击,所以您必须等待 SnackBar 消失或关闭它。根据我所有的研究,我无法仅通过在这个位置使用 SnackBar 来使下面的屏幕可点击,只有通过使用该软件包才能实现。

0

虽然有点晚了,但是可以使用ScaffoldMessenger来控制位置。请参见https://docs.flutter.dev/release/breaking-changes/scaffold-messenger

不要使用

ScaffoldMessenger.of(context).showSnackBar(snackBar);

然后,您可以使用 ScaffoldMesseneger 将已在 UI 中定位的 Scaffold 包装起来,并为其提供一个键。使用此键来显示 snackBar:

final key = GlobalKey<ScaffoldMessengerState>();
ScaffoldMessenger(
      key: key,
      child: Scaffold(
        body: ...
...
key.currentState?.showSnackBar(snackBar);

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接