【问题标题】:Parse Json Data into Existing Flutter Widget将 Json 数据解析为现有的 Flutter 小部件
【发布时间】:2023-03-26 20:15:01
【问题描述】:

你好,我现在正在学习颤振,我正在尝试获取 json 数据并将其显示在轮播小部件上,下面是完整的代码,以便您了解发生了什么

import 'package:flutter/material.dart';
import 'package:mares/components/drawer.dart';
import 'package:carousel_pro/carousel_pro.dart';
import 'package:mares/components/homecards.dart';
import 'package:mares/pages/contactus.dart';
import 'package:mares/pages/profile.dart';
import 'dart:async';
import 'dart:convert';
import 'package:http/http.dart' as http;

void main() => runApp(MyApp());

class MyApp extends StatelessWidget {
  // This widget is the root of your application.
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      debugShowCheckedModeBanner: false,
      title: 'Elaph Training',
      theme: ThemeData(fontFamily: 'Roboto'),
      home: MyHomePage(),
    );
  }
}

class MyHomePage extends StatefulWidget {

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

class _MyHomePageState extends State<MyHomePage> {


  Future<List> getSlides() async {
    final response = await http.get("http://igh-eg.com/mares/json/slides.php");
    return json.decode(response.body);
  }

  @override
  Widget build(BuildContext context) {
    Widget imagecarousel = new Container(
      height: 200.0,
      child: new Carousel(
        boxFit: BoxFit.cover,
        images: [
          AssetImage('assets/slide1.jpg'),
          AssetImage('assets/slide2.jpg'),
          AssetImage('assets/slide3.jpg'),
        ],
        autoplay: true,
        animationCurve: Curves.fastOutSlowIn,
        animationDuration: Duration(milliseconds: 2000),
        dotSize: 5.0,
        dotColor: const Color.fromRGBO(234, 91, 12, 1),
      ),
    );

    return Scaffold(
      appBar: new AppBar(
        backgroundColor: const Color.fromRGBO(32, 102, 174, 1),
        title: Text('Elaph Training Center'),
        actions: <Widget>[
          new IconButton(icon: Icon(Icons.phone_in_talk, color: Colors.white,), onPressed: (){Navigator.of(context).push(new MaterialPageRoute(builder: (context) => new ContactUsPage()));}),//search button
          new IconButton(icon: Icon(Icons.supervised_user_circle, color: Colors.white,), onPressed: (){Navigator.of(context).push(new MaterialPageRoute(builder: (context) => new Profilepage()));}),//cart button
        ],
      ),
      //--the end of the app bar--//
      //---start of the drawer---//
      drawer: NavDrawer(),
      body: new ListView(
        children: <Widget>[
          new FutureBuilder<List>(
            future: getSlides(),
            builder: (context, snapshot) {
              if (snapshot.hasError) print(snapshot.error);

              return snapshot.hasData
                  ? new ItemList(
                list: snapshot.data,
              )
                  : new Center(
                child: new CircularProgressIndicator(),
              );
            },
          ),
          imagecarousel,
          SizedBox(height: 10.0,),
          HomeCards(),
        ],
      ),
    );
  }
}

class ItemList extends StatelessWidget {
  final List list;
  ItemList({this.list});

  @override
  Widget build(BuildContext context) {
    return new ListView.builder(
      itemCount: list == null ? 0 : list.length,
      itemBuilder: (context, i) {
        return new Container(
          padding: const EdgeInsets.all(10.0),
          child: new Card(

              child: new ListTile(
                title: new Text(list[i]['name']),
                leading: new Image.network("http://igh-eg.com/mares/img/${list[i]['photo']}"),
                subtitle: new Text("Description : ${list[i]['desc']}"),
              ),
            ),
        );
      },
    );
  }
}

目前数据是代码在上面定义的 listitem 类中运行良好,但是我希望数据显示在如下所示的轮播部分上

  Widget imagecarousel = new Container(
      height: 200.0,
      child: new Carousel(
        boxFit: BoxFit.cover,
        images: [
          AssetImage('assets/slide1.jpg'),
          AssetImage('assets/slide2.jpg'),
          AssetImage('assets/slide3.jpg'),
        ],
        autoplay: true,
        animationCurve: Curves.fastOutSlowIn,
        animationDuration: Duration(milliseconds: 2000),
        dotSize: 5.0,
        dotColor: const Color.fromRGBO(234, 91, 12, 1),
      ),
    );

有什么帮助吗?我在网上搜索了很多,我看不到我错过了什么

【问题讨论】:

    标签: json flutter flutter-layout rest


    【解决方案1】:

    我已经用carousel_slider: ^2.2.1 & cached_network_image: ^2.1.0+1 包实现了类似的代码。
    你可以试试下面的代码:

    class _HomeScreenState extends State<HomeScreen> {
      Future<List<Product>> carouselProducts;
      ...
      // method to fecth data from URL 
      Future<List<Product>> getSlides() async {
        return await apiController.carouselDataFetch();
      }
    
      @override
      void initState() {
        super.initState();
        WidgetsBinding.instance.addPostFrameCallback((_) {
          carouselProducts = getSlides();
        });
      }
    

    构建方法中的小部件:

    FutureBuilder<List<Product>>(
        future: carouselProducts,
        builder: (BuildContext cont, AsyncSnapshot snapshot) {
          if (snapshot.connectionState != ConnectionState.done) {
            return Center(child: CircularProgressIndicator());
          }
          if (snapshot.connectionState == ConnectionState.none) {
            return Center(
                child: Text("Turn-On Mobile Data / WiFi Please!",));
          }
          if (snapshot.hasError) {
            return Center(
                child: Text("Something went wrong!",));
          }
          return CarouselSlider.builder(
            options: CarouselOptions(
              height: 250,
              autoPlay: true,
              enableInfiniteScroll: false,
              enlargeCenterPage: true,
              scrollDirection: Axis.horizontal,
              scrollPhysics: const BouncingScrollPhysics(),
              enlargeStrategy: CenterPageEnlargeStrategy.height,
              autoPlayCurve: Curves.fastLinearToSlowEaseIn,
            ),
            itemCount: snapshot.data.length,
            itemBuilder: (BuildContext context, int index) {
              Product prod = snapshot.data[index];
              return CachedNetworkImage(
                imageUrl: prod.productImage,
                fit: BoxFit.fill,
                useOldImageOnUrlChange: true,
                fadeInCurve: Curves.linearToEaseOut,
                placeholder: (context, url) => Center(
                    child: CircularProgressIndicator()),
                errorWidget: (context, url, error) =>
                    Icon(Icons.error),
              );
            },
          );
        },
      )
    

    输出:

    仅供参考:
    根据您的 API 响应数据更改此示例代码。

    【讨论】:

      【解决方案2】:

      谢谢大家,但我发现问题出在我使用的小部件版本上,所以我只是按照以下步骤操作

      第 1 步:我将版本 (carousel_pro: ^0.0.13) 添加到 pubspec.yaml

      第 2 步:创建以下 dart 文件

      import 'package:carousel_pro/carousel_pro.dart';
      import 'package:flutter/material.dart';
      
      Widget CarouselSlider(items) => SizedBox(
        height: 200,
        child: Carousel(
          boxFit: BoxFit.cover,
          images: items,
          autoplay: true,
          animationCurve: Curves.fastOutSlowIn,
          animationDuration: Duration(milliseconds: 1500),
        ),
      );
      

      然后在main.dart里面初始化状态时使用http,get获取数据,如下

      class _MyHomePageState extends State<MyHomePage> {
      
        var items = [];
        @override
        void initState() {
          // TODO: implement initState
          super.initState();
          //get json data function//
          getSlides();
        }
      
        Future<List> getSlides() async {
          final response = await http.get("http://igh-eg.com/mares/json/slides.php");
          var result = json.decode(response.body);
          result['data'].forEach((data){
            setState(() {
              items.add(NetworkImage("http://igh-eg.com/mares/img/${data['photo']}"));
            });
          });
          print(json.decode(response.body));
          return json.decode(response.body);
        }
      
        @override
        Widget build(BuildContext context) {
      
          return Scaffold(
            appBar: new AppBar(
              backgroundColor: const Color.fromRGBO(32, 102, 174, 1),
              title: Text('Elaph Training Center'),
              actions: <Widget>[
                new IconButton(icon: Icon(Icons.phone_in_talk, color: Colors.white,), onPressed: (){Navigator.of(context).push(new MaterialPageRoute(builder: (context) => new ContactUsPage()));}),//search button
                new IconButton(icon: Icon(Icons.supervised_user_circle, color: Colors.white,), onPressed: (){Navigator.of(context).push(new MaterialPageRoute(builder: (context) => new Profilepage()));}),//cart button
              ],
            ),
            //--the end of the app bar--//
            //---start of the drawer---//
            drawer: NavDrawer(),
            body: new ListView(
              children: <Widget>[
                CarouselSlider(items),
                SizedBox(height: 10.0,),
                HomeCards(),
              ],
            ),
          );
        }
      }
      

      它像图表一样工作,如果您正在处理大量数据和图像,更好的方法是使用 pub.dev 网站上的 networkcachedimage 小部件

      感谢大家,特别感谢@Sanket Vekariya 的帮助

      【讨论】:

        猜你喜欢
        • 2020-03-15
        • 1970-01-01
        • 1970-01-01
        • 2020-01-07
        • 2021-10-21
        • 2021-01-31
        • 2020-01-25
        • 1970-01-01
        • 2020-10-13
        相关资源
        最近更新 更多