Flutter Firebase - Retrieve array & map data - firebase

This is my dataset :
I am trying to get this type of data in my app 1st I use an array and in the array i add map data and my value but i don't get any data.
My code
child: StreamBuilder(
stream: FirebaseFirestore.instance.collection("coin").snapshots(),
builder: (context, snapshot) {
if (!snapshot.hasData) {
return Loder();
}
return ListView.builder(
itemCount: snapshot.data.document.length,
itemBuilder: (BuildContext context, int index) {
Map<dynamic, dynamic> map = snapshot.data.documents[index];
return ListTile(
title: Text(map.values.toList()[index]["coinlink"]),
);
},
);
}),
EDIT 1
I got this error I need data from coinlink title and img
The following NoSuchMethodError was thrown building StreamBuilder<QuerySnapshot<Map<String,
dynamic>>>(dirty, state: _StreamBuilderBaseState<QuerySnapshot<Map<String, dynamic>>,
AsyncSnapshot<QuerySnapshot<Map<String, dynamic>>>>#29591):
Class '_JsonQuerySnapshot' has no instance getter 'document'.
How to get this type of data?

You need column inside list of display multiple coinLinks.
return ListView.builder(
itemCount: snapshot.data.document.length,
itemBuilder: (BuildContext context, int index) {
Map<dynamic, dynamic> map = snapshot.data.documents[index];
final coinLinks = map["coinLink"] as List<Map<String,dynamic>>;
return ListTile(
title: Column(
children: coinLinks.map((coinLink){
return Text(coinLink["title"]);
}).toList()
),
);
},
);

Related

Flutter, The element type 'List<ListTile>' can't be assigned to the list type 'Widget'

I tried geting data from firebase and display it using streamBuilder but I get this error, how do I solve it.
body:
StreamBuilder<QuerySnapshot>(
stream: firestore.collection('paymnet data').snapshots(),
builder: (context, snapshot) {
return ListView(
children: [
snapshot.data!.docs.map((DocumentSnapshot document){
Map<String,dynamic> data = document.data()! as Map<String, dynamic>;
return ListTile(
title: Text(data['amount']),
subtitle: Text(data['paid date']),
);
}).toList();
],
);
})
Just remove [] from listView children
body:
StreamBuilder<QuerySnapshot>(
stream: firestore.collection('paymnet data').snapshots(),
builder: (context, snapshot) {
return snapshot.hasData?ListView(
children:
snapshot.data!.docs.map((DocumentSnapshot document){
Map<String,dynamic> data = document.data()! as Map<String, dynamic>;
return ListTile(
title: Text(data['amount']),
subtitle: Text(data['paid date']),
);
}).toList();
):Container();// or add circular progress bar
})

Unable to retrieve firebase data to Listview

I am trying to retrieve data from my real-time firebase into a listview.
The Firebase Json Tree:
I want to retrieve Item, Expiry Date and Quantity in the listview format.
My code is as follows:
var lists = [];
final database = FirebaseDatabase(
databaseURL: "https://trackkit-a5cf3-default-rtdb.asia-southeast1.firebasedatabase.app")
.reference()
.child('Location 1');
#override
Widget build(BuildContext context) {
return Scaffold(
body: Container(
child: StreamBuilder(
stream: database.onValue,
builder: (context, AsyncSnapshot<Event> snapshot) {
if (snapshot.hasData && !snapshot.hasError &&
snapshot.data!.snapshot.value != null) {
print("Error on the way");
lists.clear();
DataSnapshot dataValues = snapshot.data!.snapshot;
Map<dynamic, dynamic> values = dataValues.value;
values.forEach((key, values) {
lists.add(values);
});
return ListView.builder(
shrinkWrap: true,
itemCount: lists.length,
itemBuilder: (BuildContext context, int index) {
return Card(
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
Text("Item: " + lists[index]["Item"]),
Text("Expiry Date: " + lists[index]["Expiry Date"]),
Text("Quantity: " + lists[index]["Quantity"]),
],
),
);
},
);
}
return Container(child: Text("Add Items"));
},
),
),
);
}
The current screen shows :
type 'int' is not a subtype of type 'String'
I have been trying for days! Any help would be greatly appreciated.
Maybe you are getting a Integer value in return to your lists[index]["Quantity"]. And you cannot concat and integer with String without converting into a String.
So Please use method toString() with lists[index]["Quantity"] to make it work properly.
You have to Quantity make a String value, use toString() method on it in Text Widget,
like that: Text("Quantity: " + lists[index]["Quantity"].toString())

when fetching firestore database "itemCount: snapshot.data.documents.length" is not working anymore. does anyone know how to solve this problem?

this is the code:...............
class _MyAppState extends State<MyApp> {
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text("Practice Firebase"),
),
body: StreamBuilder(
stream:
FirebaseFirestore.instance.collection("Animals").snapshots(),
builder: (context, snapshot) {
if (!snapshot.hasData) {
return Center(
child: const CircularProgressIndicator.adaptive(),
);
} else {
return ListView.builder(
itemCount: snapshot.data?.documents.length,
itemBuilder: (context, index) {
return ListTile(
title: snapshot.data.documents[index]["name"],
);
});
}
}));
}
}
The getter 'documents' isn't defined for the type 'Object'.
Try importing the library that defines 'documents', correcting the name to the name of an existing getter, or defining a getter or field named 'documents'
You can try to use the code skeleton below (here I have an own class MyAnimal so I can use members instead of map):
StreamBuilder<QuerySnapshot>(
stream: FirebaseFirestore.instance
.collection('Animals')
.snapshots(),
builder: (BuildContext context,
AsyncSnapshot<QuerySnapshot> snapshot) {
if (snapshot.hasError) {
// handle error
return const Text('Error');
}
if (snapshot.connectionState == ConnectionState.waiting) {
// return progress indicator widget
return const Center(child: CircularProgressIndicator());
}
// here you should get the streamed documents like:
// snapshot.data!.docs
// so to build a ListView for example:
return ListView(
children:
snapshot.data!.docs.map((DocumentSnapshot document) {
final animal = document.data() as MyAnimal;
return ListTile(
title: Text(animal.name!),
);
}).toList(),
);
})
I had the same problem and this fixed it for me. So basically you need to give the snapshot the datatype of AsyncSnapshotsince .docscannot be called on an Object type.
StreamBuilder(
builder: (context, AsyncSnapshot snapshot) {
return ListView.builder(
itemCount: snapshot.data?.docs.length,
just declare the dataType of builder arguments..i mean,
builder:(BuildContext context,AsyncSnapshot snapShot)
enter image description here
Well actually, if you do this - you can access docs and length ...
builder: (BuildContext ctx, AsyncSnapshot LessThanSign QuerySnapshot GreaterThanSign streamSnapShot){}

How to retrieve data from Firebase Realtime to the flutter app in a lisview

I am looking to retrieve data stored in Firebase Realtime database and display it in a new page in a lisview, how can I achieve that. So far I can retrieve and print it out in a console terminal.
My code is below:
class BarcodesResultPreviewWidget extends StatelessWidget {
FirebaseDatabase.instance.reference().child('ScannedResults');
body: Column(
children: <Widget>[
previewView,
//printing scanned results
Expanded(
child: ListView.builder(
itemBuilder: (context, position) {
return BarcodeItemWidget(preview.barcodeItems[position]);
},
itemCount: preview.barcodeItems.length,
),
),
FlatButton(
color: Colors.grey,
child: Text('Save',),
onPressed: () {
databaseRef.push().set({
'ScannedItem': preview.barcodeItems
.map((barCodeItem) => barCodeItem.toJson())
.toString(),
});
},
),
To fetch the data into a new page and build listview, try something like this:
return Scaffold(
body: FutureBuilder(
future: databaseRef.once(),
// future: FirebaseDatabase.instance
// .reference()
// .child("ScannedResults")
// .once(),
builder: (BuildContext context, AsyncSnapshot snapshot) {
if (snapshot.connectionState == ConnectionState.waiting)
return new Text('Loading....');
if (snapshot.hasError) return new Text('Error: ${snapshot.error}');
List scannedItemsValues = [];
snapshot.data.value.forEach(
(_, values) => scannedItemsValues.add(values["ScannedItem"]));
print(scannedItemsValues);
return ListView.builder(
itemCount: scannedItemsValues.length,
itemBuilder: (BuildContext context, int index) {
// build your listView here
print(scannedItemsValues[index]);
return Text(scannedItemsValues[index]);
},
);
},
),
);

can i access the document id using this snapshot call?

This is the streambuilder im using to access all the documents at once
StreamBuilder(
stream: Firestore.instance.collection('projects').snapshots(),
builder: (context, snapshot) {
if (!snapshot.hasData) return Text('data is loading');
return ListView.builder(
itemBuilder: (ctx, index) {
return ProjectItem(
id: snapshot.data.documents[index]['id'],
title: snapshot.data.documents[index]['title'],
members: snapshot.data.documents[index]['members'],
complexity: snapshot.data.documents[index]['complexity'],
affordability: snapshot.data.documents[index]['affordability'],
duration: snapshot.data.documents[index]['duration'],
docid: snapshot.data.document[index].documentid,
);
},
itemCount: snapshot.data.documents.length,
}
Can i use docid: snapshot.data.document[index].documentid to access the document ids individually? if not whats the option? Thanks
You can make a custom Object constructor to use data from the document snapshot.
class ProjectItem {
String id;
String title;
String members;
String complexity;
String affordability;
String duration;
String docid;
ProjectItem({....});
factory ProjectItem.fromFirestore(DocumentSnapshot doc) {
return ProjectItem(
id: doc.data['id'],
title: doc.data['title'],
members: doc.data['members'],
complexity: doc.data['complexity'],
affordability: doc.data['affordability'],
duration: doc.data['duration'],
docid: doc.documentID,
);
}
}
And then just use this constructor inside the list view to make the object
return ProjectItem.fromFirestore(
snapshot.data.documents[index]
);
You can get the documentID this way
StreamBuilder(
stream: Firestore.instance.collection('projects').snapshots(),
builder: (context, snapshot) {
if (!snapshot.hasData) return Text('data is loading');
return ListView.builder(
itemBuilder: (ctx, index) {
QuerySnapshot snap = snapshot.data; // Snapshot
List<DocumentSnapshot> items = snap.documents; // List of Documents
DocumentSnapshot item = items[index]; Specific Document
return ProjectItem(
id: item.data['id'],
title: item.data['title'],
members: item.data['members'],
complexity: item.data['complexity'],
affordability: item.data['affordability'],
duration: item.data['duration'],
docid: item.documentID, // Document ID
);
},
itemCount: snapshot.data.documents.length,
);
},
),
)
THIS WORKED FOR ME:
StreamBuilder(
stream: Firestore.instance.collection('projects').snapshots(),
builder: (context, snapshot) {
if (!snapshot.hasData) return Text('data is loading');
return ListView.builder(
itemBuilder: (ctx, index) {
return ProjectItem(
id: snapshot.data.documents[index]['id'],
title: snapshot.data.documents[index]['title'],
members: snapshot.data.documents[index]['members'],
complexity: snapshot.data.documents[index]['complexity'],
affordability: snapshot.data.documents[index]['affordability'],
duration: snapshot.data.documents[index]['duration'],
docid: snapshot.data.documents[index].documentID,
);
},
itemCount: snapshot.data.documents.length,
);

Resources