簡體   English   中英

如何解決 flutter dropdownButtonFormField 動態選擇檢查 dropdownButton 的值

[英]How to resolve flutter dropdownButtonFormField dynamic selection checking for dropdownButton's value

我試圖詢問用戶 select 第一個下拉列表中的項目類型,然后 select 在第二個下拉列表中相應的可用顏色。 但是,當我選擇了一種顏色(即白色)后,現在想要切換到另一個沒有這種顏色的項目時,會拋出一個錯誤:

"There should be exactly one item with [DropdownButton]'s value: white. \nEither zero or 2 or more
[DropdownMenuItem]s were detected with the same value"

請幫忙,我已經嘗試在不同的地方設置狀態來更新值,但這個錯誤仍然發生。

以下是我的代碼片段:

StreamBuilder<QuerySnapshot>(
    stream: mainItemsSnapshots,
    builder: (context, snapshot) {
    if (snapshot.hasError) return Text("Error");
    switch (snapshot.connectionState) {
        case ConnectionState.waiting:
        return Center(child: CircularProgressIndicator());
        default:
        {
            List<DropdownMenuItem> dropdownMenuItems =
                snapshot.data.documents
                    .map((DocumentSnapshot mainItem) {
            return new DropdownMenuItem<String>(
                value: mainItem.documentID,
                child: Text(mainItem.documentID),
            );
            }).toList();
            return DropdownButtonFormField<String>(
            items: dropdownMenuItems,
            onChanged: (String value) {
                if (value != tempMainItemType) {
                    setState(() {
                    tempMainItemType = value;
                    tempItemColorsList.clear();
                    tempItemColorsList = [];
                    tempMainItemColor = null;
                    });
                }
                
                if (tempItemColorsList.isEmpty && value != null) {
                tempItemColorsList = snapshot.data.documents
                    .where((element) => element.documentID == value)
                    .first
                    .data["colors"]
                    .keys
                    .map((color) => color.toString())
                    .toList()
                    .cast<String>();
                }
                setState((){});
            },
            onSaved: (String value) {
                _order.mainItemType = value;
            },
            value: tempMainItemType,
            );
        }
    }
    },
),

// Main color
if (tempItemColorsList?.isNotEmpty)
    Padding(
    padding: const EdgeInsets.only(top: spacingGeneral),
    child: textFieldLabel(context, "Main color"),
    ),
if (tempItemColorsList?.isNotEmpty)
    DropdownButtonFormField(
    items: tempItemColorsList.map((String color) {
        return new DropdownMenuItem<String>(
        value: color,
        child: Text(color),
        );
    }).toList(),
    onSaved: (String value) {
        _order.mainColor = value;
    },
    value: tempMainItemColor,
    onChanged: (String value) {
        setState(() {
        tempMainItemColor = value;
        });
    },
    ),

這可能為時已晚,但是您可以創建一個Map<String, List<String>> ,其中鍵是第一個下拉列表的項目,值將是第二個下拉列表的項目。

在這里,我創建了一個 state 來存儲第一個下拉列表的選定項。 然后我用它來 map 第二個下拉列表的項目。

import 'package:flutter/material.dart';

void main() => runApp(MyApp());

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: SampleDD(),
    );
  }
}

class SampleDD extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: Center(
        child: DoubleDropdown(
          items: <String, List<String>>{
            'dark colors': ['black', 'gray', 'brown'],
            'light colors': ['white', 'yellow', 'green'],
          },
          onChangedFirst: (val) => print('Selected first: $val'),
          onChangedSecond: (val) => print('Selected second: $val'),
        ),
      ),
    );
  }
}

class DoubleDropdown extends StatefulWidget {
  DoubleDropdown({
    @required this.items,
    @required this.onChangedFirst,
    @required this.onChangedSecond,
  });

  final Map<String, List<String>> items;
  final ValueChanged<String> onChangedFirst;
  final ValueChanged<String> onChangedSecond;

  @override
  _DoubleDropdownState createState() => _DoubleDropdownState();
}

class _DoubleDropdownState extends State<DoubleDropdown> {
  String selectedKey;

  @override
  void initState() {
    super.initState();
    selectedKey = widget.items.keys.first;
  }

  @override
  Widget build(BuildContext context) {
    return Column(
      children: [
        _buildFirstDropdown(),
        _buildSecondDowndown(),
      ],
    );
  }

  Widget _buildFirstDropdown() => DropdownButtonFormField<String>(
        items: widget.items.keys.map((e) {
          return DropdownMenuItem<String>(
            child: Text(e),
            value: e,
          );
        }).toList(),
        onChanged: (val) {
          setState(() => selectedKey = val);
          widget.onChangedFirst(val);
        },
        value: selectedKey,
      );

  Widget _buildSecondDowndown() => DropdownButtonFormField<String>(
        items: widget.items[selectedKey].map((e) {
          return DropdownMenuItem<String>(
            child: Text(e),
            value: e,
          );
        }).toList(),
        onChanged: widget.onChangedSecond,
        value: widget.items[selectedKey].first,
      );
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM