はじめに
SwiftUI の List
で UITableView
でできていた表示はどうやるんだろう?ということで色々試してみました。(昔書いたこちらの UITableView
の記事を参考にしてます。)
Cell Style | AccessoryType | Color Cell | Selected Color |
---|---|---|---|
List Style | Inset | Color Section |
---|---|---|
Cell Style
UITableViewCell
には下記の Style
がありました。
- default (Basic)
- value1 (Right Detail)
- value2 (Left Detail)
- subtitle (Subtitle)
List
ではとくにセルに指定のクラスやプロトコルがないのでこれらを再現しようとすると自作する必要がありそうです。単純に Text
や Image
を HStack
, VStack
並べれば再現できそうです。
こんな感じ。
Cell AccessoryType
UITableViewCell
には下記の AccessoryType
がありました。
- none
- disclosureIndicator
- detailDisclosureButton
- checkmark
- detailButton
こちらも List
の場合は自作する必要がありそうです。下記の system image を使えばできそうです。
- chevron.right
- checkmark
- info.circle
こんな感じ。
Image
の foregroundColor
で自由に色を設定できます。
Cell 背景色
listRowBackground
を使うことでセルの背景色を設定できます。
1 |
Text("Row: 0").listRowBackground(Color(.systemRed)) |
こんな感じ。
Cell 選択時の背景色
そもそも List
には single selection がなさそう(チェックマーク表示のやつならできる)なのでちょっと工夫する必要がありそうです。
ボタンで選択を行い、選択時に listRowBackground
を変更するようにしてみました。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 |
@State private var selection: Int? private let rows = Array(0...6) private let colors: [UIColor] = [ .systemRed, .systemOrange, .systemYellow, .systemGreen, .systemTeal, .systemBlue, .systemPurple ] List { ForEach(rows, id: \.self) { index in let color = colors[index] Button { selection = index } label: { Text("Row: \(index)") .foregroundColor(selection == index ? .white : .black) }.listRowBackground(selection == index ? Color(color) : Color(.white)) } } |
こんな感じ。
ハイライト時グレーになってしまいますがこれ以上はちょっとわからない。。。
Separator
Separator を非表示にしたり色を変えたりインセット変えたりといったことは現状では難しそうです。
こちらの方法を試してみましたが iOS14 では効かなそうでした。
【SwiftUI】ListのSeparatorを無理やり消したい時の解決法
iOS15 からは下記があるので iOS15 からならできそうです。
ListStyle
List
には下記の ListStyle
が用意されています。
- DefaultListStyle
- BorderedListStyle
iOS15 以上 - CarouselListStyle
watchOS 用 - EllipticalListStyle
watchOS 用 - GroupedListStyle
UITableViewStyleGrouped 相当? - InsetListStyle
- InsetGroupedListStyle
UITableViewStyleInsetGrouped 相当? - PlainListStyle
UITableViewStylePlain 相当? - SidebarListStyle
セクションタップで開閉できる
Section
で header
, footer
を設定するとそれぞれこんな感じです。
1 2 3 4 5 6 7 8 9 |
List { Section(header: Text("header"), footer: Text("footer")) { ForEach(rows, id: \.self) { row in Text("Row: \(row)") } } } .listStyle(DefaultListStyle()) |
どのスタイルでもヘッダーは大文字になるようです。フッターは GroupedListStyle と InsetGroupedListStyle 以外はセルと同じ表示になるようです。
InsetListStyle てなんなんだろう?
Section Color
こちらを参考にセクションヘッダーに色をつけてみました。
SwiftUIのListのSectionの色を変える
こんな感じです。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 |
struct ColorSectionsView: View { private let rows = Array(0...6) private let colors: [UIColor] = [ .systemRed, .systemOrange, .systemYellow, .systemGreen, .systemTeal, .systemBlue, .systemPurple ] var body: some View { List { ForEach(rows, id: \.self) { Section(header: ColorSectionView(title: "Section Header: \($0)", color: Color(colors[$0]))) { Text("Row: 0") } } } } } struct ColorSectionView: View { let title: String let color: Color var body: some View { Text(title) .padding() .frame(width: UIScreen.main.bounds.width, height: 28, alignment: .leading) .background(color) .foregroundColor(.white) } } |
Insets指定
listRowInsets
を使うことによりセルの位置を指定できます。
こんな感じです。
1 |
Text("Row:0").listRowInsets(.init(top: 0, leading: 0, bottom: 0, trailing: 0)) |
おわりに
これで UITableView
でできていた表示はだいたいできるようになりました!UITableView.appearance().backgroundColor
で背景色を設定できるのでつまずいたらとりあえず appearance
を試してみるのもいいかも?
tableHeaderView
, tableFooterView
相当のやつはなくなったのかな?
コメント
[…] SwiftUIのListサンプル集(見た目編)の操作編です。 […]
[…] SwiftUIのListサンプル集(見た目編) […]