iOS Pass Data Back from Viewcontroller2 to Viewcontroller 1 with Presentmodalsegue

iOS Pass data back from viewController2 to viewController 1 with presentModalSegue

Here is my understanding of your setup.

ViewController1 -> NavigationController -> ViewController2

In this case, in the prepare for segue method, the destination viewcontroller is the Navigation Controller and Not ViewController2.
Therefore, this line of code will not be true.

if let dest = segue.destinationViewController as? MapAddressViewController{
dest.delegate = self
}

The downcast you have there will fail, because the destination VC is not MapAddressViewContoller,instead its a UINavigation controller.

To fix this, you can change the code as follows :

if let dest = segue.destinationViewController as? UINavigationController{
dest.rootViewController.delegate = self
}

However, I prefer using NSNotification to pass data back down the view controller hierarchy.
You could try that out also.

Using Notifications :

  • Step 1 : In VC1 : Register for a notification.
    override func viewDidLoad() { NSNotificationCenter.defaultCenter().addObserver(self, selector: Selector("myFunc:"), name: "SomeName", object: nil) } func myFunc(theNotifiction : NSNotification){ print("I got notified (theNotifiction.userInfo!)") }

    • Step 2 : In VC2 : Post a Notification at an appropriate time.
      NSNotificationCenter.defaultCenter().postNotificationName("SomeName", object: nil, userInfo: ["theKey":"theData"])

Pass Data from last ViewController to root ViewController

For navigation stack , Your scenario is A->B->C so stack is [A,B,C] . You can reach expected ViewController with using

 let viewControllerA = self.navigationController!.viewControllers[0] as! AViewController // 0 is viewcontroller index which in stack.

then when you want to send data to this vc or changing some data in this vc you can reach it with

viewControllerA.changingVariable = "bla bla"

How to pass variable to a ViewController that is embedded in a Navigation Controller?

You can pass the value by overriding the prepare(for segue:) function in ViewController1

    override func prepare(for segue: UIStoryboardSegue, sender: Any?) {

// Get the new view controller using segue.destination
guard let destination = segue.destination as? UINavigationController else {
return
}

guard let finalDestination = destination.viewControllers.first as? ViewController2 else {
return
}

finalDestination.testID = "Test Value"
}

ios Delegate Objective-c data sending from 2nd view controller to 1st view controller

I assume that you are calling the Second_ViewController from storyboard instead of doing programmatically.

In that case, the correct instance of Second_ViewController can be accessed in prepareForSegue. For that, you need to set a Storyboard segue identifier, eg "Second_ViewController"

-(void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender {

if ([segue.identifier isEqualToString:@"Second_ViewController"]) {

SecondViewController *aSecVC = segue.destinationViewController;
// Register the Delegate to self.So when we call the delegate method from secondVC, SendMessage will be call of ViewController
aSecVC.delegate = self;

}
}

If you use alloc-init or instantiateViewControllerWithIdentifier, when you are using a storyboard push segue, it will create another instance.

Check which ViewController made a segue (from the destination ViewController)

Here is one way to do it:

  1. Keep an array of the viewControllers you have visited as a property in each of your viewControllers. Let's call this visited. Also, create a protocol called TracksVisited that all of your viewControllers will adopt:

    protocol TracksVisited {
    var visited: [Int] { get set }
    }

    class ViewController1: UIViewController, TracksVisited {
    var visited = [Int]()

    ...
    }

    class ViewController2: UIViewController, TracksVisited {
    var visited = [Int]()

    ...
    }
  2. Add the current viewController number to this list:

    let vc = 3  // current viewController
    visited.append(vc)
  3. Generate the list of segues and choose one:

    // generate list of all viewControllers
    let all = Array(1...12)

    // remove visited from all
    let rest = all.filter { !visited.contains($0) }

    // create list of segues
    let segues = rest.map { "\(vc)-\($0)" }

    // choose random segue and go there
    let index = Int(arc4random_uniform(UInt32(segues.count)))
    let segueName = segues[index]
    self.performSegueWithIdentifier(segueName, sender: self)
  4. In prepareForSegue, pass the list of visited to the destination viewController:

    if let destinationViewController = segue.destinationViewController as? TracksVisited {
    destinationViewController.visited = visited
    }

move back to View Controller from Navigation Controller?

Try any one

navigationController?.popViewController(animated: true)

dismiss(animated: true, completion: nil)


Related Topics



Leave a reply



Submit