0

I was working with Http get requests in flutter. I am using jsonplaceholder.typicode.com. I have taken references from the flutter docs but currently, it is showing only the first item. I want to display all the 20 items in the form of cards. Can anyone help me in achieving this?

Here's my code :

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

Future<Album> fetchAlbum() async {
  final response =
      await http.get(Uri.https('jsonplaceholder.typicode.com', 'albums/1'));

  if (response.statusCode == 200) {
    return Album.fromJson(jsonDecode(response.body));
  } else {
    throw Exception('Failed to load album');
  }
}

class Album {
  final int userId;
  final int id;
  final String title;

  Album({@required this.userId, @required this.id, @required this.title});

  factory Album.fromJson(Map<String, dynamic> json) {
    return Album(
      userId: json['userId'],
      id: json['id'],
      title: json['title'],
    );
  }
}

And I am using this here:

class ShopScreen extends StatefulWidget {
  static String id = 'shop_screen';
  @override
  _ShopScreenState createState() => _ShopScreenState();
}

class _ShopScreenState extends State<ShopScreen> {
  Future<Album> futureAlbum;

  @override
  void initState() {
    super.initState();
    futureAlbum = fetchAlbum();
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text('Shops'),
        backgroundColor: Colors.deepOrangeAccent[700],
      ),
      drawer: NavList(),
      body: ListView(
        children: <Widget>[
          ShopCard(placeholderImage: 'https://picsum.photos/250?image=3'),
          ShopCard(placeholderImage: 'https://picsum.photos/250?image=100'),
          ShopCard(placeholderImage: 'https://picsum.photos/250?image=234'),
          ShopCard(placeholderImage: 'https://picsum.photos/250?image=200'),
          Container(
            padding: EdgeInsets.all(5.0),
            width: MediaQuery.of(context).size.width,
            height: 130,
            child: Card(
              shape: RoundedRectangleBorder(
                borderRadius: BorderRadius.circular(15.0),
              ),
              child: Padding(
                padding: const EdgeInsets.all(8.0),
                child: FutureBuilder<Album>(
                  future: futureAlbum,
                  builder: (context, snapshot) {
                    if (snapshot.hasData) {
                      return Column(
                        mainAxisAlignment: MainAxisAlignment.start,
                        crossAxisAlignment: CrossAxisAlignment.start,
                        children: [
                          Expanded(
                            child: Text('TITLE: ${snapshot.data.title}'),
                          ),
                          Expanded(
                            child: Text('USER_ID: ${snapshot.data.userId}'),
                          ),
                          Expanded(
                            child: Text('ID: ${snapshot.data.id}'),
                          ),
                        ],
                      );
                    } else if (snapshot.hasError) {
                      return Text("${snapshot.error}");
                    }
                    return CircularProgressIndicator();
                  },
                ),
              ),
              elevation: 5.0,
            ),
          )
        ],
      ),
    );
  }

And this is what I am getting right now. (See the last card. Only the first data is displaying.)

enter image description here

Please help me out.

Arijeet
  • 935
  • 5
  • 19
  • can you provide the response.body? – Alvin Chung Apr 29 '21 at 07:09
  • I have provided all the snippets that have been used. – Arijeet Apr 29 '21 at 07:17
  • What are you trying to achieve here? 1) If you use children property it will show only the passed item, if you want to show dynamic number of items you should use ListView.Builder 2) You are calling an API which returns a single item, either you need to call an API which returns list of items or you need to call multiple API for getting each individual item – Midhun MP Apr 29 '21 at 07:34
  • I want to show the data fetched from the above API in the form of cards but I am unable to achieve this. – Arijeet Apr 29 '21 at 07:55
  • not really understand. http://jsonplaceholder.typicode.com/albums/1 has only one album with no array, what are the 20 items? – Alvin Chung Apr 29 '21 at 08:08
  • The problem is , when i am changing http://jsonplaceholder.typicode.com/albums/1 to http://jsonplaceholder.typicode.com/albums/ , it is showing invalid argument user_id. – Arijeet Apr 29 '21 at 09:35

1 Answers1

1

You are fetching only one Album by passing 'albums/1' in API call. if you want to fetch all the Albums data then dont pass id while calling API.

final response = await http.get(Uri.https('jsonplaceholder.typicode.com', 'albums'));

and don't forgot to change Future of Album to List of Album and changes accrodingly.