在Flutter中实现自定义下拉列表,可以使用以下方法:
方法一:使用DropdownButtonFormField(推荐)
class CustomDropdown extends StatefulWidget {
  @override
  _CustomDropdownState createState() => _CustomDropdownState();
}
class _CustomDropdownState extends State<CustomDropdown> {
  String? selectedValue;
  final List<String> items = ['选项1', '选项2', '选项3', '选项4'];
  @override
  Widget build(BuildContext context) {
    return DropdownButtonFormField<String>(
      value: selectedValue,
      decoration: InputDecoration(
        labelText: '选择选项',
        border: OutlineInputBorder(),
        filled: true,
        fillColor: Colors.grey[50],
      ),
      items: items.map((String value) {
        return DropdownMenuItem<String>(
          value: value,
          child: Text(
            value,
            style: TextStyle(fontSize: 16),
          ),
        );
      }).toList(),
      onChanged: (String? newValue) {
        setState(() {
          selectedValue = newValue;
        });
      },
    );
  }
}
方法二:完全自定义实现
class CustomDropdownList extends StatefulWidget {
  @override
  _CustomDropdownListState createState() => _CustomDropdownListState();
}
class _CustomDropdownListState extends State<CustomDropdownList> {
  bool isExpanded = false;
  String selectedValue = '请选择';
  final List<String> options = ['选项A', '选项B', '选项C', '选项D'];
  @override
  Widget build(BuildContext context) {
    return Column(
      children: [
        // 下拉按钮
        GestureDetector(
          onTap: () {
            setState(() {
              isExpanded = !isExpanded;
            });
          },
          child: Container(
            padding: EdgeInsets.all(12),
            decoration: BoxDecoration(
              border: Border.all(color: Colors.grey),
              borderRadius: BorderRadius.circular(8),
            ),
            child: Row(
              mainAxisAlignment: MainAxisAlignment.spaceBetween,
              children: [
                Text(selectedValue),
                Icon(isExpanded ? Icons.arrow_drop_up : Icons.arrow_drop_down),
              ],
            ),
          ),
        ),
        
        // 下拉列表
        if (isExpanded)
          Container(
            margin: EdgeInsets.only(top: 4),
            decoration: BoxDecoration(
              color: Colors.white,
              border: Border.all(color: Colors.grey),
              borderRadius: BorderRadius.circular(8),
              boxShadow: [
                BoxShadow(
                  color: Colors.black26,
                  blurRadius: 4,
                ),
              ],
            ),
            child: Column(
              children: options.map((option) {
                return ListTile(
                  title: Text(option),
                  onTap: () {
                    setState(() {
                      selectedValue = option;
                      isExpanded = false;
                    });
                  },
                );
              }).toList(),
            ),
          ),
      ],
    );
  }
}
方法三:使用第三方包
在 pubspec.yaml 中添加:
dependencies:
  searchable_dropdown: ^2.0.0
使用示例:
SearchableDropdown(
  items: [
    DropdownMenuItem(child: Text("选项1"), value: "1"),
    DropdownMenuItem(child: Text("选项2"), value: "2"),
  ],
  value: selectedValue,
  hint: "选择选项",
  searchHint: "搜索",
  onChanged: (value) {
    setState(() {
      selectedValue = value;
    });
  },
)
主要特点
- DropdownButtonFormField:内置Material Design样式,集成表单验证
 
- 完全自定义:完全控制外观和交互
 
- 第三方包:提供更多高级功能如搜索、多选等
 
选择哪种方法取决于你的具体需求:如果需要快速实现标准下拉列表,使用方法一;如果需要完全自定义外观,使用方法二;如果需要高级功能,考虑使用第三方包。