今回は、UIButton
に Activity Indicator
を追加する方法についてです。
ページにボタンがあって、ページ読み込み中はそのボタンにローディングアイコンが表示される、という挙動をさせたくて実装しました。
参考にさせていただいた記事はこちら。
Set Activity Indicator in UIButton in Swift 3 – Mobikul
https://mobikul.com/set-activity-indicator-uibutton-swift-3/
サンプルコードはこちらです。
必要な部分だけを抜粋していますので、それ以外は適宜変更してください。
class ViewController: UIViewController { @IBOutlet weak var button: UIButton! var activityIndicator: UIActivityIndicatorView! override func viewDidLoad() { super.viewDidLoad() self.button.addTarget(self, action: #selector(self.tapButton(_:)), for: .touchUpInside) self.showSpinning() } @objc func tapButton(_ sender: UIButton) { self.hideSpinning() } public func showSpinning() { if (activityIndicator == nil) { activityIndicator = UIActivityIndicatorView() activityIndicator.hidesWhenStopped = true activityIndicator.color = UIColor.gray } self.button.setImage(nil, for: .normal) activityIndicator.translatesAutoresizingMaskIntoConstraints = false self.button.addSubview(activityIndicator) // ローディングアイコンを中央寄せ let xCenterConstraint = NSLayoutConstraint(item: self.button!, attribute: .centerX, relatedBy: .equal, toItem: activityIndicator, attribute: .centerX, multiplier: 1, constant: 0) self.button.addConstraint(xCenterConstraint) let yCenterConstraint = NSLayoutConstraint(item: self.button!, attribute: .centerY, relatedBy: .equal, toItem: activityIndicator, attribute: .centerY, multiplier: 1, constant: 0) self.button.addConstraint(yCenterConstraint) activityIndicator.startAnimating() } public hideSpinning() { activityIndicator.stopAnimating() self.button.setImage(UIImage(named: "image"), for: .normal) } }
上記を実装すると、ページが表示された時にはボタンにローディングアイコンが表示されており、ボタンをタップするとローディングが消え、指定した画像がボタンに表示されます。
意外と大事なのが 22行目の self.button.setImage(nil, for: .normal)
でした。
上記のサンプルコードでは大丈夫ですが、例えばもともとボタンに画像を設定している状態から、ローディングアイコンを表示する時には、こちらのコードがないとローディングアイコンとボタン画像の両方が表示されてしまい、大変見にくかったです。
なので、ボタンに設定するものが、画像→ローディングアイコン→画像 というように変化する可能性がある場合は、self.button.setImage(nil, for: .normal)
の記述をお忘れなく。
以上、Swift の UIButton に Activity Indicator を追加する方法についてでした。
ご参考になれば幸いです。