I have a tab bar controller that shows 5 tabs. It shows perfectly in iOS 12 or earlier as shown here
.
But if I run the same in iOS 13, the design is totally messed up
.
It totally loses the scroll view insets, and it is also not adjusting the bottom insets of my menus table view. some of the menus are hidden in the bottom. they are not scrolling up. and this is the code that I'm using in UITabBarController
override func viewDidLoad() {
super.viewDidLoad()
delegate = self
guard let user = user else {
appDelegate.instituteSelectionView()
return
}
var dashBoard: UINavigationController
var menus: UINavigationController? = nil
// Creating all the view controllers for tabs.
if user.role.caseInsensitiveCompare("student") == .orderedSame {
let dashBoardVC = mainStoryBoard.instantiateViewController(withIdentifier: "DashboardVC") as! DashboardVC
dashBoardVC.menus = ContentProvider.getMenus()
dashBoardVC.school = user.school
dashBoard = UINavigationController(rootViewController: dashBoardVC)
dashBoard.navigationBar.prefersLargeTitles = true
} else {
let dashBoardVC = mainStoryBoard.instantiateViewController(withIdentifier: "DashboardWidgetsTableViewController") as! DashboardWidgetsTableViewController
dashBoardVC.user = user
dashBoardVC.title = "Dashboard"
dashBoard = UINavigationController(rootViewController: dashBoardVC)
let menusVC = mainStoryBoard.instantiateViewController(withIdentifier: "MenusTableViewController") as! MenusTableViewController
menusVC.setMenus(ContentProvider.getMenusForStaff())
menus = UINavigationController(rootViewController: menusVC)
}
dashBoard.tabBarItem = UITabBarItem(title: "Dashboard", image: #imageLiteral(resourceName: "dashboard"), tag: 0)
if menus != nil {
menus?.navigationBar.prefersLargeTitles = true
menus?.tabBarItem = UITabBarItem(title: "Menus", image: #imageLiteral(resourceName: "menu-1"), tag: 1)
}
let notificationVC = mainStoryBoard.instantiateViewController(withIdentifier: "NotificationsTabTableViewController") as! NotificationsTabTableViewController
notificationVC.user = user
let notification = UINavigationController(rootViewController: notificationVC)
notification.tabBarItem = UITabBarItem(title: "Notifications", image: #imageLiteral(resourceName: "bell"), tag: 3)
notification.tabBarItem.badgeValue = user.badge > 0 ? String(user.badge) : nil
notification.navigationBar.prefersLargeTitles = true
let settingsVC = mainStoryBoard.instantiateViewController(withIdentifier: "SettingsTabTableViewController") as! SettingsTabTableViewController
settingsVC.user = user
let settings = UINavigationController(rootViewController: settingsVC)
settings.tabBarItem = UITabBarItem(title: "Settings", image: #imageLiteral(resourceName: "settings"), tag: 4)
settings.navigationBar.prefersLargeTitles = true
let accountsVC = mainStoryBoard.instantiateViewController(withIdentifier: "AccountsTableViewController") as! AccountsTableViewController
let accounts = UINavigationController(rootViewController: accountsVC)
accounts.tabBarItem = UITabBarItem(title: "Accounts", image: #imageLiteral(resourceName: "user_group_man_man"), tag: 5)
accounts.navigationBar.prefersLargeTitles = true
mViewControllers = [dashBoard, notification, settings, accounts]
if menus != nil {
mViewControllers.insert(menus!, at: 1)
}
// Adding logo and profile button to navigation bar of each view controller.
for vc in mViewControllers {
if let nVC = vc as? UINavigationController, let vc = nVC.topViewController {
let logo = UIImageView(image: #imageLiteral(resourceName: "educare logo"))
logo.contentMode = .scaleAspectFill
logo.clipsToBounds = true
logo.widthAnchor.constraint(equalToConstant: 24).isActive = true
logo.heightAnchor.constraint(equalToConstant: 24).isActive = true
let profileButton = UIButton(type: .custom)
profileButton.widthAnchor.constraint(equalToConstant: 24).isActive = true
profileButton.heightAnchor.constraint(equalToConstant: 24).isActive = true
profileButton.imageView?.layer.cornerRadius = 12
if #available(iOS 13.0, *) {
let image = UIImage(systemName: "person.crop.circle")
profileButton.sd_setImage(with: URL(string: user.image), for: .normal, placeholderImage: image)
} else {
profileButton.sd_setImage(with: URL(string: user.image), for: .normal, placeholderImage: #imageLiteral(resourceName: "user_circle"))
}
profileButton.addTarget(self, action: #selector(openProfile), for: .touchUpInside)
let logoButtonItem = UIBarButtonItem(customView: logo)
let profileButtonItem = UIBarButtonItem(customView: profileButton)
vc.navigationItem.leftBarButtonItem = logoButtonItem
vc.navigationItem.rightBarButtonItems = [profileButtonItem]
}
}
setViewControllers(mViewControllers, animated: true)
}
Update: Actually the first view controller in the tab bar controller renders correctly but the rest of the view controllers have that ugly navigation bar.
I Solved the problem. turns out it was the transition animation (from the initial view controller to the main tab bar controller) that was causing the problem. So i changed the code from this
if animated {
UIView.transition(from: (window?.rootViewController?.view)!, to: viewController.view, duration: duration, options: animationOptions) { (completed) in
if completed {
self.window?.rootViewController = viewController
self.window?.makeKeyAndVisible()
}
}
} else {
self.window?.rootViewController = viewController
self.window?.makeKeyAndVisible()
}
to this
guard let window = UIApplication.shared.keyWindow else { return }
window.rootViewController = viewController
window.makeKeyAndVisible()
if animated {
UIView.transition(with: window, duration: duration, options: animationOptions, animations: {})
}