Home > Software design >  Flutter - Problem showing and accessing api datas
Flutter - Problem showing and accessing api datas

Time:10-21

right now im trying to use this api https://ffxivcollect.com/api/spells/

Im trying show all the names in a ListView.builder, but i cant access the data through that link, i can just access Query, Count and Results. taking a look at the api, the datas should be in results, but i still cant access. So i removed the Count and Query, and im using only the results, i can access the data with this, but still do not show nothing.

And if i use the api link with a number after, i will access only one specific data, like this https://ffxivcollect.com/api/spells/1 and that way actually work, but just with one data, i was trying use a global var spells/global.x to add 1 and go to next data, but that didnt work, so i guess im doing something wrong here.

What can i do with my json to access and show all the datas that i want with this https://ffxivcollect.com/api/spells/

my model:

import 'package:meta/meta.dart';
import 'dart:convert';

List<FinalApi> finalApiFromMap(String str) =>
    List<FinalApi>.from(json.decode(str).map((x) => FinalApi.fromMap(x)));

String finalApiToMap(List<FinalApi> data) =>
    json.encode(List<dynamic>.from(data.map((x) => x.toMap())));

class FinalApi {
  FinalApi({
    required this.id,
    required this.name,
    required this.description,
    required this.tooltip,
    required this.order,
    required this.rank,
    required this.patch,
    required this.owned,
    required this.icon,
    required this.type,
    required this.aspect,
    required this.sources,
  });

  int id;
  String name;
  String description;
  String tooltip;
  int order;
  int rank;
  String patch;
  String owned;
  String icon;
  Aspect type;
  Aspect aspect;
  List<Source> sources;

  factory FinalApi.fromMap(Map<String, dynamic> json) => FinalApi(
        id: json["id"],
        name: json["name"],
        description: json["description"],
        tooltip: json["tooltip"],
        order: json["order"],
        rank: json["rank"],
        patch: json["patch"],
        owned: json["owned"],
        icon: json["icon"],
        type: Aspect.fromMap(json["type"]),
        aspect: Aspect.fromMap(json["aspect"]),
        sources:
            List<Source>.from(json["sources"].map((x) => Source.fromMap(x))),
      );

  Map<String, dynamic> toMap() => {
        "id": id,
        "name": name,
        "description": description,
        "tooltip": tooltip,
        "order": order,
        "rank": rank,
        "patch": patch,
        "owned": owned,
        "icon": icon,
        "type": type.toMap(),
        "aspect": aspect.toMap(),
        "sources": List<dynamic>.from(sources.map((x) => x.toMap())),
      };
}

class Aspect {
  Aspect({
    required this.id,
    required this.name,
  });

  int id;
  Name? name;

  factory Aspect.fromMap(Map<String, dynamic> json) => Aspect(
        id: json["id"],
        name: nameValues.map[json["name"]],
      );

  Map<String, dynamic> toMap() => {
        "id": id,
        "name": nameValues.reverse[name],
      };
}

enum Name {
  WATER,
  FIRE,
  BLUNT,
  PIERCING,
  LIGHTNING,
  NONE,
  EARTH,
  SLASHING,
  ICE,
  WIND,
  PIERCING_FIRE,
  BLUNT_EARTH,
  MAGIC,
  PHYSICAL
}

final nameValues = EnumValues({
  "Blunt": Name.BLUNT,
  "Blunt/Earth": Name.BLUNT_EARTH,
  "Earth": Name.EARTH,
  "Fire": Name.FIRE,
  "Ice": Name.ICE,
  "Lightning": Name.LIGHTNING,
  "Magic": Name.MAGIC,
  "None": Name.NONE,
  "Physical": Name.PHYSICAL,
  "Piercing": Name.PIERCING,
  "Piercing/Fire": Name.PIERCING_FIRE,
  "Slashing": Name.SLASHING,
  "Water": Name.WATER,
  "Wind": Name.WIND
});

class Source {
  Source({
    required this.type,
    required this.text,
    required this.relatedType,
    required this.relatedId,
  });

  Type? type;
  String text;
  dynamic relatedType;
  dynamic relatedId;

  factory Source.fromMap(Map<String, dynamic> json) => Source(
        type: typeValues.map[json["type"]],
        text: json["text"],
        relatedType: json["related_type"],
        relatedId: json["related_id"],
      );

  Map<String, dynamic> toMap() => {
        "type": typeValues.reverse[type],
        "text": text,
        "related_type": relatedType,
        "related_id": relatedId,
      };
}

enum Type { OTHER, DUNGEON }

final typeValues = EnumValues({"Dungeon": Type.DUNGEON, "Other": Type.OTHER});

class EnumValues<T> {
  Map<String, T> map;
  Map<T, String>? reverseMap;

  EnumValues(this.map);

  Map<T, String> get reverse {
    if (reverseMap == null) {
      reverseMap = map.map((k, v) => new MapEntry(v, k));
    }
    return reverseMap!;
  }
}

request:

import 'dart:convert';
import 'dart:developer';
import 'package:apifinalfantasy/globals.dart' as globals;
import 'package:apifinalfantasy/models/final_api.dart';
import 'package:flutter/cupertino.dart';
import 'package:http/http.dart' as http;

class RemoteService {
  Future<List<FinalApi>> getPosts() async {
    var client = http.Client();
    var uri = Uri.parse('https://ffxivcollect.com/api/spells/');
    var response = await client.get(uri);
    try {
      if (response.statusCode == 200) {
        var json = response.body;
        final data = FinalApi.fromMap(jsonDecode(json));
        return [data];
      }
    } catch (e) {
      log(e.toString());
    }

    return [];
  }
}

CodePudding user response:

Based on your API, the results key constains all FinalApi instance, so for https://ffxivcollect.com/api/spells It will be

if (response.statusCode == 200) {
  var json = response.body;
  final result = jsonDecode(json)["results"] as List?;
  return result?.map((e) => FinalApi.fromMap(e)).toList() ?? [];
}
  • Related