2017-08-29 4 views
3

Kann ich in Flutter etwas ähnliches wie Toasts erstellen? Nur ein kleines Benachrichtigungsfenster, das sich nicht direkt vor dem Benutzer befindet und die Ansicht dahinter nicht blockiert oder verblasst?Wie Toast in Flattern erstellen?

Antwort

8

können Sie den übergeordneten Zugriff ScaffoldState mit Scaffold.of(context)

Dann etwas tun, wie

Scaffold.of(context).showSnackBar(new SnackBar(
     content: new Text("Sending Message"), 
    )); 

Snackbar und Toast sind die gleiche Sache, nach

https://material.io/guidelines/components/snackbars-toasts.html#snackbars-toasts-specs

material.io EDIT:

Ein vollständiges Beispiel (Ich mag, wie ich das in 5 Minuten tat. Liebe Sie flattern)

enter image description here

runApp(new MaterialApp(
    home: new Scaffold(
    appBar: new AppBar(
     title: new Text("Snack bar"), 
    ), 
    body: new ListView.builder(
     itemCount: 42, 
     itemBuilder: (context, index) { 
     return new Card(
      child: new Column(
      children: <Widget>[ 
       new Image.network("https://image.freepik.com/free-vector/unicorn-background-design_1324-79.jpg"), 
       new ListTile(
       title: new Text("Wow"), 
       subtitle: new Text("That's a cool unicorn out there"), 
       trailing: new IconButton(
        icon: const Icon(Icons.star), 
        onPressed:() { 
        Scaffold.of(context).showSnackBar(
          new SnackBar(
          content: new Text("Added to favorite"), 
          action: new SnackBarAction(
           label: "UNDO", 
           onPressed:() => Scaffold.of(context).hideCurrentSnackBar(), 
          ), 
         ), 
         ); 
        }, 
       ), 
      ) 
      ], 
     ), 
     ); 
     }, 
    ), 
), 
)); 
+0

Wie sollte dies zum Beispiel in einem onPressed verpackt werden? weil ich es probiert habe und nichts auf dem Bildschirm erscheint. – aziza

5

SnackBar ist definitiv die richtige Klasse zu verwenden, wie von Darky hingewiesen.

snackbar

Eine heikle Sache über showSnackBar wird immer auf die ScaffoldState, wenn Sie versuchen, showSnackBar innerhalb der Build-Methode aufrufen, wo Sie Ihre Scaffold konstruieren.

Möglicherweise wird ein Fehler wie dieser angezeigt, der einige Erläuterungen zur Lösung des Problems enthält.

══╡ EXCEPTION CAUGHT BY GESTURE ╞═══════════════════════════════════════════════════════════════════ 
The following assertion was thrown while handling a gesture: 
Scaffold.of() called with a context that does not contain a Scaffold. 
No Scaffold ancestor could be found starting from the context that was passed to Scaffold.of(). This 
usually happens when the context provided is from the same StatefulWidget as that whose build 
function actually creates the Scaffold widget being sought. 
There are several ways to avoid this problem. The simplest is to use a Builder to get a context that 
is "under" the Scaffold. For an example of this, please see the documentation for Scaffold.of(): 
    https://docs.flutter.io/flutter/material/Scaffold/of.html 
A more efficient solution is to split your build function into several widgets. This introduces a 
new context from which you can obtain the Scaffold. In this solution, you would have an outer widget 
that creates the Scaffold populated by instances of your new inner widgets, and then in these inner 
widgets you would use Scaffold.of(). 
A less elegant but more expedient solution is assign a GlobalKey to the Scaffold, then use the 
key.currentState property to obtain the ScaffoldState rather than using the Scaffold.of() function. 
The context used was: 
    MyHomePage 
When the exception was thrown, this was the stack: 
#0  Scaffold.of (package:flutter/src/material/scaffold.dart:444:5) 
#1  MyHomePage.build.<anonymous closure> (/Users/jackson/Library/Developer/CoreSimulator/Devices/7072C907-DBAD-44FE-8F40-0257442C51D9/data/Containers/Data/Application/77FEC1A4-1453-442C-8208-96E0323DEFB2/tmp/so_scratch2Tkq9Jb/so_scratch2/lib/main.dart:23:24) 
#2  _InkResponseState._handleTap (package:flutter/src/material/ink_well.dart:323:14) 
#3  _InkResponseState.build.<anonymous closure> (package:flutter/src/material/ink_well.dart:375:30) 
#4  GestureRecognizer.invokeCallback (package:flutter/src/gestures/recognizer.dart:102:24) 
#5  TapGestureRecognizer._checkUp (package:flutter/src/gestures/tap.dart:149:9) 
#6  TapGestureRecognizer.acceptGesture (package:flutter/src/gestures/tap.dart:119:7) 
#7  GestureArenaManager.sweep (package:flutter/src/gestures/arena.dart:156:27) 
#8  BindingBase&SchedulerBinding&GestureBinding.handleEvent (package:flutter/src/gestures/binding.dart:147:20) 
#9  BindingBase&SchedulerBinding&GestureBinding.dispatchEvent (package:flutter/src/gestures/binding.dart:121:22) 
#10  BindingBase&SchedulerBinding&GestureBinding._handlePointerEvent (package:flutter/src/gestures/binding.dart:101:7) 
#11  BindingBase&SchedulerBinding&GestureBinding._flushPointerEventQueue (package:flutter/src/gestures/binding.dart:64:7) 
#12  BindingBase&SchedulerBinding&GestureBinding._handlePointerDataPacket (package:flutter/src/gestures/binding.dart:48:7) 
#13  _invoke1 (file:///b/build/slave/Mac_Engine/build/src/flutter/lib/ui/hooks.dart:100) 
#14  _dispatchPointerDataPacket (file:///b/build/slave/Mac_Engine/build/src/flutter/lib/ui/hooks.dart:58) 
Handler: onTap 
Recognizer: 
    TapGestureRecognizer#69dbc(debugOwner: GestureDetector, state: ready) 
════════════════════════════════════════════════════════════════════════════════════════════════════ 

Sie können entweder ein GlobalKey zu Ihrem Scaffold Konstruktor übergeben:

class MyHomePage extends StatelessWidget { 
    @override 
    Widget build(BuildContext context) { 
    final key = new GlobalKey<ScaffoldState>(); 
    return new Scaffold(
     key: key, 
     floatingActionButton: new Builder(
     builder: (BuildContext context) { 
      return new FloatingActionButton(
      onPressed:() { 
       key.currentState.showSnackBar(new SnackBar(
       content: new Text("Sending Message"), 
      )); 
      }, 
      tooltip: 'Increment', 
      child: new Icon(Icons.add), 
     ); 
     } 
    ), 
    ); 
    } 
} 

Oder Sie Builder verwenden können eine BuildContext zu schaffen, das ein Kind des Gerüsts ist.

Schließlich könnten Sie Ihr Widget in mehrere Klassen aufteilen, was der beste langfristige Ansatz ist.

+0

Versuchte GlobalKey, jetzt bekomme ich diese Ausnahme: 'I/Flattern (4965): Die folgende Zusicherung wurde während der Behandlung einer Geste geworfen: I/flutter (4965): Typ 'LabeledGlobalKey ' ist kein Subtyp vom Typ 'BuildContext' von 'Kontext' wo ich/flutter (4965): LabeledGlobalKey ist aus Paket: Flattern/src/widgets/framework.dart ich/flattern (4965): ScaffoldState ist aus Paket: flutter/src/Material /scaffold.dart I/flattern (4965): Scaffold ist aus Paket: Flattern/src/material/scaffold.dart I/Flattern (4965): BuildContext ist aus Paket: flutter/src/widgets/framework.dart' –

+0

Es sieht so aus, als ob Sie einen 'GlobalKey' als Argument verwenden, bei dem ein' BuildContext' erwartet wird. Ich kann dir nicht helfen, dies weiter zu debuggen, ohne mehr von deinem Code zu sehen. Schreiben Sie die Codezeile, die die Ausnahme auslöst, wahrscheinlich verwenden Sie nicht die richtigen Argumente. –