首页 > 解决方案 > Flutter - 使用计时器将 gridView() 中元素的颜色作为序列更改

问题描述

我在我的应用程序中创建了一个小游戏,它应该由一个 3x3 按钮的网格组成,这些按钮将按顺序一个接一个地随机闪烁,用户必须重新创建它。我设法创建了按钮GridView()并设置了一个计时器,但现在我正在努力改变GridView(). 这让我想到如果我使用GridView()正确。

我想通过随机顺序多次更改按钮的颜色,Timer然后用户应该重新创建它。我可以用计时器GridView()来做吗?或者有更简单的方法吗?(我的小游戏应该类似于我们当中的反应堆任务

import 'dart:async';
import 'package:flutter/material.dart';

class Challenge extends StatefulWidget {
  @override
  _ChallengeState createState() => _ChallengeState();
}

class _ChallengeState extends State<Challenge> {
  Timer timer;
  Map userData = {};
  int indexSaved;


  @override
  void initState() {
    super.initState();

    timer = new Timer.periodic(new Duration(seconds: 2), (Timer timer) {
        print('hey');
    });
  }

  @override
  void dispose() {
    super.dispose();
    timer.cancel();
  }


  @override
  Widget build(BuildContext context) {
    userData = ModalRoute.of(context).settings.arguments;
    print(userData);

    return Scaffold(
      body: SafeArea(
        child: Center(
          child: Padding(
            padding: const EdgeInsets.all(20.0),
            child: GridView.count(
              crossAxisCount: 3,
              // mainAxisSpacing: 20.0,
              shrinkWrap: true,
              children: List.generate(9, (index) {
                return Center(
                  child: MaterialButton(
                    color: Colors.blueGrey[300],
                    padding: EdgeInsets.all(50.0),
                    splashColor: Colors.white,
                    onPressed: () {
                      indexSaved = index;
                      print(indexSaved);
                    },
                  ),
                );
              }),
            ),
          ),
        ),
      ),
    );
  }
}

编辑 21/10/2020:我创建了一个应该生成序列的小函数,我正在计时器内启动它们。我研究了我得到的答案并尝试重做它们,以便我可以在我的用例中使用它们。

我正在改变的颜色:

color: indexWithColor == index
       ? Colors.indigo
       : Colors.blueGrey[300],

效果很好。

(片段已编辑)

  List<int> correctValues = [];
  int indexWithColor;
  int indexDisplayed = 0;

  void generateNewLevel() {
    final random = new Random(seed);
    correctValues.add(random.nextInt(9));
    timer = new Timer.periodic(new Duration(milliseconds: 500), (Timer timer) {
      setState(() {
        indexWithColor = correctValues[indexDisplayed];
        // print('Index color ' + indexWithColor.toString());
        indexDisplayed++;
        if (indexDisplayed == correctValues.length) {
          new Timer(new Duration(milliseconds: 500), () {
            setState(() {
              indexWithColor = null;
              indexDisplayed = 0;
            });
            timer.cancel();
          });
          timer.cancel();
        }
      });
    });
  }

现在我正在使用一个按钮来生成一个新的关卡(稍后我会在解决这个问题时更改它)。它有效,但我有问题。

  1. 用户无法区分按钮是否被按下了两次(现在它的颜色被按下了一段时间)。


2. 按钮启动时似乎有点延迟。这不是精确的 500 毫秒,睡眠真的很混乱。
3. 第一级(一长序列是不可见的,因为一旦取消计时器它就会改变。

有更好的选择吗?

编辑:2020 年 10 月 21 日下午 12:00

我用编辑的计时器解决了第二个和第三个问题,所以它现在有点用,但没有更好的方法吗?检查编辑的片段。-^

标签: flutterdartgridviewtimerwidget

解决方案


如果您只想随机更改按钮的颜色,这是一种方法:(已编辑:确保不会连续两次选择相同的索引)

final rng = Random();
int indexWithColor;

@override
void initState() {
  super.initState();
  timer = new Timer.periodic(new Duration(seconds: 2), (Timer timer) {
    setState(() {
      int tempIndex;
      do {
        tempIndex = rng.nextInt(9);
      } while (tempIndex == indexWithColor);
      indexWithColor = tempIndex;
    });
  });
}

在您的 MaterialButton 中:

color: indexWithColor == index
                    ? Colors.red
                    : Colors.blueGrey[300],

推荐阅读