iOS App Dev Tutorialsを読んで実際にやってみた。その７

## 前回の記事
[iOS App Dev Tutorialsを読んでみた。その６](https://qiita.com/shomiya181210/items/6d6783b87b8dafeb7cd5)
前回の記事を読んだ後に、この記事をご覧ください。
## 今回の範囲
[Creating the edit view](https://developer.apple.com/tutorials/app-dev-training/creating-the-edit-view)　
7回目は、編集ビューを作成して、動作するようにします。
## 内容の要約
### 1.スクラムの詳細の編集ビューを追加する。
- DailyScrum.swiftに、空のスクラムを返すemptyScrumという静的プロパティを追加します。
```DailyScrum.swift
static var emptyScrum: DailyScrum {
    DailyScrum(title: "", attendees: [], lengthInMinutes: 5, theme: .sky)
 }
```
- DetailEditView.swift という名前の新しい SwiftUI View ファイルを新しく作成します。

- 編集中のスクラムを表す scrum という名前の @State プロパティを追加します。新しいプロパティを空のスクラムで初期化します。
```DetailEditView.swift
 @State private var scrum = DailyScrum.emptyScrum
```
- テキストビューをフォームに置き換え、「会議情報」のヘッダーを持つセクションを追加します。
```DetailEditView.swift
Form {
    Section(header: Text("Meeting Info")) {
    }    
}
```
- Sectionの中に、会議タイトルのTextFieldを追加します。
```DetailEditView.swift
 TextField("Title", text: $scrum.title)
```
- DailyScrum.swiftに、スクラムの長さを倍精度で表現したものを追加し、スライダーにバインドするようにします。
```DailyScrum.swift
var lengthInMinutesAsDouble: Double {
}
```
- スクラムミーティングの長さをdouble値で返すゲッターを用意する。
```DailyScrum.swift
get {
    Double(lengthInMinutes)
}
```
- 「lengthInMinutesAsDoubleの値がスライダーで変更された場合、その値を整数に変換し、lengthInMinutesプロパティを更新する」という処理を行います。
```DailyScrum.swift
set {
    lengthInMinutes = Int(newValue)
}
```
- DetailEditView.swiftにHStackと会議の長さを表すSliderを追加し、スライダーのラベルにアクセシビリティ用のTextビューを追加する、という処理を行います。
```DetailEditView.swift
HStack {
    Slider(value: $scrum.lengthInMinutesAsDouble, in: 5...30, step: 1) {
        Text("Length")
    }
}
```
- スペーサーとテキストを追加して、会議の長さを表示します。
```DetailEditView.swift
Spacer()
Text("\(scrum.lengthInMinutes) minutes")
```
### 2.編集ビューに出席者を表示させる。
- 「出席者」ヘッダーを持つ2番目のセクションを追加します。
```DetailEditView.swift
Section(header: Text("Attendees")) {
}
```
- ForEachビューを追加し、Textビューで各出席者を表示します。

```DetailEditView.swift
ForEach(scrum.attendees) { attendee in
    Text(attendee.name)
}
```
- スクラムデータから参加者を削除するためのonDeleteモディファイアを追加する。
```DetailEditView.swift
.onDelete { indices in
        scrum.attendees.remove(atOffsets: indices)
    }
```
- 「newAttendeeName」という名前の@Stateプロパティを追加します。
```DetailEditView.swift
@State private var newAttendeeName = ""
```
- TextFieldを含むHStackを追加し、「newAttendeeName」プロパティにバインディングを渡します。
```DetailEditView.swift
HStack {
    TextField("New Attendee", text: $newAttendeeName)
}
```
- 空のアクションと画像ラベルを持つButton（ボタン）を追加します。
```DetailEditView.swift
Button(action: {}) {
    Image(systemName: "plus.circle.fill")
}
```
- 新しい出席者を作成して、新しい出席者をattendees配列に追加するアニメーションブロックを追加します。
```DetailEditView.swift
Button(action: {
    withAnimation {
        let attendee = DailyScrum.Attendee(name: newAttendeeName)
        scrum.attendees.append(attendee)
    }
}) {
```
- アニメーションブロック内で「newAttendeeName」を空文字列に設定します。
```DetailEditView.swift
newAttendeeName = ""
```
- 「newAttendeeName」 が空の場合、ボタンを無効にします。
```DetailEditView.swift
.disabled(newAttendeeName.isEmpty)
```
### 3.アクセシビリティモディファイアの追加。
- スライダーのアクセシビリティ値を設定します。
```DetailEditView.swift
.accessibilityValue("\(scrum.lengthInMinutes) minutes")
```
- 「VoiceOver」からテキスト表示を非表示にする。
```DetailEditView.swift
.accessibilityHidden(true)
```
- ボタンの画像にアクセシビリティラベルを追加する。
```DetailEditView.swift
.accessibilityLabel("Add attendee")
```
### 4.エディットビューを提示する。
- DetailView.swiftに、「isPresentingEditView」という名前のBoolean型の@Stateプロパティを追加します。
```DetailView.swift
@State private var isPresentingEditView = false
```
- リストでシートモディファイアを追加する。
```DetailView.swift
    .sheet(isPresented: $isPresentingEditView) {
        DetailEditView()
    }
```
- 「isPresentingEditView」をtrue（真または偽）に設定する編集ボタンをツールバーに追加します。
```DetailView.swift
    .toolbar {
        Button("Edit") {
            isPresentingEditView = true
        }
    }
```
- NavigationStackに「DetailEditView」を埋め込む。
```DetailView.swift
NavigationStack {
    DetailEditView()
}
```
- 編集ビューのナビゲーションタイトルを設定します。
```DetailView.swift
navigationTitle(scrum.title)
```
- スクラムの詳細の変更をキャンセルすることをユーザーに示すツールバーボタンを追加します。そしてキャンセルボタンのアクションでDetailEditViewを解除する。
```DetailView.swift
    .toolbar {
        ToolbarItem(placement: .cancellationAction) {
            Button("Cancel") {
                isPresentingEditView = false
            }
        }
    }
```
- 変更を保存していることをユーザーに示すツールバーボタンを追加する。DoneボタンのアクションでDetailEditViewを解除する。
```DetailView.swift
ToolbarItem(placement: .confirmationAction) {
    Button("Done") {
        isPresentingEditView = false
    }
}
```
#### 今回のコードと出力結果
<img width="600" alt="![スクリーンショット 2023-04-24 21.47.17.png]()
" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2918800/a03a1107-8c64-c2fe-4d18-cbde8c445242.png">
<img width="600" alt="![スクリーンショット 2023-04-24 21.47.41.png]()
" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2918800/59e264a9-e41c-0655-ab3c-398490162ec7.png">
### まとめ
今回は編集用のビューを作成してしっかりと動作するようにした。次回は複数のビューやデータの間で値を同期できるようにします。

次回　[iOS App Dev Tutorialsを読んでみた。その６](https://qiita.com/drafts/307b2ccc46a02dab55e6/edit)