今回はSwiftUIのListで、行を並べ替えたり削除したりする方法を紹介します。
環境
- Xcode12.5.1
- iOS14.6
- スクショはiPhone12Pro Maxで撮影
初めに
List
の基本的な実装方法は本記事では説明しません。とは言えコードは記載しますし、List
自体は非常に簡単に実装できると思います。
また、List
とForEach
で一覧表示を実装していること、ForEach
では更新可能な配列を使用しておりidを用いて識別されることが前提となります。
今回説明に使用するコードはこちらです。Person
は必ずHashable
に準拠するようにしてください。理由については今度詳しく説明します。
struct Person: Hashable{
var name: String
var age: Int
}
struct ContentView: View {
@State private var people = [Person(name: "John", age: 18),
Person(name: "Bob", age: 20),
Person(name: "Tony", age: 35),
Person(name: "Andy", age: 31)]
@State private var selectedValue: Int? = nil
var body: some View {
VStack {
Text("選択:\(selectedValue ?? 0)")
List {
ForEach(people, id: \.self) { person in
Text("\(person.name) : \(person.age)")
}
}
}
}
}
並べ替え
並べ替えをさせたい場合は、まずはEditButton()
を画面内のどこかに追加しましょう。このボタンを押すことでList
を編集状態に切り替えることができます。
次にForEach
に .onMove(perform:)
というモディファイアをつけます。
struct Person: Hashable{
var name: String
var age: Int
}
struct ContentView: View {
@State private var people = [Person(name: "John", age: 18),
Person(name: "Bob", age: 20),
Person(name: "Tony", age: 35),
Person(name: "Andy", age: 31)]
@State private var selectedValue: Int? = nil
var body: some View {
VStack {
Text("選択:\(selectedValue ?? 0)")
EditButton()
List {
ForEach(people, id: \.self) { person in
Text("\(person.name) : \(person.age)")
}
.onMove(perform: { indices, newOffset in
people.move(fromOffsets: indices, toOffset: newOffset)
})
}
}
}
}
.onMove
の引数のクロージャには配列の並べ替え処理を書きましょう。こうすることで以下のようにList
の並べ替えができるようになります。
削除
削除機能を追加したい場合も、並べ替えと同じようにEditButton()
を追加しましょう。
そして、.onDelete(perform:)
をForEach
に付け加えます。.onDelete(perform:)
の引数のクロージャには配列から値を削除する処理を書きます。
struct Person: Hashable{
var name: String
var age: Int
}
struct ContentView: View {
@State private var people = [Person(name: "John", age: 18),
Person(name: "Bob", age: 20),
Person(name: "Tony", age: 35),
Person(name: "Andy", age: 31)]
@State private var selectedValue: Int? = nil
var body: some View {
VStack {
Text("選択:\(selectedValue ?? 0)")
EditButton()
List {
ForEach(people, id: \.self) { person in
Text("\(person.name) : \(person.age)")
}
.onDelete(perform: { indexSet in
people.remove(atOffsets: indexSet)
})
}
}
}
}
今回は以上です。近いうちに行の選択なども説明しようと思います。
コメント