Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(modal): modal service wip #2047

Merged
merged 26 commits into from
Jul 18, 2017
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
26 commits
Select commit Hold shift + click to select a range
ccf6cf2
feat(modal): modal service wip
IlyaSurmay Jun 8, 2017
0980e03
feat(modal): wip, add close buttons attribute support, add ability to…
IlyaSurmay Jun 12, 2017
d52e9f0
feat(modal): add config, move creating of loader to constructor, add …
IlyaSurmay Jun 13, 2017
62ae2c4
fix(modal): fix service path
IlyaSurmay Jun 14, 2017
6aeca8e
fix(modal): fix api-docs
IlyaSurmay Jun 14, 2017
0301475
fix(modal): fix scroll on modals created by service, add docs
IlyaSurmay Jun 15, 2017
cf5b8d6
feat(modal): wip, add BsModalService.show output obj
IlyaSurmay Jun 15, 2017
1367f13
refactor(modal): change inner component getter
IlyaSurmay Jun 16, 2017
b093683
feat(modal): add BsModalRef and docs
IlyaSurmay Jun 19, 2017
74ef797
feat(modal): remove data-attributes, return BsModalRef, update docs
IlyaSurmay Jun 20, 2017
f608fae
feat(modal): add docs for BsModalService, BsModalRef, update demo
IlyaSurmay Jun 21, 2017
d78c020
feat(modal): add bs4 support
IlyaSurmay Jun 21, 2017
a7605f8
feat(modal): keep focus inside a modal
IlyaSurmay Jun 23, 2017
91f06a9
chore(modals): small refactoring (#2128)
valorkin Jun 26, 2017
7b153aa
chore(modals): simplify service (#2130)
valorkin Jun 26, 2017
2c5e5f0
chore(modal): view container ref made optional for component loader (…
valorkin Jun 28, 2017
04f3eb2
fix(modal): fix backdrop flickering
IlyaSurmay Jun 28, 2017
84d0788
fix(modal): fix backdrop click on the left/right sides, add class option
IlyaSurmay Jun 28, 2017
d9ed3ca
feat(modals): nested modals wip
IlyaSurmay Jul 4, 2017
d410488
fix(modal): fix multiple hide() call
IlyaSurmay Jul 4, 2017
c24c126
fix(modal): fix multiple backdrop clicks, fix padding
IlyaSurmay Jul 5, 2017
3cacde6
fix(modal): fixed padding
IlyaSurmay Jul 6, 2017
04683d2
fix(modal): fix page flickering
IlyaSurmay Jul 7, 2017
7b004e2
feat(modal): add isAnimated support, add service section to demo
IlyaSurmay Jul 12, 2017
6d7c4ec
Merge branch 'development' into feat-modal-service
IlyaSurmay Jul 14, 2017
16760cb
fix(test): fix popover and tyepahead unit tests
IlyaSurmay Jul 18, 2017
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 4 additions & 1 deletion demo/src/app/components/+modal/demo-modal.module.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,10 +8,12 @@ import { SharedModule } from '../../shared';
import { ModalSectionComponent } from './modal-section.component';
import { DEMO_COMPONENTS } from './demos';
import { routes } from './demo-modal.routes';
import { ModalContentComponent } from './demos/service-component/service-component';

@NgModule({
declarations: [
ModalSectionComponent,
ModalContentComponent,
...DEMO_COMPONENTS
],
imports: [
Expand All @@ -21,7 +23,8 @@ import { routes } from './demo-modal.routes';
SharedModule,
RouterModule.forChild(routes)
],
exports: [ModalSectionComponent]
exports: [ModalSectionComponent],
entryComponents: [ModalContentComponent]
})
export class DemoModalModule {

Expand Down
29 changes: 26 additions & 3 deletions demo/src/app/components/+modal/demos/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,17 +2,24 @@ import { DemoModalSizesComponent } from './sizes/sizes';
import { DemoModalStaticComponent } from './static/static';
import { DemoModalChildComponent } from './child/child';
import { DemoAutoShownModalComponent } from './auto-shown/auto-shown';
import { DemoNestedDropdownsComponent } from '../../+dropdown/demos/nested-dropdowns/nested-dropdowns';
import { DemoModalNestedComponent } from './nested/nested';
import { DemoModalEventsComponent } from './events/events';
import { DemoModalServiceStaticComponent } from './service-template/service-template';
import { DemoModalServiceFromComponent } from './service-component/service-component';
import { DemoModalServiceNestedComponent } from './service-nested/service-nested';
import { DemoModalServiceOptionsComponent } from './service-options/service-options';

export const DEMO_COMPONENTS = [
DemoModalSizesComponent,
DemoModalChildComponent,
DemoModalStaticComponent,
DemoAutoShownModalComponent,
DemoModalEventsComponent,
DemoModalNestedComponent
DemoModalNestedComponent,
DemoModalServiceStaticComponent,
DemoModalServiceFromComponent,
DemoModalServiceNestedComponent,
DemoModalServiceOptionsComponent,
DemoModalEventsComponent
];

export const DEMOS = {
Expand All @@ -39,5 +46,21 @@ export const DEMOS = {
events: {
component: require('!!raw-loader?lang=typescript!./events/events.ts'),
html: require('!!raw-loader?lang=markup!./events/events.html')
},
serviceTemplate: {
component: require('!!raw-loader?lang=typescript!./service-template/service-template.ts'),
html: require('!!raw-loader?lang=markup!./service-template/service-template.html')
},
serviceComponent: {
component: require('!!raw-loader?lang=typescript!./service-component/service-component.ts'),
html: require('!!raw-loader?lang=markup!./service-component/service-component.html')
},
serviceNested: {
component: require('!!raw-loader?lang=typescript!./service-nested/service-nested.ts'),
html: require('!!raw-loader?lang=markup!./service-nested/service-nested.html')
},
serviceOptions: {
component: require('!!raw-loader?lang=typescript!./service-options/service-options.ts'),
html: require('!!raw-loader?lang=markup!./service-options/service-options.html')
}
};
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
<button type="button" class="btn btn-primary" (click)="openModalWithComponent()">Create modal with component</button>
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
import { Component } from '@angular/core';
import { BsModalService } from 'ngx-bootstrap/modal';
import { BsModalRef } from 'ngx-bootstrap/modal/modal-options.class';

@Component({
selector: 'demo-modal-service-component',
templateUrl: './service-component.html'
})
export class DemoModalServiceFromComponent {
constructor(private modalService: BsModalService) {}

public openModalWithComponent() {
this.modalService.show(ModalContentComponent);
}
}

/* This is a component which we pass in modal*/

@Component({
selector: 'modal-content',
template: `
<div class="modal-header">
<h4 class="modal-title pull-left">{{title}}</h4>
<button type="button" class="close pull-right" aria-label="Close" (click)="bsModalRef.hide()">
<span aria-hidden="true">&times;</span>
</button>
</div>
<div class="modal-body">
This is a modal with component inside.
Click <b>&times;</b> to close modal.
</div>
<div class="modal-footer">
<button type="button" class="btn btn-default" (click)="bsModalRef.hide()">Close</button>
</div>
`
})
export class ModalContentComponent {
public title: string = 'Modal with component';
constructor(public bsModalRef: BsModalRef) {}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
<button type="button" class="btn btn-primary" (click)="openModal(template)">Open first modal</button>

<template #template>
<div class="modal-header">
<h4 class="modal-title pull-left">First modal</h4>
<button type="button" class="close pull-right" aria-label="Close" (click)="modalRef.hide()">
<span aria-hidden="true">&times;</span>
</button>
</div>
<div class="modal-body">
This is a first modal
<button type="button" class="btn btn-primary" (click)="openModal2(templateNested)">Open second modal</button>
</div>
</template>

<template #templateNested>
<div class="modal-header">
<h4 class="modal-title pull-left">Second modal</h4>
<button type="button" class="close pull-right" aria-label="Close" (click)="modalRef2.hide()">
<span aria-hidden="true">&times;</span>
</button>
</div>
<div class="modal-body">
This is nested modal.<br>
<button *ngIf="modalRef" type="button" class="btn btn-danger" (click)="closeFirstModal()">Close first modal</button>
</div>
</template>
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
import { Component, TemplateRef } from '@angular/core';
import { BsModalService } from 'ngx-bootstrap/modal';
import { BsModalRef } from 'ngx-bootstrap/modal/modal-options.class';

@Component({
selector: 'demo-modal-service-nested',
templateUrl: './service-nested.html'
})
export class DemoModalServiceNestedComponent {
public modalRef: BsModalRef;
public modalRef2: BsModalRef;
constructor(private modalService: BsModalService) {}

public openModal(template: TemplateRef<any>) {
this.modalRef = this.modalService.show(template, {class: 'modal-sm'});
}
public openModal2(template: TemplateRef<any>) {
this.modalRef2 = this.modalService.show(template, {class: 'second'});
}
public closeFirstModal() {
this.modalRef.hide();
this.modalRef = null;
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
<button type="button" class="btn btn-primary" (click)="openModal(template)">Open modal</button>
<button type="button" class="btn btn-primary" (click)="openModalWithClass(template)">Open modal with custom css class</button>
<br>
<br>
<button type="button" class="btn btn-primary btn-sm" (click)="config.animated = !config.animated">{{config.animated ? 'Disable' : 'Enable'}} animation</button>
<button type="button" class="btn btn-primary btn-sm" (click)="config.keyboard = !config.keyboard">{{config.keyboard ? 'Disable' : 'Enable'}} Esc</button>
<button type="button" class="btn btn-primary btn-sm" (click)="config.backdrop = !config.backdrop">{{config.backdrop ? 'Disable' : 'Enable'}} backdrop</button>
<button type="button" class="btn btn-primary btn-sm" (click)="config.ignoreBackdropClick = !config.ignoreBackdropClick">{{!config.ignoreBackdropClick ? 'Disable' : 'Enable'}} backdrop click</button>

<template #template>
<div class="modal-header">
<h4 class="modal-title pull-left">Modal</h4>
<button type="button" class="close pull-right" aria-label="Close" (click)="modalRef.hide()">
<span aria-hidden="true">&times;</span>
</button>
</div>
<div class="modal-body">
Just a modal with a bunch of words inside, nothing serious.
</div>
</template>
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
import { Component, TemplateRef } from '@angular/core';
import { BsModalService } from 'ngx-bootstrap/modal';
import { BsModalRef } from 'ngx-bootstrap/modal/modal-options.class';

@Component({
selector: 'demo-modal-service-options',
templateUrl: './service-options.html'
})
export class DemoModalServiceOptionsComponent {
public modalRef: BsModalRef;
public config = {
animated: true,
keyboard: true,
backdrop: true,
ignoreBackdropClick: false
};
constructor(private modalService: BsModalService) {}

public openModal(template: TemplateRef<any>) {
this.modalRef = this.modalService.show(template, this.config);
}

public openModalWithClass(template: TemplateRef<any>) {
this.modalRef = this.modalService.show(template, Object.assign({}, this.config, {class: 'gray modal-lg'}));
}

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
<button type="button" class="btn btn-primary" (click)="openModal(template)">Create template modal</button>

<template #template>
<div class="modal-header">
<h4 class="modal-title pull-left">Modal</h4>
<button type="button" class="close pull-right" aria-label="Close" (click)="modalRef.hide()">
<span aria-hidden="true">&times;</span>
</button>
</div>
<div class="modal-body">
This is a modal.
</div>
</template>
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
import { Component, TemplateRef } from '@angular/core';
import { BsModalService } from 'ngx-bootstrap/modal';
import { BsModalRef } from 'ngx-bootstrap/modal/modal-options.class';

@Component({
selector: 'demo-modal-service-static',
templateUrl: './service-template.html'
})
export class DemoModalServiceStaticComponent {
public modalRef: BsModalRef;
constructor(private modalService: BsModalService) {}

public openModal(template: TemplateRef<any>) {
this.modalRef = this.modalService.show(template);
}
}
2 changes: 1 addition & 1 deletion demo/src/app/components/+modal/demos/static/static.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { Component } from '@angular/core';
import {Component} from '@angular/core';

@Component({
selector: 'demo-modal-static',
Expand Down
79 changes: 66 additions & 13 deletions demo/src/app/components/+modal/modal-section.component.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,53 +13,104 @@ let titleDoc = require('html-loader!markdown-loader!./docs/title.md');
<h2>Contents</h2>
<ul>
<li><a routerLink="." fragment="usage">Usage</a></li>
<li><a routerLink="." fragment="examples">Examples</a>
<li><a routerLink="." fragment="service-section">Service</a>
<ul>
<li><a routerLink="." fragment="static">Static modal</a></li>
<li><a routerLink="." fragment="sizes">Optional sizes</a></li>
<li><a routerLink="." fragment="child">Child modal</a></li>
<li><a routerLink="." fragment="nested">Nested modals</a></li>
<li><a routerLink="." fragment="events">Modal events</a></li>
<li><a routerLink="." fragment="auto-shown">Auto shown modal</a></li>
<li><a routerLink="." fragment="service-examples">Examples</a>
<ul>
<li><a routerLink="." fragment="service-template">Template</a></li>
<li><a routerLink="." fragment="service-component">Component</a></li>
<li><a routerLink="." fragment="service-nested">Nested</a></li>
<li><a routerLink="." fragment="service-options">Options</a></li>
</ul>
</li>
</ul>
</li>
<li><a routerLink="." fragment="directive-section">Directive</a>
<ul>
<li><a routerLink="." fragment="examples">Examples</a>
<ul>
<li><a routerLink="." fragment="static">Static modal</a></li>
<li><a routerLink="." fragment="sizes">Optional sizes</a></li>
<li><a routerLink="." fragment="child">Child modal</a></li>
<li><a routerLink="." fragment="nested">Nested modals</a></li>
<li><a routerLink="." fragment="events">Modal events</a></li>
<li><a routerLink="." fragment="auto-shown">Auto shown modal</a></li>
</ul>
</li>
</ul>
</li>
<li><a routerLink="." fragment="api-reference">API Reference</a>
<ul>
<li><a routerLink="." fragment="modal-directive">ModalDirective</a></li>
<li><a routerLink="." fragment="modal-backdrop-component">ModalBackdropComponent</a></li>
<li><a routerLink="." fragment="bs-modal-service">BsModalService</a></li>
<li><a routerLink="." fragment="bs-modal-ref">BsModalRef</a></li>
<li><a routerLink="." fragment="modal-options">ModalOptions</a></li>
</ul>
</li>
</ul>

<h2 routerLink="." fragment="usage" id="usage">Usage</h2>

<p [innerHtml]="titleDoc"></p>
<h2 routerLink="." fragment="service-section" id="service-section">Service</h2>
<p>Open a modal from service</p>
<p>To be able to open modals from service, inject BsModalService to your constructor. <br>
Then, call <code>.show()</code> method of modal service. Pass a TemplateRef or a component as a first argument and config as a second (optionally). <br>
<code>.show()</code> method returns an instance of BsModalRef class with <code>.hide()</code> method and <code>content</code> property where you'll find a component which you've passed to service <br>
</p>
<h2 routerLink="." fragment="service-examples" id="service-examples">Examples</h2>
<h3 routerLink="." fragment="service-template" id="service-template">Template</h3>
<ng-sample-box [ts]="demos.serviceTemplate.component" [html]="demos.serviceTemplate.html">
<demo-modal-service-static></demo-modal-service-static>
</ng-sample-box>

<h3 routerLink="." fragment="service-component" id="service-component">Component</h3>
<p>Creating a modal with component just as easy as it is with template. Just pass your component in <code>.show()</code> method as in example, and don't forget to include your component to <code>entryComponents</code> of your NgModule<br>
If you passed a component to <code>.show()</code> you can get access to opened modal by injecting BsModalRef. See example for more info
</p>
<ng-sample-box [ts]="demos.serviceComponent.component" [html]="demos.serviceComponent.html">
<demo-modal-service-component></demo-modal-service-component>
</ng-sample-box>

<h3 routerLink="." fragment="service-nested" id="service-nested">Nested</h3>
<p>Nested modals are supported</p>
<ng-sample-box [ts]="demos.serviceNested.component" [html]="demos.serviceNested.html">
<demo-modal-service-nested></demo-modal-service-nested>
</ng-sample-box>

<h3 routerLink="." fragment="service-options" id="service-options">Options</h3>
<p>There are some options that you can configure, like animation, backdrop, closing by Esc button, additional css classes. See the demo below to learn how to configure your modal</p>
<ng-sample-box [ts]="demos.serviceOptions.component" [html]="demos.serviceOptions.html">
<demo-modal-service-options></demo-modal-service-options>
</ng-sample-box>

<h2 routerLink="." fragment="directive-section" id="directive-section">Directive</h2>
<p>Also you can use directive instead of service. See the demos below </p>

<h2 routerLink="." fragment="examples" id="examples">Examples</h2>

<h2 routerLink="." fragment="static" id="static">Static modal</h2>
<h3 routerLink="." fragment="static" id="static">Static modal</h3>
<ng-sample-box [ts]="demos.staticModal.component" [html]="demos.staticModal.html">
<demo-modal-static></demo-modal-static>
</ng-sample-box>

<h2 routerLink="." fragment="sizes" id="sizes">Optional sizes</h2>
<h3 routerLink="." fragment="sizes" id="sizes">Optional sizes</h3>
<ng-sample-box [ts]="demos.sizes.component" [html]="demos.sizes.html">
<demo-modal-sizes></demo-modal-sizes>
</ng-sample-box>

<h2 routerLink="." fragment="child" id="child">Child modal</h2>
<h3 routerLink="." fragment="child" id="child">Child modal</h3>
<p>Control modal from parent component</p>
<ng-sample-box [ts]="demos.child.component" [html]="demos.child.html">
<demo-modal-child></demo-modal-child>
</ng-sample-box>

<h2 routerLink="." fragment="nested" id="nested">Nested modals</h2>
<h3 routerLink="." fragment="nested" id="nested">Nested modals</h3>
<p>Open a modal from another modal</p>
<ng-sample-box [ts]="demos.nested.component" [html]="demos.nested.html">
<demo-modal-nested></demo-modal-nested>
</ng-sample-box>

<h2 routerLink="." fragment="events" id="events">Modal events</h2>
<p>
ModalDirective exposes 4 events: OnShow, OnShown, OnHide, OnHidden. See usage example below. <br>
Expand Down Expand Up @@ -88,6 +139,8 @@ let titleDoc = require('html-loader!markdown-loader!./docs/title.md');
<h2 routerLink="." fragment="api-reference" id="api-reference">API Reference</h2>
<ng-api-doc routerLink="." fragment="modal-directive" id="modal-directive" directive="ModalDirective"></ng-api-doc>
<ng-api-doc routerLink="." fragment="modal-backdrop-component" id="modal-backdrop-component" directive="ModalBackdropComponent"></ng-api-doc>
<ng-api-doc-class routerLink="." fragment="bs-modal-service" id="bs-modal-service" type="BsModalService"></ng-api-doc-class>
<ng-api-doc-class routerLink="." fragment="bs-modal-ref" id="bs-modal-ref" type="BsModalRef"></ng-api-doc-class>
<ng-api-doc-config routerLink="." fragment="modal-options" id="modal-options" type="ModalOptions"></ng-api-doc-config>
</demo-section>`
})
Expand Down
Loading