Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Features
Speaker Deck
PRO
Sign in
Sign up for free
Search
Search
使い勝手のよいCustomViewをつくる
Search
himaratsu
October 27, 2016
Technology
0
630
使い勝手のよいCustomViewをつくる
@IBDesignable & @IBInspectable が使えて、使い勝手のよいCustomViewの作り方をまとめて紹介しました。
iOS_LT #23 で発表した資料です。
himaratsu
October 27, 2016
Tweet
Share
More Decks by himaratsu
See All by himaratsu
microCMSではじめるAIライティング
himaratsu
0
110
Next.js × microCMSで道の駅サイトを作った話
himaratsu
0
850
PayPayフリマの速度改善
himaratsu
2
350
Goodbye Code Review, Hello Pair Programming
himaratsu
0
180
UICollectionViewでインタラクティブなCellの並び替え
himaratsu
2
9.9k
Other Decks in Technology
See All in Technology
アクセスピークを制するオートスケール再設計: 障害を乗り越えKEDAで実現したリソース管理の最適化
myamashii
1
250
AWS CDK 入門ガイド これだけは知っておきたいヒント集
anank
4
490
ゼロからはじめる採用広報
yutadayo
3
1k
NewSQLや分散データベースを支えるRaftの仕組み - 仕組みを理解して知る得意不得意
hacomono
PRO
3
210
cdk initで生成されるあのファイル達は何なのか/cdk-init-generated-files
tomoki10
1
430
OpenTelemetryセマンティック規約の恩恵とMackerel APMにおける活用例 / SRE NEXT 2025
mackerelio
2
1.3k
マルチプロダクト環境におけるSREの役割 / SRE NEXT 2025 lunch session
sugamasao
1
220
PO初心者が考えた ”POらしさ”
nb_rady
0
220
ビジネス職が分析も担う事業部制組織でのデータ活用の仕組みづくり / Enabling Data Analytics in Business-Led Divisional Organizations
zaimy
1
290
クラウド開発の舞台裏とSRE文化の醸成 / SRE NEXT 2025 Lunch Session
kazeburo
1
410
SREの次のキャリアの道しるべ 〜SREがマネジメントレイヤーに挑戦して、 気づいたこととTips〜
coconala_engineer
1
590
United™️ Airlines®️ Customer®️ USA Contact Numbers: Complete 2025 Support Guide
flyunitedguide
0
720
Featured
See All Featured
The MySQL Ecosystem @ GitHub 2015
samlambert
251
13k
BBQ
matthewcrist
89
9.7k
Documentation Writing (for coders)
carmenintech
72
4.9k
Scaling GitHub
holman
460
140k
Creating an realtime collaboration tool: Agile Flush - .NET Oxford
marcduiker
30
2.1k
Understanding Cognitive Biases in Performance Measurement
bluesmoon
29
1.8k
Large-scale JavaScript Application Architecture
addyosmani
512
110k
Building Flexible Design Systems
yeseniaperezcruz
328
39k
Done Done
chrislema
184
16k
Save Time (by Creating Custom Rails Generators)
garrettdimon
PRO
31
1.3k
How STYLIGHT went responsive
nonsquared
100
5.6k
Practical Tips for Bootstrapping Information Extraction Pipelines
honnibal
PRO
20
1.3k
Transcript
͍উखͷΑ͍ CustomViewΛͭ͘Δ @himara2 / iOS_LT
CustomView? ։ൃ͍ͯ͠ΔͱɺطଘͷUIViewΛ֦ுͨ͠ಠࣗͷΫϥεΛ࡞Γͨ͘ͳΔ
͍উखͷΑ͍CustomView?
- Storyboard / xib Ͱ͑Δ ͍উखͷΑ͍CustomView?
- Storyboard / xib Ͱ͑Δ ͍উखͷΑ͍CustomView? - ιʔείʔυ͔Β͑Δ let customView
= MyCustomView(frame: CGRect(x: 50, y: 100, width: 270, height: 200)) customView.titleLabel.text = "Hello!" view.addSubview(customView) ͜Μͳײ͡ͰॳظԽͯ͑͠Δ
- Storyboard / xib Ͱ͑Δ ͍উखͷΑ͍CustomView? - ιʔείʔυ͔Β͑Δ - @IBDesignable
& @IBInspectable ʹରԠ
- Storyboard / xib Ͱ͑Δ ͍উखͷΑ͍CustomView? - ιʔείʔυ͔Β͑Δ - @IBDesignable
& @IBInspectable ʹରԠ - ৭ʑͳը໘͔Β͍͍͢
- Storyboard / xib Ͱ͑Δ ͍উखͷΑ͍CustomView? - ιʔείʔυ͔Β͑Δ - @IBDesignable
& @IBInspectable ʹରԠ - ৭ʑͳը໘͔Β͍͍͢ → ͻͱඞཁͳͷͰɺखॱΛ·ͱΊ·ͨ͠
Step.1 UIViewΛܧঝͨ͠ΫϥεΛ࡞ͯ͠ɺ xibϑΝΠϧʹίϯϙʔωϯτΛฒΔ
Step.2 xibͷʮFile’s Ownerʯͷ߲ʹɺ ࣗͰͭͬͨ͘ΫϥεΛͯΔ ※ʮViewʯʹͯͳ͍ͷ͕ϙΠϯτ
Step.3 ॳظԽͷίʔυΛॻ͘ override init(frame: CGRect) { super.init(frame: frame) commonInit() }
required init?(coder aDecoder: NSCoder) { super.init(coder: aDecoder) commonInit() } private func commonInit() { let nib = UINib(nibName: "MyCustomView", bundle: nil) let view = nib.instantiate(withOwner: self, options: nil).first as! UIView addSubview(view) view.translatesAutoresizingMaskIntoConstraints = false let bindings = ["view": view] addConstraints(NSLayoutConstraint.constraints(withVisualFormat: "H:|[view]|", options:NSLayoutFormatOptions(rawValue: 0), metrics:nil, views: bindings)) addConstraints(NSLayoutConstraint.constraints(withVisualFormat: "V:|[view]|", options:NSLayoutFormatOptions(rawValue: 0), metrics:nil, views: bindings)) }
Step.3 override init(frame: CGRect) { super.init(frame: frame) commonInit() } required
init?(coder aDecoder: NSCoder) { super.init(coder: aDecoder) commonInit() } private func commonInit() { let nib = UINib(nibName: "MyCustomView", bundle: nil) let view = nib.instantiate(withOwner: self, options: nil).first as! UIView addSubview(view) view.translatesAutoresizingMaskIntoConstraints = false let bindings = ["view": view] addConstraints(NSLayoutConstraint.constraints(withVisualFormat: "H:|[view]|", options:NSLayoutFormatOptions(rawValue: 0), metrics:nil, views: bindings)) addConstraints(NSLayoutConstraint.constraints(withVisualFormat: "V:|[view]|", options:NSLayoutFormatOptions(rawValue: 0), metrics:nil, views: bindings)) } ॳظԽͷίʔυΛॻ͘ ίʔυ͔ΒCustomViewΛ ॳظԽͨ͠ͱ͖ݺΕΔ Storyboard/xib͔ΒCustomViewΛ ॳظԽͨ͠ͱ͖ݺΕΔ viewͷॳظԽॲཧ
Step.4 @IBDesignable, @IBInspectable ͷଐੑΛઃఆ @IBDesignable class MyCustomView: UIView { …
} @IBInspectable var titleText: String = "" { didSet { titleLabel.text = titleText } } @IBInspectable var iconImage: UIImage? { didSet { iconImageView.image = iconImage } }
!
tips ຖճviewͷॳظԽ·ΘΓͷίʔυΛॻ͘ͷπϥΠͷͰɺProtocolΛ༻ҙ͢Δͱྑ͍ protocol XibInstantiatable { func instantiate() } extension XibInstantiatable
where Self: UIView { func instantiate() { let bundle = Bundle(for: type(of: self)) let nib = UINib(nibName: String(describing: type(of: self)), bundle: bundle) guard let view = nib.instantiate(withOwner: self, options: nil).first as? UIView else { return } addSubview(view) view.translatesAutoresizingMaskIntoConstraints = false let bindings = ["view": view] addConstraints(NSLayoutConstraint.constraints(withVisualFormat: “H:|[view]|", … addConstraints(NSLayoutConstraint.constraints(withVisualFormat: “V:|[view]|", … } } override init(frame: CGRect) { super.init(frame: frame) instantiate() } required init?(coder aDecoder: NSCoder) { super.init(coder: aDecoder) instantiate() } CustomViewଆ͔Β ͜Μͳײ͡Ͱ͏
NibDesignable ͱ͍͏ OSS ͱ͋Θͤͯ͏ͱศརʢΒ͍͠ʣ tips - Swift 3Ͱ͏·͘ϏϧυͰ͖ͣɺ·ͩࢼͤͯͳ͍ - ઌ΄ͲͷExtensionΛݞΘΓͯ͘͠ΕΔΑ͏ͳͷ
IUUQTHJUIVCDPNNCPHI/JC%FTJHOBCMF
ຊ͓ݟͤͨ͠αϯϓϧίʔυ ɹ- https://github.com/himaratsu/CustomViewSample ɹ- ࠓͷLTΛ͖͔͚ͬʹSwift 3ରԠ͠·ͨ͠✌ ੲॻ͍ͨϒϩά ɹ- http://himaratsu.hatenablog.com/entry/ios/customview ɹ-
ࠓͷΑΓ͏ͪΐͬͱৄ͘͠ॻ͍ͯ·͢ ͦͷଞ
͓ΘΓ