Retrieve String Value from Function with Closure in Swift

Retrieve String value from function with closure in Swift

You need to create completion handler like this

func GetUsername(uid:String , completion: (String) -> ()) {
firebase.child("Users").child(uid).observeSingleEventOfType(.Value) { (snapshot:FIRDataSnapshot) in
if let username = snapshot.value!["Username"] as? String
completion(username)
}
else {
completion("")
}
}

And call function like this way

self.GetUsername(str) { (name) -> () in
if name.characters.count > 0 {
print(name)
}
else {
print("Not found")
}
}

How to capture the return value of a closure

If you wanted to do this purely with a closure (and not a function that accepts a closure), you could do something like:

let myClosure: (Int) -> String = { age in
if age < 10 {
return "You're just a baby"
}
else {
return "You can play the game"
}
}

let answer = myClosure(4) // "You're just a baby"

Retrieve value from function with swift closure

If I'm understanding the structure/question correctly, your goal is to access the WholeDocument array in another SwiftUI view. The way to do that could be:

class UserData : ObservableObject {

// Use Firebase library to configure APIs
private var db = Firestore.firestore()

@Published var WholeDocument : Array<String> = []

init() {
db.collection("Users").getDocuments() { (querySnapshot, err) in
if let err = err {
print("Error getting documents: \(err)")
completion([""])
} else {
for document in querySnapshot!.documents {
// print("\(document.documentID) => \(document.data())")
self.WholeDocument.append(document.documentID)
}
}
}
}
}

struct MyContentView : View {

@ObservedObject var database: UserData

var body: some View {
// access database.WholeDocument
List(database.WholeDocument, id: \.self) {
// do something
}
}

That way, when you initialize MyContentView with an instance of UserData, you will be able to observe WholeDocument in that view.

How do I set the return value of a closure function to a variable?

Try to set value of x variable inside of the closure:

loadData1(onCompletion: { (json) in
x = json
})

In your approach variable x initialized with a closure, that's why you received a warning.

Until closure will be executed, variable x have default value var x = [[String: String]]()
or remain unresolved if you did not provide default value along with declaration.

Swift. How to return a function from a closure

Closure does not support return statement. Instead use completion block inside main thread to perform the task:

i.e

function AA( completion: @escaping (Result<[Return Type], Error>) -> Void) {
localPlayer.authenticateHandler{
//…
if trigger {
DispatchQueue.main.async {
completion(//Whatever Return Value)
}
}
dosomething()
}
}

How to return value from a Closure in Swift?

You are correct, sendTwitterRequest will return after your function has already returned, so there is no way for the outer function to return an imageURL.

Instead, in the closure, take the return value that you want in the cell and store it somewhere (in a member variable) and have the tableView update it itself (e.g. with tableView.reloadData()).

This will cause it to get the cell again (cellForRow ...). Change the implementation to use the member variable where you stored the value from the call.

Add a return value to a closure

You can give the function params an @escaping callback returning an array or whatever you need;

An example of this for a network request;

class func getGenres(completionHandler: @escaping (genres: NSArray) -> ()) {
...
let task = session.dataTask(with:url) {
data, response, error in
...
resultsArray = results
completionHandler(genres: resultsArray)
}
...
task.resume()
}

Then to call it you could do something like this;

override func viewDidLoad() {
getGenres {
genres in
print("View Controller: \(genres)")
}
}

how to get a value from an escaping closure and assign it to a variable and display in tableview

The problem was solved under my teacher's help.
The solution is creating an instance variable, then calling self.tableview.reload directly in the closure. In the tableView cellForRowAT, just loading the value from instance variable.

func searchAddress(_ address: String)
{
self.forwardGeocoding(address:address, completion: {(location) in
if let locationTo = location {
// calculate distance
self.donorDistance.append((self.mainDelegate.currLocation?.distance(from: locationTo) ?? 0))
print(self.mainDelegate.currLocation?.distance(from: locationTo) ?? 0)
if self.donorDistance.count == self.donors.count
{
self.tableview.reloadData()
}
} else {
// not found destination, show alert
print("cannot find address")
}
})
}


Related Topics



Leave a reply



Submit