Swift - Pass JSON Data to Other Views

Swift - Pass json data to other views

Here is a simplified version of your code

class AuthViewModel: ObservableObject {
// I don't have your Model info
//You can have an empty object of your model or you can make it an optional, etc
@Published var user: YourModel? = nil
@Published var alert: CustomAlert? = nil
let networkService: NetworkService = NetworkService.shared
var authentication: AuthenticationCheck? = nil
func signIn(username: String, password: String) {
networkService.signIn(username: username, password: password){ (result) in
switch result {
case .success(let user):
print("This user last name is: \(user)")
//Assign you value to the Published variable here
self.user = user
self.authentication?.updateValidation(success: true)
self.alert = CustomAlert(title: "Success", message: "You logged in")

case .failure(let error):
print("The error is: \(error)")
//Reset the variable
self.user = nil
self.authentication?.updateValidation(success: false)
//You can pass a better message to the user like this
self.alert = CustomAlert(title: "Invalid Credentials", message: "\(error)")

}
}
}

func logout() {
self.user = nil
authentication?.updateValidation(success: false)
self.alert = CustomAlert(title: "See you later", message: "You logged out")
}
}
class AuthenticationCheck: ObservableObject {
@Published var isValidated = false
func updateValidation(success: Bool) {
withAnimation {
isValidated = success
}
}
}
struct SampleNetworkView: View {
@StateObject var vm: AuthViewModel = AuthViewModel()
@StateObject var authentication: AuthenticationCheck = AuthenticationCheck()
@State var username: String = ""
@State var password: String = ""
var body: some View {
NavigationView{
switch authentication.isValidated{
case true:
VStack{
Text("Signed In - you are now in the content view")
.toolbar(content: {
Button("log out", action: {
vm.logout()
})
})
}
case false:
VStack{
TextField("username", text: $username).textFieldStyle(RoundedBorderTextFieldStyle())
SecureField("password", text: $password).textFieldStyle(RoundedBorderTextFieldStyle())
Button("sign in", action: {
vm.signIn(username: username, password: password)
}).disabled(username.isEmpty || password.isEmpty)
}
}

}
//Inject the StateObjects to the navigation view so you can access the variables
.environmentObject(authentication)
.environmentObject(vm)
//Create a shared Alert for the ViewModel
.alert(item: $vm.alert, content: { customAlert in
Alert(title: Text(customAlert.title), message: Text(customAlert.message), dismissButton: .default(Text("ok")))
})
//Pass the authentication to the ViewModel so you can pass info
.onAppear(perform: {
vm.authentication = authentication
})
}
}

struct SampleNetworkView_Previews: PreviewProvider {
static var previews: some View {
SampleNetworkView()
}
}
//This assists in creating a shared alert
struct CustomAlert : Identifiable {
let id: UUID = UUID()
var title: String
var message: String
}

How to pass json data in swift app between two viewcontrollers

I would do something like this:

let newController = self.storyboard?.instantiateViewControllerWithIdentifier("newControllerIdentifier") as! NewControllerClassName
newController.data = array
self.navigationController?.pushViewController(newController, animated: true)

It also appears you are using a array of string type that are comma separated.
I would rather create a variable like below

var jsonArray:[[String:String]]?

How to pass JSON data to another view controller from login function using post method?

For loop here is unnecessary because you are not getting array of Login data what you need is to directly use self.myResponse to make object of Login. Also you are performing segue twice with different identifier perform segue to specific identifier with your corresponding destination controller.

Alamofire.request("http://192.168.100.5:84/Token", method: .post, parameters: parameters, encoding:  URLEncoding.httpBody, headers: headers).responseJSON { (response:DataResponse<Any>) in

switch(response.result) {
case.success(let data):
print("success",data)
let statusCode = (response.response?.statusCode)!
if statusCode == 200{
self.view.makeToast(message: "Welcome !!")
}else{
self.view.makeToast(message: "Username or password invalid")
}
self.myResponse = JSON(data)
let login = Login(loginJson: self.myResponse)
DispatchQueue.main.async(execute: { () -> Void in
self.performSegue(withIdentifier: "pass_data", sender: login)
})
case.failure(let error):
print("Not Success",error)
}
}

Now make your prepareForSegue like this

override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if segue.identifier == "pass_data" {
if let eventsVC = segue.destination as? MenuDrawerViewController,
let loginData = sender as? Login {
eventsVC.login_details = loginData
}
}
}

How do I pass Json Data from one class to another?

Update your fetch data with completion

func fetchWeather(cityName: String,completionHandler: @escaping (WeatherModel?) -> Void){

let weatherURL = "https://api.openweathermap.org/data/2.5/weather?q=\(cityName)&appid=55dbb1b10e9f55181ad910227f1460ae&units=metric"
let objectURL = URL(string: weatherURL)
let task = URLSession.shared.dataTask(with: objectURL!, completionHandler: {(data,reponse,error)in
if error != nil{
print(error!)
} else{
do{
let json = try JSONDecoder().decode(CityWeatherInfo.self, from: data!)
print(json)
let saveData: WeatherModel = WeatherModel(name: json.name,
temp: json.main.temp, feelsLike: json.main.feelsLike,
tempMin: json.main.tempMin, tempMax: json.main.tempMax,
main: json.weathers[0].main, description: json.weathers[0].main)
print(saveData)

completionHandler(saveData)

} catch{
completionHandler(nil)
print("error")
}
}
})
task.resume()
}

How to use

class WeatherDetailViewController: UIViewController {

var weatherPresenter: WeatherDetailPresenter?
public var cityName: String?

let request = RequestManager()

override func viewDidLoad() {
super.viewDidLoad()
request.fetchWeather(cityName: "", completionHandler: { [weak self] weatherModel in
// here you get object and you can set labels

self?.tempMinLabel.text = weatherModel.tempMin
self?. tempMaxLabel.text = weatherModel.tempMax
//....
})
}
}

Passing JSON data from HTTP request to another view controller in Swift 3

You should set up a manual segue in Storyboard, that you only call inside the completion handler of your network request. If the segue is connected to a single tableview cell, it will be called by the system before your async function would finish execution. Once you changed your segue to be manual and not connected to a static table view cell, you can call it using the function performSegue.

func retrieveTime(jobDateValue: String) -> Void {
if let crew = user!["crew"] as? [String:Any], let crewID = crew["crew_id"] as? String{
let param = ["action": "retrieve time", "job": ["crew_id": crewID, "jobDate": jobDateValue]] as [String : Any]
let headers = [ "content-type": "application/json", "cache-control": "no-cache" ]

if let postData = (try? JSONSerialization.data(withJSONObject: param, options: [])) {
var request = URLRequest(url: URL(string: "http://52.221.231.3/gv/app_api.php")!, cachePolicy: .useProtocolCachePolicy, timeoutInterval: 10.0)
request.httpMethod = "POST"
request.allHTTPHeaderFields = headers
request.httpBody = postData

let task = URLSession.shared.dataTask(with: request) { (data, response, error) -> Void in
guard error == nil, let data = data else {return}
DispatchQueue.main.async{
if let json = (try? JSONSerialization.jsonObject(with: data)) as? [String:Any]{
let result = json["result"] as? String
if (result == "success") {
let passValue = json
self.performSegue(withIdentifier: "YourSegue", sender: json)
} else{

}
}
}
}
task.resume()
}
}
}

Also use native Swift objects when available instead of their Foundation counterparts (such as NSDictionary, NSMutableURLRequest).

You should also use the sender option of performSegue to send the json data to your other view controller instead of storing it in another variable unless you use the json object in your first view controller as well.

override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if segue.identifier == "SecondVCSegue"{
if let destination = segue.destination as? SecondVC, let json = sender as? [String:Any] {
destination.passedData = json
}
}
}

How to send Json Data to Table View Array? Swift

First you have an empty function showTable inside your viewDidLoad - This does nothing. Presumably it is something hanging around from your various attempts. Delete that.

As you have probably worked out, your network fetch operation is going to occur asynchronously and you need to reload the table view once the data has been fetched.

You have some code in viewDidLoad that kind of tries to do this, but it isn't related to the fetch operation. It is just dispatched asynchronously on the next run loop cycle; This is probably still before the data has been fetched.

However, even if the data has been fetched, it won't show up because you are assigning userFeedPosts from a second instance of your API object to AA at initialisation time. This array is empty and will remain empty since Swift arrays are value types, not reference types. When userFeedPosts is updated, AA will hold the original empty array.

To load the data you need to

  1. Start a load operation when the view loads
  2. Pass a completion handler to that load operation to be invoked when the load is complete
  3. Reload your table view with the new data
class EntertainmentViewController: UIViewController, UITableViewDelegate, UITableViewDataSource {

var data = [EntertainmentPageData]()
@IBOutlet weak var entPostTableView: UITableView!

override func viewDidLoad() {

entPostTableView.register(EntertainmentViewrTableViewCell.nib(), forCellReuseIdentifier: EntertainmentViewrTableViewCell.identifier)
entPostTableView.delegate = self
entPostTableView.dataSource = self
super.viewDidLoad()

EntertainmentAPI.getFeedPosts { result in
DispatchQueue.main.async { // Ensure UI updates on main queue
switch result {
case .error(let error):
print("There was an error: \(error)")
case .success(let data):
self.data = data
self.entPostTableView.reloadData
}
}
}
}

func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {

let customCell1 = tableView.dequeueReusableCell(withIdentifier: EntertainmentViewrTableViewCell.identifier, for: indexPath) as! EntertainmentViewrTableViewCell
let post = data[indexPath.row)
customCell1.profileDisplayName.text = data[indexPath.row].postDisplayName
customCell1.configure(with: post.postDisplayName, PostImage: post.imageURLString, PostDescription: post.postDescription)
return customCell1
}

func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return data.count
}

func numberOfSections(in tableView: UITableView) -> Int {
return 1
}
}

public class EntertainmentAPI {
static func getFeedPosts(completion: @escaping ((Result<[EntertainmentPageData],Error>) -> Void) ) {
guard let apiURL = URL(string: "https://api.quickques.com/....") else {
return
}

let task = URLSession.shared.dataTask(with: apiURL) { data, apiResponse, error in

if let error = error {
completion(.failure(error))
return
}

guard let data = data else {
/// TODO - Invoke the completion handler with a .failure case
return
}

do {
let entPostData = try JSONDecoder().decode([EntertainmentPageData].self, from: Data)
completion(.success(entPostData))
}
catch {
completion(.failure(error))
}

}.resume()
}
}

How do I pass my json data to table views and other view controllers?

You should take 3 viewcontroller
1. HomeViewController: You show only season listing data (Using tableview datasource and delegate )


  1. EpisodesViewController: If user select any row like user just select any Season, then you can also show the all Episodes of that season, you should pass that data from HomeViewController to EpisodesViewController

  2. EpisodesDetailsViewController :
    If any Episode is selected then you should send only the details json data

    from EpisodesViewController to EpisodesDetailsViewController
    And you just show data in this page
    This is the steps you have to follow

If you have any problem, please comment here
my email id is : sudebsarkar21@gmail.com, contact here

Pass Json response from one Viewcontroller to another Viewcontroller and populate CollectionView

You need to present it inside the callback of the URLSession.shared.dataTask like

DispatchQueue.main.async {
self.arrayDrinks.append(response.drinks)
let destinationVC = DrinksListCollectionViewController()
destinationVC.remoteArray = response.drinks
print("print array drink \(destinationVC.remoteArray)")
self.present(destinationVC,animated:true,completion:nil)
}

If it's a segue then replace above with ( also inside the completion )

DispatchQueue.main.async {
performSegue(withIdentifier: "InglistSegue", sender: response.drinks)
}

Add this method

override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
let destinationVC = segue.destination as! DrinksListCollectionViewController
destinationVC.remoteArray = sender as! [Model] // model it type of drinks
}


Related Topics



Leave a reply



Submit