Passing data between views in ONE ViewController in Swift
EDIT: Sorry, when I created this answer I was having ViewControllers in mind. A much easier way would be to create a method in SomeView and talk directly to it.
Example:
class MainViewController: UIViewController {
var view1: SomeView!
var view2: SomeView!
override func viewDidLoad() {
super.viewDidLoad()
// Create the views here
view1 = SomeView()
view2 = SomeView()
view.addSubview(view1)
view.addSubview(view2)
}
@IBAction func someAction(sender: UIButton) {
view1.changeString("blabla")
}
}
class SomeView: UIView {
var someString: String?
func changeString(someText: String) {
someString = someText
}
}
Delegate:
First you create a protocol:
protocol NameOfDelegate: class { // ": class" isn't mandatory, but it is when you want to set the delegate property to weak
func someFunction() // this function has to be implemented in your MainViewController so it can access the properties and other methods in there
}
In your Views you have to add:
class SomeView: UIView, NameOfDelegate {
// your code
func someFunction() {
// change your slider settings
}
}
And the last step, you'll have to add a property of the delegate, so you can "talk" to it. Personally I imagine this property to be a gate of some sort, between the two classes so they can talk to each other.
class MainViewController: UIViewController {
weak var delegate: NameOfDelegate?
@IBAction func button(sender: UIButton) {
if delegate != nil {
let someString = delegate.someFunction()
}
}
}
I used a button here just to show how you could use the delegate. Just replace it with your slider to change the properties of your Views
EDIT: One thing I forgot to mention is, you'll somehow need to assign SomeView as the delegate. But like I said, I don't know how you're creating the views etc so I can't help you with that.
Passing data between two views (in the same ViewController)
Let's say you have two views view1
and view2
.
For example some data changed in view2
and you need to pass this data to view1
. I'd do this with delegation pattern. So here's the setup:
protocol View2Delegate {
func didChangeSomeData(data: String)
}
Now in view2
class View2: UIView {
var delegate: View2Delegate?
var text: String = String() {
didSet {
self.delegate.didChangeSomeData(data: text)
}
}
}
and in view1
class View1: UIView, View2Delegate {
var textToChange: String = String()
func didChangeSomeData(data: String) {
// Do whatever you want with that changed data from view2
textToChange = data
}
}
and in your viewController
class MyViewController: UIViewController {
var: view1 = View1()
var: view2 = View2()
func viewDidLoad() {
super.viewDidLoad()
view2.delegate = view1
}
Now, if you don't really want to couple view1
and view2
, you could listen via the same pattern changes of view2
in ViewController
and then pass it directly to the view1
via property accessor.
class MyViewController: UIViewController, View2Delegate {
var: view1 = View1()
var: view2 = View2()
func viewDidLoad() {
super.viewDidLoad()
view2.delegate = self
}
func didChangeSomeData(data: String) {
view1.textToChange = data
}
More on protocols in the Apple's Documentation
Update
You could also go with Key Value Observing pattern. You could setup it like this:
class MyViewController: UIViewController {
var view1 = View1()
var view2 = View2()
override func viewDidLoad() {
super.viewDidLoad()
let observation = view2.observe(\.text) { (observed, change) in
if let newValue = change.newValue {
view1.textToChange = newValue
}
}
}
}
Passing data between a ViewController to another ViewController with navigation controller Swift 5
If you are using segue, then add "segue_identifier" in storyboard and the in secondviewcontroller add:
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if segue.identifier == "segue_ identifier" {
let mainTab = segue.destination as! tabBarController
let nav = mainTab.viewControllers[0] as! UINavigationController
let vc = nav.viewControllers.first as! HomeViewController
vc.cid = cityId
}
}
Because your segue destination is UINavigationController, you need to send data to view controller like this
Passing Data Between View Controllers in Swift 4
Your problem is that your prepare
methods never run because you never call them.
Look, when you call performSegue
, then prepare(for segue: sender:)
is called too, so you can override this method in your ViewController and because you're passing identifier
as parameter of performSegue
method you can determine what should happen if segue has this or this identifier
So, delete prepare for segue methods from IBActions
@IBAction func backButton(_ sender: Any) {
if installer == "verified"{
performSegue(withIdentifier: "main/login", sender: self)
}
}
@IBAction func button1(_ sender: Any) {
if installer == "verified"{
performSegue(withIdentifier: "Button1", sender: self)
}
}
instead override prepare(for segue: sender:)
method of ViewController and inside specify what should happen if segue has "main/login"
indentifier or "Button1"
:
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if segue.identifier == "main/login" {
let mainController = segue.destination as! ViewController
mainController.myvar = installer
} else if segue.identifier == "Button1"
let IPController = segue.destination as! IP_ModuleQuickStartViewController
IPController.verified = installer
}
}
Swift 3 - Passing data between a View Controller and after that to another 2
Before calling presentViewController
add :
nextViewController.name = yourTextField.text
You could also delete the segue
call. That is redundant.
Here is an example that I've used in the past :
@IBAction func doSegue(_ sender: UIButton) {
buttonTag = sender.tag
let storyboard = UIStoryboard (name: "Main", bundle: nil)
let resultVC = storyboard.instantiateViewController(withIdentifier: "ResultViewController")as! ResultViewController
// Communicate with new VC - These values are stored in the destination
// you can set any value stored in the destination VC here
resultVC.firstValue = buttonTag
resultVC.secondValue = randomOpponentValue()
self.navigationController?.pushViewController(resultVC, animated: true)
}
Related Topics
iOS - Setobject VS. Synchronize
Swift and Nsuserdefaults - Exc_Bad_Instruction When User Defaults Empty
Uitextfield Starting Cursor Position Is Wrong
How to Instantiate and Load a View Controller Before Segueing to It Using Swift
How to Make Designable Textfield Code Class in Swift
Swift: Nil Is Incompatible with Return Type String
How to Set the Size of an Uiviewrepresentable
Live Render Iboutlet Connected Subviews via Ibinspectable Properties
App Installation Failed: Unknown Error Xcode 7
How to Get All Events Out of a Calendar (Swift)
Get "No Keychain Available" Error When Try to Access Keychain from App Extension
Swift Save Viewcontroller State Using Coder Beyond App Close
iOS Do Scheduled Operation in Background or When App Active
Swift Good Coding Practice: If Statement with Optional Type Bool
Swift - How to Open Another Viewcontroller with Collectionviewcell Inside Uitableviewcell