LoginSignup
12
11

More than 5 years have passed since last update.

一度だけ実行したい処理がある...そんなあなたにおすすめの可愛いわんこちゃん

Last updated at Posted at 2016-03-20

概要

関数(呼び出し元)毎に一度だけ処理を実行させるInuというライブラリを書いてみました。

背景

iOSアプリ開発していると一度だけ処理を実行させたい場面がたまにあります。
例えば、viewWillAppear(animated:)等でCustomViewをaddSubViewさせたい場合などあったりするのではないでしょうか。
この場合だとBool型のpropertyでFlag制御したり、dispatch_once()を使った制御等が考えられます。

    var isOnce: Bool = false
    override func viewWillAppear(animated: Bool) {
        super.viewWillAppear(animated)
        if !isOnce {
            anyFunction()
            isOnce = true
        }
    }
    var token: dispatch_once_t = 0
    override func viewWillAppear(animated: Bool) {
        super.viewWillAppear(animated)
        dispatch_once(&token) {
            self.anyFunction()
        }
    }

実現したい内容やタイミングが多様化するとプロパティを増やしたりする必要がありそうです。
個人的には狭いスコープで使用するためのプロパティを増やすのはあまり好きではないです。

インスタンスメソッド単位での処理の制御なら簡単に出来そうだと思ってInuを書きました。

使い方

class ViewController: UIViewController, OnceType {
   override func viewWillAppear(animated: Bool) {
        super.viewWillAppear(animated)
        once.call() {
            anyFunction()
        }
    }

OnceTypeというprotocolを適用して
once.call() { }を呼び出すことでクロージャの中の処理を一度だけ実行します。

中身は

public protocol OnceType: AnyObject { }
public extension OnceType {
    public var once: Once {
        guard let object = objc_getAssociatedObject(self, &OnceAssociatedObjectHandle.OnceKey) as? Once else {
            let once = Once()
            objc_setAssociatedObject(self, &OnceAssociatedObjectHandle.OnceKey, once, .OBJC_ASSOCIATION_RETAIN)
            return once
        }
        return object
    }
}
    private var callStack: [String] = []
    public func call(withKey: String = __FUNCTION__, @noescape _ closure: Void -> Void) {
        if callStack.contains(withKey) {
            return
        }
        closure()
        callStack.append(withKey)
    }

こんな感じです。

AnyObjectであればなんでもいいので、頻繁に使用するようなクラスがあれば   

extension UIView: OnceType { }
extension UIViewController: OnceType { }

ベースクラスに書いてしまえば、継承しているサブクラスでも使えるのは利点かなと思ってます。
副作用もありそうですが。。。

他にも少し違った用途のメソッドも用意されています。
このわんこのことを可愛いと感じたらスターください。

\(^o^)/

12
11
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
12
11