Skip to content

Commit

Permalink
feat(modal): add inset modal feature
Browse files Browse the repository at this point in the history
* feat(inset-modal): add dynamic component loading functionality for inset modal

* style(modal): moved border-radius to a variable, added an additional data binding activity in moved border-radius to a variable, added an additional data binding activity in an e2e test

* refactor(modal): refactor sass and remove some unnecessary stuff

* refactor(modal): migrate to Angular RC import syntax

Closes #5423
  • Loading branch information
danbucholtz authored and adamdbradley committed May 18, 2016
1 parent ece1eba commit a658524
Show file tree
Hide file tree
Showing 6 changed files with 153 additions and 30 deletions.
12 changes: 10 additions & 2 deletions ionic/components/modal/modal.ios.scss
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,16 @@
// --------------------------------------------------

$modal-ios-background-color: $background-ios-color !default;
$modal-ios-border-radius: 5px !default;


ion-page.modal {
.modal ion-page {
background-color: $modal-ios-background-color;
}

.modal-wrapper {
@media only screen and (min-width: 768px) and (min-height: 600px) {
overflow: hidden;

border-radius: $modal-ios-border-radius;
}
}
2 changes: 1 addition & 1 deletion ionic/components/modal/modal.md.scss
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,6 @@
$modal-md-background-color: $background-md-color !default;


ion-page.modal {
.modal ion-page {
background-color: $modal-md-background-color;
}
55 changes: 41 additions & 14 deletions ionic/components/modal/modal.scss
Original file line number Diff line number Diff line change
Expand Up @@ -3,27 +3,54 @@
// Modals
// --------------------------------------------------

ion-page.modal {
z-index: $z-index-overlay;
$modal-inset-min-width: 768px !default;
$modal-inset-min-height-small: 600px !default;
$modal-inset-min-height-large: 768px !default;
$modal-inset-width: 600px !default;
$modal-inset-height-small: 500px !default;
$modal-inset-height-large: 600px !default;

// hidden by default to prevent flickers, the animation will show it
transform: translate3d(0, 100%, 0);
.modal {
position: absolute;
top: 0;
left: 0;

@media only screen and (min-width: 768px) and (min-height: 600px){
display: block;

width: 100%;
height: 100%;

.backdrop {
@media not all and (min-width: $modal-inset-min-width) and (min-height: $modal-inset-min-height-small) {
display: none;
}
}
}

.modal-wrapper {
z-index: 10;

height: 100%;

@media only screen and (min-width: $modal-inset-min-width) and (min-height: $modal-inset-min-height-small) {
position: absolute;
top: calc(50% - 250px);
left: calc(50% - 300px);
top: calc(50% - (#{$modal-inset-height-small}/2));
left: calc(50% - (#{$modal-inset-width}/2));

width: 600px;
height: 500px;
width: $modal-inset-width;
height: $modal-inset-height-small;
}

@media only screen and (min-width: 768px) and (min-height: 768px){
@media only screen and (min-width: $modal-inset-min-width) and (min-height: $modal-inset-min-height-large) {
position: absolute;
top: calc(50% - 300px);
left: calc(50% - 300px);
top: calc(50% - (#{$modal-inset-height-large}/2));
left: calc(50% - (#{$modal-inset-width}/2));

width: 600px;
height: 600px;
width: $modal-inset-width;
height: $modal-inset-height-large;
}
}

.show-page ion-page {
display: flex;
}
77 changes: 68 additions & 9 deletions ionic/components/modal/modal.ts
Original file line number Diff line number Diff line change
@@ -1,3 +1,6 @@
import {Component, DynamicComponentLoader, ViewChild, ViewContainerRef} from '@angular/core';

import {NavParams} from '../nav/nav-params';
import {ViewController} from '../nav/view-controller';
import {Animation} from '../../animations/animation';
import {Transition, TransitionOptions} from '../../transitions/transition';
Expand Down Expand Up @@ -103,8 +106,9 @@ import {Transition, TransitionOptions} from '../../transitions/transition';
*/
export class Modal extends ViewController {

constructor(componentType, data = {}) {
super(componentType, data);
constructor(componentType, data: any = {}) {
data.componentToPresent = componentType;
super(ModalComponent, data);
this.viewType = 'modal';
this.isOverlay = true;
}
Expand All @@ -127,19 +131,50 @@ export class Modal extends ViewController {

}

@Component({
selector: 'ion-modal',
template: `
<div class="backdrop"></div>
<div class="modal-wrapper">
<div #wrapper></div>
</div>
`
})
class ModalComponent {

@ViewChild('wrapper', {read: ViewContainerRef}) wrapper: ViewContainerRef;

constructor(private _loader: DynamicComponentLoader, private _navParams: NavParams, private _viewCtrl: ViewController) {
}

ngAfterViewInit() {
let component = this._navParams.data.componentToPresent;
this._loader.loadNextToLocation(component, this.wrapper).then(componentInstance => {
this._viewCtrl.setInstance(componentInstance.instance);
// TODO - validate what life cycle events aren't call and possibly call them here if needed
});
}
}

/**
* Animations for modals
*/
class ModalSlideIn extends Transition {
constructor(enteringView: ViewController, leavingView: ViewController, opts: TransitionOptions) {
super(opts);

let ele = enteringView.pageRef().nativeElement;
let backdrop = new Animation(ele.querySelector('.backdrop'));
backdrop.fromTo('opacity', 0.01, 0.4);
let wrapper = new Animation(ele.querySelector('.modal-wrapper'));
wrapper.fromTo('translateY', '100%', '0%');
this
.element(enteringView.pageRef())
.easing('cubic-bezier(0.36,0.66,0.04,1)')
.duration(400)
.fromTo('translateY', '100%', '0%')
.before.addClass('show-page');
.before.addClass('show-page')
.add(backdrop)
.add(wrapper);

if (enteringView.hasNavbar()) {
// entering page has a navbar
Expand All @@ -155,11 +190,19 @@ Transition.register('modal-slide-in', ModalSlideIn);
class ModalSlideOut extends Transition {
constructor(enteringView: ViewController, leavingView: ViewController, opts: TransitionOptions) {
super(opts);

let ele = leavingView.pageRef().nativeElement;
let backdrop = new Animation(ele.querySelector('.backdrop'));
backdrop.fromTo('opacity', 0.4, 0.0);
let wrapper = new Animation(ele.querySelector('.modal-wrapper'));
wrapper.fromTo('translateY', '0%', '100%');

this
.element(leavingView.pageRef())
.easing('ease-out')
.duration(250)
.fromTo('translateY', '0%', '100%');
.add(backdrop)
.add(wrapper);
}
}
Transition.register('modal-slide-out', ModalSlideOut);
Expand All @@ -168,13 +211,21 @@ Transition.register('modal-slide-out', ModalSlideOut);
class ModalMDSlideIn extends Transition {
constructor(enteringView: ViewController, leavingView: ViewController, opts: TransitionOptions) {
super(opts);

let ele = enteringView.pageRef().nativeElement;
let backdrop = new Animation(ele.querySelector('.backdrop'));
backdrop.fromTo('opacity', 0.01, 0.4);
let wrapper = new Animation(ele.querySelector('.modal-wrapper'));
wrapper.fromTo('translateY', '40px', '0px');

this
.element(enteringView.pageRef())
.easing('cubic-bezier(0.36,0.66,0.04,1)')
.duration(280)
.fromTo('translateY', '40px', '0px')
.fadeIn()
.before.addClass('show-page');
.before.addClass('show-page')
.add(backdrop)
.add(wrapper);

if (enteringView.hasNavbar()) {
// entering page has a navbar
Expand All @@ -190,12 +241,20 @@ Transition.register('modal-md-slide-in', ModalMDSlideIn);
class ModalMDSlideOut extends Transition {
constructor(enteringView: ViewController, leavingView: ViewController, opts: TransitionOptions) {
super(opts);

let ele = leavingView.pageRef().nativeElement;
let backdrop = new Animation(ele.querySelector('.backdrop'));
backdrop.fromTo('opacity', 0.4, 0.0);
let wrapper = new Animation(ele.querySelector('.modal-wrapper'));
wrapper.fromTo('translateY', '0px', '40px');

this
.element(leavingView.pageRef())
.duration(200)
.easing('cubic-bezier(0.47,0,0.745,0.715)')
.fromTo('translateY', '0px', '40px')
.fadeOut();
.fadeOut()
.add(wrapper)
.add(backdrop);
}
}
Transition.register('modal-md-slide-out', ModalMDSlideOut);
2 changes: 1 addition & 1 deletion ionic/components/modal/modal.wp.scss
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,6 @@
$modal-wp-background-color: $background-wp-color !default;


ion-page.modal {
.modal ion-page {
background-color: $modal-wp-background-color;
}
35 changes: 32 additions & 3 deletions ionic/components/modal/test/basic/index.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
import {App, Page, Config, Platform} from '../../../../../ionic';
import {Modal, ActionSheet, NavController, NavParams, Transition, TransitionOptions, ViewController} from '../../../../../ionic';;

import {Modal, ActionSheet, NavController, NavParams, Transition, TransitionOptions, ViewController} from '../../../../../ionic';

@Page({
templateUrl: 'main.html'
Expand Down Expand Up @@ -105,6 +104,22 @@ class ModalPassData {
submit() {
this.viewCtrl.dismiss(this.data);
}

onPageWillEnter(){
console.log("ModalPassData onPagewillEnter fired");
}

onPageDidEnter(){
console.log("ModalPassData onPageDidEnter fired");
}

onPageWillLeave(){
console.log("ModalPassData onPageWillLeave fired");
}

onPageDidLeave(){
console.log("ModalPassData onPageDidLeave fired");
}
}


Expand Down Expand Up @@ -242,11 +257,25 @@ class ContactUs {
</p>
<f></f><f></f><f></f><f></f><f></f><f></f><f></f><f></f><f></f><f></f>
<f></f><f></f><f></f><f></f><f></f><f></f><f></f><f></f><f></f><f></f>
<ion-list>
<ion-item *ngFor="#item of items">
Item Number: {{item.value}}
</ion-item>
</ion-list>
</ion-content>
`
})
class ModalFirstPage {
constructor(private nav: NavController) {}

private items:any[];
constructor(private nav: NavController) {
this.items = [];
for ( let i = 0; i < 50; i++ ){
this.items.push({
value: (i + 1)
});
}
}

push() {
let page = ModalSecondPage;
Expand Down

0 comments on commit a658524

Please sign in to comment.