/*
// To parse this JSON data, do
//
// final hisselist = hisselistFromJson(jsonString);
import 'dart:convert';
Hisselist hisselistFromJson(String str) => Hisselist.fromJson(json.decode(str));
String hisselistToJson(Hisselist data) => json.encode(data.toJson());
class Hisselist {
Hisselist({
required this.success,
required this.result,
});
bool success;
List<ResultClass> result;
factory Hisselist.fromJson(Map<String, dynamic> json) => Hisselist(
success: json["success"], result: json["result"].map<ResultClass>((x) => ResultClass.fromJson(x)).toList(),
);
Map<String, dynamic> toJson() => {
"success": success,
"result": result.map((x) => x.toJson()),
};
}
class ResultClass {
ResultClass({
required this.rate,
required this.lastprice,
required this.lastpricestr,
required this.hacim,
required this.hacimstr,
required this.text,
required this.code,
});
double rate;
double lastprice;
String lastpricestr;
double hacim;
String hacimstr;
String text;
String code;
factory ResultClass.fromJson(Map<String, dynamic> json) => ResultClass(
rate: double.tryParse(json["rate"].toString()) ?? 0.0,
lastprice: double.tryParse(json["lastprice"].toString()) ?? 0.0,
lastpricestr: json["lastpricestr"],
hacim: double.tryParse(json["hacim"].toString()) ?? 0.0,
hacimstr: json["hacimstr"],
text: json["text"],
code: json["code"],
);
Map<String, dynamic> toJson() => {
"rate": rate,
"lastprice": lastprice,
"lastpricestr": lastpricestr,
"hacim": hacim,
"hacimstr": hacimstr,
"text": text,
"code": code,
};
}
*/
// To parse this JSON data, do
//
// final hisselist = hisselistFromJson(jsonString);
import 'dart:convert';
Hisselist hisselistFromJson(String str) => Hisselist.fromJson(json.decode(str));
String hisselistToJson(Hisselist data) => json.encode(data.toJson());
class Hisselist {
Hisselist({
required this.success,
required this.result,
});
bool success;
List<Result> result;
factory Hisselist.fromJson(Map<String, dynamic> json) => Hisselist(
success: json["success"],
result: List<Result>.from(json["result"].map((x) => Result.fromJson(x))),
);
Map<String, dynamic> toJson() => {
"success": success,
"result": List<dynamic>.from(result.map((x) => x.toJson())),
};
}
class Result {
Result({
this.rate,
this.lastprice,
this.lastpricestr,
this.hacim,
this.hacimstr,
this.min,
this.minstr,
this.max,
this.maxstr,
this.time,
this.text,
this.code,
});
double? rate;
double? lastprice;
String? lastpricestr;
String? hacim;
String? hacimstr;
dynamic min;
String? minstr;
dynamic max;
String? maxstr;
Time? time;
String? text;
String? code;
factory Result.fromJson(Map<String, dynamic> json) => Result(
rate: json["rate"].toDouble(),
lastprice: json["lastprice"].toDouble(),
lastpricestr: json["lastpricestr"],
hacim: json["hacim"],
hacimstr: json["hacimstr"],
min: json["min"],
minstr: json["minstr"],
max: json["max"],
maxstr: json["maxstr"],
time: timeValues.map[json["time"]],
text: json["text"],
code: json["code"],
);
Map<String, dynamic> toJson() => {
"rate": rate,
"lastprice": lastprice,
"lastpricestr": lastpricestr,
"hacim": hacim,
"hacimstr": hacimstr,
"min": min,
"minstr": minstr,
"max": max,
"maxstr": maxstr,
"time": timeValues.reverse[time],
"text": text,
"code": code,
};
}
enum Time { THE_1809, THE_1808, THE_1805, THE_1810, THE_1759, THE_1755 }
final timeValues = EnumValues({
"17:55": Time.THE_1755,
"17:59": Time.THE_1759,
"18:05": Time.THE_1805,
"18:08": Time.THE_1808,
"18:09": Time.THE_1809,
"18:10": Time.THE_1810
});
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!;
}
}
And this is where i call api :
import 'package:flutter/material.dart';
import 'package:http/http.dart' as http;
import '../models/apis/hisselist.dart';
class Hisseler extends StatefulWidget {
const Hisseler({Key? key}) : super(key: key);
#override
State<Hisseler> createState() => _HisselerState();
}
class _HisselerState extends State<Hisseler> {
final scaffoldKey = GlobalKey<ScaffoldState>();
final url = Uri.parse('https://api.collectapi.com/economy/hisseSenedi');
var counter;
Hisselist? hisseResult;
Future callHisse() async {
try{
Map<String, String> requestHeaders = {
'Content-Type': 'application/json',
'Authorization': 'apikey 4xxxxP'
};
final response = await http.get(url,headers:requestHeaders);
if(response.statusCode == 200){
var result = hisselistFromJson(response.body);
if(mounted);
setState(() {
counter = result.result.length;
result.result.sort((a, b) => (a.text ?? "").compareTo(b.text ?? ""));
hisseResult = result;
});
return result;
} else {
print(response.statusCode);
}
} catch(e) {
print(e.toString());
}
}
#override
void initState() {
// TODO: implement initState
super.initState();
callHisse();
}
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
centerTitle: false,
automaticallyImplyLeading: false,
title: Text(
'Hisseler'
),
),
body: Center(
child: Padding(
padding: const EdgeInsets.all(8.0),
child: counter != null ?
ListView.separated(
itemCount: counter,
separatorBuilder: (context, index) {
return Divider(color: Colors.grey[400]);
},
itemBuilder: (context, index){
return Card(
child: ListTile(
contentPadding: EdgeInsets.all(10),
title: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
Text(hisseResult?.result[index].code??"", style: TextStyle(color: Colors.black, fontSize: 16, fontWeight: FontWeight.w500)),
Text(hisseResult?.result[index].text??"",style: TextStyle(color: Colors.grey[500], fontSize: 14))
],
),
trailing: Column(
children: <Widget>[
Text(hisseResult?.result[index].lastpricestr??"", style: TextStyle(color: Colors.black, fontSize: 16, fontWeight: FontWeight.w500)),
Container(
alignment: Alignment.center,
decoration: BoxDecoration(
borderRadius: BorderRadius.circular(5),
color: Colors.red
),
width: 75,
height: 25,
child: Text(hisseResult?.result[index].rate.toString()??"",style: TextStyle(color: Colors.white))
)
],
),
),);
}) : Center(child: CircularProgressIndicator(
)),
),
),
);
}
}
This is the result i get:
as you see here, code response start with "https:" i don't want to show this "https:" part from response. How i can fix this?
Thanks for your help
seems the "https:" comes emberded in your API data, therefore we need to replace that string from the variable code.
Replace the Text code with this:
Text((hisseResult?.result[index].code ?? "")
.replaceAll("https:", ""),
style: TextStyle(
color: Colors.black,
fontSize: 16,
fontWeight: FontWeight.w500))
Try this:
hisseResult?.result[index].code?.substring(5)
null safety fix also added
subString changed into substring
Related
hey im building a application which shows some information about certain things and this one certain widget does not show any type of information and just returns a white screen, this was no problem at first since i only really tested in on my emulator (Which worked everytime) but now that i downloaded the APK it only shows a white screen. i have used
<uses-permission android:name="android.permission.INTERNET" />
in my aindroidmanifest file.
my code:
Main.dart
class AllChampionsListedRoute extends StatefulWidget {
String summonerId, summonerName;
AllChampionsListedRoute(this.summonerId, this.summonerName);
#override
State<StatefulWidget> createState() {
return _AllChampionsListedRouteState(this.summonerId, this.summonerName);
}
}
class _AllChampionsListedRouteState extends State<AllChampionsListedRoute> {
TextEditingController editingController = TextEditingController();
var items = <String>[];
List<String> allChampListUncapitalized = [];
String summonerId, summonerName;
_AllChampionsListedRouteState(this.summonerId, this.summonerName);
#override
void initState() {
super.initState();
for (var champ in allChampList) {
allChampListUncapitalized.add(champ.toLowerCase());
items.add(champ.toLowerCase());
}
}
void filterSearchResults(String query) {
List<String> dummySearchList = <String>[];
dummySearchList.addAll(allChampListUncapitalized);
if(query.isNotEmpty) {
List<String> dummyListData = <String>[];
dummySearchList.forEach((item) {
if(item.contains(query)) {
dummyListData.add(item);
}
});
setState(() {
items.clear();
items.addAll(dummyListData);
});
return;
} else {
setState(() {
items.clear();
items.addAll(allChampListUncapitalized);
});
}
}
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: customAppBar(),
body: Container(
decoration: BoxDecoration(
gradient: LinearGradient(
begin: Alignment.centerLeft,
end: Alignment.centerRight,
colors: [
bgColorFront,
bgColorEnd,
],
),
),
child: Center(
child: Expanded(
child: FutureBuilder<Champions>(
future: getChampions(), // a previously-obtained Future<String> or null
builder: (BuildContext context, AsyncSnapshot<Champions> snapshotChamps) {
if (snapshotChamps.hasData) {
return Column(
children: [
TextField(
onChanged: (value) {
filterSearchResults(value);
},
inputFormatters: [
UpperCaseTextFormatter(),
],
controller: editingController,
style: TextStyle(
color: customColorGray,
fontSize: 20,
),
decoration: new InputDecoration(
enabledBorder: OutlineInputBorder(
borderSide: BorderSide(color: customColorDarkBlue, width: 2.0),
),
labelText: 'Champion',
labelStyle: TextStyle(
color: customColorTextBlue,
fontFamily: 'Spiegel',
fontSize: 20,
),
hintText: 'Fill in your champion here',
hintStyle: TextStyle(
color: customColorTextBlue,
fontFamily: 'Spiegel',
fontSize: 20,
),
),
maxLines: null,
),
Expanded(
child: ListView.builder(
shrinkWrap: true,
itemCount: items.length,
itemBuilder: (context, index) {
return ListTile(
title: Text(
'${capitalize(items[index])}',
style: TextStyle(
fontSize: 25,
),
),
onTap: () {
Navigator.push(
context,
MaterialPageRoute(builder: (context) => SummonerMasteryRoute(
snapshotChamps.data!.data["${capitalize(items[index])}"]!.key, capitalize(items[index]),
summonerId, snapshotChamps.data!.data["${capitalize(items[index])}"]!.image.full, summonerName
)),
);
},
);
},
),
)
],
);
} else if (snapshotChamps.hasError) {
return Text('Error: ${snapshotChamps.error}');
} else {
return SizedBox(
width: 60,
height: 60,
child: CircularProgressIndicator(),
);
}
},
),
)
),
),
);
}
}
Remoteservice.dart:
Future<Champions> getChampions() async {
String link = 'http://ddragon.leagueoflegends.com/cdn/12.22.1/data/en_US/champion.json';
final response = await http
.get(Uri.parse(link));
if (response.statusCode == 200) {
return Champions.fromJson(jsonDecode(response.body));
} else {
return throw Exception('Failed to load album');
}
}
champion.dart (class):
import 'dart:convert';
Champions championsFromJson(String str) => Champions.fromJson(json.decode(str));
String championsToJson(Champions data) => json.encode(data.toJson());
class Champions {
Champions({
required this.type,
required this.format,
required this.version,
required this.data,
});
Type? type;
String format;
Version? version;
Map<String, ChampData> data;
factory Champions.fromJson(Map<String, dynamic> json) => Champions(
type: typeValues.map[json["type"]],
format: json["format"],
version: versionValues.map[json["version"]],
data: Map.from(json["data"]).map((k, v) => MapEntry<String, ChampData>(k, ChampData.fromJson(v))),
);
Map<String, dynamic> toJson() => {
"type": typeValues.reverse?[type],
"format": format,
"version": versionValues.reverse?[version],
"data": Map.from(data).map((k, v) => MapEntry<String, dynamic>(k, v.toJson())),
};
}
class ChampData {
ChampData({
required this.version,
required this.id,
required this.key,
required this.name,
required this.title,
required this.blurb,
required this.info,
required this.image,
required this.tags,
required this.partype,
required this.stats,
});
Version? version;
String id;
String key;
String name;
String title;
String blurb;
Info info;
ChampImage image;
List<Tag> tags;
String partype;
Map<String, double> stats;
factory ChampData.fromJson(Map<String, dynamic> json) => ChampData(
version: versionValues.map[json["version"]],
id: json["id"],
key: json["key"],
name: json["name"],
title: json["title"],
blurb: json["blurb"],
info: Info.fromJson(json["info"]),
image: ChampImage.fromJson(json["image"]),
tags: List<Tag>.from(json["tags"].map((x) => tagValues.map[x])),
partype: json["partype"],
stats: Map.from(json["stats"]).map((k, v) => MapEntry<String, double>(k, v.toDouble())),
);
Map<String, dynamic> toJson() => {
"version": versionValues.reverse?[version],
"id": id,
"key": key,
"name": name,
"title": title,
"blurb": blurb,
"info": info.toJson(),
"image": image.toJson(),
"tags": List<dynamic>.from(tags.map((x) => tagValues.reverse?[x])),
"partype": partype,
"stats": Map.from(stats).map((k, v) => MapEntry<String, dynamic>(k, v)),
};
}
class ChampImage {
ChampImage({
required this.full,
required this.sprite,
required this.group,
required this.x,
required this.y,
required this.w,
required this.h,
});
String full;
Sprite? sprite;
Type? group;
int x;
int y;
int w;
int h;
factory ChampImage.fromJson(Map<String, dynamic> json) => ChampImage(
full: json["full"],
sprite: spriteValues.map[json["sprite"]],
group: typeValues.map[json["group"]],
x: json["x"],
y: json["y"],
w: json["w"],
h: json["h"],
);
Map<String, dynamic> toJson() => {
"full": full,
"sprite": spriteValues.reverse?[sprite],
"group": typeValues.reverse?[group],
"x": x,
"y": y,
"w": w,
"h": h,
};
}
enum Type { CHAMPION }
final typeValues = EnumValues({
"champion": Type.CHAMPION
});
enum Sprite { CHAMPION0_PNG, CHAMPION1_PNG, CHAMPION2_PNG, CHAMPION3_PNG, CHAMPION4_PNG, CHAMPION5_PNG }
final spriteValues = EnumValues({
"champion0.png": Sprite.CHAMPION0_PNG,
"champion1.png": Sprite.CHAMPION1_PNG,
"champion2.png": Sprite.CHAMPION2_PNG,
"champion3.png": Sprite.CHAMPION3_PNG,
"champion4.png": Sprite.CHAMPION4_PNG,
"champion5.png": Sprite.CHAMPION5_PNG
});
class Info {
Info({
required this.attack,
required this.defense,
required this.magic,
required this.difficulty,
});
int attack;
int defense;
int magic;
int difficulty;
factory Info.fromJson(Map<String, dynamic> json) => Info(
attack: json["attack"],
defense: json["defense"],
magic: json["magic"],
difficulty: json["difficulty"],
);
Map<String, dynamic> toJson() => {
"attack": attack,
"defense": defense,
"magic": magic,
"difficulty": difficulty,
};
}
enum Tag { FIGHTER, TANK, MAGE, ASSASSIN, MARKSMAN, SUPPORT }
final tagValues = EnumValues({
"Assassin": Tag.ASSASSIN,
"Fighter": Tag.FIGHTER,
"Mage": Tag.MAGE,
"Marksman": Tag.MARKSMAN,
"Support": Tag.SUPPORT,
"Tank": Tag.TANK
});
enum Version { THE_12221 }
final versionValues = EnumValues({
"12.22.1": Version.THE_12221
});
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;
}
}
This is how it was supposed to look (and how it looks on my emulator):
This is my model;
/*
// To parse this JSON data, do
//
// final hisselist = hisselistFromJson(jsonString);
import 'dart:convert';
Hisselist hisselistFromJson(String str) => Hisselist.fromJson(json.decode(str));
String hisselistToJson(Hisselist data) => json.encode(data.toJson());
class Hisselist {
Hisselist({
required this.success,
required this.result,
});
bool success;
List<ResultClass> result;
factory Hisselist.fromJson(Map<String, dynamic> json) => Hisselist(
success: json["success"], result: json["result"].map<ResultClass>((x) => ResultClass.fromJson(x)).toList(),
);
Map<String, dynamic> toJson() => {
"success": success,
"result": result.map((x) => x.toJson()),
};
}
class ResultClass {
ResultClass({
required this.rate,
required this.lastprice,
required this.lastpricestr,
required this.hacim,
required this.hacimstr,
required this.text,
required this.code,
});
double rate;
double lastprice;
String lastpricestr;
double hacim;
String hacimstr;
String text;
String code;
factory ResultClass.fromJson(Map<String, dynamic> json) => ResultClass(
rate: double.tryParse(json["rate"].toString()) ?? 0.0,
lastprice: double.tryParse(json["lastprice"].toString()) ?? 0.0,
lastpricestr: json["lastpricestr"],
hacim: double.tryParse(json["hacim"].toString()) ?? 0.0,
hacimstr: json["hacimstr"],
text: json["text"],
code: json["code"],
);
Map<String, dynamic> toJson() => {
"rate": rate,
"lastprice": lastprice,
"lastpricestr": lastpricestr,
"hacim": hacim,
"hacimstr": hacimstr,
"text": text,
"code": code,
};
}
*/
// To parse this JSON data, do
//
// final hisselist = hisselistFromJson(jsonString);
import 'dart:convert';
Hisselist hisselistFromJson(String str) => Hisselist.fromJson(json.decode(str));
String hisselistToJson(Hisselist data) => json.encode(data.toJson());
class Hisselist {
Hisselist({
required this.success,
required this.result,
});
bool success;
List<Result> result;
factory Hisselist.fromJson(Map<String, dynamic> json) => Hisselist(
success: json["success"],
result: List<Result>.from(json["result"].map((x) => Result.fromJson(x))),
);
Map<String, dynamic> toJson() => {
"success": success,
"result": List<dynamic>.from(result.map((x) => x.toJson())),
};
}
class Result {
Result({
this.rate,
this.lastprice,
this.lastpricestr,
this.hacim,
this.hacimstr,
this.min,
this.minstr,
this.max,
this.maxstr,
this.time,
this.text,
this.code,
});
double? rate;
double? lastprice;
String? lastpricestr;
String? hacim;
String? hacimstr;
dynamic min;
String? minstr;
dynamic max;
String? maxstr;
Time? time;
String? text;
String? code;
factory Result.fromJson(Map<String, dynamic> json) => Result(
rate: json["rate"].toDouble(),
lastprice: json["lastprice"].toDouble(),
lastpricestr: json["lastpricestr"],
hacim: json["hacim"],
hacimstr: json["hacimstr"],
min: json["min"],
minstr: json["minstr"],
max: json["max"],
maxstr: json["maxstr"],
time: timeValues.map[json["time"]],
text: json["text"],
code: json["code"],
);
Map<String, dynamic> toJson() => {
"rate": rate,
"lastprice": lastprice,
"lastpricestr": lastpricestr,
"hacim": hacim,
"hacimstr": hacimstr,
"min": min,
"minstr": minstr,
"max": max,
"maxstr": maxstr,
"time": timeValues.reverse[time],
"text": text,
"code": code,
};
}
enum Time { THE_1809, THE_1808, THE_1805, THE_1810, THE_1759, THE_1755 }
final timeValues = EnumValues({
"17:55": Time.THE_1755,
"17:59": Time.THE_1759,
"18:05": Time.THE_1805,
"18:08": Time.THE_1808,
"18:09": Time.THE_1809,
"18:10": Time.THE_1810
});
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!;
}
}
This is where i call api:
class Hisseler extends StatefulWidget {
const Hisseler({Key? key}) : super(key: key);
#override
State<Hisseler> createState() => _HisselerState();
}
class _HisselerState extends State<Hisseler> {
final controller = TextEditingController();
final scaffoldKey = GlobalKey<ScaffoldState>();
final url = Uri.parse('https://api.collectapi.com/economy/hisseSenedi');
var counter;
Hisselist? hisseResult;
Future callHisse() async {
try{
Map<String, String> requestHeaders = {
'Content-Type': 'application/json',
'Authorization': 'apikey xxx:xxx'
};
final response = await http.get(url,headers:requestHeaders);
if(response.statusCode == 200){
var result = hisselistFromJson(response.body);
if(mounted);
setState(() {
counter = result.result.length;
result.result.sort((a, b) => (a.text ?? "").compareTo(b.text ?? ""));
hisseResult = result;
});
return result;
} else {
print(response.statusCode);
}
} catch(e) {
print(e.toString());
}
}
#override
void initState() {
// TODO: implement initState
super.initState();
callHisse();
}
#override
Widget build(BuildContext context) {
final style = controller.text.isEmpty
? const TextStyle(color: Colors.black54)
: const TextStyle(color: Colors.black);
return Scaffold(
appBar: AppBar(
centerTitle: false,
automaticallyImplyLeading: false,
title: Text(
'Hisseler'
),
),
body: Column(
children: [
Container(
margin: const EdgeInsets.fromLTRB(16, 16, 16, 16),
child: TextField(
controller: controller,
decoration: InputDecoration(
prefixIcon: const Icon(Icons.search),
suffixIcon: controller.text.isNotEmpty
? GestureDetector(
child: Icon(Icons.close, color: style.color),
onTap: () {
controller.clear();
FocusScope.of(context).requestFocus(FocusNode());
searchHisse('');
},
)
: null,
hintText: 'Hisse Ara',
border: OutlineInputBorder(
borderRadius: BorderRadius.circular(20),
borderSide: const BorderSide(color: Colors.black26),
),
),
onChanged: searchHisse,
),
),
Expanded(
child: Center(
child: Padding(
padding: const EdgeInsets.all(8.0),
child: counter != null ?
ReorderableListView.builder(
itemCount: counter,
itemBuilder: (context, index){
return Card(
key: ValueKey(hisseResult?.result[index]),
child: ListTile(
contentPadding: EdgeInsets.all(10),
title: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
Text((hisseResult?.result[index].code ?? "")
.replaceAll("https:", ""),
style: TextStyle(
color: Colors.black,
fontSize: 16,
fontWeight: FontWeight.w500)),
Text(hisseResult?.result[index].text??"",style: TextStyle(color: Colors.grey[500], fontSize: 14))
],
),
trailing: Column(
children: <Widget>[
Text(hisseResult?.result[index].lastpricestr??"", style: TextStyle(color: Colors.black, fontSize: 16, fontWeight: FontWeight.w500)),
Container(
alignment: Alignment.center,
decoration: BoxDecoration(
borderRadius: BorderRadius.circular(5),
color: (hisseResult?.result[index].rate ?? 0) > 0
? Colors.green
: Colors.red),
width: 75,
height: 25,
child: Text(hisseResult?.result[index].rate.toString() ?? "",
style: TextStyle(color: Colors.white)))
],
),
onTap: () => Navigator.push(
context, MaterialPageRoute(builder: (context) => StocksDetailScreen(
degisimoran: hisseResult?.result[index].rate!.toDouble(),
sondeger: hisseResult?.result[index].lastpricestr??"",
hacim: hisseResult?.result[index].hacimstr ?? "",
mindeger : hisseResult?.result[index].minstr?? "",
maxdeger : hisseResult?.result[index].maxstr?? "",
hisseismi : hisseResult?.result[index].text?? "",
hissekodu : hisseResult?.result[index].code?? "",
min : hisseResult?.result[index].min!.toDouble(),
max : hisseResult?.result[index].max!.toDouble(),
son : hisseResult?.result[index].lastprice!.toDouble(),
)),),
),
);
},
onReorder: (oldIndex, newIndex) {
setState(() {
if (newIndex > oldIndex) {
newIndex = newIndex - 1;
}
final element = hisseResult?.result.removeAt(oldIndex);
hisseResult?.result.insert(newIndex, element!);
});
},) : Center(child: CircularProgressIndicator(
)),
),
),
),
],
),
);
}
void searchHisse(String query) {
final suggestions = hisseResult?.result.where((code) {
final hisseTitle = hisseResult?.result;
final input = query.toLowerCase();
return hisseTitle!.contains(input);
}).toList();
setState(() => hisseResult = suggestions as Hisselist?);
}
}
But nothing happens on search result :
I think the problem is on searchHisse() but i am not sure. How can i make this work? Thanks for your help
Based on your code , you only call api once and you get the full list only once too.
i think you need to separated in to 2 list object.
eg case:
initstate you fetch api callHisse(); and get the data.
then you can show all the data from hisseResult.
after 1 onchanged on Textfield you call searchHisse(String query) , which is updated your hisseResult. now you only have data with first letters from onchanged
then you tapped on textfield and clear the controller. there is no data on the list left that match to query
this is what i suggest
Hisselist? hisseResult; // data you get from API
Hisselist? hisseShow; // list that you show
and on your search function you need to add this condition
void searchHisse(String query) {
if (query == '') {
setState((){hisseShow =hisseResult;});
return;
}
final suggestions = hisseResult?.result.where((code) {
final hisseTitle = hisseResult?.result;
final input = query.toLowerCase();
return hisseTitle!.contains(input);
}).toList();
// based on your model data
setState(() => hisseShow = Hisselist(result: suggestions, success:true );
}
}
and you show your list
return Card(
key: ValueKey(hisseShow?.result[index]),
child: ListTile(
.....
I use this json to list stocks(BIST). https://bigpara.hurriyet.com.tr/api/v1/hisse/list This is my model:
// To parse this JSON data, do
//
// final bigParaList = bigParaListFromJson(jsonString);
import 'dart:convert';
BigParaList bigParaListFromJson(String str) => BigParaList.fromJson(json.decode(str));
String bigParaListToJson(BigParaList data) => json.encode(data.toJson());
class BigParaList {
BigParaList({
required this.code,
required this.data,
});
String code;
List<Datum> data;
factory BigParaList.fromJson(Map<String, dynamic> json) => BigParaList(
code: json["code"],
data: List<Datum>.from(json["data"].map((x) => Datum.fromJson(x))),
);
Map<String, dynamic> toJson() => {
"code": code,
"data": List<dynamic>.from(data.map((x) => x.toJson())),
};
}
class Datum {
Datum({
required this.id,
required this.kod,
required this.ad,
required this.tip,
});
int? id;
String? kod;
String? ad;
Tip? tip;
factory Datum.fromJson(Map<String, dynamic> json) => Datum(
id: json["id"],
kod: json["kod"],
ad: json["ad"],
tip: tipValues.map[json["tip"]],
);
Map<String, dynamic> toJson() => {
"id": id,
"kod": kod,
"ad": ad,
"tip": tipValues.reverse[tip],
};
}
enum Tip { HISSE }
final tipValues = EnumValues({
"Hisse": Tip.HISSE
});
class EnumValues<T> {
Map<String, T> map;
Map<T, String>? reverseMap;
EnumValues(this.map);
Map<T, String> get reverse {
return reverseMap ??= map.map((k, v) => MapEntry(v, k));
}
}
And this is my 2nd model which includes stock details. https://bigpara.hurriyet.com.tr/api/v1/borsa/hisseyuzeysel/AEFES (AEFES is a sample any of the stocks can be used from the previous list)
// To parse this JSON data, do
//
// final bigParaDetay = bigParaDetayFromJson(jsonString);
import 'dart:convert';
BigParaDetay bigParaDetayFromJson(String str) => BigParaDetay.fromJson(json.decode(str));
String bigParaDetayToJson(BigParaDetay data) => json.encode(data.toJson());
class BigParaDetay {
BigParaDetay({
required this.code,
required this.data,
});
String code;
Map<String, Datum?> data;
factory BigParaDetay.fromJson(Map<String, dynamic> json) => BigParaDetay(
code: json["code"],
data: Map.from(json["data"]).map((k, v) => MapEntry<String, Datum?>(k, v == null ? null : Datum.fromJson(v))),
);
Map<String, dynamic> toJson() => {
"code": code,
"data": Map.from(data).map((k, v) => MapEntry<String, dynamic>(k, v == null ? null : v.toJson())),
};
}
class Datum {
Datum({
this.sembolid,
this.sembol,
this.tarih,
this.sektorid,
this.alis,
this.satis,
this.acilis,
this.yuksek,
this.yukseK1,
this.yukseK2,
this.dusuk,
this.dusuK1,
this.dusuK2,
this.kapanis,
this.kapaniS1,
this.kapaniS2,
this.hacimlot,
this.hacimloT1,
this.hacimloT2,
this.aort,
this.aorT1,
this.aorT2,
this.hacimtldun,
this.hacimyuzdedegisim,
this.hacimtl,
this.hacimtL1,
this.hacimtL2,
this.dunkukapanis,
this.oncekikapanis,
this.izafikapanis,
this.tavan,
this.taban,
this.yilyuksek,
this.yildusuk,
this.ayyuksek,
this.aydusuk,
this.haftayuksek,
this.haftadusuk,
this.oncekiyilkapanis,
this.oncekiaykapanis,
this.oncekihaftakapanis,
this.yilortalama,
this.ayortalama,
this.haftaortalama,
this.yuzdedegisimS1,
this.yuzdedegisimS2,
this.yuzdedegisim,
this.fiyatadimi,
this.kaykar,
this.sermaye,
this.saklamaor,
this.netkar,
this.net,
this.fiyatkaz,
this.piydeg,
this.kapanisfark,
this.donem,
this.ozsermaye,
this.beta,
this.xU100Ag,
this.aciklama,
});
int? sembolid;
String? sembol;
DateTime? tarih;
int? sektorid;
double? alis;
double? satis;
double? acilis;
double? yuksek;
double? yukseK1;
double? yukseK2;
double? dusuk;
double? dusuK1;
double? dusuK2;
double? kapanis;
double? kapaniS1;
double? kapaniS2;
int? hacimlot;
int? hacimloT1;
int? hacimloT2;
double? aort;
double? aorT1;
double? aorT2;
int? hacimtldun;
double? hacimyuzdedegisim;
int? hacimtl;
int? hacimtL1;
int? hacimtL2;
int? dunkukapanis;
int? oncekikapanis;
int? izafikapanis;
double? tavan;
double? taban;
double? yilyuksek;
double? yildusuk;
double? ayyuksek;
double? aydusuk;
double? haftayuksek;
double? haftadusuk;
double? oncekiyilkapanis;
double? oncekiaykapanis;
double? oncekihaftakapanis;
double? yilortalama;
double? ayortalama;
double? haftaortalama;
double? yuzdedegisimS1;
double? yuzdedegisimS2;
double? yuzdedegisim;
double? fiyatadimi;
int? kaykar;
int? sermaye;
double? saklamaor;
int? netkar;
double? net;
double? fiyatkaz;
double? piydeg;
dynamic kapanisfark;
String? donem;
int? ozsermaye;
double? beta;
double? xU100Ag;
String? aciklama;
factory Datum.fromJson(Map<String, dynamic> json) => Datum(
sembolid: json["sembolid"],
sembol: json["sembol"],
tarih: DateTime.parse(json["tarih"]),
sektorid: json["sektorid"],
alis: json["alis"].toDouble(),
satis: json["satis"].toDouble(),
acilis: json["acilis"].toDouble(),
yuksek: json["yuksek"].toDouble(),
yukseK1: json["yukseK1"].toDouble(),
yukseK2: json["yukseK2"].toDouble(),
dusuk: json["dusuk"].toDouble(),
dusuK1: json["dusuK1"].toDouble(),
dusuK2: json["dusuK2"].toDouble(),
kapanis: json["kapanis"].toDouble(),
kapaniS1: json["kapaniS1"].toDouble(),
kapaniS2: json["kapaniS2"].toDouble(),
hacimlot: json["hacimlot"],
hacimloT1: json["hacimloT1"],
hacimloT2: json["hacimloT2"],
aort: json["aort"].toDouble(),
aorT1: json["aorT1"].toDouble(),
aorT2: json["aorT2"].toDouble(),
hacimtldun: json["hacimtldun"],
hacimyuzdedegisim: json["hacimyuzdedegisim"].toDouble(),
hacimtl: json["hacimtl"],
hacimtL1: json["hacimtL1"],
hacimtL2: json["hacimtL2"],
dunkukapanis: json["dunkukapanis"],
oncekikapanis: json["oncekikapanis"],
izafikapanis: json["izafikapanis"],
tavan: json["tavan"].toDouble(),
taban: json["taban"].toDouble(),
yilyuksek: json["yilyuksek"].toDouble(),
yildusuk: json["yildusuk"].toDouble(),
ayyuksek: json["ayyuksek"].toDouble(),
aydusuk: json["aydusuk"].toDouble(),
haftayuksek: json["haftayuksek"].toDouble(),
haftadusuk: json["haftadusuk"].toDouble(),
oncekiyilkapanis: json["oncekiyilkapanis"].toDouble(),
oncekiaykapanis: json["oncekiaykapanis"].toDouble(),
oncekihaftakapanis: json["oncekihaftakapanis"].toDouble(),
yilortalama: json["yilortalama"].toDouble(),
ayortalama: json["ayortalama"].toDouble(),
haftaortalama: json["haftaortalama"].toDouble(),
yuzdedegisimS1: json["yuzdedegisimS1"].toDouble(),
yuzdedegisimS2: json["yuzdedegisimS2"].toDouble(),
yuzdedegisim: json["yuzdedegisim"].toDouble(),
fiyatadimi: json["fiyatadimi"].toDouble(),
kaykar: json["kaykar"],
sermaye: json["sermaye"],
saklamaor: json["saklamaor"].toDouble(),
netkar: json["netkar"],
net: json["net"].toDouble(),
fiyatkaz: json["fiyatkaz"].toDouble(),
piydeg: json["piydeg"].toDouble(),
kapanisfark: json["kapanisfark"],
donem: json["donem"],
ozsermaye: json["ozsermaye"],
beta: json["beta"].toDouble(),
xU100Ag: json["xU100AG"].toDouble(),
aciklama: json["aciklama"],
);
Map<String, dynamic> toJson() => {
"sembolid": sembolid,
"sembol": sembol,
"tarih": tarih.toString(),
"sektorid": sektorid,
"alis": alis,
"satis": satis,
"acilis": acilis,
"yuksek": yuksek,
"yukseK1": yukseK1,
"yukseK2": yukseK2,
"dusuk": dusuk,
"dusuK1": dusuK1,
"dusuK2": dusuK2,
"kapanis": kapanis,
"kapaniS1": kapaniS1,
"kapaniS2": kapaniS2,
"hacimlot": hacimlot,
"hacimloT1": hacimloT1,
"hacimloT2": hacimloT2,
"aort": aort,
"aorT1": aorT1,
"aorT2": aorT2,
"hacimtldun": hacimtldun,
"hacimyuzdedegisim": hacimyuzdedegisim,
"hacimtl": hacimtl,
"hacimtL1": hacimtL1,
"hacimtL2": hacimtL2,
"dunkukapanis": dunkukapanis,
"oncekikapanis": oncekikapanis,
"izafikapanis": izafikapanis,
"tavan": tavan,
"taban": taban,
"yilyuksek": yilyuksek,
"yildusuk": yildusuk,
"ayyuksek": ayyuksek,
"aydusuk": aydusuk,
"haftayuksek": haftayuksek,
"haftadusuk": haftadusuk,
"oncekiyilkapanis": oncekiyilkapanis,
"oncekiaykapanis": oncekiaykapanis,
"oncekihaftakapanis": oncekihaftakapanis,
"yilortalama": yilortalama,
"ayortalama": ayortalama,
"haftaortalama": haftaortalama,
"yuzdedegisimS1": yuzdedegisimS1,
"yuzdedegisimS2": yuzdedegisimS2,
"yuzdedegisim": yuzdedegisim,
"fiyatadimi": fiyatadimi,
"kaykar": kaykar,
"sermaye": sermaye,
"saklamaor": saklamaor,
"netkar": netkar,
"net": net,
"fiyatkaz": fiyatkaz,
"piydeg": piydeg,
"kapanisfark": kapanisfark,
"donem": donem,
"ozsermaye": ozsermaye,
"beta": beta,
"xU100AG": xU100Ag,
"aciklama": aciklama,
};
}
This is where i call api :
class Hisseler extends StatefulWidget {
const Hisseler({Key? key}) : super(key: key);
#override
State<Hisseler> createState() => _HisselerState();
}
class _HisselerState extends State<Hisseler> {
Future<BigParaDetay?> callHisseDetail(String kod) async {
try {
final detailUrl = Uri.parse("https://bigpara.hurriyet.com.tr/api/v1/borsa/hisseyuzeysel/$kod");
final response = await http.get(detailUrl);
if(response.statusCode == 200){
final data = bigParaDetayFromJson(response.body);
return data;
} else {
print(response.statusCode);
}
} catch(e) {
print(e.toString());
}
return null;
}
final scaffoldKey = GlobalKey<ScaffoldState>();
final url = Uri.parse('https://bigpara.hurriyet.com.tr/api/v1/hisse/list');
var counter;
BigParaList? hisseResult;
Future callHisse() async {
try{
final response = await http.get(url,);
if(response.statusCode == 200){
var data = bigParaListFromJson(response.body);
if(mounted);
setState(() {
counter = data.data.length;
hisseResult = data;
});
return data;
} else {
print(response.statusCode);
}
} catch(e) {
print(e.toString());
}
}
#override
void initState() {
// TODO: implement initState
super.initState();
callHisse();
}
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
centerTitle: false,
automaticallyImplyLeading: false,
title: Text(
'Hisseler'
),
),
body: Center(
child: Padding(
padding: const EdgeInsets.all(8.0),
child: counter != null ?
ListView.separated(
itemCount: counter,
separatorBuilder: (context, index) => SizedBox(
height: 2,
),
itemBuilder: (context, index){
return Card(
child: ListTile(
title: Text(hisseResult?.data[index].kod.toString()??""),
subtitle: Text(hisseResult?.data[index].ad??""),
onTap: () async {
final detailData = await callHisseDetail(hisseResult?.data[index].kod ?? "");
Navigator.push(
context,
MaterialPageRoute(
builder: (context) => StocksDetailScreen(
subtitle: hisseResult?.data[index].ad??"",
title: hisseResult?.data[index].kod??"",
data: detailData,
),
),
);
}
),
);
}) : Center(child: CircularProgressIndicator(
)),
),
),
);
}
}
Everything is ok until here. This is the detail page structure when I want to show stock details from the 2nd model to the stock I call from the first API.
import 'package:flutter/material.dart';
import 'package:provider/provider.dart';
import '../blocs/ads_bloc.dart';
import '../models/apis/bigpara_detay.dart';
import '../widgets/banner_ad_admob.dart';
class StocksDetailScreen extends StatelessWidget {
final String title;
final String subtitle;
final BigParaDetay? data;
const StocksDetailScreen({
Key? key,
required this.title,
required this.subtitle,
this.data,
}) : super(key: key);
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text(title,style: TextStyle(fontSize: 18, fontWeight: FontWeight.w900),),
),
body: SafeArea(
bottom: true,
top: false,
maintainBottomViewPadding: true,
child: Column(
children: [
Expanded(
child: CustomScrollView(
slivers: <Widget>[
SliverToBoxAdapter(
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
Padding(
padding: const EdgeInsets.all(8.0),
child: Container(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
Text(data.sembol,style: TextStyle(fontSize: 18, fontWeight: FontWeight.w900),),
],
),
),
),
Divider(height: 3.6,),
SizedBox(height: 50,),
Padding(
padding: const EdgeInsets.all(8.0),
child: Center(
child: Text(subtitle,style: TextStyle(fontSize: 20,fontWeight: FontWeight.w600), textAlign: TextAlign.center,),
),
)
],
),
),
],
),
),
// -- Banner ads --
context.watch<AdsBloc>().bannerAdEnabled == false ? Container()
: BannerAdAdmob() //admob
//: BannerAdFb() //fb
],
),
)
);
}
}
As you see here I will use details from the 2nd model. This page is not finished. But I want to call data from 2nd model to continue.
I tried
Text(data.sembol,style: TextStyle(fontSize: 18, fontWeight: FontWeight.w900),),
to show the data from the 2nd model but I get this error: The property 'symbol' can't be unconditionally accessed because the receiver can be 'null'.
How can I fix this? How can I call data from the 2n model on the detail page? Thanks for your help
BigParaDetay
Future<BigParaDetay?> callHisseDetail(String kod) async {
try {
final detailUrl = Uri.parse("https://bigpara.hurriyet.com.tr/api/v1/borsa/hisseyuzeysel/$kod");
final response = await http.get(detailUrl);
if(response.statusCode == 200){
final data = bigParaDetayFromJson(response.body);
return data;
} else {
print(response.statusCode);
}
} catch(e) {
print(e.toString());
}
return null;
}
Your data is nullable final BigParaDetay? data;, provide default value on cases like
Text(data?.data??"got null", ),
if you like access sembol it will be like
Text("${data?.data.values.first["sembol"]}")
//or
Text("${data?.data.values?.first["sembol"]}")
data?.data will provide a map of
/*
// To parse this JSON data, do
//
// final hisselist = hisselistFromJson(jsonString);
import 'dart:convert';
Hisselist hisselistFromJson(String str) => Hisselist.fromJson(json.decode(str));
String hisselistToJson(Hisselist data) => json.encode(data.toJson());
class Hisselist {
Hisselist({
required this.success,
required this.result,
});
bool success;
List<ResultClass> result;
factory Hisselist.fromJson(Map<String, dynamic> json) => Hisselist(
success: json["success"], result: json["result"].map<ResultClass>((x) => ResultClass.fromJson(x)).toList(),
);
Map<String, dynamic> toJson() => {
"success": success,
"result": result.map((x) => x.toJson()),
};
}
class ResultClass {
ResultClass({
required this.rate,
required this.lastprice,
required this.lastpricestr,
required this.hacim,
required this.hacimstr,
required this.text,
required this.code,
});
double rate;
double lastprice;
String lastpricestr;
double hacim;
String hacimstr;
String text;
String code;
factory ResultClass.fromJson(Map<String, dynamic> json) => ResultClass(
rate: double.tryParse(json["rate"].toString()) ?? 0.0,
lastprice: double.tryParse(json["lastprice"].toString()) ?? 0.0,
lastpricestr: json["lastpricestr"],
hacim: double.tryParse(json["hacim"].toString()) ?? 0.0,
hacimstr: json["hacimstr"],
text: json["text"],
code: json["code"],
);
Map<String, dynamic> toJson() => {
"rate": rate,
"lastprice": lastprice,
"lastpricestr": lastpricestr,
"hacim": hacim,
"hacimstr": hacimstr,
"text": text,
"code": code,
};
}
*/
// To parse this JSON data, do
//
// final hisselist = hisselistFromJson(jsonString);
import 'dart:convert';
Hisselist hisselistFromJson(String str) => Hisselist.fromJson(json.decode(str));
String hisselistToJson(Hisselist data) => json.encode(data.toJson());
class Hisselist {
Hisselist({
required this.success,
required this.result,
});
bool success;
List<Result> result;
factory Hisselist.fromJson(Map<String, dynamic> json) => Hisselist(
success: json["success"],
result: List<Result>.from(json["result"].map((x) => Result.fromJson(x))),
);
Map<String, dynamic> toJson() => {
"success": success,
"result": List<dynamic>.from(result.map((x) => x.toJson())),
};
}
class Result {
Result({
this.rate,
this.lastprice,
this.lastpricestr,
this.hacim,
this.hacimstr,
this.min,
this.minstr,
this.max,
this.maxstr,
this.time,
this.text,
this.code,
});
double? rate;
double? lastprice;
String? lastpricestr;
String? hacim;
String? hacimstr;
dynamic min;
String? minstr;
dynamic max;
String? maxstr;
Time? time;
String? text;
String? code;
factory Result.fromJson(Map<String, dynamic> json) => Result(
rate: json["rate"].toDouble(),
lastprice: json["lastprice"].toDouble(),
lastpricestr: json["lastpricestr"],
hacim: json["hacim"],
hacimstr: json["hacimstr"],
min: json["min"],
minstr: json["minstr"],
max: json["max"],
maxstr: json["maxstr"],
time: timeValues.map[json["time"]],
text: json["text"],
code: json["code"],
);
Map<String, dynamic> toJson() => {
"rate": rate,
"lastprice": lastprice,
"lastpricestr": lastpricestr,
"hacim": hacim,
"hacimstr": hacimstr,
"min": min,
"minstr": minstr,
"max": max,
"maxstr": maxstr,
"time": timeValues.reverse[time],
"text": text,
"code": code,
};
}
enum Time { THE_1809, THE_1808, THE_1805, THE_1810, THE_1759, THE_1755 }
final timeValues = EnumValues({
"17:55": Time.THE_1755,
"17:59": Time.THE_1759,
"18:05": Time.THE_1805,
"18:08": Time.THE_1808,
"18:09": Time.THE_1809,
"18:10": Time.THE_1810
});
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!;
}
}
And this is where i call api :
import 'package:flutter/material.dart';
import 'package:http/http.dart' as http;
import '../models/apis/hisselist.dart';
class Hisseler extends StatefulWidget {
const Hisseler({Key? key}) : super(key: key);
#override
State<Hisseler> createState() => _HisselerState();
}
class _HisselerState extends State<Hisseler> {
final scaffoldKey = GlobalKey<ScaffoldState>();
final url = Uri.parse('https://api.collectapi.com/economy/hisseSenedi');
var counter;
Hisselist? hisseResult;
Future callHisse() async {
try{
Map<String, String> requestHeaders = {
'Content-Type': 'application/json',
'Authorization': 'apikey 4xxxxP'
};
final response = await http.get(url,headers:requestHeaders);
if(response.statusCode == 200){
var result = hisselistFromJson(response.body);
if(mounted);
setState(() {
counter = result.result.length;
result.result.sort((a, b) => (a.text ?? "").compareTo(b.text ?? ""));
hisseResult = result;
});
return result;
} else {
print(response.statusCode);
}
} catch(e) {
print(e.toString());
}
}
#override
void initState() {
// TODO: implement initState
super.initState();
callHisse();
}
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
centerTitle: false,
automaticallyImplyLeading: false,
title: Text(
'Hisseler'
),
),
body: Center(
child: Padding(
padding: const EdgeInsets.all(8.0),
child: counter != null ?
ListView.separated(
itemCount: counter,
separatorBuilder: (context, index) {
return Divider(color: Colors.grey[400]);
},
itemBuilder: (context, index){
return Card(
child: ListTile(
contentPadding: EdgeInsets.all(10),
title: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
Text(hisseResult?.result[index].code??"", style: TextStyle(color: Colors.black, fontSize: 16, fontWeight: FontWeight.w500)),
Text(hisseResult?.result[index].text??"",style: TextStyle(color: Colors.grey[500], fontSize: 14))
],
),
trailing: Column(
children: <Widget>[
Text(hisseResult?.result[index].lastpricestr??"", style: TextStyle(color: Colors.black, fontSize: 16, fontWeight: FontWeight.w500)),
Container(
alignment: Alignment.center,
decoration: BoxDecoration(
borderRadius: BorderRadius.circular(5),
color: Colors.red
),
width: 75,
height: 25,
child: Text(hisseResult?.result[index].rate.toString()??"",style: TextStyle(color: Colors.white))
)
],
),
),);
}) : Center(child: CircularProgressIndicator(
)),
),
),
);
}
}
This is the result i get:
as you see here, rate result can be negative or positive. I want to make the red color green if the value is green. how can I do this?
Thanks for your help
replace your container with this code:
Container(
alignment: Alignment.center,
decoration: BoxDecoration(
borderRadius: BorderRadius.circular(5),
color: (hisseResult?.result[index].rate ?? 0) > 0
? Colors.green
: Colors.red),
width: 75,
height: 25,
child: Text(hisseResult?.result[index].rate.toString() ?? "",
style: TextStyle(color: Colors.white)))
if rate > 0, the container is set to green, else container is set to red
Greetings!
Flutter allows conditions when giving values to widgets atributes.
Just use a ternary operator which is very clean visual and suits this perfectly:
color: hisseResult?.result[index].rate > 0 ? Colors.green : Colors.red,
Selamlar :)
I'M trying to call an api. This is my model file:
// To parse this JSON data, do
//
// final hisselist = hisselistFromJson(jsonString);
import 'dart:convert';
Hisselist hisselistFromJson(String str) => Hisselist.fromJson(json.decode(str));
String hisselistToJson(Hisselist data) => json.encode(data.toJson());
class Hisselist {
Hisselist({
required this.success,
required this.result,
});
bool success;
List<ResultClass> result;
factory Hisselist.fromJson(Map<String, dynamic> json) => Hisselist(
success: json["success"],
result: List<dynamic>.from(json["result"])
.map((i) => ResultClass.fromJson(i))
.toList()
);
Map<String, dynamic> toJson() => {
"success": success,
"result": result.map((item) => item.toJson()).toList(),
};
}
class ResultClass {
ResultClass({
required this.rate,
required this.lastprice,
required this.lastpricestr,
required this.hacim,
required this.hacimstr,
required this.text,
required this.code,
});
double rate;
double lastprice;
String lastpricestr;
double hacim;
String hacimstr;
String text;
String code;
factory ResultClass.fromJson(Map<String, dynamic> json) => ResultClass(
rate: json["rate"] as double,
lastprice: json["lastprice"] as double,
lastpricestr: json["lastpricestr"],
hacim: json["hacim"] as double,
hacimstr: json["hacimstr"],
text: json["text"],
code: json["code"],
);
Map<String, dynamic> toJson() => {
"rate": rate,
"lastprice": lastprice,
"lastpricestr": lastpricestr,
"hacim": hacim,
"hacimstr": hacimstr,
"text": text,
"code": code,
};
}
This is where I call the API :
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:http/http.dart' as http;
import '../models/apis/hisselist.dart';
class Stocks extends StatefulWidget {
Stocks({Key? key}) : super(key: key);
#override
_StocksState createState() => _StocksState();
}
class _StocksState extends State<Stocks> with AutomaticKeepAliveClientMixin {
ScrollController? controller;
final scaffoldKey = GlobalKey<ScaffoldState>();
final url = Uri.parse('https://api.collectapi.com/economy/hisseSenedi');
var counter;
Hisselist? hisseResult;
Future callHisse() async {
try{
Map<String, String> requestHeaders = {
'Content-Type': 'application/json',
'Authorization': 'apikey xxx'
};
final response = await http.get(url,headers:requestHeaders);
if(response.statusCode == 200){
var result = hisselistFromJson(response.body);
if(mounted);
setState(() {
counter = result.result.length;
hisseResult = result;
});
return result;
} else {
print(response.statusCode);
}
} catch(e) {
print(e.toString());
}
}
#override
void initState() {
// TODO: implement initState
super.initState();
callHisse();
}
#override
Widget build(BuildContext context) {
super.build(context);
return Scaffold(
appBar: AppBar(
centerTitle: false,
automaticallyImplyLeading: false,
title: Text(
'Hisseler'
),
),
body: Center(
child: Padding(
padding: const EdgeInsets.all(8.0),
child: counter != null ?
ListView.builder(
itemCount: counter,
itemBuilder: (context, index){
return Card(
child: ListTile(
title: Text(hisseResult?.result[index].code??""),
subtitle: Text(hisseResult?.result[index].code??""), ),
);
}) : Center(child: CircularProgressIndicator(
)),
),
),
);
}
#override
bool get wantKeepAlive => true;
}
I' getting this on console and API not showing : type 'String' is not a subtype of type 'double' in type cast
How can I fix this? Thanks for your help
How can I fix this?
It is better to use .tryParse instead of forcing with as prefix. Try this for non string value
lastprice: double.tryParse(json["lastprice"]) ?? 0.0,
factory ResultClass.fromJson(Map<String, dynamic> json) => ResultClass(
rate: double.tryParse(json["rate"]) ?? 0.0,
lastprice: double.tryParse(json["lastprice"]) ?? 0.0,
lastpricestr: json["lastpricestr"],
hacim: double.tryParse(json["hacim"]) ?? 0.0,
hacimstr: json["hacimstr"],
text: json["text"],
code: json["code"],
);
Try this and when ever you like to use any double as string use .toString()
class ResultClass {
final double rate;
final double lastprice;
final String lastpricestr;
final double hacim;
final String hacimstr;
final String text;
final String code;
ResultClass({
required this.rate,
required this.lastprice,
required this.lastpricestr,
required this.hacim,
required this.hacimstr,
required this.text,
required this.code,
});
Map<String, dynamic> toMap() {
final result = <String, dynamic>{};
result.addAll({'rate': rate});
result.addAll({'lastprice': lastprice});
result.addAll({'lastpricestr': lastpricestr});
result.addAll({'hacim': hacim});
result.addAll({'hacimstr': hacimstr});
result.addAll({'text': text});
result.addAll({'code': code});
return result;
}
factory ResultClass.fromMap(Map<String, dynamic> map) {
return ResultClass(
rate: map['rate']?.toDouble() ?? 0.0,
lastprice: map['lastprice']?.toDouble() ?? 0.0,
lastpricestr: map['lastpricestr'] ?? '',
hacim: map['hacim']?.toDouble() ?? 0.0,
hacimstr: map['hacimstr'] ?? '',
text: map['text'] ?? '',
code: map['code'] ?? '',
);
}
String toJson() => json.encode(toMap());
factory ResultClass.fromJson(String source) =>
ResultClass.fromMap(json.decode(source));
}