▪️

@Outputによる親への通知

に公開

はじめに

Angularでは、子コンポーネントから親コンポーネントへの値の受け渡しに @Output を使う。
この記事では、その基本的な使い方とイベント通知の流れを解説する。

Outputデコレータとは

@Output は、子コンポーネントから親コンポーネントへイベントを通知する仕組み。
EventEmitter を使ってイベントを発火し、親側は $event として値を受け取って処理する。

コンポーネントを扱う際に、他のコンポーネントに何かが起こったことを通知しなければならない場合があります。ボタンがクリックされた、リストに項目が追加/削除された、またはその他の重要な更新が行われたなどです。このようなシナリオでは、コンポーネントは親コンポーネントと通信する必要があります。
Angularは、@Outputデコレーターを使用してこのタイプの動作を可能にします。

https://angular.jp/tutorials/learn-angular/9-output

Outputの実装手順

ディレクトリ構造(親子関係)

src/
└── app/
    ├── app.component.ts        // 親
    ├── app.component.html
    ├── app.module.ts           
    └── child/                  
        ├── child.component.ts  // 子
        └── child.component.html

子コンポーネントの実装

@Output() デコレータを使って addItemEvent を定義する。
この EventEmitter インスタンスを通じて、親に文字列データを送信する。

child.component.ts
import { Component, EventEmitter, Output } from '@angular/core';

@Component({
  selector: 'app-child',
  templateUrl: './child.component.html',
  styleUrls: ['./child.component.css']
})
export class ChildComponent {
  // @Outputデコレータでイベントを定義
  @Output() addItemEvent = new EventEmitter<string>();

  // イベントを発火するメソッド
  addItem() {
    // 子コンポーネント内で emit() を呼び出すことで、親に通知する
    this.addItemEvent.emit('新しいアイテム');
  }
}

テンプレート側ではボタンのクリックを addItem() に紐づける。

child.component.html
<div>
  <h2>子コンポーネント</h2>
  <button (click)="addItem()">アイテムを追加</button>
</div>

親コンポーネントの実装

子コンポーネントがemitするイベントを (addItemEvent) で受け取る。
受け取ったデータは、handleAddItem() で処理される。

app.component.html
<div>
  <h1>親コンポーネント</h1>
  
  <!-- 子コンポーネントのイベントをバインド -->
  <app-child (addItemEvent)="handleAddItem($event)"></app-child>
  
  <div *ngIf="items.length > 0">
    <h3>追加されたアイテム:</h3>
    <ul>
      <li *ngFor="let item of items">{{ item }}</li>
    </ul>
  </div>
</div>

TypeScript側では、受け取った文字列を items 配列に追加し、状態を更新する。

app.component.ts
import { Component } from '@angular/core';

@Component({
  selector: 'app-root',
  templateUrl: './app.component.html',
  styleUrls: ['./app.component.css']
})
export class AppComponent {
  items: string[] = [];

  // 子コンポーネントから送信されたデータを処理するメソッド
  handleAddItem(newItem: string) {
    this.items.push(newItem);
    console.log('アイテムが追加されました:', newItem);
  }
}

処理の流れ

  1. 子コンポーネントで @Output + EventEmitter を定義
  2. イベント発火時に emit() でデータ送信
  3. 親コンポーネントが (イベント名)="メソッド($event)" で受け取る
  4. 親のメソッドで受信データを処理

おわりに

@Output を使えば、親子間のデータ連携を明示的に扱える。

Discussion