import { Component, ComponentResolver, HostListener, Renderer, ViewChild, ViewContainerRef } from '@angular/core';
import { addSelector } from '../../config/bootstrap';
import { Animation } from '../../animations/animation';
import { isPresent, pascalCaseToDashCase } from '../../util/util';
import { Key } from '../../util/key';
import { NavParams } from '../nav/nav-params';
import { PageTransition } from '../../transitions/page-transition';
import { TransitionOptions } from '../../transitions/transition';
import { ViewController } from '../nav/view-controller';
import { windowDimensions } from '../../util/dom';
/**
* @name Modal
* @description
* A Modal is a content pane that goes over the user's current page.
* Usually it is used for making a choice or editing an item. A modal uses the
* `NavController` to
* {@link /docs/v2/api/components/nav/NavController/#present present}
* itself in the root nav stack. It is added to the stack similar to how
* {@link /docs/v2/api/components/nav/NavController/#push NavController.push}
* works.
*
* When a modal (or any other overlay such as an alert or actionsheet) is
* "presented" to a nav controller, the overlay is added to the app's root nav.
* After the modal has been presented, from within the component instance The
* modal can later be closed or "dismissed" by using the ViewController's
* `dismiss` method. Additionally, you can dismiss any overlay by using `pop`
* on the root nav controller.
*
* Data can be passed to a new modal through `Modal.create()` as the second
* argument. The data can then be accessed from the opened page by injecting
* `NavParams`. Note that the page, which opened as a modal, has no special
* "modal" logic within it, but uses `NavParams` no differently than a
* standard page.
*
* @usage
* ```ts
* import { Modal, NavController, NavParams } from 'ionic-angular';
*
* @Component(...)
* class HomePage {
*
* constructor(nav: NavController) {
* this.nav = nav;
* }
*
* presentProfileModal() {
* let profileModal = Modal.create(Profile, { userId: 8675309 });
* this.nav.present(profileModal);
* }
*
* }
*
* @Component(...)
* class Profile {
*
* constructor(params: NavParams) {
* console.log('UserId', params.get('userId'));
* }
*
* }
* ```
*
* A modal can also emit data, which is useful when it is used to add or edit
* data. For example, a profile page could slide up in a modal, and on submit,
* the submit button could pass the updated profile data, then dismiss the
* modal.
*
* ```ts
* import { Component } from '@angular/core';
* import { Modal, NavController, ViewController } from 'ionic-angular';
*
* @Component(...)
* class HomePage {
*
* constructor(nav: NavController) {
* this.nav = nav;
* }
*
* presentContactModal() {
* let contactModal = Modal.create(ContactUs);
* this.nav.present(contactModal);
* }
*
* presentProfileModal() {
* let profileModal = Modal.create(Profile, { userId: 8675309 });
* profileModal.onDismiss(data => {
* console.log(data);
* });
* this.nav.present(profileModal);
* }
*
* }
*
* @Component(...)
* class Profile {
*
* constructor(viewCtrl: ViewController) {
* this.viewCtrl = viewCtrl;
* }
*
* dismiss() {
* let data = { 'foo': 'bar' };
* this.viewCtrl.dismiss(data);
* }
*
* }
* ```
* @demo /docs/v2/demos/modal/
* @see {@link /docs/v2/components#modals Modal Component Docs}
*/
export class Modal extends ViewController {
constructor(componentType: any, data: any = {}, opts: ModalOptions = {}) {
data.componentType = componentType;
opts.showBackdrop = isPresent(opts.showBackdrop) ? !!opts.showBackdrop : true;
opts.enableBackdropDismiss = isPresent(opts.enableBackdropDismiss) ? !!opts.enableBackdropDismiss : true;
data.opts = opts;
super(ModalCmp, data);
this.isOverlay = true;
this.usePortal = true;
}
/**
* @private
*/
getTransitionName(direction: string) {
let key = (direction === 'back' ? 'modalLeave' : 'modalEnter');
return this._nav && this._nav.config.get(key);
}
/**
* Create a modal with the following options
*
* | Option | Type | Description |
* |-----------------------|------------|------------------------------------------------------------------------------------------------------------------|
* | showBackdrop |`boolean` | Whether to show the backdrop. Default true. |
* | enableBackdropDismiss |`boolean` | Whether the popover should be dismissed by tapping the backdrop. Default true. |
*
*
* @param {object} componentType The Modal view
* @param {object} data Any data to pass to the Modal view
* @param {object} opts Modal options
*/
static create(componentType: any, data: any = {}, opts: ModalOptions = {}) {
return new Modal(componentType, data, opts);
}
// Override the load method and load our child component
loaded(done: Function) {
// grab the instance, and proxy the ngAfterViewInit method
let originalNgAfterViewInit = this.instance.ngAfterViewInit;
this.instance.ngAfterViewInit = () => {
if (originalNgAfterViewInit) {
originalNgAfterViewInit();
}
this.instance.loadComponent(done);
};
}
}
export interface ModalOptions {
showBackdrop?: boolean;
enableBackdropDismiss?: boolean;
}
@Component({
selector: 'ion-modal',
template:
'