Flutter GetX计时器错误.主页未刷新



我试图每30秒获取一次数据,但我不知道如何做到。我创建的Getx控制器文件没有问题。我可以提取数据,但不能刷新。

这是我的控制器:

class AllCoinController extends GetxController {
var coinList = [].obs;
var coinCounter = 0.obs;
Future callAllCoins() async {
try {
final response = await http.get(url);
if (response.statusCode == 200) {
List<dynamic> values = [];
values = allCoinsFromJson(response.body);
coinCounter.value = values.length;
if (values.length > 0) {
for (int i = 0; i < values.length; i++) {
if (values[i] != null) {
coinList.add(values[i]);
}
}
}
return coinList;
} else {
print(response.statusCode);
}
} catch (e) {
print(e.toString());
}
}
@override
void onInit() {
callAllCoins();
Timer.periodic(Duration(seconds: 30), (timer) => callAllCoins());
super.onInit();
}
}

我的主页:

class HomePage extends StatelessWidget {
final AllCoinController allCoinController = Get.put(AllCoinController());
@override
Widget build(BuildContext context) {
return Scaffold(
body: Obx(
() => ListView.builder(
scrollDirection: Axis.vertical,
itemCount: allCoinController.coinCounter.value,
itemBuilder: (context, index) {
return Container(
width: 150,
child: Row(
children: [
SizedBox(
width: 50,
height: 50,
child: Padding(
padding: const EdgeInsets.all(8.0),
child: Image.network(
allCoinController.coinList[index].image),
),
),
Padding(
padding: const EdgeInsets.all(8.0),
child: Text(allCoinController.coinList[index].name),
),
Padding(
padding: const EdgeInsets.all(8.0),
child: Text(allCoinController.coinList[index].symbol),
),
Padding(
padding: const EdgeInsets.all(8.0),
child: Obx(
() => Text(allCoinController.coinList[index].currentPrice
.toString()),
),
),
],
),
);
},
),
),
);
}
}

代码没有问题,唯一的问题是计时器不工作

我认为您的控制器有问题。例如,您通过循环手动在列表上预先设置值。您可以在REST调用后简单地使用coinList.assignAll(values),而无需编写所有手动代码。assignAll()方法的好处之一是它可以通知更改。因此,您不需要coinCounter变量,只需执行以下操作即可:

... 
values = allCoinsFromJson(response.body);
coinList.assignAll(values);
...

ListView.builder上使用itemCount: allCoinController.coinList.length

您发布的代码每30秒向列表中添加一次新值,但计数不会增加。为了显示这些新值,您必须增加nem项目的数量替换列表中的现有值(添加前清空(

另外,请注意,以下代码在init上调用callAllCoins((两次。

@override
void onInit() {
callAllCoins(); // This should be removed
Timer.periodic(Duration(seconds: 30), (timer) => callAllCoins()); // This is called right in this line, then every 30 sec.
super.onInit();
}

我在下面给你举一个关于我想法的基本例子。

import 'dart:async';
import 'package:flutter/material.dart';
import 'package:get/get.dart';
void main() {
runApp(MyApp());
}
class MyApp extends StatelessWidget {
final controller = Get.put(MyAppController());
@override
Widget build(BuildContext context) {
return MaterialApp(
home: Container(
child: Obx(() {
print(controller.counter);
return ListView.builder(
itemBuilder: (context, index) => Text(controller.list[index]),
itemCount: controller.counter.value,
);
}),
),
);
}
}
class MyAppController extends GetxController {
var list = [].obs;
var counter = 0.obs;
callIncrement() {
list.add('->');
counter.value += 1;
}
@override
void onInit() {
Timer.periodic(Duration(seconds: 1), (_) => callIncrement());
super.onInit();
}
}

最新更新