①③① 在 Tab Bar 添加自訂 Button 並使用 UITabBarAppearance 調整 Tab Bar Items 的位置
iOS App “私人書藏-PrivLibrary” 系列 I
這次預計做一個藏書管理 App,用來練習 CRUM、各種資料儲存與想要實現的 UI 物件。第一篇就從在 Tab Bar 放個特別的按鈕開始,像是智生活跟記帳城市這樣子:
Storyboard
先把畫面拉一下,因為希望按下自訂 Button 之後顯示新增書籍的頁面 Add A Book Controller,新增完一本書之後就離開頁面,因此不用連接在 Tab Bar 旗下。
Tab Bar Controller 的 Appearances 選擇 Standard
這個選擇之後大有用處:
自定義顏色
到 Coolers 網站找一些配色靈感,建立一個 Colors structure:
struct Colors {
static let chiliRed = UIColor(red: 214/255, green: 73/255, blue: 51/255, alpha: 1)
static let redWood = UIColor(red: 169/255, green: 99/255, blue: 88/255, alpha: 1)
static let grey = UIColor(red: 124/255, green: 124/255, blue: 124/255, alpha: 1)
static let silver = UIColor(red: 181/255, green: 177/255, blue: 179/255, alpha: 1)
static let frenchGrey = UIColor(red: 210/255, green: 203/255, blue: 206/255, alpha: 1)
static let lavenderBlush = UIColor(red: 238/255, green: 229/255, blue: 233/255, alpha: 1)
static let lightBlue = UIColor(red: 192/255, green: 225/255, blue: 231/255, alpha: 1)
static let nonPhotoBlue = UIColor(red: 146/255, green: 220/255, blue: 229/255, alpha: 1)
static let airForceBlue = UIColor(red: 95/255, green: 134/255, blue: 144/255, alpha: 1)
static let gunMetal = UIColor(red: 43/255, green: 48/255, blue: 58/255, alpha: 1)
}
之後可直接引用:
TabBarController
建立一個 TabBarController 來設定 Tab Bar 的程式:
把 Storyboard 中的 Custom Class 也選起來:
在 Tab Bar 中宣告一個 centralButton 常數,用來自定義:
class TabBarController: UITabBarController {
// 設定自訂的 button
let centralButton = UIButton()
setButton()
設定 centralButton 的方法,因為 TabBarController 繼承 UITabBarController,因此有 tabBar 與 tabBarItem 等內建實例屬性可以使用:
// 設定 centralButton
func setButton() {
// 設定大小為 tabBar
centralButton.frame.size = CGSize(width: 114, height: tabBar.bounds.height * 0.5)
// 設定位置在 tabBar 正中央
centralButton.center = CGPoint(x: tabBar.bounds.midX, y: tabBar.bounds.midY)
// 設定背景色
centralButton.backgroundColor = Colors.chiliRed
// 設定邊框弧度
centralButton.layer.cornerRadius = 13
// 設定文字
centralButton.setTitle("Add A Book", for: .normal)
// 設定普通情況下的文字顏色
centralButton.setTitleColor(Colors.lavenderBlush, for: .normal)
// 裁剪掉弧線邊框外的內容
centralButton.clipsToBounds = true
// 設定點擊 centralButton 觸發的動作,調用 showAddingBookViewController 方法
centralButton.addTarget(self, action: #selector(showAddingBookViewController), for: .touchDown)
// 將 centralButton 添加到 tabBar 內
tabBar.addSubview(centralButton)
}
其中 centralButton.addTarget(self, action: #selector(showAddingBookViewController), for: .touchDown)
掌管點擊 central button 後出現 AddingBookViewController
的動作,在 showAddingBookViewController
中定義轉場方式、視圖呈現方式與 present 的方法:
// 顯示 showAddingBookViewController 的方法
@objc func showAddingBookViewController() {
// 創建一個 AddingBookViewController 實例
let addingBookViewController = AddingBookViewController()
// 設定轉場樣式
addingBookViewController.modalTransitionStyle = .flipHorizontal
// 設定 ViewController 的格式
addingBookViewController.modalPresentationStyle = .pageSheet
// 呈現 addingBookViewController
present(addingBookViewController, animated: true, completion: nil)
}
ViewDidLoad 呼喚:
override func viewDidLoad() {
super.viewDidLoad()
setButton()
}
這當下的 Tab Bar 長這樣:
兩側的 Tab Bar Item 離按鈕太近了,這時剛剛在 Storyboard 將 Tab Bar 的 Appearances 設定為 Standard 就可以派上用場了。
stackedItemPositioning
在 Standard 模式內,於 Storyboard 中可以看到有一組 Standard Stacked Item,裡面的 Positioning 可以將 item 們設定為 Fill 或 Centered(Default 跟 Automatic 我試起來都是 Fill)。
Fill 是常見的平均分散布置,而 Centered 則是向中間靠攏。所以我們試著用 Centered,再調整控制 items 間隔的 Spacing,應該就能達到設定位置的目的。
的確可行!不過如果要適應不同的螢幕寬度,像下圖,左邊的 iPhone 15 pro Max 要使用 180 的 spacing 才有分開的感覺,但對第一代 iPhone SE 來說,這個間隔會把 item 推出去,超過它能設定的範圍,因此原地不動。看來只能透過程式設定位置。
建立一個 setTabBarAppearence() 方法,將兩個 Tab Bat Item 的間隔設為 tabBar 的百分之 45 寬:
// 設定 Tab Bar Item 的位置
func setTabBarAppearence() {
tabBar.standardAppearance.stackedItemPositioning = .centered
tabBar.standardAppearance.stackedItemSpacing = tabBar.bounds.width * 0.45
}
ViewDidLoad 呼喚:
override func viewDidLoad() {
super.viewDidLoad()
setButton()
setTabBarAppearence()
}
這樣就比較好看了:
謝謝收看!
GitHub:
Reference: