1

The problem: Created a view controller in a xib with a table view. But, the table view acts very weirdly and doesn't look like the table view we use in the storyboard.

enter image description here

My plan was to populate this table view with a custom table view cell which I have created in another xib file. But, sadly, it doesn't work as I have expected because everything was off and those cells are instantiated, I know my custom cells work because it has worked in my other view controller that was created in the storyboard:

]]]]]]

I wanted a way to design my view controllers so I can just instantiate them when I need, my reasoning behind this is I don't want to have a very populated storyboard. Now I know that I can't use a table view in a xib file like how we use it in a storyboard. Is there a work around to this? do I need another storyboard to achieve this?

Brendon Cheung
  • 995
  • 9
  • 29
  • What you've created looks like a table view instead of a table view controller. That's why they are different. Also, there is nothing preventing you from creating another storyboard. That is super common too as the project grows. – Yuchen Aug 25 '17 at 01:14
  • Hi Yuchen, it was meant to be a table view and not a table view controller. Why do people have more one than storyboards in their projects and why it is useful and common ? – Brendon Cheung Aug 25 '17 at 01:21
  • Storyboard is xml based, which can result in conflicts easily when there are multiple people working on it at the same time. And the conflicts are pretty hard to resolve. Also, a storyboard can render pretty slow and hard to work with as it becomes more complex. So yay, it is easier to keep them small. – Yuchen Aug 25 '17 at 01:33
  • Take a look at storyboard references. For example see: https://useyourloaf.com/blog/refactoring-with-storyboard-references/ – Mike Taverne Aug 25 '17 at 02:18

3 Answers3

1

Yes, you can use as many storyboards as you would like in an application.

I try to setup 1 storyboard per workflow. However some less storyboard enthusiastic developers use 1 storyboard per view controller.

To get the initial view controller from a storyboard named "MyStoryboard":

let storyboard = UIStoryboard(name: "MyStoryboard", bundle: nil)
let viewController = storyboard.instantiateInitialViewController()!

or to get a view controller with the identifier "MyViewController".

let storyboard = UIStoryboard(name: "MyStoryboard", bundle: nil)
let viewController = storyboard.instantiateViewController(withIdentifier: "MyViewController")!

There are two basic ways for a view controller to access a second view controller in another storyboard.

  1. In the storyboard, use a Storyboard Reference to the second view controller, then use a show segue to push the second view controller.

  2. In the view controller's source, create the second view controller using instantiateInitialViewController() or instantiateViewController(withIdentifier:) and push it onto the navigation controller.

Jeffery Thomas
  • 42,202
  • 8
  • 92
  • 117
  • Thanks for the reply, if my first storyboard contains a navigation view controller, how does my second storyboard know about that navigation controller that was embedded in the first storyboard? in other words, how to I continue that "navigation"? – Brendon Cheung Aug 25 '17 at 01:48
1

Task 1. Load UIViewcontroller form Xib

We can load a UIViewcontroller form Xib instead of Storyboard. We can use following procedure:

1. Create a UIViewcontroller.

 XCode File -> New -> File -> Cocoa Touch Class -> Fill Class with your class name , subclass of with UIViewController , check Also create Xib file, language Swift -> Next - Create.

 Example: ViewControllerFromXib

2. Override init().

override init(nibName nibNameOrNil: String?, bundle nibBundleOrNil: Bundle?) 
{
   super.init(nibName: "ViewControllerFromXib", bundle: Bundle.main)
}

required init?(coder aDecoder: NSCoder) 
{
   super.init(coder:aDecoder)
}

3. Open newly created Controller

let controller = ViewControllerFromXib.init()
self.present(controller, animated: true, completion: nil)

In this above way, We can load a UIViewcontroller from XIB.

Task 2. Create a tableview & populate it's cell using custom xib

1. Create a Custom UItableViewCell

XCode File -> New -> File -> Cocoa Touch Class -> Fill Class with your cell name , subclass of with TableViewCell , check Also create Xib file, language Swift -> Next - Create.

Example: CustomTableViewCell

1.Register UItableViewCell for Your TableView.

override func viewDidLoad() {
    super.viewDidLoad()
    self.title = "Item"
    self.tableView.register(UINib(nibName: "CustomTableViewCell", bundle:Bundle.main), forCellReuseIdentifier: "CustomTableViewCell");
}

2. Implement UITableViewDataSource into Your Viewcontroller

extension ViewControllerFromXib:UITableViewDataSource {

    func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
        return 3;
    }

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

        let cell = tableView.dequeueReusableCell(withIdentifier: "CustomTableViewCell", for: indexPath) as! CustomTableViewCell
        return cell

    }

}

2. Implement UITableViewDelegate into Your Viewcontroller.

extension ViewControllerFromXib:UITableViewDelegate {

    func tableView(_ tableView: UITableView, heightForRowAt indexPath: IndexPath) -> CGFloat{

        return UITableViewAutomaticDimension;

    }

}
Mamun
  • 131
  • 3
0

You can have many storyboards in the same project.

I usually like to have 1 storyboard per "main" screen, which is easy to instantiate programmatically, and can be linked in the IB as well.

As for your problem, i'd suggest your custom uitableviewcell be created in a .xib file. As an independent view. This way on your code you can just register it as the "reusable cell" for any view controller you want regardless of the storyboard that contains it.

Pochi
  • 13,391
  • 3
  • 64
  • 104
  • I did create a custom table view cell. Why would having many storyboards help with your workflow? thanks – Brendon Cheung Aug 25 '17 at 01:50
  • Because when working on large projects, many people can focus on individual parts of the application. Plus there is really no downside nowadays of splitting them since storyboards can be linked with each other using storyboard references or simply have a managing class that presents programatically the required storyboard. This is specially good with the MVVM pattern as views and their controllers have almost no business logic in them. – Pochi Aug 25 '17 at 02:21