2017-10-20 47 views
2

J'essaie de créer un SimpleDialog qui permet à l'utilisateur d'entrer son nom. Mais quand il est affiché la boîte de dialogue est à moitié cachée par le clavier à l'écran:Afficher une boîte de dialogue de champ de texte sans être couvert par le clavier?

Screenshot

Comment puis-je obtenir le Dialog d'être pleinement visible? Edit: Je trouve étrange que le widget de la page d'accueil (FocusVisibilityDemo) reconnaît la hauteur réduite et ajuste donc la position du bouton «Push Me» pour rester au centre. Malheureusement, le dialogue ne se comporte pas de la même manière.

Voici mon code:

import 'package:flutter/material.dart'; 

class FocusVisibilityDemo extends StatefulWidget { 
    @override 
    _FocusVisibilityDemoState createState() => new _FocusVisibilityDemoState(); 
} 

class _FocusVisibilityDemoState extends State<FocusVisibilityDemo> { 
    @override 
    Widget build(BuildContext context) { 
    return new Scaffold(
     appBar: new AppBar(title: new Text('Text Dialog Demo')), 
     body: new Center(
     child: new RaisedButton(
      onPressed: _showDialog, 
      child: new Text("Push Me"), 
     ), 
    ), 
    ); 
    } 

    _showDialog() async { 
    await showDialog<String>(
     context: context, 
     child: new AlertDialog(
     contentPadding: const EdgeInsets.all(16.0), 
     content: new Row(
      children: <Widget>[ 
      new Expanded(
       child: new TextField(
       autofocus: true, 
       decoration: new InputDecoration(
        labelText: 'Full Name', hintText: 'eg. John Smith'), 
      ), 
      ) 
      ], 
     ), 
     actions: <Widget>[ 
      new FlatButton(
       child: const Text('CANCEL'), 
       onPressed:() { 
       Navigator.pop(context); 
       }), 
      new FlatButton(
       child: const Text('OPEN'), 
       onPressed:() { 
       Navigator.pop(context); 
       }) 
     ], 
    ), 
    ); 
    } 
} 

void main() { 
    runApp(new MaterialApp(home: new FocusVisibilityDemo())); 
} 
+0

Vous pouvez utiliser un typage plein écran dans ce cas. – Darky

Répondre

2

Si votre cas d'utilisation est d'ajouter plusieurs TextFields dans votre Dialog afin que votre principale Form ne beaucoup de monde, je ne crois pas qu'il vaut mieux si vous construisez quelque chose de plus personnalisable que AlertDialog et SimpleDialog car ils sont utilisés pour des activités simples (confirmations, radios..etc).

Sinon, pourquoi voulez-vous utiliser un Dialog pour un seul TextField?

Lorsque nous ajoutons plusieurs TextField s nous devons faire attention à nos choix de conception puisque d'autres personnes vont interagir avec ce point de vue de remplir les données, dans ce cas, je préfère utiliser fullscreenDialog propriété de PageRoute classe. Je ne suis pas sûr si SimpleDialog peut être adapté à cela dans Flutter.

Voici un exemple rapide sur la façon d'utiliser un FullScreenDialog, j'espère que cette aide et vous devriez être en mesure de modifier la façon dont vous voulez:

import 'package:flutter/material.dart'; 


void main() { 
    runApp(new MaterialApp(home: new MyApp(),)); 
} 

class MyApp extends StatefulWidget { 
    @override 
    MyAppState createState() => new MyAppState(); 
} 

class MyAppState extends State<MyApp> { 
    FullScreenDialog _myDialog = new FullScreenDialog(); 

    @override 
    Widget build(BuildContext context) { 
    return new Scaffold(
     appBar: new AppBar(
      title: new Text("Fill this form"), 
     ), 
     body: new Column(
      children: <Widget>[ 
      new TextField(controller: new TextEditingController(
       text: "Add a single text field"),), 

      new Card(child: new ListTile(
       title: new Text("Click to add your top 3 amazing skills"), 
       subtitle: new Text(
        "${_myDialog._skillOne} ${_myDialog._skillTwo} ${_myDialog 
         ._skillThree}"), 
       onTap:() { 
       Navigator.push(context, new MaterialPageRoute(
        builder: (BuildContext context) => _myDialog, 
        fullscreenDialog: true, 
       )); 
       }, 
      ), 
      ), 
      ], 
     ) 
    ); 
    } 

} 


class FullScreenDialog extends StatefulWidget { 
    String _skillOne = "You have"; 
    String _skillTwo = "not Added"; 
    String _skillThree = "any skills yet"; 

    @override 
    FullScreenDialogState createState() => new FullScreenDialogState(); 
} 

class FullScreenDialogState extends State<FullScreenDialog> { 
    TextEditingController _skillOneController = new TextEditingController(); 
    TextEditingController _skillTwoController = new TextEditingController(); 

    TextEditingController _skillThreeController = new TextEditingController(); 

    @override 
    Widget build(BuildContext context) { 
    return new Scaffold(
     appBar: new AppBar(
      title: new Text("Add your top 3 skills"), 
     ), 
     body: new Padding(child: new ListView(
      children: <Widget>[ 
      new TextField(controller: _skillOneController,), 
      new TextField(controller: _skillTwoController,), 
      new TextField(controller: _skillThreeController,), 
      new Row(
       children: <Widget>[ 
       new Expanded(child: new RaisedButton(onPressed:() { 
        widget._skillThree = _skillThreeController.text; 
        widget._skillTwo = _skillTwoController.text; 
        widget._skillOne = _skillOneController.text; 
        Navigator.pop(context); 
       }, child: new Text("Save"),)) 
       ], 
      ) 
      ], 
     ), padding: const EdgeInsets.symmetric(horizontal: 20.0),) 
    ); 
    } 


} 

EDIT

Après avoir fait quelques recherche, il semble que this is a bug dans la version actuelle de Flutter, la solution temporaire est également documentée dans ce numéro.

enter image description here

import 'package:flutter/material.dart'; 

void main() { 
    runApp(new MaterialApp(home: new FocusVisibilityDemo())); 
} 

class FocusVisibilityDemo extends StatefulWidget { 
    @override 
    _FocusVisibilityDemoState createState() => new _FocusVisibilityDemoState(); 
} 


class _FocusVisibilityDemoState extends State<FocusVisibilityDemo> { 
    @override 
    Widget build(BuildContext context) { 
    return new Scaffold(
     appBar: new AppBar(title: new Text('Text Dialog Demo')), 
     body: new Center(
     child: new RaisedButton(
      onPressed: _showDialog, 
      child: new Text("Push Me"), 
     ), 
    ), 
    ); 
    } 

    _showDialog() async { 
    await showDialog<String>(
     context: context, 
     child: new _SystemPadding(child: new AlertDialog(
     contentPadding: const EdgeInsets.all(16.0), 
     content: new Row(
      children: <Widget>[ 
      new Expanded(
       child: new TextField(
       autofocus: true, 
       decoration: new InputDecoration(
        labelText: 'Full Name', hintText: 'eg. John Smith'), 
      ), 
      ) 
      ], 
     ), 
     actions: <Widget>[ 
      new FlatButton(
       child: const Text('CANCEL'), 
       onPressed:() { 
       Navigator.pop(context); 
       }), 
      new FlatButton(
       child: const Text('OPEN'), 
       onPressed:() { 
       Navigator.pop(context); 
       }) 
     ], 
    ),), 
    ); 
    } 
} 


class _SystemPadding extends StatelessWidget { 
    final Widget child; 

    _SystemPadding({Key key, this.child}) : super(key: key); 

    @override 
    Widget build(BuildContext context) { 
    var mediaQuery = MediaQuery.of(context); 
    return new AnimatedContainer(
     padding: mediaQuery.padding, 
     duration: const Duration(milliseconds: 300), 
     child: child); 
    } 
} 
+0

Non Je ne veux pas ajouter plusieurs champs de texte - Je veux simplement que l'utilisateur entre une valeur de texte. Un dialogue est approprié dans mon cas car il garde l'écran propre et minimal. Laissez-moi vous expliquer: imaginez un écran d'accueil pour un jeu qui a deux boutons: «Créer une nouvelle partie» et «Accéder à un jeu partagé». Lorsque l'utilisateur clique sur le second bouton, l'application demande à l'utilisateur de taper l'identifiant unique du jeu auquel l'utilisateur souhaite accéder. – Mark

+0

Mon mauvais, j'ai trouvé cela émis comme un bug, vérifiez la section éditée dans la réponse. – aziza

+0

Merci - la solution de contournement _SystemPadding fonctionne bien pour moi! – Mark