Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to get a custom tab bar to display a tab bar item's selected image set in Xcode?

Tags:

xcode

swift3

I've created a custom tab bar that is displaying tab bar items correctly. When I select a tab / icon the tab bar item's view controller is displayed but the icon does not change to the 'Selected image' icon i.e. the icons don't change when their view controller is being shown.

What am I doing wrong? How can I get the icons to update to the images that I've set on IB as the selected images?

Here is some of my code:

class CustomTabBarController: UITabBarController, CustomTabBarDataSource, CustomTabBarDelegate {
 override func viewDidLoad() {
  super.viewDidLoad()
  self.tabBar.isHidden = true
  let customTabBar = CustomTabBar(frame: self.tabBar.frame)
  customTabBar.datasource = self
  customTabBar.delegate = self
  customTabBar.setup()
  self.view.addSubview(customTabBar)
 }
 // MARK: - CustomTabBarDataSource
 func tabBarItemsInCustomTabBar(_ tabBarView: CustomTabBar) -> [UITabBarItem] {
  return tabBar.items!
 }
 // MARK: - CustomTabBarDelegate
 func didSelectViewController(_ tabBarView: CustomTabBar, atIndex index: Int) {
  self.selectedIndex = index
 }   
}


class CustomTabBar: UIView {
 var tabBarItems: [UITabBarItem]!
 var customTabBarItems: [CustomTabBarItem]!
 var tabBarButtons: [UIButton]!

func setup() {
 tabBarItems = datasource.tabBarItemsInCustomTabBar(self)
 customTabBarItems = []
 tabBarButtons = []
 let containers = createTabBarItemContainers()
 createTabBarItems(containers)
}

func createTabBarItems(_ containers: [CGRect]) {

var index = 0
 for item in tabBarItems {
  let container = containers[index]
  let customTabBarItem = CustomTabBarItem(frame: container)
  customTabBarItem.setup(item)
  self.addSubview(customTabBarItem)
  customTabBarItems.append(customTabBarItem)
  let button = UIButton(frame: CGRect(x: 0, y: 0, width: container.width, height: container.height))
  button.addTarget(self, action: #selector(CustomTabBar.barItemTapped(_:)), for: UIControlEvents.touchUpInside)
  customTabBarItem.addSubview(button)
  tabBarButtons.append(button)
  index += 1
 }
}

func barItemTapped(_ sender : UIButton) {
 let index = tabBarButtons.index(of: sender)!
 delegate.didSelectViewController(self, atIndex: index)
}
like image 758
grabury Avatar asked Mar 13 '17 02:03

grabury


People also ask

How do I add an image to the tab bar in iOS?

iOS UITabBarController Changing Tab Bar Item Title and Icon For a custom icon, add the required images to the assets folder and set the 'System Item' from earlier to 'custom'. Now, set the icon to be shown when the tab is selected from the 'selected image' drop down and the default tab icon from the 'image' drop down.

How do I add items to my tab bar controller?

To add a tab, first drag a new View Controller object to the storybard. Next control-drag from the tab bar controller to new view controller and select view controllers under Relationship Segue . Your tab bar controller will update with a new tab.

How do I create a custom tab bar in Swift?

Implement a view controller that can hold some other view controllers. Show one of those view controllers. Show a tab bar at the bottom of the screen over the shown view controller. Switch between the various view controllers when the user taps on a tab bar button.


2 Answers

Change

class CustomTabBar: UIView {

to:

class CustomTabBar: UITabBar {

Then your custom tab bar will act like a tab bar!

like image 62
leanne Avatar answered Nov 15 '22 10:11

leanne


Well I had a same kind of functionality and implemented with UITabBarController like this.

enum TabType:Int{
case viewController1 = 0
case viewController2 = 1
case viewController3 = 2
}

class CustomTabbarVC: UITabBarController {

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

    override func didReceiveMemoryWarning() {
        super.didReceiveMemoryWarning()
        // Dispose of any resources that can be recreated.
    }

    convenience init(userType : UserType){
        self.init()
        addViewControllers()
        setupOnInit()

        let tabBar = self.tabBar
        tabBar.selectionIndicatorImage = UIImage().createSelectionIndicator(UIColor(red: 22/255, green: 52/255, blue: 89/255, alpha: 1.0), size: CGSize(width: tabBar.frame.width/CGFloat(tabBar.items!.count), height: tabBar.frame.height), lineWidth: 3.0)
    }


    func setupOnInit(){

        delegate = self
        tabBar.barStyle = UIBarStyle.black
        tabBar.isTranslucent = false
    }

    func addViewControllers(){

        // We will add 3 controllers

        let viewController1 = viewController1(nibName: “viewController1”, bundle: nil)
        let viewController2 = viewController2(nibName: “viewController2”, bundle: nil)
        let viewController3 = viewController3(nibName: “viewController3”, bundle: nil)

        let viewController1Navigation =  UINavigationController(rootViewController: viewController1)
        viewController1Navigation.tabBarItem = getTabbarItem(.viewController1)
        viewController1Navigation.tabBarItem.imageInsets = UIEdgeInsetsMake(6, 0, -6, 0)

        let viewController2Navigation =  UINavigationController(rootViewController: viewController2)
        viewController2Navigation.tabBarItem = getTabbarItem(.viewController2)
        viewController2Navigation.tabBarItem.imageInsets = UIEdgeInsetsMake(6, 0, -6, 0)

        let viewController3Navigation =  UINavigationController(rootViewController: viewController3)
        viewController3Navigation.tabBarItem = getTabbarItem(.viewController3)
        viewController3Navigation.tabBarItem.imageInsets = UIEdgeInsetsMake(6, 0, -6, 0)

        viewControllers = [viewController1Navigation,viewController2Navigation,viewController3Navigation]

    }


    func getTabbarItem(_ tabType:TabType)->UITabBarItem{

        // Fetch tab bar item and set image according to it.

        var image = String()
        var selectedImage = String()

        if tabType == .viewController1{
            image = “img_viewController1_tab_nonSelected”
            selectedImage = “img_viewController1_tab_Selected”
        }else if tabType == .viewController2{
            image = “img_viewController2_tab_nonSelected”
            selectedImage = “img_viewController2_tab_Selected”
        }else if tabType == .viewController3{
            image = “img_viewController3_tab_nonSelected”
            selectedImage = “img_viewController3_tab_Selected”
        }else{
            print("Unknown tab type")
        }

        if let imageName:String = image,let selectedImageName:String = selectedImage{
            return UITabBarItem(title: nil, image: UIImage(named: imageName)?.withRenderingMode(.alwaysOriginal), selectedImage: UIImage(named: selectedImageName)?.withRenderingMode(.alwaysOriginal))
        }else{
            return UITabBarItem()
        }
    }

}

extension UIImage {
    func createSelectionIndicator(_ color: UIColor, size: CGSize, lineWidth: CGFloat) -> UIImage {
        UIGraphicsBeginImageContextWithOptions(size, false, 0)
        color.setFill()
        UIRectFill(CGRect(x: 0, y: size.height - lineWidth, width: size.width, height: lineWidth))
        let image = UIGraphicsGetImageFromCurrentImageContext()
        UIGraphicsEndImageContext()
        return image!
    }
}

How to implement in App delegate

class AppDelegate: UIResponder, UIApplicationDelegate{

    var window: UIWindow?
    var customTabbarVC: CustomTabbarVC?

    func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {

         window = UIWindow(frame: UIScreen.main.bounds)
         customTabbarVC = customTabbarVC() // It will invoke init methods of customtabbarvc
         window?.rootViewController = customTabbarVC // Here your tab bar controller will setup 

        return true
     }

  // Other APP DELEGATE METHODS

}

Let me know if you have any questions..

like image 38
Anil Kukadeja Avatar answered Nov 15 '22 10:11

Anil Kukadeja