Flutter,Gridview,API使用,List.Generate:RangeError(索引):无效值:有效值范围为空:0

时间:2019-07-09 18:42:19

标签: android gridview flutter dart fetch

颤动网格视图的实现,旨在通过OnTap(GestureDetector)转到另一个屏幕。 问题出在

children: _buildGridTileList(15));

List<GestureDetector> _buildGridTileList(int count) =>
          List.generate(count, (index) {
            CharBio char = _charbio[index];

索引的目的是从https://swapi.co/api/people/?format=json中适当选择一个字符履历,该履历不提供对类的直接访问,但将履历放在“结果”子文件夹中。因此,这就是我实现API的本地存储库的方式:

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

class CharApi {
  Future<Stream<CharBio>> getChars() async {
    final String url = 'https://swapi.co/api/people/?format=json&page=1';

    final client = new http.Client();
    final streamedRest = await client.send(http.Request('get', Uri.parse('$url/results')));

    return streamedRest.stream
        .transform(utf8.decoder)
        .transform(json.decoder)
        .expand((data) => (data as List))
        .map((data) => CharBio.fromJson(data));
  }
}

代码:

import 'package:flutter/material.dart';
import 'color.dart';
import 'bio_details.dart';
import 'CharBio.dart';
import 'bio_api.dart';
//import 'game.dart'; // para ir para batalha após selecionar personagem

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

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      debugShowCheckedModeBanner: false,
      title: 'choose',
      theme: ThemeData(primarySwatch: primaryBlack),
      home: Choose(),
    );
  }
}

class Choose extends StatefulWidget {
  @override
  _ChooseState createState() => _ChooseState();
}

class _ChooseState extends State<Choose> {
  CharApi _api = new CharApi();
  List<CharBio> _charbio = <CharBio>[];

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

  void listenForChars() async {
    final Stream<CharBio> stream = await _api.getChars();
    stream.listen((CharBio beer) => setState(() => _charbio.add(beer)));
  }

  Widget _buildGrid() => GridView.extent(
      maxCrossAxisExtent: 171,
      padding: const EdgeInsets.all(4),
      mainAxisSpacing: 4,
      crossAxisSpacing: 4,
      children: _buildGridTileList(15));

  List<GestureDetector> _buildGridTileList(int count) =>
      List.generate(count, (index) {

        CharBio char = _charbio[index];
        return GestureDetector(
          onTap: () {
            Navigator.of(context).push(MaterialPageRoute(
                builder: (BuildContext context) => new DetailsBio(char)));
          },
          child: index == null
          ? CircularProgressIndicator()
          : Container(
            child: Image.asset('assets/images/pic$i (Personalizado).jpg'),
          ),
        );
      });

  @override
  Widget build(BuildContext context) {
    return Scaffold(
        appBar: AppBar(
          centerTitle: true,
          title: Text('Choose your Destiny'),
          textTheme: TextTheme(
            title: TextStyle(
              fontFamily: 'StarJedi',
              color: Color(0xFFFFFF00),
              fontSize: 24.0,
            ),
          ),
        ),
        body: _buildGrid(),
        bottomNavigationBar: BottomAppBar(
          color: Colors.black,
          child: Container(
            height: 16.0,
            //padding: new EdgeInsets.only(top: 16.0),
            child: new Row(
              crossAxisAlignment: CrossAxisAlignment.start,
              mainAxisAlignment: MainAxisAlignment.center,
              children: <Widget>[
                Text('Hold for Bio',
                    style: new TextStyle(
                      fontSize: 10.0,
                      fontFamily: 'StarJedi',
                      color: new Color(0xFF26C6DA),
                    )),
              ],
            ),
          ),
        ));
  }
}

在从API提取之前,代码可以正常工作,并且如果我将_buildGridTileList(int count)设置为0,则所有代码都可以正常工作,但这不是预期的结果,因为网格中未显示任何图像。
该如何解决?
此处较大项目的最后期限为30小时。 :/

0 个答案:

没有答案