UIButtonの同時タップを禁止する方法
isExclusiveTouchで同時タップを禁止
同時タップしてほしくないボタンのisExclusiveTouchを true にすると、同時タップができなくなるので安心です。
code: Swift
buttonA.isExclusiveTouch = true
buttonB.isExclusiveTouch = true
Outlet Collectionでほぼ自動
Outlet Collection をつくる方法は簡単です。
通常の Outlet をつくるように、controlキーを押しながらボタンをクリックして、ストーリーボードからソースファイルにぐいっとドラッグします。するとポップアップ画面が表示されるので、 connection を Outlet Collection に変更して name に名前を入力して、 connect ボタンをクリックします。 https://gyazo.com/f89bd3fbd3385485d8fe015520bc7340
あとは、 Outlet Collection に追加したいボタンをcontrolキーを押しながらクリックして、さきほど作成した Outlet Collection のところまでドラッグします。そうすると、ひとつの Outlet Collection に複数のボタンが登録されます。
https://gyazo.com/498ef87e5732a67fa35a4f032bc17318
ソースファイルでは、 Outlet Collection は下記のようになります。
code:Swift
@IBOutlet var exclusiveButtons: UIButton! UIButton の部分が [UIButton] になっているところからわかるように、 Outlet Collection はアウトレットの配列です。配列であれば for-in がつかえるので、下記のようなコードでいっきに isExclusiveTouchを true に変更できます。 code:Swift
for button in exclusiveButtons {
button.isExclusiveTouch = true
}
https://gyazo.com/6a1fe089477238015be7425be40d86ed
viewDidLoad などで上の処理を実行すれば、 Outlet Collection に追加しているボタンの同時タップを禁止することができます。
デフォルト設定すれば全自動
Qiitaでshtnkgmさんにコメントをいただいて追記しました。ありがとうございます! 以下のようにappearanceをつかって書くと UIButton 全体にデフォルト値として適用が可能だそうです。つぎに紹介する exclusiveAllTouches メソッドも便利ですが、たとえば viewDidLoad よりあとに動的に追加されたボタンへも反映できるそうです。 なにこれ素敵!
code:Swift
UIButton.appearance().isExclusiveTouch = true
再帰メソッドをつかえば全自動
Outlet Collection も便利ですが、ボタンを追加したときに設定し忘れるかもしれません。そんなときに便利な方法をこちらの記事で紹介していました。
viewDidLoadなどで exclusiveAllTouchesメソッドを呼び出せば、再帰的にすべてのボタンを検索してisExclusiveTouchをtrueにしてくれます。便利ですね。 code: Swift
extension UIViewController {
func exclusiveAllTouches() {
self.applyAllViews { $0.isExclusiveTouch = true }
}
func applyAllViews(apply: (UIView) -> ()) {
apply(self.view)
self.applyAllSubviews(self.view, apply: apply)
}
private func applyAllSubviews(view: UIView, apply: (UIView) -> ()) {
let subviews = view.subviews as UIView subviews.map { (view: UIView) -> () in // Swiftのmapって戻り値なくても大丈夫なのね(ちょっと不気味
apply(view)
self.applyAllSubviews(view, apply: apply)
}
}
}