Starts in:
3 DAYS
12 HRS
13 MIN
34 SEC
Starts in:
3 D
12 H
13 M
34 S

Modal

ModalComponent is a pre-built component exposed by @abp/ng.theme.shared package to show modals. The component uses the ng-bootstrap's modal service inside to render a modal.

The abp-modal provides some additional benefits:

  • It is flexible. You can pass header, body, footer templates easily by adding the templates to the abp-modal content. It can also be implemented quickly.
  • Provides several inputs be able to customize the modal and several outputs be able to listen to some events.
  • Automatically detects the close button which has a abpClose directive attached to and closes the modal when pressed this button.
  • Automatically detects the abp-button and triggers its loading spinner when the busy input value of the modal component is true.
  • Automatically checks if the form inside the modal has changed, but not saved. It warns the user by displaying a confirmation popup in this case when a user tries to close the modal or refresh/close the tab of the browser.

Note: A modal can also be rendered by using the ng-bootstrap modal. For further information, see Modal doc on the ng-bootstrap documentation.

Getting Started

In order to use the abp-modal in an HTML template, the ThemeSharedModule should be imported into your module like this:

// ...
import { ThemeSharedModule } from '@abp/ng.theme.shared';

@NgModule({
  //...
  imports: [..., ThemeSharedModule],
})
export class MyFeatureModule {}

Usage

You can add the abp-modal to your component very quickly. See an example:

<!-- sample.component.html -->

<button class="btn btn-primary" (click)="isModalOpen = true">Open modal</button>

<abp-modal [(visible)]="isModalOpen">
  <ng-template #abpHeader>
    <h3>Modal Title</h3>
  </ng-template>

  <ng-template #abpBody>
  <p>Modal content</p>
  </ng-template>

  <ng-template #abpFooter>
    <button type="button" class="btn btn-secondary" abpClose>Close</button>
  </ng-template>
</abp-modal>
// sample.component.ts

@Component(/* component metadata */)
export class SampleComponent {
    isModalOpen = false
}

Example modal result

See an example form inside a modal:

<!-- book.component.ts -->

<abp-modal [(visible)]="isModalOpen" [busy]="inProgress">
  <ng-template #abpHeader>
    <h3>Book</h3>
  </ng-template>

  <ng-template #abpBody>
    <form id="book-form" [formGroup]="form" (ngSubmit)="save()">
      <div class="form-group">
        <label for="book-name">Author</label><span> * </span>
        <input type="text" id="author" class="form-control" formControlName="author" autofocus />
      </div>

      <div class="form-group">
        <label for="book-name">Name</label><span> * </span>
        <input type="text" id="book-name" class="form-control" formControlName="name" />
      </div>

      <div class="form-group">
        <label for="book-price">Price</label><span> * </span>
        <input type="number" id="book-price" class="form-control" formControlName="price" />
      </div>

      <div class="form-group">
        <label for="book-type">Type</label><span> * </span>
        <select class="form-control" id="book-type" formControlName="type">
          <option [ngValue]="null">Select a book type</option>
          <option [ngValue]="0">Undefined</option>
          <option [ngValue]="1">Adventure</option>
          <option [ngValue]="2">Biography</option>
          <option [ngValue]="3">Fantastic</option>
          <option [ngValue]="4">Science</option>
        </select>
      </div>

      <div class="form-group">
        <label for="book-publish-date">Publish date</label><span> * </span>
        <input
          id="book-publish-date"
          formControlName="publishDate"
          class="form-control"
          type="date"
        />
      </div>
    </form>
  </ng-template>

  <ng-template #abpFooter>
    <button type="button" class="btn btn-secondary" abpClose>
      Cancel
    </button>

    <button form="book-form" class="btn btn-primary" [disabled]="form.invalid || form.pristine">
      <i class="fa fa-check mr-1"></i>
      Save
    </button>
  </ng-template>
</abp-modal>
// book.component.ts

import { Component } from '@angular/core';
import { FormBuilder, Validators } from '@angular/forms';

@Component(/* component metadata */)
export class BookComponent {
 form = this.fb.group({
    author: [null, [Validators.required]],
    name: [null, [Validators.required]],
    price: [null, [Validators.required, Validators.min(0)]],
    type: [null, [Validators.required]],
    publishDate: [null, [Validators.required]],
  });

  inProgress: boolean;

  isModalOpen: boolean;

  constructor(private fb: FormBuilder, private service: BookService) {}

  save() {
    if (this.form.invalid) return;

    this.inProgress = true;

    this.service.save(this.form.value).subscribe(() => {
      this.inProgress = false;
    });
  }
}

The modal with form looks like this:

Form example result

API

Inputs

visible

@Input() visible: boolean

visible is a boolean input that determines whether the modal is open. It is also can be used two-way binding.

busy

@Input() busy: boolean

busy is a boolean input that determines whether the busy status of the modal is true. When busy is true, the modal cannot be closed and the abp-button loading spinner is triggered.

options

@Input() options: NgbModalOptions

options is an input typed NgbModalOptions. It is configuration for the ng-bootstrap modal.

Examples:

  • animation: This is an NgbModalOption property of type boolean. It controls whether the modal opens and closes with an animation. By default, it is set to true, meaning that the modal will have a smooth transition when it opens and closes. Setting it to false will disable these animations.
import { Component } from '@angular/core';
import { NgbModal } from '@ng-bootstrap/ng-bootstrap';

@Component({
  selector: 'ngbd-modal-options',
  ...})

export class NgbdModalOptions {
  modalService = inject(NgbModal);
  animationModal(content) {
    this.modalService.open(content, { animation: true });
  }
}

       The result of this configuration would be like this:

Modal example result

       On the contrary, if we set it as false:

Modal example result

  • fullscreen: This is an NgbModalOption property of type boolean or string. When set to true, the element will expand to cover the entire screen, hiding all other interface elements. When set to false, the element remains in its regular size and position within the page.
import { Component } from '@angular/core';
import { NgbModal } from '@ng-bootstrap/ng-bootstrap';

@Component({
 selector: 'ngbd-modal-options',
 ...})

export class NgbdModalOptions {
 modalService = inject(NgbModal);
 fullscreenModal(content) {
   this.modalService.open(content, { fullscreen: true });
 }
}

       If fullscreen: true:

Modal example result

suppressUnsavedChangesWarning

@Input() suppressUnsavedChangesWarning: boolean

suppressUnsavedChangesWarning is a boolean input that determines whether the confirmation popup triggering active or not. It can also be set globally as shown below:

//app.module.ts

// app.module.ts

import { SUPPRESS_UNSAVED_CHANGES_WARNING } from '@abp/ng.theme.shared';

// ...

@NgModule({
  // ...
  providers: [{provide: SUPPRESS_UNSAVED_CHANGES_WARNING, useValue: true}]
})
export class AppModule {}

Note: The suppressUnsavedChangesWarning input of abp-modal value overrides the SUPPRESS_UNSAVED_CHANGES_WARNING injection token value.

Outputs

visibleChange

@Output() readonly visibleChange = new EventEmitter<boolean>();

visibleChange is an event emitted when the modal visibility has changed. The event payload is a boolean.

appear

  @Output() readonly appear = new EventEmitter<void>();

appear is an event emitted when the modal has opened.

disappear

  @Output() readonly disappear = new EventEmitter<void>();

disappear is an event emitted when the modal has closed.

Contributors


Last updated: September 19, 2024 Edit this page on GitHub

Was this page helpful?

Please make a selection.

To help us improve, please share your reason for the negative feedback in the field below.

Please enter a note.

Thank you for your valuable feedback!

Please note that although we cannot respond to feedback, our team will use your comments to improve the experience.

In this document
Community Talks

What’s New with .NET 9 & ABP 9?

21 Nov, 17:00
Online
Register Now
Mastering ABP Framework Book
Mastering ABP Framework

This book will help you gain a complete understanding of the framework and modern web application development techniques.

Learn More