TraitとBar周りの英単語の語彙が乏しいのでドキュメント読み直した
本記事はiOSアドベントカレンダーの12日目です。
- スマブラSPについて
アドベンチャーモードの分量と難易度、どっちも調整おかしいんじゃねえのと思いながら週末溶かしてアドベントカレンダーどころではなくなった。
- 現在地
看板が読める気がするいややっぱわからん
雑談はさておいて、本記事では、ドキュメントが英語で書いてあってよく読み取れないので頑張って読み取ります。
新規性なんてなかった。
本記事のネタを書くに至った経緯について
上手に UINavigationBar
に背景画像を表示させたいな!端末のサイズによって適切な背景画像のサイズが異なるから上手に計算したいな!
そういえばsize classなるものがあってregularとcompactの2種類があったな?
Adaptivity and Layout - Visual Design - iOS - Human Interface Guidelines - Apple Developer
Size classes are traits that are automatically assigned to content areas based on their size. The system defines two size classes, regular (denotes expansive space) and compact (denotes constrained space), which describe the height and width of a view.
もしや setBackground
で UIBarMetrics
を指定するときにこの知識が役に立つのでは…?
UIBarMetrics - UIKit | Apple Developer Documentation
Constants to specify metrics to use for appearance.
case default
Specifies default metrics for the device.
case compact
Specifies metrics when using the phone idiom.
なるほど、defaultとcompactの2種類があるんだな!いやdefaultってお前誰だよ。ていうかphone idiomってなんだよ。つーかprompt propertyってなんだよ。英語難しいな!
size classを擁するtraitについて
iOSのインターフェース環境はtrait(特徴)を持ち、このtraitには
- size class (
UIUserInterfaceSizeClass
)- 縦と横それぞれ
- display scale (浮動小数点数)
- 1.0は非Retinaディスプレイ、2.0や3.0はRetinaディスプレイ。
- display gamut (
UIDisplayGamut
)- 色域のこと。iOSは基本的にsRGBを使用する。最近のディスプレイはP3対応。
- user interface idiom (
UIUserInterfaceIdiom
)phone
やpad
といったインターフェースの種類を指す。ちなみに、idiomには慣用句の他に表現方法という意味もあるらしい。
- force touch capability (
UIForceTouchCapability
)- 3D touchが使えるかどうか
- layout direction (
UITraitEnvironmentLayoutDirection
)- レイアウト方向がLTRかRTLか
- user interface style (
UIUserInterfaceStyle
)- darkスタイルにすべきかlightスタイルにすべきか。tvOSやCarPlay限定。
- preferredContentSizeCategory (
UIContentSizeCategory
)- Dynamic Typeでユーザが設定したサイズ???
がある。
これらはclass UITraitCollection
でまとめて表されており、protocol UITraitEnvironment
の
var traitCollection: UITraitCollection { get }
や
func traitCollectionDidChange(_ previousTraitCollection: UITraitCollection?)
から取得することができる。
いろいろなscaleについて
UIScreen
から取れるscaleは3種類存在する。
var traitCollection: UITraitCollection
経由で取れるdisplayScale
nativeScale
scale
このうち役割が違うのが nativeScale
で(多分)、ユーザがDisplay Zoomの設定を変えると nativeScale
の値も変わる(きっとそう)。
公式ドキュメントのどこかに明記されていたら教えてください。
色空間について
Color - Visual Design - iOS - Human Interface Guidelines - Apple Developer
このグラフはXY色度図といい、XYZ表色系における色を2次元グラフ上に表したもの。Zの値はXとYが決まれば定義から求められるのでグラフ上には載っていない。
図中の三角形をカラートライアングルという。Display P3やsRGBなどの色空間が定める3原色をつないだもので、各色空間は三角形の中の色のみを再現できる。要するに、sRGBよりDisplay P3の方が再現可能な色が多い(だから必要な時はP3を使ってね!by Apple)ということが図から読み取れる。
本題: UINavigationBarの背景画像を変更する
次のメソッドで背景画像を設定することができる。
func setBackgroundImage(_ backgroundImage: UIImage?, for barMetrics: UIBarMetrics)
問題は
barMetrics
A bar metrics constant.
これ。
そもそもBarには protocol UIBarPositioning
というprotocolが用意されていて、 UINavigationBar
や UISearchBar
は var barPosition: UIBarPosition
経由でBarの位置を取得することができる。
この protocol UIBarPositioning
が enum UIBarPosition
の他に enum UIBarMetrics
を擁する。metrics = 指標。
なまえ | 種類 | 役割 |
---|---|---|
UIBarPositioning |
protocol | Barの位置の取得方法を提供。 var barPosition をつければOK |
UIBarPosition |
enum | 上とか下とか |
UIBarMetrics |
enum | appearance(= 外観)のために用いる指標 |
UIBarMetrics
は以下4つの要素を持つ。
- default
- Specifies default metrics for the device.
- compact
- Specifies metrics when using the phone idiom.
- defaultPrompt
- Specifies default metrics for the device for bars with the prompt property, such as
UINavigationBar
andUISearchBar
.
- Specifies default metrics for the device for bars with the prompt property, such as
- compactPrompt
- Specifies metrics for bars with the prompt property when using the phone idiom, such as
UINavigationBar
andUISearchBar
.
- Specifies metrics for bars with the prompt property when using the phone idiom, such as
compactとpromptが何を表しているかというと…
試しに
UINavigationBar.appearance().setBackgroundImage(赤色画像, for: .default) UINavigationBar.appearance().setBackgroundImage(青色画像, for: .compact)
などでどちらが使われるか試してみると、
size class for w&h | bar metrics | |
---|---|---|
iPhone 8縦 | compact®ular | regular |
iPhone 8横 | compact&compact | compact |
iPhone 8 Plus縦 | compact®ular | regular |
iPhone 8 Plus横 | regular&compact | regular |
iPhone XS Max縦 | compact®ular | regular |
iPhone XS Max横 | regular&compact | regular |
となる。つまり
size classを雑に参照すれば違うUIBarMetrics
も定まる違う.compact
にphone idiomと書いてあるからiPhoneは全部.compact
になる- Plus、Max、XRのような、Landscape時にregular&compactとなっている端末は常に
.regular
設定が使われる ←これが正解!
である。
promptはこれのことっぽい。(が、prompt stringとセットで使っても反映されない・・)
UINavigationBar - UIKit | Apple Developer Documentation
結論
- 英語難しい
"compactPrompt"
でGoogle検索してもenum要素の1つであることしかわからないことがわかった。使ってる人あんまいないんちゃう?func setBackgroundImage(_: barMetrics:)
はそこまで上手にやってくれないので我々が頑張りましょう。縦時背景画像は.regular
で横時背景画像は.compact
とか設定するのは間違い。
参考文献
- UITraitEnvironment - UIKit | Apple Developer Documentation
- displayScale - UITraitCollection | Apple Developer Documentation
- nativeScale - UIScreen | Apple Developer Documentation
- scale - UIScreen | Apple Developer Documentation
- UIUserInterfaceSizeClass - UIKit | Apple Developer Documentation
- displayScale - UITraitCollection | Apple Developer Documentation
- UIDisplayGamut - UIKit | Apple Developer Documentation
- UIUserInterfaceIdiom - UIKit | Apple Developer Documentation
- UIForceTouchCapability - UIKit | Apple Developer Documentation
- UIUserInterfaceStyle - UIKit | Apple Developer Documentation
- UINavigationBar - UIKit | Apple Developer Documentation
- UIBarMetrics - UIKit | Apple Developer Documentation
- UIBarPositioning - UIKit | Apple Developer Documentation
Color - Visual Design - iOS - Human Interface Guidelines - Apple Developer
- Displays
- Scaling Fonts Automatically | Apple Developer Documentation
Typography - Visual Design - iOS - Human Interface Guidelines - Apple Developer
- XYZ-RGB の変換式とカラートライアングル(JavaScript版)
- XYZ表色系|色の表わし方|DIC Color Design, Inc.
- 色の3原色