提供程序不刷新DropDownMenu的列表- Flutter

b09cbbtk  于 2023-01-09  发布在  Flutter
关注(0)|答案(1)|浏览(112)

我有一个个人API,从那里我可以检索所有需要的信息,连接工作正常,但问题是当我想显示这些值时,我有一个提供程序,我可以将API中所有需要的数据放在那里,我调用它将这些项放在DropDownMenu中,但问题是这些值不显示,即使在数据到达之后,我也知道这一点,这要感谢调试,下面是一些代码:
这是我调用提供程序的小部件的代码:

Column(
                children: [
                  Container(
                    color: Colors.green,
                    child: Row(
                        mainAxisAlignment: MainAxisAlignment.center,
                        children: [
                          Container(
                            margin: const EdgeInsets.only(top: 20, bottom: 20),
                            height: 10,
                            width: 100,
                            decoration: BoxDecoration(
                                borderRadius: BorderRadius.circular(10),
                                color: Colors.grey),
                          )
                        ]),
                  ),
                  IconList(
                    labelText: 'Landmarks',
                    icon: Icons.panorama_horizontal_outlined,
                    items: context.watch<Landmarks>().getLandmarksNameList(), //Here is my provider
                  ),
                  const IconInput(
                      labelText: '1', icon: Icons.addchart_outlined),
                  const IconInput(
                      labelText: '1', icon: Icons.addchart_outlined),
                  ListView.builder(
                    physics: const NeverScrollableScrollPhysics(),
                    shrinkWrap: true,
                    itemCount: 2,
                    itemBuilder: (BuildContext context, int index) {
                      return UserCard(user: usersList[index]);
                    },
                  ),
                ],
              ),

这是小部件图标列表,其中有下拉菜单:

import 'package:flutter/material.dart';

class IconList extends StatefulWidget {
  final String labelText;
  final IconData icon;
  final List<String> items = [];

  IconList({super.key, required this.labelText, required this.icon, items});

  @override
  State<IconList> createState() => _IconListState();
}

class _IconListState extends State<IconList> {
  @override
  Widget build(BuildContext context) {
    String selectedItem = '';
    if (widget.items.isNotEmpty) {
      selectedItem = widget.items.first;
    }
    return Container(
      margin: const EdgeInsets.all(10.0),
      child: Row(
        children: [
          Icon(widget.icon),
          DropdownButton<String>(
            value: selectedItem,
            items: widget.items.map<DropdownMenuItem<String>>((String value) {
              return DropdownMenuItem<String>(
                value: value,
                child: Text(value),
              );
            }).toList(),
            onChanged: (String? value) {
              setState(() {
                selectedItem = value!;
              });
            },
          ),
        ],
      ),
    );
  }
}

这是我的供应商:

class Landmarks with ChangeNotifier {
  final List<Landmark> _items = [];

  List<Landmark> get landmarks => _items;

  void addLandmarks(List<Landmark> value) {
    _items.addAll(value);
    notifyListeners();
  }

  List<String> getLandmarksNameList() {
    List<String> list = [];
    print(_items.length);
    for (int i = 0; i < _items.length; i++) {
      list.add(_items[i].name);
    }
    return list;
  }
}
dy2hfwbg

dy2hfwbg1#

您的代码有两个问题:

问题1

IconList构造函数中

IconList({super.key, required this.labelText, required this.icon, items});

您正在访问items,但实际上您应该访问this.items
为此,您也不应使用以下内容初始化项目:

final List<String> items = [];

您的代码应该如下所示:

class IconList extends StatefulWidget {
  final String labelText;
  final IconData icon;
  final List<String> items;

  IconList(
      {super.key,
      required this.labelText,
      required this.icon,
      required this.items});
问题2

build方法中:

@override
Widget build(BuildContext context) {
    String selectedItem = '';
    if (widget.items.isNotEmpty) {
      selectedItem = widget.items.first;
    }

你正在初始化selectedItem,这意味着每一个setStateselectedItem都将被重置为它的原始值,因为它在build方法内。相反,把selectedItem移到build之外,移到你的_state类中:

class _IconListState extends State<IconList> {
  String selectedItem = ''; //<-- Initialize it here
  @override
  Widget build(BuildContext context) {
    if (widget.items.isNotEmpty) {
      selectedItem = widget.items.first;
    }
    return Container(

您的IconList应该如下所示:

class IconList extends StatefulWidget {
  final String labelText;
  final IconData icon;
  final List<String> items;

  IconList(
      {super.key,
      required this.labelText,
      required this.icon,
      required this.items});

  @override
  State<IconList> createState() => _IconListState();
}

class _IconListState extends State<IconList> {
  String selectedItem = ''; //<-- Initialize it here
  @override
  Widget build(BuildContext context) {
    if (widget.items.isNotEmpty) {
      selectedItem = widget.items.first;
    }
    return Container(
      margin: const EdgeInsets.all(10.0),
      child: Row(
        children: [
          Icon(widget.icon),
          DropdownButton<String>(
            value: selectedItem,
            items: widget.items.map<DropdownMenuItem<String>>((String value) {
              print("item is $value");
              return DropdownMenuItem<String>(
                value: value,
                child: Text(value),
              );
            }).toList(),
            onChanged: (String? value) {
              setState(() {
                selectedItem = value!;
              });
            },
          ),
        ],
      ),
    );
  }
}

相关问题