Merge branch 'master' of github.com:driftyco/ionic2

This commit is contained in:
jbavari
2015-10-09 08:12:50 -06:00
35 changed files with 271 additions and 188 deletions

View File

@@ -1,10 +1,10 @@
<ion-nav [root]="root"></ion-nav>
<style>
.md .nav .navbar-container {
.md .navbar-container {
background-color: #2FD9BB !important;
}
.md .nav .navbar-title {
.md .navbar-title {
color: #FDFEFE;
}
#tabs tab-bar:before {

View File

@@ -1,4 +1,4 @@
import {Directive, ElementRef, Renderer} from 'angular2/angular2';
import {Directive, ElementRef, Renderer, Attribute} from 'angular2/angular2';
import {IonicConfig} from '../../config/config';
@@ -14,18 +14,13 @@ export class Button {
constructor(
config: IonicConfig,
elementRef: ElementRef,
renderer: Renderer
renderer: Renderer,
@Attribute('type') type: string
) {
let element = elementRef.nativeElement;
if (config.get('hoverCSS') === false) {
element.classList.add('disable-hover');
}
// TODO this isn't working in the popup
if (element.hasAttribute('type')) {
let type = element.getAttribute("type");
renderer.setElementAttribute(elementRef, type, "");
renderer.setElementClass(elementRef, 'disable-hover', true);
}
if (element.hasAttribute('ion-item')) {
@@ -33,6 +28,10 @@ export class Button {
return;
}
if (type) {
renderer.setElementAttribute(elementRef, type, '');
}
// figure out if and where the icon lives in the button
let childNodes = element.childNodes;
let childNode;

View File

@@ -10,6 +10,11 @@
<button block>button[block]</button>
</p>
<p>
<a button block href="#"><icon help-circle></icon> a[button][block] icon</a>
<button block><icon help-circle></icon> button[block] icon</button>
</p>
<p>
<a button block outline secondary href="#">a[button][block][outline][secondary]</a>
<button block outline secondary>button[block][outline][secondary]</button>

View File

@@ -1,4 +1,4 @@
import {Component, View, Directive, Optional, NgControl} from 'angular2/angular2';
import {Component, View, Directive, Optional, NgControl, ElementRef, Renderer} from 'angular2/angular2';
import {Ion} from '../ion';
import {IonicForm} from '../form/form';
@@ -24,7 +24,6 @@ import {IonicForm} from '../form/form';
'id'
],
host: {
'class': 'item',
'role': 'checkbox',
'tappable': 'true',
'[attr.tab-index]': 'tabIndex',
@@ -47,8 +46,11 @@ export class Checkbox {
constructor(
form: IonicForm,
@Optional() ngControl: NgControl
@Optional() ngControl: NgControl,
elementRef: ElementRef,
renderer: Renderer
) {
renderer.setElementClass(elementRef, 'item', true);
this.form = form;
form.register(this);

View File

@@ -66,27 +66,33 @@ select[readonly] {
// Focus Utils
// -------------------------------
focus-holder input {
focus-ctrl {
position: fixed;
top: 1px;
width: 9px;
left: -9999px;
z-index: 9999;
input,
button {
position: fixed;
top: 1px;
width: 9px;
left: -9999px;
z-index: 9999;
}
}
/*focus-holder input[tabindex="999"] {
/*focus-ctrl input[tabindex="999"] {
left: 0px;
}
focus-holder input[tabindex="1001"] {
focus-ctrl input[tabindex="1001"] {
left: 20px;
}
focus-holder input[tabindex="1002"] {
focus-ctrl input[tabindex="1002"] {
left: auto;
right: 10px;
}
focus-holder input:focus {
focus-ctrl input:focus {
background: red;
}*/

View File

@@ -28,9 +28,7 @@ export class IonicForm {
this._focused = null;
zone.runOutsideAngular(() => {
if (this._config.get('keyboardScrollAssist')) {
this.initHolders(document);
}
this.initHolders(document, this._config.get('keyboardScrollAssist'));
if (this._config.get('keyboardInputListener') !== false) {
this.initKeyInput(document);
@@ -78,55 +76,72 @@ export class IonicForm {
document.addEventListener('keydown', keyDown);
}
initHolders(document) {
initHolders(document, scrollAssist) {
// raw DOM fun
this._holder = document.createElement('focus-holder');
this._ctrl = document.createElement('focus-ctrl');
this._ctrl.setAttribute('aria-hidden', true);
this._prev = document.createElement('input');
this._prev.tabIndex = NO_FOCUS_TAB_INDEX;
this._holder.appendChild(this._prev);
if (scrollAssist) {
this._prev = document.createElement('input');
this._prev.tabIndex = NO_FOCUS_TAB_INDEX;
this._ctrl.appendChild(this._prev);
this._next = document.createElement('input');
this._next.tabIndex = NO_FOCUS_TAB_INDEX;
this._holder.appendChild(this._next);
this._next = document.createElement('input');
this._next.tabIndex = NO_FOCUS_TAB_INDEX;
this._ctrl.appendChild(this._next);
this._temp = document.createElement('input');
this._temp.tabIndex = NO_FOCUS_TAB_INDEX;
this._holder.appendChild(this._temp);
this._temp = document.createElement('input');
this._temp.tabIndex = NO_FOCUS_TAB_INDEX;
this._ctrl.appendChild(this._temp);
}
document.body.appendChild(this._holder);
this._blur = document.createElement('button');
this._blur.tabIndex = NO_FOCUS_TAB_INDEX;
this._ctrl.appendChild(this._blur);
document.body.appendChild(this._ctrl);
function preventDefault(ev) {
ev.preventDefault();
ev.stopPropagation();
}
this._prev.addEventListener('keydown', preventDefault);
this._next.addEventListener('keydown', preventDefault);
this._temp.addEventListener('keydown', preventDefault);
if (scrollAssist) {
this._prev.addEventListener('keydown', preventDefault);
this._next.addEventListener('keydown', preventDefault);
this._temp.addEventListener('keydown', preventDefault);
this._prev.addEventListener('focus', () => {
this.focusPrevious();
});
this._prev.addEventListener('focus', () => {
this.focusPrevious();
});
this._next.addEventListener('focus', () => {
this.focusNext();
});
this._next.addEventListener('focus', () => {
this.focusNext();
});
let self = this;
let resetTimer;
function queueReset() {
clearTimeout(resetTimer);
let self = this;
let resetTimer;
function queueReset() {
clearTimeout(resetTimer);
resetTimer = setTimeout(function() {
self._zone.run(() => {
self.resetInputs();
});
}, 100);
resetTimer = setTimeout(function() {
self._zone.run(() => {
self.resetInputs();
});
}, 100);
}
document.addEventListener('focusin', queueReset);
document.addEventListener('focusout', queueReset);
}
document.addEventListener('focusin', queueReset);
document.addEventListener('focusout', queueReset);
}
focusOut() {
console.debug('focusOut')
this._blur.tabIndex = NORMAL_FOCUS_TAB_INDEX;
this._blur.focus();
this._blur.tabIndex = NO_FOCUS_TAB_INDEX;
}
setFocusHolder(type) {
@@ -216,8 +231,7 @@ export class IonicForm {
if (index > -1 && (index + inc) < this._inputs.length) {
let siblingInput = this._inputs[index + inc];
if (siblingInput) {
siblingInput.initFocus();
return;
return siblingInput.initFocus();
}
}
this._focused.initFocus();
@@ -232,4 +246,3 @@ const PREV_TAB_INDEX = 999;
const ACTIVE_FOCUS_TAB_INDEX = 1000;
const NEXT_TAB_INDEX = 1001;
const TEMP_TAB_INDEX = 2000;

View File

@@ -3,9 +3,6 @@ import {Directive, ElementRef, Attribute, Renderer} from 'angular2/angular2';
import {IonicConfig} from '../../config/config';
/**
* TODO
*/
@Directive({
selector: 'icon',
inputs: [
@@ -15,17 +12,11 @@ import {IonicConfig} from '../../config/config';
'isActive'
],
host: {
'[attr.aria-label]': 'label',
'role': 'img'
}
})
export class Icon {
/**
* TODO
* @param {ElementRef} elementRef TODO
* @param {IonicConfig} config TODO
* @param {Renderer} renderer TODO
*/
constructor(
private elementRef: ElementRef,
config: IonicConfig,
@@ -37,9 +28,6 @@ export class Icon {
this.mode = config.get('iconMode');
}
/**
* TODO
*/
onInit() {
let ele = this.eleRef.nativeElement;
@@ -101,7 +89,8 @@ export class Icon {
this._name = this.name;
this.renderer.setElementClass(this.elementRef, this.name, true);
this.label = this.name.replace('ion-', '').replace('ios-', '').replace('md-', '').replace('-', ' ');
this.renderer.setElementAttribute(this.elementRef, 'aria-label',
this.name.replace('ion-', '').replace('ios-', '').replace('md-', '').replace('-', ' '));
}
}

View File

@@ -38,7 +38,7 @@ export class ItemGroupTitle {
* TODO
* @param {ElementRef} elementRef TODO
*/
constructor(elementRef: ElementRef, config: IonicConfig, @Host() content: Content) {
constructor(elementRef: ElementRef, config: IonicConfig, @Optional() @Host() content: Content) {
this.isSticky = true;
this.content = content;
this.ele = elementRef.nativeElement;
@@ -46,6 +46,7 @@ export class ItemGroupTitle {
}
onInit() {
if(!this.content) { return; }
this.scrollContent = this.content.elementRef.nativeElement.children[0];

View File

@@ -1,4 +1,4 @@
import {Component, Directive, View, ElementRef, NgIf, Host, Optional} from 'angular2/angular2';
import {Component, Directive, View, ElementRef, NgIf, Host, Optional, Renderer} from 'angular2/angular2';
import {Gesture} from 'ionic/gestures/gesture';
import {DragGesture} from 'ionic/gestures/drag-gesture';
@@ -30,10 +30,7 @@ import {CSS, raf} from 'ionic/util/dom';
*/
@Component({
selector: 'ion-item-sliding,[ion-item-sliding]',
host: {
'class': 'item'
},
properties: [
inputs: [
'sliding'
]
})
@@ -53,7 +50,9 @@ export class ItemSliding {
* TODO
* @param {ElementRef} elementRef A reference to the component's DOM element.
*/
constructor(elementRef: ElementRef, @Optional() @Host() list: List) {
constructor(elementRef: ElementRef, renderer: Renderer, @Optional() @Host() list: List) {
renderer.setElementClass(elementRef, 'item', true);
this._isOpen = false;
this._isSlideActive = false;
this._isTransitioning = false;

View File

@@ -149,7 +149,7 @@ $item-md-sliding-transition: transform 250ms ease-in-out !default;
}
icon[item-left] + ion-item-content,
icon[item-left] + .text-input {
icon[item-left] + [text-input] {
margin-left: $item-md-padding-left + ($item-md-padding-left / 2);
}

View File

@@ -1,4 +1,4 @@
import {Directive, ElementRef} from 'angular2/angular2';
import {Directive, ElementRef, Renderer} from 'angular2/angular2';
import {Ion} from '../ion';
import {IonicConfig} from '../../config/config';
@@ -22,10 +22,7 @@ import * as util from 'ionic/util';
'items',
'virtual',
'content'
],
host: {
'class': 'list'
}
]
})
export class List extends Ion {
/**
@@ -33,8 +30,9 @@ export class List extends Ion {
* @param {ElementRef} elementRef TODO
* @param {IonicConfig} config TODO
*/
constructor(elementRef: ElementRef, config: IonicConfig) {
constructor(elementRef: ElementRef, config: IonicConfig, renderer: Renderer) {
super(elementRef, config);
renderer.setElementClass(elementRef, 'list', true);
this.ele = elementRef.nativeElement;
}
/**

View File

@@ -5,6 +5,6 @@
$navbar-ios-height: 4.4rem !default;
.nav .navbar-container {
.navbar-container {
min-height: $navbar-ios-height;
}

View File

@@ -5,23 +5,19 @@
$navbar-md-height: 5.6rem !default;
.nav {
.navbar-container {
min-height: $navbar-md-height;
}
.back-button {
margin: 0 0 0 12px;
box-shadow: none;
}
.back-button-icon {
margin: 0;
min-width: 44px;
font-size: 2.4rem;
font-weight: normal;
text-align: left;
}
.navbar-container {
min-height: $navbar-md-height;
}
.toolbar .back-button {
margin: 0 0 0 12px;
box-shadow: none;
}
.toolbar .back-button-icon {
margin: 0;
min-width: 44px;
font-size: 2.4rem;
font-weight: normal;
text-align: left;
}

View File

@@ -1,4 +1,4 @@
import {Component, Directive, View, Optional, ElementRef, TemplateRef, forwardRef, Inject} from 'angular2/angular2';
import {Component, Directive, View, Optional, ElementRef, Renderer, TemplateRef, forwardRef, Inject} from 'angular2/angular2';
import {Ion} from '../ion';
import {Icon} from '../icon/icon';
@@ -50,10 +50,7 @@ class BackButtonText extends Ion {
@Component({
selector: 'ion-navbar',
host: {
'class': 'toolbar'
}
selector: 'ion-navbar'
})
@View({
template:
@@ -77,9 +74,11 @@ export class Navbar extends ToolbarBase {
app: IonicApp,
@Optional() viewCtrl: ViewController,
elementRef: ElementRef,
config: IonicConfig
config: IonicConfig,
renderer: Renderer
) {
super(elementRef, config);
renderer.setElementClass(elementRef, 'toolbar', true);
this.app = app;
viewCtrl && viewCtrl.navbarView(this);

View File

@@ -1,4 +1,4 @@
import {ComponentRef, Compiler, ElementRef, Injector, bind, NgZone, DynamicComponentLoader, AppViewManager} from 'angular2/angular2';
import {Compiler, ElementRef, Injector, bind, NgZone, DynamicComponentLoader, AppViewManager} from 'angular2/angular2';
import {Ion} from '../ion';
import {makeComponent} from '../../config/decorators';
@@ -188,7 +188,7 @@ export class NavController extends Ion {
let enteringView = new ViewController(this, componentType, params);
// add the view to the stack
this.add(enteringView);
this._add(enteringView);
if (this.router) {
// notify router of the state change
@@ -253,12 +253,13 @@ export class NavController extends Ion {
}
/**
* @private
* Pop to a specific view in the history stack
*
* @param view {Component} to pop to
* @param view {ViewController} to pop to
* @param opts {object} pop options
*/
popTo(view, opts = {}) {
_popTo(view, opts = {}) {
// Get the target index of the view to pop to
let viewIndex = this._views.indexOf(view);
@@ -304,7 +305,7 @@ export class NavController extends Ion {
* @param opts extra animation options
*/
popToRoot(opts = {}) {
this.popTo(this._views[0]);
this._popTo(this.first());
}
/**
@@ -331,6 +332,27 @@ export class NavController extends Ion {
this._incrementId(viewCtrl);
this._views.splice(index, 0, viewCtrl);
return Promise.resolve();
}
/**
* Removes a view from the nav stack at the specified index.
* @param {TODO} index TODO
* @returns {Promise} TODO
*/
remove(index) {
if (index < 0 || index >= this._views.length) {
return Promise.reject("Index out of range");
}
let viewToRemove = this._views[index];
if (this.isActive(viewToRemove)){
return this.pop();
} else {
this._remove(index);
viewToRemove.destroy();
return Promise.resolve();
}
}
/**
@@ -383,7 +405,7 @@ export class NavController extends Ion {
viewCtrl.shouldCache = false;
// add the item to the stack
this.add(viewCtrl);
this._add(viewCtrl);
}
}
}
@@ -520,7 +542,14 @@ export class NavController extends Ion {
viewContainer.remove(index);
}
};
return new ComponentRef(newLocation, component, type, null, dispose);
// TODO: make-shift ComponentRef_, this is pretty much going to
// break in future versions of ng2, keep an eye on it
return {
location: newLocation,
instance: component,
dispose: dispose
};
}
/**
@@ -749,7 +778,7 @@ export class NavController extends Ion {
});
destroys.forEach(view => {
this.remove(view);
this._remove(view);
view.destroy();
});
@@ -873,11 +902,12 @@ export class NavController extends Ion {
}
/**
* @private
* TODO
* @param {TODO} view TODO
* @returns {TODO} TODO
*/
add(view) {
_add(view) {
this._incrementId(view);
this._views.push(view);
}
@@ -887,11 +917,12 @@ export class NavController extends Ion {
}
/**
* @private
* TODO
* @param {TODO} viewOrIndex TODO
* @returns {TODO} TODO
*/
remove(viewOrIndex) {
_remove(viewOrIndex) {
util.array.remove(this._views, viewOrIndex);
}

View File

@@ -405,13 +405,10 @@ class ContentAnchor {
* @private
*/
@Component({
selector: 'ion-pane',
host: {
'class': 'nav'
}
selector: 'ion-pane'
})
@View({
template: '' +
template:
'<section class="navbar-container">' +
'<template navbar-anchor></template>' +
'</section>' +
@@ -437,9 +434,7 @@ class Pane {
showNavbar(hasNavbar) {
this.navbar = hasNavbar;
if (!hasNavbar) {
this.renderer.setElementAttribute(this.elementRef, 'no-navbar', '');
}
this.renderer.setElementAttribute(this.elementRef, 'no-navbar', hasNavbar ? null : '' );
}
}

View File

@@ -104,6 +104,7 @@ class SecondPage {
<p>
<button id="from3To2" (click)="pop()">Pop (Go back to 2nd)</button>
<button id="insert" (click)="insert()">Insert first page into history before this</button>
<button id="remove" (click)="removeSecond()">Remove second page in history</button>
</p>
<div class="yellow"><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></div>
</ion-content>
@@ -124,6 +125,10 @@ class ThirdPage {
this.nav.insert(FirstPage, 2);
}
removeSecond() {
this.nav.remove(1);
}
}

View File

@@ -46,7 +46,7 @@ export function run() {
});
destroys.forEach(view => {
nav.remove(view);
nav._remove(view);
view.destroy();
});
cb();
@@ -75,7 +75,7 @@ export function run() {
let activeView = new ViewController();
activeView.state = 1; // ACTIVE_STATE
nav.add(activeView);
nav._add(activeView);
var active = nav.getActive();
expect(active).toBe(activeView);
@@ -83,7 +83,7 @@ export function run() {
let secondActiveView = new ViewController();
secondActiveView.state = 1; // ACTIVE_STATE
nav.add(secondActiveView);
nav._add(secondActiveView);
active = nav.getActive();
expect(active).toBe(activeView);
@@ -122,11 +122,11 @@ export function run() {
expect(FirstPage).toBeDefined();
expect(nav._views.length).toBe(0);
spyOn(nav, 'add').and.callThrough();
spyOn(nav, '_add').and.callThrough();
nav.transition = mockTransitionFn;
nav.push(FirstPage, {}, {}).then(() => {
expect(nav.add).toHaveBeenCalled();
expect(nav._add).toHaveBeenCalled();
expect(nav._views.length).toBe(1);
done();
});
@@ -207,5 +207,39 @@ export function run() {
});
});
describe("remove", () => {
it('should remove the view at the specified index', () => {
let vc1 = new ViewController(),
vc2 = new ViewController(null, FirstPage),
vc3 = new ViewController(null, SecondPage);
nav._views = [vc1, vc2, vc3];
expect(nav._views.length).toBe(3);
expect(nav._views[1].componentType).toBe(FirstPage);
nav.remove(1);
expect(nav._views.length).toBe(2);
expect(nav._views[1].componentType).toBe(SecondPage);
});
it('should pop if index is of active view', () => {
let vc1 = new ViewController(),
vc2 = new ViewController(null, FirstPage),
vc3 = new ViewController(null, SecondPage);
vc3.state = 1; //ACTIVE_STATE
nav._views = [vc1, vc2, vc3];
spyOn(nav, 'pop').and.callThrough();
nav.remove(1);
expect(nav.pop).not.toHaveBeenCalled();
nav.remove(1);
expect(nav.pop).toHaveBeenCalled();
});
});
});
}

View File

@@ -1,4 +1,4 @@
import {Component, Directive, ElementRef, Host, Optional, NgControl, Query, QueryList, View} from 'angular2/angular2';
import {Component, Directive, ElementRef, Renderer, Host, Optional, NgControl, Query, QueryList, View} from 'angular2/angular2';
import {IonicConfig} from '../../config/config';
import {Ion} from '../ion';
@@ -45,7 +45,6 @@ import {ListHeader} from '../list/list';
@Directive({
selector: 'ion-radio-group',
host: {
'class': 'list',
'role': 'radiogroup',
'[attr.aria-activedescendant]': 'activeId',
'[attr.aria-describedby]': 'describedById'
@@ -64,10 +63,13 @@ export class RadioGroup extends Ion {
constructor(
elementRef: ElementRef,
config: IonicConfig,
renderer: Renderer,
@Optional() ngControl: NgControl,
@Query(ListHeader) private headerQuery: QueryList<ListHeader>
) {
super(elementRef, config);
renderer.setElementClass(elementRef, 'list', true);
this.id = ++radioGroupIds;
this.radioIds = -1;
this.onChange = (_) => {};
@@ -170,7 +172,6 @@ export class RadioGroup extends Ion {
'id'
],
host: {
'class': 'item',
'role': 'radio',
'tappable': 'true',
'[attr.id]': 'id',
@@ -200,9 +201,12 @@ export class RadioButton extends Ion {
constructor(
@Host() @Optional() group: RadioGroup,
elementRef: ElementRef,
config: IonicConfig
config: IonicConfig,
renderer: Renderer
) {
super(elementRef, config)
super(elementRef, config);
renderer.setElementClass(elementRef, 'item', true);
this.group = group;
this.tabIndex = 0;
}

View File

@@ -23,7 +23,7 @@ $search-bar-ios-input-close-icon-svg: "<svg xmlns='http://www.w3.org/2000/sv
$search-bar-ios-input-close-icon-size: 17px !default;
.search-bar {
ion-search-bar {
padding: $search-bar-ios-padding;
background: $search-bar-ios-background-color;
border-bottom: 1px solid $search-bar-ios-border-color;
@@ -95,6 +95,6 @@ $search-bar-ios-input-close-icon-size: 17px !default;
padding-right: 0;
}
&.hairlines .search-bar {
&.hairlines ion-search-bar {
border-bottom-width: 0.55px;
}

View File

@@ -21,7 +21,7 @@ $search-bar-md-input-close-icon-svg: "<svg xmlns='http://www.w3.org/2000/svg
$search-bar-md-input-close-icon-size: 22px !default;
.search-bar {
ion-search-bar {
padding: $search-bar-md-padding;
background: $search-bar-md-background-color;
}

View File

@@ -3,7 +3,7 @@
// --------------------------------------------------
.search-bar {
ion-search-bar {
position: relative;
display: flex;
align-items: center;

View File

@@ -3,6 +3,7 @@ import {
View,
Directive,
ElementRef,
Renderer,
Host,
Optional,
NgControl,
@@ -84,7 +85,6 @@ class MediaSwitch {
'id'
],
host: {
'class': 'item',
'role': 'checkbox',
'tappable': 'true',
'[attr.tab-index]': 'tabIndex',
@@ -119,11 +119,14 @@ export class Switch {
form: IonicForm,
elementRef: ElementRef,
config: IonicConfig,
renderer: Renderer,
@Optional() private ngControl: NgControl
) {
this.form = form;
form.register(this);
renderer.setElementClass(elementRef, 'item', true);
this.lastTouch = 0;
this.mode = config.get('mode');

View File

@@ -68,7 +68,7 @@ import * as dom from 'ionic/util/dom';
}
})
@View({
template: '' +
template:
'<section class="navbar-container">' +
'<template navbar-anchor></template>' +
'</section>' +
@@ -146,7 +146,7 @@ export class Tabs extends NavController {
* TODO
*/
addTab(tab) {
this.add(tab.viewCtrl);
this._add(tab.viewCtrl);
// return true/false if it's the initial tab
return (this.length() === 1);

View File

@@ -32,7 +32,7 @@ ion-input[floating-label] {
max-width: 100%;
}
.text-input {
[text-input] {
align-self: stretch;
width: auto;
}

View File

@@ -14,7 +14,6 @@ import {pointerCoord, hasPointerMoved} from '../../util/dom';
],
host: {
'[attr.id]': 'id',
'class': 'input-label',
'(touchstart)': 'pointerStart($event)',
'(touchend)': 'pointerEnd($event)',
'(mousedown)': 'pointerStart($event)',

View File

@@ -8,12 +8,12 @@ $input-label-ios-color: #7f7f7f !default;
.list,
ion-card {
.text-input {
[text-input] {
margin: $item-ios-padding-top ($item-ios-padding-right / 2) $item-ios-padding-bottom ($item-ios-padding-left / 2);
padding: 0;
}
ion-input[inset] .text-input {
ion-input[inset] [text-input] {
margin: ($item-ios-padding-top / 2) $item-ios-padding-right ($item-ios-padding-bottom / 2) $item-ios-padding-left;
padding: ($item-ios-padding-top / 2) ($item-ios-padding-right / 2) ($item-ios-padding-bottom / 2) ($item-ios-padding-left / 2);
}
@@ -28,8 +28,8 @@ ion-card {
margin-bottom: 4px;
}
[stacked-label] .text-input,
[floating-label] .text-input {
[stacked-label] [text-input],
[floating-label] [text-input] {
margin-top: 8px;
margin-bottom: 8px;
}

View File

@@ -9,7 +9,7 @@ $input-label-md-color: #999 !default;
.list,
ion-card {
.text-input {
[text-input] {
margin: $item-md-padding-top ($item-md-padding-right / 2) $item-md-padding-bottom ($item-md-padding-left / 2);
padding: 0;
}
@@ -19,7 +19,7 @@ ion-card {
left: 0;
}
ion-input[inset] .text-input {
ion-input[inset] [text-input] {
margin: ($item-md-padding-top / 2) $item-md-padding-right ($item-md-padding-bottom / 2) $item-md-padding-left;
padding: ($item-md-padding-top / 2) ($item-md-padding-right / 2) ($item-md-padding-bottom / 2) ($item-md-padding-left / 2);
}
@@ -48,8 +48,8 @@ ion-card {
color: $text-input-highlight-color;
}
[stacked-label] .text-input,
[floating-label] .text-input {
[stacked-label] [text-input],
[floating-label] [text-input] {
margin-bottom: 8px;
margin-top: 8px;
}

View File

@@ -24,13 +24,13 @@ ion-input.item {
}
}
ion-input .text-input {
ion-input [text-input] {
flex: 1;
background-color: $text-input-background-color;
pointer-events: none;
}
ion-input.has-focus .text-input {
ion-input.has-focus [text-input] {
pointer-events: auto;
}

View File

@@ -1,4 +1,4 @@
import {Directive, View, Host, Optional, ElementRef, Attribute, Query, QueryList, NgZone} from 'angular2/angular2';
import {Directive, View, Host, Optional, ElementRef, Renderer, Attribute, Query, QueryList, NgZone} from 'angular2/angular2';
import {IonicConfig} from '../../config/config';
import {IonicForm} from '../form/form';
@@ -21,8 +21,7 @@ import {IonicPlatform} from '../../platform/platform';
'(touchend)': 'pointerEnd($event)',
'(mouseup)': 'pointerEnd($event)',
'[class.has-focus]': 'hasFocus',
'[class.has-value]': 'hasValue',
'class': 'item'
'[class.has-value]': 'hasValue'
}
})
export class TextInput {
@@ -40,11 +39,14 @@ export class TextInput {
form: IonicForm,
elementRef: ElementRef,
config: IonicConfig,
renderer: Renderer,
app: IonicApp,
zone: NgZone,
platform: IonicPlatform,
@Optional() @Host() scrollView: Content
) {
renderer.setElementClass(elementRef, 'item', true);
this.form = form;
form.register(this);
@@ -72,7 +74,8 @@ export class TextInput {
*/
onInit() {
if (this.input && this.label) {
this.input.labelledBy = this.label.id = (this.label.id || 'label-' + this.inputId);
this.label.id = (this.label.id || 'label-' + this.inputId)
this.input.labelledBy(this.label.id);
}
let self = this;
@@ -322,8 +325,6 @@ export class TextInput {
// ensure the body hasn't scrolled down
document.body.scrollTop = 0;
this.form.resetInputs();
});
if (this.scrollAssist && this.scrollView) {
@@ -386,9 +387,7 @@ export class TextInput {
'tabIndex'
],
host: {
'[tabIndex]': 'tabIndex',
'[attr.aria-labelledby]': 'labelledBy',
'class': 'text-input'
'[tabIndex]': 'tabIndex'
}
})
export class TextInputElement {
@@ -397,6 +396,7 @@ export class TextInputElement {
form: IonicForm,
@Attribute('type') type: string,
elementRef: ElementRef,
renderer: Renderer,
@Optional() textInputWrapper: TextInput
) {
this.form = form;
@@ -404,6 +404,9 @@ export class TextInputElement {
this.elementRef = elementRef;
this.tabIndex = 0;
this.renderer = renderer;
renderer.setElementAttribute(this.elementRef, 'text-input', '');
if (textInputWrapper) {
// it's within ionic's ion-input, let ion-input handle what's up
textInputWrapper.registerInput(this);
@@ -414,6 +417,10 @@ export class TextInputElement {
}
}
labelledBy(val) {
this.renderer.setElementAttribute(this.elementRef, 'aria-labelledby', val);
}
initFocus() {
this.elementRef.nativeElement.focus();
}

View File

@@ -1,4 +1,4 @@
import {Component, Directive, View, Host, ElementRef, Optional, forwardRef, Inject} from 'angular2/angular2';
import {Component, Directive, View, Host, ElementRef, Renderer, Optional, forwardRef, Inject} from 'angular2/angular2';
import {Ion} from '../ion';
import {IonicConfig} from '../../config/config';
@@ -56,10 +56,7 @@ export class ToolbarBase extends Ion {
* TODO
*/
@Component({
selector: 'ion-toolbar',
host: {
'class': 'toolbar'
}
selector: 'ion-toolbar'
})
@View({
template:
@@ -74,9 +71,11 @@ export class ToolbarBase extends Ion {
export class Toolbar extends ToolbarBase {
constructor(
elementRef: ElementRef,
config: IonicConfig
config: IonicConfig,
renderer: Renderer
) {
super(elementRef, config);
renderer.setElementClass(elementRef, 'toolbar', true);
}
}

View File

@@ -114,9 +114,6 @@ function appendConfig(cls, config) {
cls.delegates = config.delegates;
let componentId = (config.selector && config.selector.replace('ion-', ''));
config.host['class'] = ((config.host['class'] || '') + ' ' + componentId).trim();
return config;
}
@@ -128,17 +125,19 @@ export function App(args={}) {
// get current annotations
let annotations = Reflect.getMetadata('annotations', cls) || [];
// create @Component
// default to select <ion-app>
args.selector = args.selector || 'ion-app';
annotations.push(new Component(args));
// create @View
// if no template was provided, default so it has a root ion-nav
// auto add Ionic directives
args.directives = args.directives ? args.directives.concat(IONIC_DIRECTIVES) : IONIC_DIRECTIVES;
// if no template was provided, default so it has a root <ion-nav>
if (!args.templateUrl && !args.template) {
args.template = '<ion-nav></ion-nav>';
}
annotations.push(new PageImpl(args));
// create @Component
annotations.push(new Component(args));
// redefine with added annotations
Reflect.defineMetadata('annotations', annotations, cls);

View File

@@ -11,7 +11,7 @@
"link": "npm install && gulp src && npm link"
},
"dependencies": {
"angular2": "2.0.0-alpha.39",
"angular2": "2.0.0-alpha.40",
"@reactivex/rxjs": "0.0.0-prealpha.3",
"reflect-metadata": "0.1.1",
"zone.js": "0.5.8"

View File

@@ -8,7 +8,7 @@ module.exports = function(config) {
frameworks: ['jasmine'],
files: buildConfig.scripts.concat([
'node_modules/angular2/bundles/test_lib.dev.js',
'node_modules/angular2/bundles/test_lib.js',
'dist/tests/**/*.spec.js',
'scripts/karma/test-main.js'
]),

View File

@@ -11,7 +11,7 @@ exports.config = {
specs: 'dist/e2e/**/*e2e.js',
//specs: 'dist/e2e/tabs/**/*e2e.js',
sleepBetweenSpecs: 1400,
sleepBetweenSpecs: 1000,
platformDefauls: {
browser: 'chrome',