# 画面設計書 30-EditAction（アクション編集）

## 概要

本ドキュメントは、Windows Terminal のアクション編集画面（EditAction）の設計を記述する。個別のアクション（コマンド）の名前、ショートカットアクション種別、引数パラメータ、キーバインドを編集する画面である。

### 本画面の処理概要

**業務上の目的・背景**：個々のアクション（コマンド）を詳細に編集するための画面である。アクションの表示名、紐付けるショートカットアクション（splitPane、newTab、closeTab 等）の選択、アクション固有の引数パラメータの設定、キーバインド（KeyChord）の追加・編集・削除を行える。引数の型に応じたテンプレート（数値入力、テキスト入力、Enum選択、ブール値、カラー選択、ファイル/フォルダパス選択等）が動的に適用される。

**画面へのアクセス方法**：Actions（アクション一覧）画面からアクションをクリックするか、新規追加ボタンを押すことでアクセスする。

**主要な操作・処理内容**：
1. アクション名の編集（TextBox）
2. ショートカットアクション種別の選択（ComboBox）
3. アクション引数の編集（型に応じた動的テンプレート）
4. キーバインドの追加（Add Key Chord ボタン）
5. キーバインドの編集（KeyChordListener + Accept/Cancel ボタン）
6. キーバインドの削除（確認フライアウト付き）
7. アクション全体の削除（確認フライアウト付き、ユーザー定義アクションのみ）

**画面遷移**：
- 遷移元：Actions（アクション一覧）
- 遷移先：Actions（アクション一覧）- 戻る操作（BreadcrumbBar経由）

**権限による表示制御**：IsUserAction プロパティにより、ユーザー定義アクションの場合のみ削除ボタンが有効化される。ビルトインアクションの削除ボタンは無効化（IsEnabled=false）される。

## 関連機能

| 機能No | 機能名 | 関連種別 | 関連する操作・処理 |
|--------|--------|----------|------------------|
| 82 | 設定の読み込み・保存 | 主機能 | 個別アクションの名称・キーバインド・パラメータ編集 |
| 84 | 設定UI | 主機能 | アクション編集のUI表示 |

## 画面種別

編集（詳細）

## URL/ルーティング

UWP/WinUI アプリケーションのためURL/ルーティングは適用されない。MainPage の contentFrame 内に Frame.Navigate で表示される。ナビゲーションパラメータとして NavigateToCommandArgs（CommandViewModel + WindowRoot）が渡される。

## 入出力項目

| 項目名 | 入出力 | データ型 | 説明 |
|--------|--------|----------|------|
| Name | 入出力 | String | アクション名 |
| DisplayName | 入力（表示） | String | アクション表示名（PlaceholderText として使用） |
| ProposedShortcutActionName | 入出力 | Object | 選択中のショートカットアクション名 |
| AvailableShortcutActions | 入力（表示） | IObservableVector<String> | 選択可能なショートカットアクション一覧 |
| ActionArgsVM | 入力（表示） | ActionArgsViewModel | アクション引数のViewModel（HasArgs, ArgValues） |
| KeyChordList | 入出力 | IObservableVector<KeyChordViewModel> | キーバインド一覧 |
| IsUserAction | 入力（表示制御） | Boolean | ユーザー定義アクションか |

## 表示項目

| 表示領域 | 項目名 | コントロール種別 | 説明 |
|----------|--------|-----------------|------|
| 名前 | Actions_Name | TextBlock + TextBox | アクション名ラベルとテキストボックス（Width=300） |
| アクション | Actions_ShortcutAction | TextBlock + ComboBox | ショートカットアクション選択 |
| 引数 | Actions_Arguments | TextBlock + ItemsControl | 引数ラベルと動的テンプレート（HasArgs=true時のみ表示） |
| キーバインド | Actions_Keybindings | TextBlock + ListView（KeyChordTemplate） | キーバインド一覧（ヘッダーに追加ボタン） |
| キーバインド（編集中） | KeyChordListener | カスタムコントロール | キー入力リスナー |
| キーバインド（編集中） | Accept/Cancel ボタン | Button（32x32px） | 編集の確定/キャンセル |
| キーバインド | 削除ボタン | Button（DeleteSmallButtonStyle） + 確認Flyout | キーバインド削除 |
| 削除 | Actions_DeleteButton2 | Button（DeleteButtonStyle） + 確認Flyout | アクション削除（IsUserAction時のみ有効） |

## イベント仕様

### 1-OnNavigatedTo

Actions からナビゲートされた時に発火する。ナビゲーションパラメータの NavigateToCommandArgs から CommandViewModel と WindowRoot を取得する。PropagateWindowRootRequested イベントを購読し、ArgWrapper に WindowRoot を伝播する。FocusContainer イベントを購読し、KeyChordViewModel のコンテナにフォーカスを設定する。レイアウト更新後に CommandNameTextBox にプログラム的フォーカスを設定する（LayoutUpdated 使用、1回のみ）。

### 2-アクション名編集

CommandNameTextBox の Text は ViewModel.Name に TwoWay バインドされている。PlaceholderText には ViewModel.DisplayName が設定され、名前が空の場合にデフォルト表示名が表示される。

### 3-ショートカットアクション選択

ComboBox で AvailableShortcutActions から選択する。選択が変更されると ProposedShortcutActionName が更新され、ActionArgsVM.ArgValues も対応する引数セットに更新される。

### 4-引数編集

ArgsTemplateSelector により引数の型に応じた適切なテンプレートが選択される。対応テンプレート:
- Int32Template, UInt32Template, Int32OptionalTemplate, UInt32OptionalTemplate: 数値入力（NumberBox）
- FloatTemplate, SplitSizeTemplate: 浮動小数点入力（NumberBox）
- StringTemplate: テキスト入力（TextBox）
- BoolTemplate: ブール値（ToggleSwitch）
- BoolOptionalTemplate: オプショナルブール値（三状態 CheckBox）
- EnumTemplate, ColorSchemeTemplate: 列挙値選択（ComboBox）
- FlagTemplate: フラグ選択（CheckBox リスト）
- FilePickerTemplate, FolderPickerTemplate: パス入力 + ファイル/フォルダ参照ボタン
- TerminalCoreColorOptionalTemplate, WindowsUIColorOptionalTemplate: 色選択（NullableColorPicker）

### 5-キーバインド追加

ListView.Header 内の追加ボタンクリックで ViewModel.AddKeybinding_Click が呼ばれ、新しい KeyChordViewModel が KeyChordList に追加される。

### 6-キーバインド編集（KeyChordTemplate）

各 KeyChordViewModel は通常モードと編集モードを持つ。通常モードではキーバインドテキスト表示ボタン、編集モードでは KeyChordListener + Accept/Cancel ボタンが表示される。ToggleEditMode で切替、AcceptChanges で確定、CancelChanges でキャンセル。AcceptChangesFlyout は重複キーバインド検出時に表示される。

### 7-キーバインド削除

各キーバインドの削除ボタンで確認フライアウトが表示され、確認後に DeleteKeyChord が呼ばれる。

### 8-アクション削除

アクション削除ボタンで確認フライアウトが表示され、確認後に ViewModel.Delete_Click が呼ばれる。IsUserAction=false の場合はボタンが無効化される。

## データベース更新仕様

### 操作別データベース影響一覧

| 操作（イベント） | 対象テーブル | 操作種別 | 概要 |
|----------------|-------------|---------|------|
| Name変更 | メモリ上のモデル | UPDATE | アクション名を更新 |
| ショートカットアクション変更 | メモリ上のモデル | UPDATE | アクション種別と引数を更新 |
| 引数変更 | メモリ上のモデル | UPDATE | アクション引数を更新 |
| キーバインド追加/編集/削除 | メモリ上のモデル | INSERT/UPDATE/DELETE | キーバインドを操作 |
| Delete_Click | メモリ上のモデル | DELETE | アクション全体を削除 |

### テーブル別更新項目詳細

全操作はメモリ上のモデル変更のみ。MainPage の SaveButton 経由で settings.json に永続化される。

## メッセージ仕様

| 種別 | メッセージID | 表示条件 | 内容 |
|------|-------------|----------|------|
| 確認 | Actions_DeleteConfirmationMessage | キーバインド削除時（Flyout内） | キーバインド削除の確認 |
| 確認 | Actions_CommandDeleteConfirmationMessage | アクション削除時（Flyout内） | アクション削除の確認 |

## 例外処理

- キーバインド重複検出: AcceptChanges 時に重複キーバインドが検出された場合、AcceptChangesFlyout が表示される
- ビルトインアクション保護: IsUserAction=false の場合、削除ボタンが無効化される

## 備考

- ArgumentNameWidth は 148px 固定で、引数名と入力コントロールのレイアウトが統一されている。
- KeyChordTemplate 内の編集モードは IsInEditMode プロパティで制御され、ToggleEditMode で切替可能。
- ArgsTemplateSelector は16種類の引数テンプレートを管理し、引数の TypeHint に基づいて適切なテンプレートを選択する。
- FocusContainer イベントにより、キーバインド操作後に適切なコンテナにフォーカスが戻る。
- Dark/Light/HighContrast テーマ対応。KeyChordBorderStyle は Button 型で定義されており、PointerOver 時にアクセントカラーの背景が表示される。

---

## コードリーディングガイド

本画面を理解するために参照すべきファイルと、推奨する読み解き順序を以下に示す。

### 推奨読解順序

#### Step 1: データ構造を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | ActionsViewModel.idl | `src/cascadia/TerminalSettingsEditor/ActionsViewModel.idl` | CommandViewModel（Name, DisplayName, AvailableShortcutActions, ProposedShortcutActionName, ActionArgsVM, KeyChordList, IsUserAction）を確認 |
| 1-2 | ActionsViewModel.idl | `src/cascadia/TerminalSettingsEditor/ActionsViewModel.idl` | ArgWrapper（Name, Type, TypeHint, Value, EnumValue, EnumList, FlagList）と各 Unbox/BindBack メソッドを確認 |
| 1-3 | ActionsViewModel.idl | `src/cascadia/TerminalSettingsEditor/ActionsViewModel.idl` | KeyChordViewModel（KeyChordText, ProposedKeys, IsInEditMode, ToggleEditMode, AcceptChanges, CancelChanges, DeleteKeyChord）を確認 |
| 1-4 | ActionsViewModel.idl | `src/cascadia/TerminalSettingsEditor/ActionsViewModel.idl` | NavigateToCommandArgs（Command, WindowRoot）を確認 |

**読解のコツ**: ArgWrapper は非常に多くの Unbox/BindBack メソッドを持つが、これらは x:Bind の TwoWay バインディングで型変換を行うためのヘルパーである。

#### Step 2: エントリーポイントを理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | EditAction.cpp | `src/cascadia/TerminalSettingsEditor/EditAction.cpp` | OnNavigatedTo（行19-52）で NavigateToCommandArgs からの ViewModel 取得、PropagateWindowRootRequested/FocusContainer イベント購読、LayoutUpdated でのフォーカス設定を確認 |

**主要処理フロー**:
1. **行21-22**: NavigateToCommandArgs から CommandViewModel と WindowRoot を取得
2. **行23-30**: PropagateWindowRootRequested イベント購読（ArgWrapper に WindowRoot 伝播）
3. **行32-45**: FocusContainer イベント購読（KeyChordViewModel コンテナへのフォーカス）
4. **行46-51**: LayoutUpdated で CommandNameTextBox にフォーカス

#### Step 3: XAML レイアウトを理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | EditAction.xaml | `src/cascadia/TerminalSettingsEditor/EditAction.xaml` | 5行 x 2列のGrid構造（Name, ShortcutAction, Arguments, Keybindings, Delete）、16種類の引数テンプレート、KeyChordTemplate（通常/編集モード切替）を理解する |

### プログラム呼び出し階層図

```
Actions.CmdListItemClicked / AddNewCommand
    |
    +-- MainPage._Navigate -> EditAction (NavigateToCommandArgs)
            |
            +-- EditAction::OnNavigatedTo
            |       +-- CommandViewModel 取得
            |       +-- PropagateWindowRootRequested 購読
            |       +-- FocusContainer 購読
            |       +-- LayoutUpdated (CommandNameTextBox フォーカス)
            |
            +-- ショートカットアクション変更
            |       +-- ProposedShortcutActionName 更新
            |       +-- ActionArgsVM.ArgValues 更新
            |       +-- ArgsTemplateSelector で動的テンプレート選択
            |
            +-- キーバインド操作
            |       +-- AddKeybinding_Click -> 新規 KeyChordViewModel 追加
            |       +-- ToggleEditMode -> 編集モード切替
            |       +-- AcceptChanges -> AttemptAddOrModifyKeyChord
            |       +-- CancelChanges -> 編集モード解除
            |       +-- DeleteKeyChord -> キーバインド削除
            |
            +-- Delete_Click
                    +-- アクション削除 -> Actions 一覧に戻る
```

### データフロー図

```
[入力]                          [処理]                          [出力]

NavigateToCommandArgs --------> EditAction Page          -----> Name TextBox
  +-- CommandViewModel           |                               +-- ShortcutAction ComboBox
  +-- WindowRoot                 +-- x:Bind TwoWay               +-- 引数テンプレート（動的）
                                 |                               +-- KeyChord ListView
                                 +-- ArgsTemplateSelector        +-- Delete ボタン
                                 |       +-- 型判定 -> テンプレート選択
                                 |
                                 +-- KeyChordListener
                                         +-- キー入力キャプチャ
                                         +-- AcceptChanges / CancelChanges
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| EditAction.xaml | `src/cascadia/TerminalSettingsEditor/EditAction.xaml` | テンプレート | UI レイアウト定義（16種類の引数テンプレート含む） |
| EditAction.cpp | `src/cascadia/TerminalSettingsEditor/EditAction.cpp` | ソース | ページ実装 |
| ActionsViewModel.idl | `src/cascadia/TerminalSettingsEditor/ActionsViewModel.idl` | IDL | CommandViewModel, ArgWrapper, KeyChordViewModel, ActionArgsViewModel 等の定義 |
| ActionsViewModel.h | `src/cascadia/TerminalSettingsEditor/ActionsViewModel.h` | ソース | ViewModel クラス定義 |
| ActionsViewModel.cpp | `src/cascadia/TerminalSettingsEditor/ActionsViewModel.cpp` | ソース | ViewModel 実装 |
| KeyChordListener.h | `src/cascadia/TerminalSettingsEditor/KeyChordListener.h` | ソース | キー入力リスナーコントロール |
| NullableColorPicker.h | `src/cascadia/TerminalSettingsEditor/NullableColorPicker.h` | ソース | Nullable カラーピッカーコントロール |
| CommonResources.xaml | `src/cascadia/TerminalSettingsEditor/CommonResources.xaml` | リソース | 共通スタイル定義 |
