触发onPressed时setState不更新UI

时间:2019-12-30 12:26:21

标签: flutter dart

我从Navigator.of参数获取计数器整数,并将其显示在appBar上。它可以正常工作,但是我有一个递减按钮,每次触发计数器时,该计数器应将计数器递减1,但是在调用setState之后,UI不会更新。

class _MyHomePageState extends State<MyHomePage> {
  @override
  Widget build(BuildContext context) {
    final routeArgs = ModalRoute.of(context).settings.arguments as Map<String, String>;
    int count;
    String title;
    if(routeArgs == null){
      count = 1;
      title = 'Title';
    }
    else {
      count = int.parse(routeArgs['count']);
      title = routeArgs['title'];
    }
    return Scaffold(
        appBar: AppBar(
          centerTitle: true,
          title: Row(
            mainAxisAlignment: MainAxisAlignment.spaceEvenly,
            children: <Widget>[
              IconButton(
                icon: Icon(Icons.arrow_back_ios),
                onPressed: (){
                  setState(() {
                    count -= 1; //calling setState to decrease count by 1
                  });
                },
              ),
              InkWell(
                child: Container(
                  child: Text(title),
                ),
                onTap: ()=>Navigator.of(context).pushNamed('/choice'),
              ),
              Container(
                  child: Text(count.toString()), //This is not updating after setState called.
                ),
              IconButton(
                icon: Icon(Icons.arrow_forward_ios),
                onPressed: () {},
              ),
            ],
          ),
        ),
        drawer: Drawer(),
      );
  }
}

4 个答案:

答案 0 :(得分:1)

我认为问题是您在build方法中声明了int count。每次您调用setState时,都会重新初始化count变量,因此它不起作用。尝试按以下方法将其移出构建方法

class _MyHomePageState extends State<MyHomePage> {
  int count; //this is moved outside of build function
  @override
  Widget build(BuildContext context) {
    final routeArgs = ModalRoute.of(context).settings.arguments as Map<String, String>;
    String title;
    if(routeArgs == null){
      count = count?? 1;
      title = 'Title';
    }
    else {
      count = count?? int.parse(routeArgs['count']);
      title = routeArgs['title'];
    }
    return Scaffold(
        appBar: AppBar(
          centerTitle: true,
          title: Row(
            mainAxisAlignment: MainAxisAlignment.spaceEvenly,
            children: <Widget>[
              IconButton(
                icon: Icon(Icons.arrow_back_ios),
                onPressed: (){
                  setState(() {
                    count -= 1; //calling setState to decrease count by 1
                  });
                },
              ),
              InkWell(
                child: Container(
                  child: Text(title),
                ),
                onTap: ()=>Navigator.of(context).pushNamed('/choice'),
              ),
              Container(
                  child: Text(count.toString()), //This is not updating after setState called.
                ),
              IconButton(
                icon: Icon(Icons.arrow_forward_ios),
                onPressed: () {},
              ),
            ],
          ),
        ),
        drawer: Drawer(),
      );
  }
}

答案 1 :(得分:0)

如果将状态变量放入构建函数中,则每次构建函数运行时都会对其进行初始化,这很常见。 您应该始终在build方法外部和类内部定义状态变量,以便build函数的重新运行不会影响状态变量所保存的当前值。

答案 2 :(得分:0)

您必须将计数变量设置为 0 值,如下代码:

int count = 0;

答案 3 :(得分:0)

尝试一下

class _MyHomePageState extends State<MyHomePage> {
  int count = 1;
  String title = 'Title';

  @override
  void initState() {
    WidgetsBinding.instance.addPostFrameCallback(_initializeFromArgs);
    super.initState();
  }

  void _initializeFromArgs(_) {
    final routeArgs =
        ModalRoute.of(context).settings.arguments as Map<String, String>;
    if (routeArgs != null) {
      count = int.parse(routeArgs['count']);
      title = routeArgs['title'];
    }
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        centerTitle: true,
        title: Row(
          mainAxisAlignment: MainAxisAlignment.spaceEvenly,
          children: <Widget>[
            IconButton(
              icon: Icon(Icons.arrow_back_ios),
              onPressed: () {
                setState(() {
                  count -= 1;
                });
              },
            ),
            InkWell(
              child: Container(
                child: Text(title),
              ),
              onTap: () => Navigator.of(context).pushNamed('/choice'),
            ),
            Container(
              child: Text(count.toString()),
            ),
            IconButton(
              icon: Icon(Icons.arrow_forward_ios),
              onPressed: () {},
            ),
          ],
        ),
      ),
      drawer: Drawer(),
    );
  }
}