【问题标题】:Flutter - Making several calls to an API and updating the UI with the changes gotten back from internetFlutter - 多次调用 API 并使用从互联网返回的更改更新 UI
【发布时间】:2021-04-04 09:54:23
【问题描述】:

`

import 'package:http/http.dart' as http;
import 'dart:convert';

class BinDetails {
  BinDetails({this.url});
  String url;
  Future getCardMetadata() async {
    try {
      http.Response response = await http.get(url);
      if (response.statusCode == 200) {
        String data = response.body;
        print(jsonDecode(data));
        return jsonDecode(data);
      } else {
        print(response.statusCode);
        print(response.body);
      }
    } catch (e) {
      print("An error occurred: $e");
    }
  }

  
}`

`
import 'package:flutter/material.dart';
    import 'package:extension/extension.dart';
    import 'package:mask_text_input_formatter/mask_text_input_formatter.dart';
    import 'package:binlist/services/networking.dart';
    
    String url = "https://lookup.binlist.net/$cardNumber";
    String cardNumber = "";
    String cardScheme = "-";
    String cardType = "-";
    String cardLength = "-";
    String prepaid = "-";
    String bankName = "-";
    String countryName = "-";
    
    class CardDetails extends StatefulWidget {
      @override
      _CardDetailsState createState() => _CardDetailsState();
    }
    
    class _CardDetailsState extends State<CardDetails> {
      Future<dynamic> getCalledCardMetaData() async {
        BinDetails getBinDetails = BinDetails(url: url);
        var cardMetaData = await getBinDetails.getCardMetadata();
    
        if (cardMetaData['scheme'] == null) {
          setState(() {
            cardScheme = "-";
          });
        }
        if (cardMetaData['type'] == null) {
          setState(() {
            cardType = "-";
          });
        }
    
        if (cardMetaData['number']['length'] == null) {
          setState(() {
            cardLength = "-";
          });
        }
        if (cardMetaData['prepaid'] == null) {
          setState(() {
            prepaid = "-";
          });
        }
        if (cardMetaData['bank'] == null) {
          setState(() {
            bankName = "-";
          });
        }
        if (cardMetaData['country'] == null) {
          setState(() {
            countryName = "-";
          });
        }
        setState(() {
          cardScheme = cardMetaData['scheme'];
          cardType = cardMetaData['type'];
          cardLength = cardMetaData['number']['length'].toString();
          if (cardLength == "null") {
            cardLength = "-";
          }
          prepaid = cardMetaData['prepaid'].toString();
          if (prepaid == "false") {
            prepaid = "No";
          } else if (prepaid == "true") {
            prepaid = "Yes";
          } else if (prepaid == "null") {
            prepaid = "-";
          }
          bankName = cardMetaData['bank']['name'];
          countryName = cardMetaData['country']['name'];
          print(cardScheme);
          print(countryName);
          print(cardLength);
          print(cardType);
          print(bankName);
          print(prepaid);
        });
        return cardMetaData;
      }
    
      final _imputedNumber = TextEditingController();
    
      void clearCardNumber() {
        setState(() {
          _imputedNumber.clear();
          cardScheme = "-";
          cardType = "-";
          cardLength = "-";
          prepaid = "-";
          bankName = "-";
          countryName = "-";
          print(cardNumber);
        });
      }
    
      @override
      Widget build(BuildContext context) {
        var maskFormatter = MaskTextInputFormatter(
            mask: '#### ####', filter: {"#": RegExp(r'[0-9]')});
        return Scaffold(
          appBar: AppBar(
            title: Text(
              'Bin List',
            ),
          ),
          body: Column(
            children: [
              Expanded(
                child: Column(
                  children: [
                    Container(
                      width: MediaQuery.of(context).size.width * 0.9,
                      child: TextField(
                        inputFormatters: [maskFormatter],
                        controller: _imputedNumber,
                        onChanged: (value) {
                          String maskedNumber = value;
                          cardNumber =
                              maskedNumber.replaceAll(new RegExp(r'\s'), '');
                          print(cardNumber);
                          print(cardNumber.length);
                         
                          if (cardNumber.length == 8) {
                            getCalledCardMetaData();
                          }
                        },
                        keyboardType: TextInputType.number,
                        textAlign: TextAlign.center,
                        decoration: InputDecoration(
                          contentPadding: EdgeInsets.symmetric(horizontal: 5.0),
                          enabledBorder: UnderlineInputBorder(
                            borderSide: BorderSide(color: Colors.black54),
                          ),
                          focusedBorder: UnderlineInputBorder(
                            borderSide:
                                BorderSide(color: Colors.lightBlue, width: 2.0),
                          ),
                          suffix: TextButton(
                            onPressed: clearCardNumber,
                            child: Icon(
                              Icons.clear,
                              color: Colors.grey.shade600,
                            ),
                          ),
                        ),
                      ),
                    ),`

我制作了一个应用程序,它使用 bin 列表 API (https://lookup.binlist.net/YOUR_CARD_NUMBER_HERE) 来获取卡片的元数据。当我从冷启动应用程序时,输入 CARD A 的卡号,并发出获取请求,我会取回卡元数据并用于更新 UI。当我清除 CARD A 的数字并为 CARD B 输入卡号时,我仍然得到 CARD A 而不是 CARD B 的元数据。但是当我再次从冷启动应用程序并输入 CARD B 的卡号时只有这样,我才能在 UI 上获得 CARD B 的正确元数据。

我试图通过在 TextField 的值发生变化时将卡号打印到控制台来进行调试。我输入了正确的数字,这个输入的数字是发送到 API 的,但是第二张卡的元数据没有从 API 中检索到。我每次都必须从冷启动应用程序以检索正确的元数据。我能做些什么来解决这个问题?谢谢。

[

【问题讨论】:

    标签: android api flutter dart


    【解决方案1】:

    在评估所有条件后,在您的代码中,尝试在调用 getCalledCardMetaData() 之前调用清除先前值的函数。

    if (cardNumber.length == 8) {
        clearCardNumber();
        getCalledCardMetaData();
    }
    

    【讨论】:

    • 这并不能解决问题。它在调用 API 之前清除卡号,当我点击它时,取消图标也会这样做
    猜你喜欢
    • 2022-01-20
    • 1970-01-01
    • 2013-05-30
    • 1970-01-01
    • 2020-09-03
    • 1970-01-01
    • 2021-10-07
    • 1970-01-01
    • 2020-09-26
    相关资源
    最近更新 更多