Home>

How can I call VC method test () from class hoge as shown below?

class hoge: UIView {
/ .............

@IBAction func didTapButton () {

     // I want to call it here!
    }
/ ...........
}
class MainpageViewController: UIViewController {

func test () {
// Do something
}

override func viewDidLoad () {
        super.viewDidLoad ()
    }
}

ー ー ー ー ー ー Added- ー ー ー ー ー ー
When a button in the MainpageViewController is tapped, ContainerView pops up and I want to call test with the text entered in the text field declared on the hoge in that view as an argument. test () is a method that displays the component on the mainpage.

Although we are currently trying to use the delegate method, the error Unexpectedly found nil while unwrapping an Optional value is displayed when setting the delegate of the class that delegates itself with hogeView.delegate = self This is written in viewDidLoad (), but when viewDidLoad () is executed, hogeView is nill, so I think that it is an error, what should I do? ?

Specifically, this program,
https://github.com/shin8484/PopupWindow

Demo's RegisterPopupView button is pressed when I want to execute a method in VC!

  • Answer # 1

    You probably have hogeView as an instance variable in your ViewController code.
    If not, keep it.

    class MainpageViewController: UIViewController {
        @IBOutlet private weak var hogeView: HogeView! // added
        func test () {
          // Do something
        }
        override func viewDidLoad () {
            super.viewDidLoad ()
        }
    }

    On the HogeView side, have an instance of MainpageViewController.

    class HogeView: UIView {
        weak var viewController: MainpageViewController? // added
        @IBAction func didTapButton () {
            // I want to call it here!
        }
    }

    The point to note here is that ViewController already holds the view with a strong reference, so when the view holds the view controller, it needs to be weakly referenced. (Holding each other with a strong reference causes a problem of circular references.)

    Now, let's put a value in HogeView's viewController variable in MainpageViewController!

    class MainpageViewController: UIViewController {
        @IBOutlet private weak var hogeView: HogeView! // added
        func test () {
          // Do something
        }
        override func viewDidLoad () {
            super.viewDidLoad ()
            hogeView.viewController = self // add
        }
    }

    Let's call the method of MainpageViewController with IBAction of HogeView. However, note that the viewController variable may be nil, so call it with?.

    class HogeView: UIView {
        weak var viewController: MainpageViewController? // added
        @IBAction func didTapButton () {
            // I want to call it here!
            viewController? .test () // add
        }
    }

    I think you can now calltest ()from HogeView.
    In fact, this pattern is called the delegate pattern, and it is a frequent pattern when developing iOS.
    In the delegate pattern, there is a convention that a weak reference variable such as this viewController variable is defined with the name delegate.
    To summarize the above, the code looks like this:

    class MainpageViewController: UIViewController {
        @IBOutlet private weak var hogeView: HogeView! // added
        func test () {
          // Do something
        }
        override func viewDidLoad () {
            super.viewDidLoad ()
            hogeView.delegate = self // add
        }
    }
    class HogeView: UIView {
        weak var delegate: MainpageViewController? // added
        @IBAction func didTapButton () {
            // I want to call it here!
            delegate? .test () // add
        }
    }

  • Answer # 2

    I often see it recently, but I use delegate to implement it. It may be one of several walls for learning swift. Try reading various explanations and writing them (maybe it won't work at first).

    Put a reference link.
    I think this link is relatively easy to understand because it implements delegate in VC.

    Qiita

  • Answer # 3

    Whether you want to change the appearance of another UI while the UI is displayed, or just want to reference the value of a member variable that another UI has. You should change the way depending on the application.

    * I think that it will be easier to get a more appropriate answer if you show what you want to do by calling the method test of another UI class with didTapButton.

    In the former case, "Appearance change" cannot be done, so it will be changed when transitioning or returning to another UI.
    So, after all, it's all about changing some variables.
    (However, the appropriate method will change depending on the application.)

    From the information presented, it seems that delegates are common.
    You may prepare a common variable for AppDelegate (refer to multiple classes), and
    There is also UserDefaults.