import { Meta } from '@storybook/blocks';

<Meta title="Utilities/Portal" />

# Portal

#### Renders an Angular component or template in a different part of the DOM.

## Features

- ✅ Render any Angular component or template outside of your App's main structure.
- ✅ Appends to a custom container element, which can be configured as needed.

## Installation

To use the [Angular CDK Portal](https://material.angular.io/cdk/portal/overview), first install the CDK package:

```bash
npm install @angular/cdk
```

## Basic Usage

### Defining a Portal

First, create the component or template that you want to render in a different location:

```typescript
import { Component } from '@angular/core';

@Component({
  selector: 'component-portal-content',
  standalone: true,
  template: `
    <p>This is portal content!</p>
  `
})
export class PortalContentComponent {}
```

### Using the Portal

In your main component, set up the portal and the outlet:

```typescript
// app.component.ts
import { Component, ViewChild, AfterViewInit, inject, ApplicationRef, Injector, ViewContainerRef } from '@angular/core';
import { CdkPortal, DomPortalOutlet } from '@angular/cdk/portal';
import { PortalContentComponent } from './portal-content.component';

@Component({
  selector: 'app-root',
  standalone: true,
  template: `
    <ng-template cdkPortal>
      <app-portal-content></app-portal-content>
    </ng-template>
    <div #portalOutlet></div>
  `
})
export class AppComponent implements AfterViewInit {
  private readonly appRef = inject(ApplicationRef);
  private readonly injector = inject(Injector);

  @ViewChild(CdkPortal) portal: CdkPortal;
  @ViewChild('portalOutlet', { read: ViewContainerRef }) portalOutlet: ViewContainerRef;

  private host: DomPortalOutlet;

  ngAfterViewInit() {
    this.host = new DomPortalOutlet(this.portalOutlet.element.nativeElement, this.injector, this.appRef);
    this.host.attach(this.portal);
  }
}
```

## Anatomy

The Angular CDK Portal utility consists of a few key elements:

1. **Portal**:
   An Angular directive (`CdkPortal`) that defines the content to be rendered elsewhere.

2. **Portal Outlet**:
   An Angular directive (`CdkPortalOutlet`) or a host (`DomPortalOutlet`) where the portal content will be rendered.
