android - 如何在 SmartRefresher 上实现 FutureBuilder - Flutter Dart

标签 android flutter dart

我想在 futurebuilder 上实现 SmartRefresher,但在拉动刷新时无法获取最新数据。我不使用 listView,但我只想将数据放在现有字段中。

主程序:

class _StatisticPageState extends State<StatisticPage> {

  Future<Banjir> futureBanjir;

  RefreshController _refreshController = 
    RefreshController(initialRefresh: false);

  @override
  void initState(){
    super.initState();
    futureBanjir = fetchBanjir();
  }

  ProgressDialog pr;

  @override
  Widget build(BuildContext context) {
    return SmartRefresher(
      controller: _refreshController,
      enablePullDown: true,
      enablePullUp: false,
      onRefresh: () async{
        // this is my problem
        _refreshController.loadComplete();
      },
      child: SingleChildScrollView(
        physics: const AlwaysScrollableScrollPhysics(),
        child: FutureBuilder<Banjir>(
          future: futureBanjir,
          builder: (context, snapshot){
            if(snapshot.hasData == null){
              return _buildAll(
                AppColors.offColor,
                "N/A",
                "N/A",
                "N/A",
                "N/A",
                "N/A",
                "N/A",
                "N/A",
                "N/A",
                "N/A",
              );
            } else if(snapshot.hasError){
              return Center(
                child: Text("Error : ${snapshot.error}"),
              );
            } else{
              if(snapshot.data.siteStatus != "Active"){
                return _buildAll(
                  AppColors.offColor, 
                  (snapshot.data.data.tanggal).toString(),
                  (snapshot.data.data.jam).toString(), 
                  snapshot.data.data.ketinggian, 
                  "SITE MATI", 
                  snapshot.data.today.min, 
                  snapshot.data.today.max, 
                  (snapshot.data.today.banjir).toString(), 
                  (snapshot.data.today.awas).toString(), 
                  (snapshot.data.today.waspada).toString()
                );
              } 
            }
            return SpinKitDoubleBounce(
              color: AppColors.mainColor,
            );
          },
        ),
      ),
    );
  }

这是我的 Future 函数

Future<Banjir> fetchBanjir() async{
  final response = await http.get(RestAPI.BASE_URL + "/last");

  if(response.statusCode == 200){
    return Banjir.fromJson(json.decode(response.body));
  } else{
    throw Exception('Failed to Load Data');
  }
}

我不知道如何在 SmartRefresher 上实现 FutureBuilder,我卡在了这里

最佳答案

您可以在下面复制粘贴运行完整代码
您可以再次使用 set futureBanjir 并调用 setState

onRefresh: () async {
      futureBanjir = fetchBanjir();
      setState(() {});
      _refreshController.refreshCompleted();
    },

工作演示

enter image description here

完整代码

import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:flutter_spinkit/flutter_spinkit.dart';
import 'package:http/http.dart' as http;
import 'package:pull_to_refresh/pull_to_refresh.dart';
import 'dart:convert';

class RefreshScrollBehavior extends ScrollBehavior {
  @override
  Widget buildViewportChrome(
      BuildContext context, Widget child, AxisDirection axisDirection) {
    // When modifying this function, consider modifying the implementation in
    // _MaterialScrollBehavior as well.
    switch (getPlatform(context)) {
      case TargetPlatform.iOS:
        return child;
      case TargetPlatform.macOS:
      case TargetPlatform.android:
        return GlowingOverscrollIndicator(
          child: child,
          // this will disable top Bouncing OverScroll Indicator showing in Android
          showLeading: true, //顶部水波纹是否展示
          showTrailing: true, //底部水波纹是否展示
          axisDirection: axisDirection,
          notificationPredicate: (notification) {
            if (notification.depth == 0) {
              // 越界了拖动触发overScroll的话就没必要展示水波纹
              if (notification.metrics.outOfRange) {
                return false;
              }
              return true;
            }
            return false;
          },
          color: Theme.of(context).primaryColor,
        );
      case TargetPlatform.fuchsia:
    }
    return null;
  }
}

Banjir banjirFromJson(String str) => Banjir.fromJson(json.decode(str));

String banjirToJson(Banjir data) => json.encode(data.toJson());

class Banjir {
  Banjir({
    this.data,
  });

  List<Datum> data;

  factory Banjir.fromJson(Map<String, dynamic> json) => Banjir(
        data: List<Datum>.from(json["data"].map((x) => Datum.fromJson(x))),
      );

  Map<String, dynamic> toJson() => {
        "data": List<dynamic>.from(data.map((x) => x.toJson())),
      };
}

class Datum {
  Datum({
    this.tanggal,
    this.jam,
    this.ketinggian,
  });

  int tanggal;
  int jam;
  String ketinggian;

  factory Datum.fromJson(Map<String, dynamic> json) => Datum(
        tanggal: json["tanggal"],
        jam: json["jam"],
        ketinggian: json["ketinggian"],
      );

  Map<String, dynamic> toJson() => {
        "tanggal": tanggal,
        "jam": jam,
        "ketinggian": ketinggian,
      };
}

class StatisticPage extends StatefulWidget {
  @override
  _StatisticPageState createState() => _StatisticPageState();
}

class _StatisticPageState extends State<StatisticPage> {
  Future<Banjir> futureBanjir;

  RefreshController _refreshController =
      RefreshController(initialRefresh: false);
  List<Datum> dataList = [];

  @override
  void initState() {
    super.initState();
    futureBanjir = fetchBanjir();
  }

  Future<Banjir> fetchBanjir() async {
    //final response = await http.get(RestAPI.BASE_URL + "/last");
    print("fetchBanjir");
    dataList.add(Datum(tanggal: 1, jam: 2, ketinggian: "test"));
    print(dataList.length);
    return Future.value(Banjir(data: dataList));
  }

  //ProgressDialog pr;

  @override
  Widget build(BuildContext context) {
    return SmartRefresher(
        header: WaterDropHeader(),
        controller: _refreshController,
        enablePullDown: true,
        enablePullUp: true,
        onRefresh: () async {
          futureBanjir = fetchBanjir();
          setState(() {});
          _refreshController.refreshCompleted();
        },
        child: Column(
          children: [
            Text("test"),
            Expanded(
              child: FutureBuilder<Banjir>(
                  future: futureBanjir,
                  builder: (context, snapshot) {
                    switch (snapshot.connectionState) {
                      case ConnectionState.none:
                        return Text('none');
                      case ConnectionState.waiting:
                        return Center(child: CircularProgressIndicator());
                      case ConnectionState.active:
                        return Text('');
                      case ConnectionState.done:
                        if (snapshot.hasError) {
                          return Text(
                            '${snapshot.error}',
                            style: TextStyle(color: Colors.red),
                          );
                        } else {
                          return ListView.builder(
                              itemCount: snapshot.data.data.length,
                              itemBuilder: (context, index) {
                                return Card(
                                    elevation: 6.0,
                                    child: Padding(
                                      padding: const EdgeInsets.only(
                                          top: 6.0,
                                          bottom: 6.0,
                                          left: 8.0,
                                          right: 8.0),
                                      child: Row(
                                        crossAxisAlignment:
                                            CrossAxisAlignment.start,
                                        children: <Widget>[
                                          Text(snapshot.data.data[index].jam
                                              .toString()),
                                          Spacer(),
                                          Text(snapshot
                                              .data.data[index].ketinggian),
                                        ],
                                      ),
                                    ));
                              });
                        }
                    }
                  }),
            ),
          ],
        ));
  }
}

void main() {
  runApp(MyApp());
}

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return RefreshConfiguration(
      footerTriggerDistance: 1.0,
      dragSpeedRatio: 0.91,
      headerBuilder: () => MaterialClassicHeader(),
      footerBuilder: () => ClassicFooter(),
      enableLoadingWhenNoData: false,
      shouldFooterFollowWhenNotFull: (state) {
        // If you want load more with noMoreData state ,may be you should return false
        return false;
      },
      autoLoad: true,
      child: MaterialApp(
        title: 'Flutter Demo',
        theme: ThemeData(
          primarySwatch: Colors.blue,
          visualDensity: VisualDensity.adaptivePlatformDensity,
        ),
        builder: (context, child) {
          return ScrollConfiguration(
            child: child,
            behavior: RefreshScrollBehavior(),
          );
        },
        home: MyHomePage(title: 'Flutter Demo Home Page'),
      ),
    );
  }
}

class MyHomePage extends StatefulWidget {
  MyHomePage({Key key, this.title}) : super(key: key);

  final String title;

  @override
  _MyHomePageState createState() => _MyHomePageState();
}

class _MyHomePageState extends State<MyHomePage> {
  int _counter = 0;

  void _incrementCounter() {
    setState(() {
      _counter++;
    });
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text(widget.title),
      ),
      body: StatisticPage(),
      floatingActionButton: FloatingActionButton(
        onPressed: _incrementCounter,
        tooltip: 'Increment',
        child: Icon(Icons.add),
      ),
    );
  }
}

关于android - 如何在 SmartRefresher 上实现 FutureBuilder - Flutter Dart,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/62421150/

相关文章:

android - 记录后重新抛出 UncaughtExceptionHandler 异常

flutter 测试 : How to check the background color of a widget during integration test

android - 无法在 FutureBuilder 中滚动 ListView

firefox - 有没有办法在 Firefox 中运行 Dart 用于开发目的?

android - 从媒体 Controller 中删除后退和前进按钮

安卓错误: Execution failed for task ':app:buildInfoGeneratorDebug' .

flutter - 在 Flutter 中清除主体的背景图像

flutter - 如何在导航上放置父级小部件的同级

dart - 在 Flutter 中获取设备的宽度和高度

java - 每当我尝试重建项目时,它都会出现编译错误,无法在 android studio 中完成