2
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

Swift5.1 dynamicMemberLookup^KeyPathを使ってSwiftにKotolinのapplyを実装する

Last updated at Posted at 2019-10-04

デモ

.swift
final class ViewController: UIViewController {
    override func loadView() {
        view = UILabel().apply { $0
            .text("Apply Swift")
            .textAlignment(.center)
            .textColor(.white)
            .font(.boldSystemFont(ofSize: 24))
            .backgroundColor(.black)
        }
    }
}
Simulator Screen Shot - iPhone 8 - 2019-10-10 at 22.43.54.png

私以外にもKotolinのapplyをSwiftでもやりたいと思ったことのある人はいるでしょう。
例えば以下のようにUILabelを定義する場面を考えます。

.swift
let label: UILabel = {
   let it = UILabel()
   it.text = "label.." 
   return it
}()

以前までは、以下のようなプロトコルを定義することで

.swift
protocol Applicatable {}

extension Applicatable {
  func apply(_ closure: ((Self) -> ())) -> Self {
        closure(self)
        return self
    }
}

extension NSObject: Applicatable {}

それっぽく実装することができました。

.swift
let label = UILabel().apply { it in
   it.text = "label.."
}

しかし言語の進化により、もっとKotolinのapplyに近づけることができるようになりました。
つい先日DuctTapeというライブラリが公開されたのをきっかけにそれが可能になってたことを知りました。(Swiftのキャッチアップに遅れぎみです)

dynamicMemberLookup

Swift4.2で追加された機能ですが

.swift
@dynamicMemberLookup
struct StringMaker {
    subscript(dynamicMember value: String) -> String {
        return value
    }
}

let maker = StringMaker()
debugPrint(maker.id) // String: id
debugPrint(maker.name) // String: name

Swift5.1からKeyPathを使えるようになったみたいです。

@dynamicMemberLookup attribute requires ‘xxx’ to have a ‘subscript(dynamicMember:)’ method that accepts either ‘ExpressibleByStringLiteral’ or a keypath

これを使って参考ライブラリをパクりつつインターフェースの変更を40行程度実装すると

.swift
      let label = UILabel().apply { $0
            .text("Apply Swift")
            .textAlignment(.center)
            .textColor(.white)
            .backgroundColor(.black)
        }

debugPrint(label.text) // Optional(Apply Swift)

上記のような実装をすることができました。
一応ソースはGistに公開しておきます。

2
1
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
2
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?