初學(xué)swift5 實(shí)現(xiàn)簡(jiǎn)易自定義tababar

本文是剛學(xué)習(xí)swift后宙拉,第一個(gè)練手的項(xiàng)目,主要目的是將學(xué)到的swift知識(shí)去完成一個(gè)簡(jiǎn)易的自定義tabbar

先看效果


總效果圖

然后我們?cè)谝粚右粚涌?/p>

根據(jù)自己的需求,用CGContext 畫的背景圖
中間的tabBarItem不設(shè)置圖片醇锚,只設(shè)置文字
在tabbar上的背景圖上插入自定義的控件
這里自定義的控件是button

到這里贼穆,總結(jié)下就是题山,
我們自定義的tabbar,根據(jù)需求添加一個(gè)背景圖故痊,然后在插入我們自定義的控件到正確的位置上即可顶瞳,其他的都沿用原生的tabbar,因?yàn)樽远x控件會(huì)擋住原生tabbaritem愕秫,所以需要單獨(dú)為我們自定義的控件添加點(diǎn)擊事件(后面會(huì)講道自定義控件的點(diǎn)擊事件)慨菱。

代碼:

class CustomTabbar: UITabBar {
    private lazy var centerBtn: UIButton = {
        let btn = UIButton.init(type: .custom)
        btn.setImage(UIImage.initWithOriginalMode(named: "tab_diy"), for: .normal)
        btn.setImage(UIImage.initWithOriginalMode(named: "tab_diy_sel"), for: .selected)
        btn.sizeToFit()
        btn.imageEdgeInsets = UIEdgeInsets.init(top: -10, left: 0, bottom: 0, right: 0)
        btn.addTarget(self, action: #selector(clickAtItem), for: .touchUpInside)
        return btn
    }()
    weak open var clickDelegate: CustomTabbarDelegate?

   ...

    override init(frame: CGRect) {
        super.init(frame: frame)
        //   添加背景圖
        let backV = UIImageView.init(frame: CGRect.init(x: 0, y: -26, width: ScreenW, height: 75))
        backV.backgroundColor = UIColor.clear
        self.addSubview(backV)

        // 自己繪制的背景圖
        let img = drawCustomTabbarBackImg()
        backV.image = img

        // 添加自定義的btn控件
        self.addSubview(centerBtn)
    }

    override func layoutSubviews() {
        super.layoutSubviews()
        // 重新計(jì)算自定義btn控件的位置
        centerBtn.frame = CGRect.init(x: ScreenW/5*2, y: -26, width: ScreenW/5, height: 75)
        self.bringSubviewToFront(centerBtn)
    }


    @objc func clickAtItem(btn: UIButton) {
        // btn 點(diǎn)擊之后狀態(tài)給反轉(zhuǎn)下
        btn.isSelected = !btn.isSelected
        // 讓代理去實(shí)現(xiàn)點(diǎn)擊事件。
        clickDelegate?.clickTabbarItem((self, centerBtn))
    }

## 重寫hitTest方法戴甩,去監(jiān)聽中間按鈕點(diǎn)擊符喝,目的是為了讓凸出的部分點(diǎn) 擊也有反應(yīng) ##
## 當(dāng)然你的視圖不超出父視圖,這個(gè)也可以不寫 ##

    override func hitTest(_ point: CGPoint, with event: UIEvent?) -> UIView? {
        if !self.isHidden, centerBtn.frame.contains(point) {
            return centerBtn
        }
        // 記得把centerbtn 設(shè)置成 nomal狀態(tài)
        centerBtn.isSelected = false
        return super.hitTest(point, with: event)
    }
}
}}

有一個(gè)代理的注意點(diǎn)甜孤,(畢竟初學(xué)swift协饲,還是有必要提一下)

## OC 中代理都是用 weak 修飾 防止循環(huán)引用,這里也要遵守 ##
weak open var clickDelegate: CustomTabbarDelegate?

@objc func clickAtItem(btn: UIButton) {
        // btn 點(diǎn)擊之后狀態(tài)給反轉(zhuǎn)下
        btn.isSelected = !btn.isSelected
        // 讓代理去實(shí)現(xiàn)點(diǎn)擊事件缴川。
        clickDelegate?.clickTabbarItem((self, centerBtn))
    }

## :后面的 class囱稽,指定只能給class用不能給值類型用 ##
protocol CustomTabbarDelegate: class {
    func clickTabbarItem(_: (Any));
}

接下來就是 tabbarController 里面替換成我們自定義的tabbar了
關(guān)鍵一句就是:

self.setValue(customTab, forKey: "tabBar")
class BaseTabVC: UITabBarController {

    override func viewDidLoad() {
        super.viewDidLoad()
        self.customTabbar()

        let temple = (titles: ["首頁", "分類", "DIY", "圈子", "我的"], images: ["tab_home", "tab_material", "", "tab_social", "tab_my"])
        let vcs = [HomeVC.init(), MaterialVC.init(), DIYVC.init(), SocialVC.init(), ProfileVC.init()].enumerated().map { (idx, vc) -> UIViewController in
            self.controller(createTabbarItemWith: vc, title: temple.titles[idx], image: temple.images[idx])
            let nav = BaseNavVC.init(rootViewController: vc)
            return nav
        }

        self.viewControllers = vcs
    }

    func customTabbar() {
        let customTab = CustomTabbar.init(frame: CGRect.init(x: 0, y: ScreenH - TabbarH, width: ScreenW, height: TabbarH))
        // 別忘了實(shí)現(xiàn)代理
        customTab.clickDelegate = self
        self.setValue(customTab, forKey: "tabBar")

## 這里還是我們熟悉的調(diào)整tabbar 上面的一些屬性 ##
## 根據(jù)我們的需求調(diào)整就行 ##

        //調(diào)整tabbar 上面橫線陰影顏色
        self.tabBar.backgroundImage = UIImage.init()
        self.tabBar.shadowImage = UIImage.init();
        self.tabBar.barTintColor = HEX(hexValue: 0xFFFFFF)
        self.tabBar.tintColor = HEX(hexValue: 0x0D57F6)
        self.tabBar.unselectedItemTintColor = HEX(hexValue: 0x000000)
        self.tabBar.isTranslucent = false
    }
    ...

切換tabBarItem的方法

self.selectedIndex = 2
// 擴(kuò)展里面, 實(shí)現(xiàn) 點(diǎn)擊 customTabbar 的代理
extension BaseTabVC: CustomTabbarDelegate {
    func clickTabbarItem(_: (Any)) {
        guard let vc = self.viewControllers?[2] else { return }
## 切換當(dāng)前tabitem 到我們需要的控制器 ##
        self.selectedIndex = 2
    }
}

寫在最后,實(shí)現(xiàn)自定義的tabbar 可以有很多種思路二跋,復(fù)雜的可以寫一個(gè)view 替換掉tabbar战惊,然后將系統(tǒng)的tabbar 給隱藏掉,都是可以的扎即,只不過需要實(shí)現(xiàn)tabbar所有的功能吞获,會(huì)比較繁瑣。這個(gè)自定義的好處是谚鄙,整體代碼量不多各拷,思路實(shí)現(xiàn)也不復(fù)雜,主要是不影響原生tabbar的功能闷营。

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末烤黍,一起剝皮案震驚了整個(gè)濱河市知市,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌速蕊,老刑警劉巖嫂丙,帶你破解...
    沈念sama閱讀 217,406評(píng)論 6 503
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場(chǎng)離奇詭異规哲,居然都是意外死亡跟啤,警方通過查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,732評(píng)論 3 393
  • 文/潘曉璐 我一進(jìn)店門唉锌,熙熙樓的掌柜王于貴愁眉苦臉地迎上來隅肥,“玉大人,你說我怎么就攤上這事袄简⌒确牛” “怎么了?”我有些...
    開封第一講書人閱讀 163,711評(píng)論 0 353
  • 文/不壞的土叔 我叫張陵绿语,是天一觀的道長(zhǎng)捉片。 經(jīng)常有香客問我,道長(zhǎng)汞舱,這世上最難降的妖魔是什么伍纫? 我笑而不...
    開封第一講書人閱讀 58,380評(píng)論 1 293
  • 正文 為了忘掉前任,我火速辦了婚禮昂芜,結(jié)果婚禮上莹规,老公的妹妹穿的比我還像新娘。我一直安慰自己泌神,他們只是感情好良漱,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,432評(píng)論 6 392
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著欢际,像睡著了一般母市。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上损趋,一...
    開封第一講書人閱讀 51,301評(píng)論 1 301
  • 那天患久,我揣著相機(jī)與錄音,去河邊找鬼浑槽。 笑死蒋失,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的桐玻。 我是一名探鬼主播篙挽,決...
    沈念sama閱讀 40,145評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼,長(zhǎng)吁一口氣:“原來是場(chǎng)噩夢(mèng)啊……” “哼镊靴!你這毒婦竟也來了铣卡?” 一聲冷哼從身側(cè)響起链韭,我...
    開封第一講書人閱讀 39,008評(píng)論 0 276
  • 序言:老撾萬榮一對(duì)情侶失蹤,失蹤者是張志新(化名)和其女友劉穎煮落,沒想到半個(gè)月后敞峭,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,443評(píng)論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡州邢,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,649評(píng)論 3 334
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了褪子。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片量淌。...
    茶點(diǎn)故事閱讀 39,795評(píng)論 1 347
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖嫌褪,靈堂內(nèi)的尸體忽然破棺而出呀枢,到底是詐尸還是另有隱情,我是刑警寧澤笼痛,帶...
    沈念sama閱讀 35,501評(píng)論 5 345
  • 正文 年R本政府宣布裙秋,位于F島的核電站,受9級(jí)特大地震影響缨伊,放射性物質(zhì)發(fā)生泄漏摘刑。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,119評(píng)論 3 328
  • 文/蒙蒙 一刻坊、第九天 我趴在偏房一處隱蔽的房頂上張望枷恕。 院中可真熱鬧,春花似錦谭胚、人聲如沸徐块。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,731評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽胡控。三九已至,卻和暖如春旁趟,著一層夾襖步出監(jiān)牢的瞬間昼激,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 32,865評(píng)論 1 269
  • 我被黑心中介騙來泰國(guó)打工锡搜, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留癣猾,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 47,899評(píng)論 2 370
  • 正文 我出身青樓余爆,卻偏偏與公主長(zhǎng)得像纷宇,于是被迫代替她去往敵國(guó)和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子蛾方,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,724評(píng)論 2 354

推薦閱讀更多精彩內(nèi)容