MohammedAli
MohammedAli

Reputation: 2519

how to Create and Use SnackBar for ReUse(Globally) in Flutter

i want create SnackBar for reusable(globally)

i already created but its only for 1 page , i don't know how to create reusable.

below code:

import 'package:flutter/material.dart';

class SnackBarMain extends StatefulWidget {
  @override
  _SnackBarMainState createState() => _SnackBarMainState();
}

class _SnackBarMainState extends State<SnackBarMain> {
  final globalKey = GlobalKey<ScaffoldState>();
  String title = 'SnackBar';

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      key: globalKey,
      resizeToAvoidBottomPadding: false,
      appBar: AppBar(
        centerTitle: true,
        title: Text(title),
      ),
      body: Center(
        child: RaisedButton(
          shape: new RoundedRectangleBorder(
              borderRadius: new BorderRadius.circular(18.0),
              side: BorderSide(color: Colors.purple)),
          onPressed: () => snackBarMsg(context),
          color: Colors.purple,
          textColor: Colors.white,
          child: Text("SnackBar",
              style: TextStyle(fontSize: 18)),
        ),
      ),
    );
  }

snackBarMsg(BuildContext context) {
    final sb = SnackBar(
      elevation: 0.0,
      //behavior: SnackBarBehavior.floating,
      content: Text('SnackBar Bottom Message'),
      duration: new Duration(seconds: 5000000),
      shape: RoundedRectangleBorder(
        borderRadius: BorderRadius.only(
            topLeft: Radius.circular(16.0), topRight: Radius.circular(16.0)),
      ),
      //backgroundColor: Colors.redAccent,
      action: SnackBarAction(
        textColor: Color(0xFFFAF2FB),
        label: 'OK',
        onPressed: () {},
      ),
    );
    globalKey.currentState.showSnackBar(sb);
  }
}

so any one please give me example for this

Upvotes: 10

Views: 13051

Answers (6)

Anuj Kumar
Anuj Kumar

Reputation: 21

I suggest you try to build a Extension like that then your problem will be solve if you try to create a widget for that then you face some problems so try to use extension Output will be look like this

 extension SnackBarExt on BuildContext {
  void fluidSnackBar(String message) {
    ScaffoldMessenger.of(this)
      ..hideCurrentSnackBar()
      ..showSnackBar(SnackBar(
          behavior: SnackBarBehavior.floating,
          margin: const EdgeInsets.all(Dimension.d4),
          shape: RoundedRectangleBorder(
              borderRadius: BorderRadius.circular(Dimension.d1)),
          backgroundColor: secondarySwatch.shade800,
          duration: const Duration(seconds: 4),
          padding: const EdgeInsets.symmetric(
              vertical: Dimension.d3, horizontal: Dimension.d4),
          content: Text(message,
              style: fluidTextStyles.caption.colored(secondarySwatch.shade25),
              overflow: TextOverflow.ellipsis)));
  }

Upvotes: 0

Michael Stephen
Michael Stephen

Reputation: 81

you can create a public snackbar class like this

//=========================================================
// PUBLIC SNACK BAR WIDGET
//=========================================================
class PublicSnackBar extends SnackBar {
  const PublicSnackBar({Key? key, required super.content}) : super(key: key);
}

and call it in any pages or files in the project, tho I am using public context here.

 ScaffoldMessenger.of(navigatorKey.currentContext as BuildContext)
        .showSnackBar(PublicSnackBar(content: Text('$result')));

this is my public context, just in case you were wondering,

//=========================================================================
// NAVIGATING WITH OUT CONTEXT
//=========================================================================
final GlobalKey<NavigatorState> navigatorKey = GlobalKey<NavigatorState>();

Upvotes: 0

Rahul Kushwaha
Rahul Kushwaha

Reputation: 6722

Scaffold.of(context).showSnackbar is deprecated now. You should use ScaffoldMessenger instead. Use like this:-

ScaffoldMessenger.of(context).showSnackBar(SnackBar(
          content: Text('User Successfully Logged In...'),
        ));

Upvotes: 3

Mateen
Mateen

Reputation: 448

Just create a public class and put your custom functions inside, here you go for example:

//Custom class in project directory
class CustomWidgets {
 CustomWidgets._();
 static buildErrorSnackbar(BuildContext context, String message) {
  Scaffold.of(context)
     .showSnackBar(
    SnackBar(
      content: Text("$message"),
    ),
  );
 }
}

 // This is any page in your project

class _MyHomePageState extends State<MyHomePage> {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
     backgroundColor: Colors.white,
      //        Always create body with Builder method so you can 
      //        get exact context to pass
      body: Builder(
      builder: (context) =>
          Center(
              child: RaisedButton(
              color: Colors.pink,
              textColor: Colors.white,
              onPressed: (){
                CustomWidgets.buildErrorSnackbar(context,"Your message here");
              },
              child: Text('Display SnackBar'),
          ),
         ),
     ),
  );
 }
}

Upvotes: 17

Sebastian
Sebastian

Reputation: 3894

You can have a class that has a static method show() which receives the context and shows a snackbar. Check te code below.

class GlobalSnackBar {
  final String message;

  const GlobalSnackBar({
    @required this.message,
  });

  static show(
    BuildContext context,
    String message,
  ) {
    Scaffold.of(context).showSnackBar(
      SnackBar(
        elevation: 0.0,
        //behavior: SnackBarBehavior.floating,
        content: Text(message),
        duration: new Duration(seconds: 5000000),
        shape: RoundedRectangleBorder(
          borderRadius: BorderRadius.only(
              topLeft: Radius.circular(16.0), topRight: Radius.circular(16.0)),
        ),
        //backgroundColor: Colors.redAccent,
        action: SnackBarAction(
          textColor: Color(0xFFFAF2FB),
          label: 'OK',
          onPressed: () {},
        ),
      ),
    );
  }
}

And you can call it from anywhere like this:

class MyWidget extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return RaisedButton(
      child: Text('SHOW Snackbar'),
      onPressed: () => GlobalSnackBar.show(context, 'Test'),
    );
  }
}

Remember that the context you pass to show() method has to be a descendant from Scaffold in order to show the SnackBar

Upvotes: 21

drogel
drogel

Reputation: 2717

You can use the Snackbar you have already defined to reuse it everywhere by putting it in a public folder, that can be accessed from anywhere in your app. You don't need to enclose it inside a widget or a class. Then, you can show it by calling Scaffold.of(context).showSnackBar(...). For that, you will need to pass the current BuildContext, of course. This way, as long as the context from which you call showSnackBar has a parent Scaffold, the snackbar will be shown for your current page, and you can do this from anywhere.

Consider this example, that I myself have used in the past:

  void buildErrorSnackbar(BuildContext context) {
    Scaffold.of(context).showSnackBar(
      SnackBar(
        content: Text("Oops! Something went wrong."),
      ),
    );
  }

Upvotes: 0

Related Questions