# 通知設計書 34-NOTIFICATION_RESIZED

## 概要

本ドキュメントは、GodotエンジンのControlクラスにおけるNOTIFICATION_RESIZED通知の設計仕様を記載する。この通知はUIコントロールのサイズが変更された際に発火され、UIレイアウトの再計算や子要素の再配置を可能にする重要なライフサイクルイベントである。

### 本通知の処理概要

NOTIFICATION_RESIZEDは、Controlノードのサイズ（width/height）が変更された際に発行される通知である。この通知により、UI要素は自身のサイズ変更を検出し、内部レイアウトの調整や再描画をトリガーできる。

**業務上の目的・背景**：GUIアプリケーションでは、ウィンドウサイズの変更、コンテナによるレイアウト、アニメーションなど様々な理由でコントロールのサイズが動的に変化する。この通知により、ボタン内のテキスト配置、グラフの再描画、スクロールバーの調整など、サイズ依存の処理を適切に更新できる。

**通知の送信タイミング**：Controlノードのset_size()呼び出し、コンテナによるレイアウト更新、アンカー/オフセットの変更によるサイズ計算結果の変更時に発火される。_size_changed()メソッド内で実際のサイズ変化が検出された場合にのみ通知される。

**通知の受信者**：Controlを継承するすべてのUIノード。Button、Label、TextEdit、Container派生クラス、ItemList、Tree、GraphEditなど、サイズに応じた描画やレイアウトを行うすべてのUI要素が受信者となる。

**通知内容の概要**：通知値は40（NOTIFICATION_RESIZED = 40）として定義され、コントロールのサイズが変更されたことを示す。

**期待されるアクション**：受信ノードはサイズに依存する内部状態を更新する。テキスト折り返しの再計算、子要素の再配置、描画キューへの登録（queue_redraw()）などが典型的な処理。通知後には「resized」シグナルも発行される。

## 通知種別

ゲームエンジン内部通知（Object._notificationで受信）

## 送信仕様

### 基本情報

| 項目 | 内容 |
|-----|------|
| 送信方式 | 同期（サイズ変更時に即座に発行） |
| 優先度 | 高（UIレイアウトの整合性維持に必須） |
| リトライ | なし（一度のみ発行） |

### 送信先決定ロジック

1. ノードがシーンツリー内に存在すること
2. set_size()またはレイアウト計算によりサイズが変更されること
3. 変更前後のサイズが異なること（同一サイズへの設定では発火しない）
4. 上記条件を満たすControlノードに対してnotification()が呼び出される

## 通知テンプレート

### 内部通知の場合

| 項目 | 内容 |
|-----|------|
| 通知定数名 | NOTIFICATION_RESIZED |
| 通知値 | 40 |
| 逆順送信 | false（通常順） |
| 形式 | 整数値（int p_what） |

### 本文テンプレート

```cpp
// _notification()での受信例
void MyControl::_notification(int p_what) {
    switch (p_what) {
        case NOTIFICATION_RESIZED: {
            // サイズが変更された
            Size2 new_size = get_size();
            // レイアウトを再計算
            update_layout();
            // 再描画をリクエスト
            queue_redraw();
        } break;
    }
}

// GDScriptでの例
func _notification(what):
    if what == NOTIFICATION_RESIZED:
        # サイズ変更時の処理
        var new_size = size
        update_layout()
        queue_redraw()
```

### 添付ファイル

該当なし（内部通知のため）

## テンプレート変数

| 変数名 | 説明 | データ取得元 | 必須 |
|--------|------|-------------|-----|
| p_what | 通知種別 | notification()引数 | Yes |

## 送信トリガー・条件

### トリガー一覧

| トリガー種別 | トリガーイベント | 送信条件 | 説明 |
|------------|----------------|---------|------|
| 直接設定 | set_size() / reset_size() | サイズが実際に変化 | コードからの直接サイズ設定 |
| レイアウト更新 | _size_changed()内部処理 | サイズが実際に変化 | コンテナやアンカーによる自動計算 |
| アンカー変更 | set_anchor() / set_offset() | 結果としてサイズが変化 | アンカー/オフセット調整 |
| 親サイズ変更 | 親コンテナのサイズ変更 | 子のサイズが変化 | レイアウト伝播 |

### 送信抑止条件

| 条件 | 説明 |
|-----|------|
| サイズ未変更 | 同一サイズへの設定では発火しない |
| ツリー外のノード | シーンツリーに追加されていないノード |
| 初期化前 | data.initializedがfalseの状態 |

## 処理フロー

### 送信フロー

```mermaid
flowchart TD
    A[サイズ変更トリガー] --> B[_size_changed呼び出し]
    B --> C[新しいサイズ計算]
    C --> D{サイズが変化した?}
    D -->|No| E[処理終了]
    D -->|Yes| F[size_cacheを更新]
    F --> G{is_inside_tree?}
    G -->|No| E
    G -->|Yes| H[_notify_transform呼び出し]
    H --> I[item_rect_changed呼び出し]
    I --> J[notification NOTIFICATION_RESIZED発行]
    J --> K[派生クラス_notification処理]
    K --> L[resizedシグナル発行]
    L --> E
```

## データベース参照・更新仕様

### 参照テーブル一覧

該当なし（ゲームエンジン内部処理のためデータベースは使用しない）

### テーブル別参照項目詳細

該当なし

### 更新テーブル一覧

該当なし

## エラー処理

### エラーケース一覧

| エラー種別 | 発生条件 | 対処方法 |
|----------|---------|---------|
| 無限ループ | 通知ハンドラ内でサイズを変更し再帰的に通知が発生 | サイズ比較による重複防止 |
| レイアウト不整合 | 親子間のサイズ計算順序不正 | コンテナのlayout処理で順序制御 |
| パフォーマンス低下 | 頻繁なサイズ変更による連続通知 | 必要に応じてバッチ処理 |

### リトライ仕様

| 項目 | 内容 |
|-----|------|
| リトライ回数 | 0（リトライなし） |
| リトライ間隔 | 該当なし |
| リトライ対象エラー | 該当なし |

## 配信設定

### レート制限

| 項目 | 内容 |
|-----|------|
| 1分あたり上限 | 制限なし |
| 1日あたり上限 | 制限なし |

### 配信時間帯

エンジン実行中いつでも発火可能。UIレイアウト更新時に即座に発火。

## セキュリティ考慮事項

エンジン内部通知のため、外部からの直接的なセキュリティリスクはない。ただし、悪意のあるスクリプトが意図的に頻繁なサイズ変更を行うことでパフォーマンス問題を引き起こす可能性がある。

## 備考

- 通知後に「resized」シグナルが発行される（control.cpp 3935行目）
- NOTIFICATION_RESIZEDはControl固有の通知で、Node2Dなど他のCanvasItem派生クラスでは使用されない
- コンテナ内のコントロールは親コンテナのレイアウト処理によりサイズが決定される
- get_combined_minimum_size()によるミニマムサイズも考慮される

---

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

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

### 推奨読解順序

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

まず、Controlクラスの構造と通知定数の定義を理解する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | control.h | `scene/gui/control.h` | NOTIFICATION_RESIZED = 40定義（424行目）、size_cacheメンバ変数（218行目） |

**読解のコツ**: 値40はControl固有の通知定数。Data構造体内のsize_cacheがサイズ比較に使用される。

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

サイズ変更通知のトリガーメカニズムを理解する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | control.cpp | `scene/gui/control.cpp` | _size_changed()メソッド（1803-1815行目付近） |

**主要処理フロー**:
1. **1804-1805行目**: is_inside_tree()とサイズ変更チェック
2. **1806-1808行目**: _notify_transform()呼び出し
3. **1810-1811行目**: item_rect_changed()呼び出し
4. **1812行目**: notification(NOTIFICATION_RESIZED)発行

#### Step 3: 通知後の処理を理解する

_notification()でのNOTIFICATION_RESIZED処理を確認する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | control.cpp | `scene/gui/control.cpp` | _notification() NOTIFICATION_RESIZED処理（3934-3936行目） |

**主要処理フロー**:
- **3935行目**: emit_signal(SceneStringName(resized))でシグナル発行

#### Step 4: 派生クラスでの処理例を理解する

具体的なUI要素での処理パターンを確認する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 4-1 | label.cpp | `scene/gui/label.cpp` | NOTIFICATION_RESIZED処理（テキスト折り返し） |
| 4-2 | text_edit.cpp | `scene/gui/text_edit.cpp` | NOTIFICATION_RESIZED処理（エディタレイアウト） |
| 4-3 | item_list.cpp | `scene/gui/item_list.cpp` | NOTIFICATION_RESIZED処理（アイテム再配置） |

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

```
Control::set_size() / コンテナレイアウト
    │
    └─ Control::_size_changed()
           │
           ├─ サイズ変化チェック
           │      │
           │      └─ size_cache比較
           │
           ├─ _notify_transform()
           │
           ├─ item_rect_changed()
           │
           └─ notification(NOTIFICATION_RESIZED)
                  │
                  └─ Control::_notification(NOTIFICATION_RESIZED)
                         │
                         └─ emit_signal("resized")
                                │
                                └─ 接続されたコールバック実行
```

### データフロー図

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

set_size() ───▶ _size_changed() ───▶ notification(40)
               │                          │
               ├─ size_cache更新          ├─▶ 派生クラス処理
               │                          │
               └─ 変化チェック            └─▶ "resized"シグナル
                                                │
                                                └─▶ 接続コールバック
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| control.h | `scene/gui/control.h` | ヘッダ | Controlクラス定義、NOTIFICATION定数 |
| control.cpp | `scene/gui/control.cpp` | ソース | _size_changed()、_notification()実装 |
| container.cpp | `scene/gui/container.cpp` | ソース | コンテナでのレイアウト処理 |
| label.cpp | `scene/gui/label.cpp` | ソース | ラベルでの通知処理例 |
| button.cpp | `scene/gui/button.cpp` | ソース | ボタンでの通知処理例 |
| text_edit.cpp | `scene/gui/text_edit.cpp` | ソース | テキストエディタでの通知処理例 |
| item_list.cpp | `scene/gui/item_list.cpp` | ソース | アイテムリストでの通知処理例 |
| tree.cpp | `scene/gui/tree.cpp` | ソース | ツリーでの通知処理例 |
| graph_edit.cpp | `scene/gui/graph_edit.cpp` | ソース | グラフエディタでの通知処理例 |
| Control.xml | `doc/classes/Control.xml` | ドキュメント | 公式APIドキュメント |
