How to get value out of an object in dart - dart

With named route like this with the returned result as searchedCity in this case.
TextButton(
onPressed: () async {
var searchedCity = await Navigator.pushNamed(context,'/city',);
);
In the city page, after I pop this page with a list object with a value London.
onPressed: () {
Navigator.pop(context, <String>['London']);
},
I tried to print the searchedCity variable:
print(searchedCity);
And I got this in the console. So I know that this searchedCity object is a list and this contains London inside.
[London]
Now I have this which expect input as a String.
weatherData = await weather.weatherDataCity(Expect a string variable);
I tried to created a new String variable and assigned to searchedCity as below, but not working, please give me a hint for this?
String cityName = searchedCity[0];
So the result I expect would be like this:
weatherData = await weather.weatherDataCity(cityName);

Related

Getting current value from Stream

There is a StreamBuilder (using RxDart) which displays some date. After click on InkWell widget I need to calculate a new date on basis of old one. The code below simply explains the algo but when I run it there is nothing happens and execution stops after underlined row, i.e. I never see the value of lastCalcDate.
GUI:
child: StreamBuilder(
stream: bloc.getDate,
builder: (context,snapshot) {
return InkWell(
onTap: () => tapHandler
);
}),
void tapHandler() async {
var lastCalcDate = await bloc.getDate.single;
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
print(lastCalcDate);
var newCalcDate = lastCalcDate.add(Duration(days:1));
bloc.setDate(newCalcDate)
}
BLoC:
class Bloc {
// BehaviourSubject is usedto be sure that last sent date will be accessible in `tapHandler`.
final _dateSubject = BehaviourSubject<DateTime>();
Observable<DateTime> get getDate => _dateSubject.stream;
Function(DateTime) get setDate => _dateSubject.add;
}
To implement what I need I created some workaround but I don't like it because I fill that I can do the same thing using observables.
BLoC (workaround):
class Bloc {
final _dateSubject = BehaviourSubject<DateTime>();
Observable<DateTime> get getDate => _dateSubject.stream;
DateTime _date;
void setDateWorkaround(DateTime date) {
_date = date;
_dateSubject.add(date);
}
}
Could you someone to give me advise. What I did wrong?
single will not work because it is going to return the next item in the stream, however, that has to be added first. This means that single will just wait for the next item and in your case it will not happen.
Since you are using rxdart and BehaviorSubject already, you can easily access the current element like this:
class Bloc {
final _dateSubject = BehaviourSubject<DateTime>();
Observable<DateTime> get getDate => _dateSubject.stream;
Function(DateTime) get setDate => _dateSubject.add;
DateTime get currentDate => _dateSubject.value;
}
In this case, I am making use of BehaviorSubject.value, which is actually the whole point of that class.
Now, you can just use currentDate in your tap handler:
void tapHandler() async {
var lastCalcDate = bloc.currentDate;
print(lastCalcDate);
var newCalcDate = lastCalcDate.add(Duration(days:1));
bloc.setDate(newCalcDate)
}
Use StreamProvider from provider
Listen to a Stream and expose the latest value emitted.

createdAt updatedAt aqueduct

In mongoose, there's the timestamp: true option to a schema, which auto-populates a createdAt and updatedAt for any model item added.
Is there something similar in Aqueduct?
If not, how do I manually do so?
I currently tried this, which is failing, as usual:
#Operation.post()
Future<Response> createICD(#Bind.body() ICD body) async {
body.createdAt = DateTime.now();
final query = Query<ICD>(context)..values = body;
final insertICD = await query.insert();
return Response.ok({'state': true, 'data': insertICD});
}
Error from the above approach is:
Converting object to an encodable object failed: Instance of 'ICD'
It's failing when you send the response; you need to call asMap() on insertICD. The response body object you are providing is a standard Dart map - it doesn't have any special encoding behavior, so it doesn't know how to encode a complex type like ManagedObject. Invoke asMap() on the managed object to convert it to a standard Dart map:
#Operation.post()
Future<Response> createICD(#Bind.body() ICD body) async {
body.createdAt = DateTime.now();
final query = Query<ICD>(context)..values = body;
final insertICD = await query.insert();
return Response.ok({'state': true, 'data': insertICD.asMap()});
}
Also, see http://aqueduct.io/docs/db/validations/#update-and-insert-callbacks for setting timestamps at create/update events.

How to access and edit a value of a existent key of a map that's inside a list on Dart/Flutter?

I'm create a list of maps, each map have two keys ["title"] and ["time"], all the values of keys is submitted in a setState method, with the values submited as Strings by a button, and a map object is added inside the list, that's List _tasks = [], so what I would like to do is access the ["time"] element of the last Map added in the list and be able to change the value.
This is part of a little project of application, to help me to learn more about Flutter. The repository of application is on Github on https://github.com/jsdaniell/remindme
The list is declared:
List _tasks = [];
The function that's adding a map object to the list:
void _addTask() {
setState(
() {
Map<String, dynamic> newTask = Map();
newTask["title"] = _taskController.text;
newTask["time"] = _timeGlobal.toString();
_taskController.text = "";
_tasks.add(newTask);
},
);
}
The point is that I want to subtract a value of 1 every second of variable _timeGlobal, what's a int in the global scope and is the value that is set as a String in the ["time"] in the Map, so I write this code:
String countdownTime(Map newTask) {
Timer timer = new Timer.periodic(new Duration(seconds: 1), (timer) {
// Here I want to access the value of ["time"] element, where's in the last position of list and update the value.
_saveData();
return Home();
});
// Stop the periodic timer using another timer which runs only once after specified duration
new Timer(new Duration(minutes: _timeGlobal), () {
timer.cancel();
});
}
I hope that have some way to access the last map in a list of maps, and a specific key on this map.
to access to the last element in the list you can use :
_tasks[_tasks.length - 1];
so if you want the "time" key from the Map thats inside the last element of your list use :
var lastTime = _tasks[_tasks.length - 1]["time"];

Push objects into array in Dart

List returnMovies = [];
Future<List> _getData() async {
final response = await http.get("https:../getTodayMovies",
headers: {HttpHeaders.AUTHORIZATION: Acess_Token.access_token});
if (response.body != null) {
returnMovies = json.decode(response.body);
.....
setState(() {});
} else {
final responseUpcoming = await http.get("/upcoming",
headers: {HttpHeaders.AUTHORIZATION: Acess_Token.access_token});
returnMovies = json.decode(responseUpcoming.body);
}
The response.body looks like:
[{"id":394470548,"host_group_name":"heyab redda","movie_image":"..png","type":"horror","code":"X123","name":"Lovely","start_time":1554364800,"end_time":1554393600,"}]
The responseUpcoming.body looks like:
{"id":394470545,"host_group_name":"foo redda","movie_image":".png","type":"horror","code":"X123","name":"Lovely","start_time":1554364800,"end_time":1554393600,"}, {"id":394470548,"host_group_name":"foo1 redda","movie_image":"..png","type":"comic","code":"X125","name":"Lovely1","start_time":1554364800,"end_time":1554393600,"}
The error I get is: String, dynamic is not a subtype of type List<dynamic>.
In the first API call that I am doing I normally get in return an array of objects, however, when this is empty, the second API call returns a list of objects that I want to push into the array called returnMovies, how can I achieve this?? Is there any way to .push these objects in the array?? So then I want to use this array to build dynamically a Listview.builder.
Also is it correct the way I am declaring it? I am quite new on Dart. Thank you
Sounds like you are looking for addAll
returnMovies.addAll(json.decode(returnUpcoming.body))
I will suggest to use
returnMovies.addAll({your object here})
When you do this json.decode(response.body) you are getting a List of Map you should use List<dynamic> movieListData and get the items like this:
movieListData = json.decode(response.body);
returnMovies = movieListData.map((dynamic movieData) {
String id = movieData['_id'];
String host_group_name = movieData['host_group_name'];
String duration = movieData['duration'];
return new Movie(id,title, duration);
}).toList();

How do you get the document id after adding document in Cloud Firestore in Dart

Im using the following code to update a Cloud Firestore collection using Dart/Flutter.
final docRef = Firestore.instance.collection('gameLevels');
docRef.document().setData(map).then((doc) {
print('hop');
}).catchError((error) {
print(error);
});
I'm trying to get the documentID created when I add the document to the collection but the (doc) parameter comes back as null. I thought it was supposed to be a documentReference?
Since it's null, I obviously can't use doc.documentID.
What am I doing wrong?
You can try the following:
DocumentReference docRef = await
Firestore.instance.collection('gameLevels').add(map);
print(docRef.documentID);
Since add() method creates new document and autogenerates id, you don't have to explicitly call document() method
Or if you want to use "then" callback try the following:
final collRef = Firestore.instance.collection('gameLevels');
DocumentReferance docReference = collRef.document();
docReferance.setData(map).then((doc) {
print('hop ${docReferance.documentID}');
}).catchError((error) {
print(error);
});
#Doug Stevenson was right and calling doc() method will return you document ID. (I am using cloud_firestore 1.0.3)
To create document you just simply call doc(). For example I want to get message ID before sending it to the firestore.
final document = FirebaseFirestore.instance
.collection('rooms')
.doc(roomId)
.collection('messages')
.doc();
I can print and see document's id.
print(document.id)
To save it instead of calling add() method, we have to use set().
await document.set({
'id': document.id,
'user': 'test user',
'text': "test message",
'timestamp': FieldValue.serverTimestamp(),
});
Using value.id ,You can fetch documentId after adding to FireStore .
CollectionReference users = FirebaseFirestore.instance.collection('candidates');
Future<void> registerUser() {
// Call the user's CollectionReference to add a new user
return users.add({
'name': enteredTextName, // John Doe
'email': enteredTextEmail, // Stokes and Sons
'profile': dropdownValue ,//
'date': selectedDate.toLocal().toString() ,//// 42
})
.then((value) =>(showDialogNew(value.id)))
.catchError((error) => print("Failed to add user: $error"));
}
If the Dart APIs are anything like other platforms, the document() method should return a document reference that has an id property with the randomly generated id for the document that's about to be added to the collection.
This worked for me
//add a passed employee to firebase collection called employees
static Future<void> addEmployee(Employee employee) async {
final CollectionReference employees = FirebaseFirestore.instance.collection('employees');
var doc = employees.doc();
employee.employeeID = doc.id;
await doc.set(employee.toJson());
}

Resources