質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.46%
Flutter

Flutterは、iOSとAndroidのアプリを同じコードで開発するためのフレームワークです。オープンソースで開発言語はDart。双方のプラットフォームにおける高度な実行パフォーマンスと開発効率を提供することを目的としています。

Dart

Dartは、Googleによって開発されたJavaScriptの代替となることを目的に作られた、ウェブ向けのプログラミング言語である。

Q&A

解決済

1回答

2832閲覧

【Flutter】ダイアログの中のラジオボタンが効かない

Yariii

総合スコア61

Flutter

Flutterは、iOSとAndroidのアプリを同じコードで開発するためのフレームワークです。オープンソースで開発言語はDart。双方のプラットフォームにおける高度な実行パフォーマンスと開発効率を提供することを目的としています。

Dart

Dartは、Googleによって開発されたJavaScriptの代替となることを目的に作られた、ウェブ向けのプログラミング言語である。

0グッド

0クリップ

投稿2020/09/24 08:41

こんにちは。
現在、予約機能UIを作っています。
ラジオボタンで予約時間を選択できて、
「4時間以上」を選択すると、ダイアログでそれ以上の選択肢を選んでもらう仕様です。

添付写真は、現在のコードで出力されたものです。
「4時間以上」を選択した際に、下に現れるボタンを押すと、ダイアログが出てくる仕様で考えています。
その下に現れるボタンには、ダイアログで選択した値がテキスト出力されています。!
イメージ説明
イメージ説明

しかし、現状ではダイアログ内のラジオを選択しても、タップ反応(一瞬灰色になる)はあるのですが、チェック色が変わらず、ラジオの値もボタンに反映されない状態です。

flutter

1 final List sortTime = ['1時間', '2時間', '3時間', '4時間以上']; 2 3 bool _inputTime = false; 4 //ここにチェックされた選択肢を入れる 5 String sortTimeChecked = ""; 6 List<Widget> get _sortTimeList { 7 List<Widget> sortTimeCheckedList = List(); 8 sortTime.forEach((item) { 9 sortTimeCheckedList.add(Container( 10 margin: const EdgeInsets.symmetric(horizontal: 4.0), 11 child: item != '4時間以上' 12 ? ChoiceChip( 13 labelPadding: EdgeInsets.symmetric(vertical: 4), 14 padding: EdgeInsets.only(left: 12, right: 12), 15 label: Text(item), 16 shape: RoundedRectangleBorder( 17 borderRadius: BorderRadius.circular(8.0)), 18 selected: sortTimeChecked == item, // 判定 19 onSelected: (selected) { 20 setState(() { 21 sortTimeChecked = item; // 代入 22 _inputTime = false; 23 }); 24 }, 25 ) 26 : ChoiceChip( 27 labelPadding: EdgeInsets.symmetric(vertical: 4), 28 padding: EdgeInsets.only(left: 12, right: 12), 29 label: Text(item), 30 shape: RoundedRectangleBorder( 31 borderRadius: BorderRadius.circular(8.0)), 32 selected: sortTimeChecked == item, // 判定 33 onSelected: (selected) { 34 setState(() { 35 sortTimeChecked = item; // 代入 36 _inputTime = true; 37 }); 38 }, 39 ))); 40 }); 41 return sortTimeCheckedList; 42 } 43 44 List<String> sortTimeOthers = ['4時間', '5時間', '6時間', '7時間', '8時間', '9時間']; 45 String _currentIndex = '4時間'; 46 Future _selectsortTimeOthers() async { 47 await showDialog( 48 context: context, 49 builder: (BuildContext context) => new AlertDialog( 50 title: Text(''), 51 actions: <Widget>[ 52 FlatButton( 53 onPressed: () { 54 Navigator.pop(context, null); 55 }, 56 child: Text('CANCEL'), 57 ), 58 FlatButton( 59 onPressed: () { 60 Navigator.pop(context, sortTimeOthers); 61 }, 62 child: Text('OK'), 63 ), 64 ], 65 content: Container( 66 width: double.minPositive, 67 height: 300, 68 child: ListView.builder( 69 shrinkWrap: true, 70 itemCount: sortTimeOthers.length, 71 itemBuilder: (BuildContext context, int index) { 72 return RadioListTile( 73 value: index, 74 activeColor: Colors.blue, 75 groupValue: _currentIndex, 76 title: Text(sortTimeOthers[index]), 77 onChanged: (val) { 78 setState(() { 79 print(index); 80 _currentIndex = val; 81 }); 82 }, 83 ); 84 }, 85 ), 86 ), 87 ), 88 ); 89 } 90 91 Widget sortTimeWidget() { 92 return Column( 93 crossAxisAlignment: CrossAxisAlignment.start, 94 children: [ 95 Wrap( 96 direction: Axis.horizontal, 97 alignment: WrapAlignment.start, 98 children: _sortTimeList, 99 ), 100 _inputTime == true 101 ? OutlineButton( 102 color: Colors.white, 103 disabledBorderColor: Colors.black, 104 onPressed: () { 105 _selectsortTimeOthers(); 106 }, 107 child: Text(_currentIndex), 108 ) 109 : Container(), 110 ], 111 ); 112 } 113

参考サイトは以下です
https://androidkt.com/display-auto-size-alertdialog-with-listview-in-flutter-simple-list-checkbox-list-radio-button-list/

参考から試行錯誤していろいろいじったので、若干違うところが多々あるかと思いますが...

原因がわからず、対処方法をご教授いただければ嬉しいです。
よろしくお願いいたします。

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答1

0

ベストアンサー

質問内のコードだとint型とString型のミスマッチが起きていたので、まずこれを直す必要があります。

diff

1 return RadioListTile<String>( 2- value: index, 3+ value: sortTimeOthers[index], 4 activeColor: Colors.blue, 5 groupValue: _currentIndex, 6 title: Text(sortTimeOthers[index]), 7 onChanged: (val) { 8 setState(() { 9 print(index); 10 _currentIndex = val; 11 }); 12 }, 13 ); 14

次に、チェックを画面に反映させるため、タイルが選択された時にダイアログの中身を更新してやる必要があります。

質問内のコードでも、onChangedの中でsetStateが使われているのですが、これは元ページのsetStateなので、ダイアログの中身は更新されません。

この問題を解決するために、参考リンクのコードではStatefulBuilderというウィジェットが使われていました。
自分も今初めて知ったくらいマイナーなウィジェットですが、これを使うと、以下のようになります。
ちゃんと動くか分かりませんが、一度試してみてください。

dart

1 Future _selectsortTimeOthers() async { 2 await showDialog( 3 context: context, 4 builder: (BuildContext context) { 5 return StatefulBuilder( 6 builder: (context, setState) { 7 return AlertDialog( 8 title: Text(''), 9 actions: <Widget>[ 10 FlatButton( 11 onPressed: () { 12 Navigator.pop(context, null); 13 }, 14 child: Text('CANCEL'), 15 ), 16 FlatButton( 17 onPressed: () { 18 Navigator.pop(context, sortTimeOthers); 19 }, 20 child: Text('OK'), 21 ), 22 ], 23 content: Container( 24 width: double.minPositive, 25 height: 300, 26 child: ListView.builder( 27 shrinkWrap: true, 28 itemCount: sortTimeOthers.length, 29 itemBuilder: (BuildContext context, int index) { 30 return RadioListTile<String>( 31 value: sortTimeOthers[index], 32 activeColor: Colors.blue, 33 groupValue: _currentIndex, 34 title: Text(sortTimeOthers[index]), 35 onChanged: (val) { 36 // ダイアログを更新 37 setState(() { 38 print(index); 39 _currentIndex = val; 40 }); 41 }, 42 ); 43 }, 44 ), 45 ), 46 ); 47 }, 48 ); 49 }, 50 ); 51 52 // 元ページを更新 (場合によっては`onChanged`の中に書くのもアリかも) 53 setState(() {}); 54 } 55

投稿2020/09/24 10:57

nskhei

総合スコア704

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

Yariii

2020/09/24 12:40 編集

ご回答ありがとうございます。 おかげさまでラジオボタン選択できるようになりました。ありがとうございます! 1点だけ、ダイヤログの「OK」を押したら、値が反映されず、「OK」→ダイアログ消える→「4時間以上」をもう一度押したら、ダイアログの値に更新されるという動きになりました。 「OK」のonPressedに仕掛けが必要だと思うのですが、 参考サイトでは「OK」のonPressedに Navigator.pop(context, sortTimeOthers[_currentIndex]); と表記があり、入れてみたところ_currentIndexがあることでエラーになってしまいます。↓ The argument type 'String' can't be assigned to the parameter type 'int'. ここはどのようにすれば反映されますでしょうか?
nskhei

2020/09/24 13:00

> Navigator.pop(context, sortTimeOthers[_currentIndex]); と表記があり、入れてみたところ_currentIndexがあることでエラーになってしまいます。 これは、String型である_currentIndexという値を配列の添字に使おうとしたためだと思います。 ですが、今のコードだとこの部分は関係ないと思います。
nskhei

2020/09/24 13:02

値が反映されない理由は分からないです...。 もしかしたら、質問のコードで省かれている部分が原因かもしれません。 あと、回答のコードの一番下のsetStateがちゃんと書かれているか確認してください。
Yariii

2020/09/24 13:53

すみません、別箇所のバグでホットリロードが効いていなかったのが原因でした。~ ~; ですので今回も無事解決できました、ありがとうございました...!
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.46%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問