diff --git a/demos/chip/index.ts b/demos/chip/index.ts new file mode 100644 index 0000000000..63773d3346 --- /dev/null +++ b/demos/chip/index.ts @@ -0,0 +1,24 @@ +import { Component } from '@angular/core'; + +import { ionicBootstrap } from 'ionic-angular'; + + +@Component({ + templateUrl: 'main.html' +}) +class ApiDemoPage { + delete(chip: Element) { + chip.remove(); + } +} + + +@Component({ + template: '' +}) +class ApiDemoApp { + root = ApiDemoPage; +} + +ionicBootstrap(ApiDemoApp); + diff --git a/demos/chip/main.html b/demos/chip/main.html new file mode 100644 index 0000000000..f8c46b5319 --- /dev/null +++ b/demos/chip/main.html @@ -0,0 +1,96 @@ + + + + Chips + + + + + + + +

Text Chips

+ + + Default + + + + Secondary Label + + + + Another With Longer Text + + +

Color Chips

+ + + + Primary + + + + Secondary w/ Dark label + + + + Danger + + +

Icon Chips

+ + + + Default + + + + Secondary + + + +

Avatar Chips

+ + + + + + Default + + + + Right Avatar + + + + + +

Delete Chips

+ + + Default + + + + + + With Icon + + + + + + + + With Avatar + + + +
diff --git a/src/components.ts b/src/components.ts index be011c30f1..18fd1ce1ba 100644 --- a/src/components.ts +++ b/src/components.ts @@ -7,6 +7,7 @@ export { Backdrop } from './components/backdrop/backdrop'; export { Badge } from './components/badge/badge'; export { Button } from './components/button/button'; export { Checkbox } from './components/checkbox/checkbox'; +export { Chip } from './components/chip/chip'; export { Content } from './components/content/content'; export { DateTime } from './components/datetime/datetime'; export { Icon } from './components/icon/icon'; diff --git a/src/components/chip/chip.ios.scss b/src/components/chip/chip.ios.scss index 617d5028c3..8804a29b4e 100644 --- a/src/components/chip/chip.ios.scss +++ b/src/components/chip/chip.ios.scss @@ -3,17 +3,64 @@ // iOS Chip // -------------------------------------------------- +/// @prop - Margin of the chip +$chip-ios-margin: 2px 0 !default; + +/// @prop - Height of the chip +$chip-ios-height: 32px !default; + +/// @prop - Border radius of the chip +$chip-ios-border-radius: 16px !default; + +/// @prop - Font size of the chip +$chip-ios-font-size: 13px !default; + +/// @prop - Text color of the chip +$chip-ios-text-color: rgba(0, 0, 0, .87) !default; + +/// @prop - Background color of the chip +$chip-ios-background-color: rgba(0, 0, 0, .12) !default; + +/// @prop - Margin of the label in the chip +$chip-ios-label-margin: 0 10px !default; + +/// @prop - Background color of the icon in the chip +$chip-ios-icon-background-color: color($colors-ios, primary) !default; + +/// @prop - Text color of the icon in the chip +$chip-ios-icon-text-color: color-contrast($colors-ios, $chip-ios-icon-background-color) !default; + + +ion-chip { + margin: $chip-ios-margin; + + height: $chip-ios-height; + + border-radius: $chip-ios-border-radius; + font-size: $chip-ios-font-size; + line-height: $chip-ios-height; + color: $chip-ios-text-color; + background: $chip-ios-background-color; + + > ion-label { + margin: $chip-ios-label-margin; + } + + > ion-icon { + color: $chip-ios-icon-text-color; + background-color: $chip-ios-icon-background-color; + } +} // Generate iOS Chip Colors // -------------------------------------------------- @each $color-name, $color-base, $color-contrast in get-colors($colors-ios) { - ion-chip { - ion-icon[#{$color-name}] { - color: $color-contrast; - background-color: $color-base; - } + .chip-#{$color-name}, + ion-chip .icon-#{$color-name} { + color: $color-contrast; + background-color: $color-base; } } diff --git a/src/components/chip/chip.md.scss b/src/components/chip/chip.md.scss index 6d5bcdc7c8..b383639981 100644 --- a/src/components/chip/chip.md.scss +++ b/src/components/chip/chip.md.scss @@ -3,17 +3,64 @@ // Material Design Chip // -------------------------------------------------- +/// @prop - Margin of the chip +$chip-md-margin: 2px 0 !default; + +/// @prop - Height of the chip +$chip-md-height: 32px !default; + +/// @prop - Border radius of the chip +$chip-md-border-radius: 16px !default; + +/// @prop - Font size of the chip +$chip-md-font-size: 13px !default; + +/// @prop - Text color of the chip +$chip-md-text-color: rgba(0, 0, 0, .87) !default; + +/// @prop - Background color of the chip +$chip-md-background-color: rgba(0, 0, 0, .12) !default; + +/// @prop - Margin of the label in the chip +$chip-md-label-margin: 0 10px !default; + +/// @prop - Background color of the icon in the chip +$chip-md-icon-background-color: color($colors-md, primary) !default; + +/// @prop - Text color of the icon in the chip +$chip-md-icon-text-color: color-contrast($colors-md, $chip-md-icon-background-color) !default; + + +ion-chip { + margin: $chip-md-margin; + + height: $chip-md-height; + + border-radius: $chip-md-border-radius; + font-size: $chip-md-font-size; + line-height: $chip-md-height; + color: $chip-md-text-color; + background: $chip-md-background-color; + + > ion-label { + margin: $chip-md-label-margin; + } + + > ion-icon { + color: $chip-md-icon-text-color; + background-color: $chip-md-icon-background-color; + } +} // Generate Material Design Chip Colors // -------------------------------------------------- @each $color-name, $color-base, $color-contrast in get-colors($colors-md) { - ion-chip { - ion-icon[#{$color-name}] { - color: $color-contrast; - background-color: $color-base; - } + .chip-#{$color-name}, + ion-chip .icon-#{$color-name} { + color: $color-contrast; + background-color: $color-base; } } diff --git a/src/components/chip/chip.scss b/src/components/chip/chip.scss index c840d9d8e3..3542c36148 100644 --- a/src/components/chip/chip.scss +++ b/src/components/chip/chip.scss @@ -3,56 +3,62 @@ // Chip // -------------------------------------------------- -$chip-background-color: rgba(0, 0, 0, .12) !default; -$chip-font-size: 13px !default; -$chip-height: 32px !default; -$chip-border-radius: 16px !default; -$chip-padding: 0 12px !default; -$chip-margin: 2px 0 !default; +/// @prop - Border radius of the button in the chip +$chip-button-border-radius: 50% !default; + +/// @prop - Margin of the button in the chip +$chip-button-margin: 0 !default; + +/// @prop - Width and height of the button in the chip +$chip-button-size: 32px !default; + +/// @prop - Border radius of the icon in the chip +$chip-icon-border-radius: 50% !default; + +/// @prop - Width and height of the icon in the chip +$chip-icon-size: 32px !default; + +/// @prop - Font size of the icon in the chip +$chip-icon-font-size: 18px !default; + +/// @prop - Width and height of the avatar in the chip +$chip-avatar-size: 32px !default; + +/// @prop - Border radius of the avatar in the chip +$chip-avatar-border-radius: 50% !default; -$chip-label-color: rgba(0, 0, 0, .87) !default; -$chip-icon-color: rgba(0, 0, 0, .87) !default; -$chip-remove-icon-color: rgba(137, 137, 137, .54) !default; ion-chip { display: inline-flex; align-self: center; - - margin: $chip-margin; - padding: $chip-padding; - - height: $chip-height; - - border-radius: $chip-border-radius; - font-size: $chip-font-size; font-weight: normal; - line-height: $chip-height; - background: $chip-background-color; - vertical-align: middle; box-sizing: border-box; - ion-label { - margin: 0; - - color: $chip-label-color; + .button { + border-radius: $chip-button-border-radius; + margin: $chip-button-margin; + height: $chip-button-size; + width: $chip-button-size; } - > ion-icon, - > ion-avatar { - margin-left: -12px; + ion-icon { + border-radius: $chip-icon-border-radius; + line-height: $chip-icon-size; - width: 32px; - height: 32px; + font-size: $chip-icon-font-size; + width: $chip-icon-size; + height: $chip-icon-size; + } - border-radius: 50%; - font-size: 18px; - line-height: 32px; - text-align: center; - color: $chip-icon-color; - vertical-align: top; + ion-avatar { + border-radius: $chip-avatar-border-radius; + width: $chip-avatar-size; + height: $chip-avatar-size; + min-width: $chip-avatar-size; + min-height: $chip-avatar-size; img { display: block; @@ -62,31 +68,7 @@ ion-chip { height: 100%; max-height: 100%; - border-radius: 50%; - } - - + ion-label { - margin-left: 8px; + border-radius: $chip-avatar-border-radius; } } - - ion-avatar { - min-width: 32px; - min-height: 32px; - } - - .button { - margin: 0; - margin-right: -4px; - - height: inherit; - } - - ion-icon[name="close-circle"] { - margin: 0 -8px 2px -4px; - - font-size: 1.4em; - - color: $chip-remove-icon-color; - } -} +} \ No newline at end of file diff --git a/src/components/chip/chip.ts b/src/components/chip/chip.ts index e79c06bda7..6bb498b23d 100644 --- a/src/components/chip/chip.ts +++ b/src/components/chip/chip.ts @@ -1,111 +1,132 @@ -import { Component, ElementRef, Renderer, Attribute } from '@angular/core'; - -import { Config } from '../../config/config'; +import { Directive, ElementRef, Input, Renderer } from '@angular/core'; /** * @name Chip * @module ionic * @description * Chips represent complex entities in small blocks, such as a contact. - * @see {@link /docs/v2/components/#chips Chips Component Docs} + * + * + * @usage + * + * ```html + * + * Default + * + * + * + * Secondary Label + * + * + * + * Secondary w/ Dark label + * + * + * + * Danger + * + * + * + * + * Default + * + * + * + * + * Default + * + * + * + * + * + * + * Default + * + * ``` + * + * + * @advanced + * + * ```html + * + * Default + * + * + * + * + * + * With Icon + * + * + * + * + * + * + * + * With Avatar + * + * + * ``` + * + * ```ts + * @Component({ + * templateUrl: 'main.html' + * }) + * class E2EPage { + * delete(chip: Element) { + * chip.remove(); + * } + * } + * ``` + * + * @demo /docs/v2/demos/chip/ **/ - -@Component({ - selector: 'ion-chip', - template: '' +@Directive({ + selector: 'ion-chip' }) - export class Chip { - private deletable: boolean = false; + /** @internal */ + _color: string; + + /** + * @input {string} The predefined color to use. For example: `"primary"`, `"secondary"`, `"danger"`. + */ + @Input() + get color(): string { + return this._color; + } + + set color(value: string) { + this._updateColor(value); + } constructor( - config: Config, private _elementRef: ElementRef, private _renderer: Renderer - ) { - let element = _elementRef.nativeElement; + ) { } - this._readAttrs(element); + /** + * @internal + */ + _updateColor(newColor: string) { + this._setElementColor(this._color, false); + this._setElementColor(newColor, true); + this._color = newColor; } /** - * @private + * @internal */ - ngOnInit() { - this._fixContent(this._elementRef.nativeElement); - } - - /** - * @private - */ - private _readAttrs(element: HTMLElement) { - - let elementAttrs = element.attributes; - let attrName: string; - - for (let i = 0, l = elementAttrs.length; i < l; i++) { - if (elementAttrs[i].value !== '') continue; - - attrName = elementAttrs[i].name; - - if (attrName === 'deletable') { - this._setDeletable(); - } + _setElementColor(color: string, isAdd: boolean) { + if (color !== null && color !== '') { + this._renderer.setElementClass(this._elementRef.nativeElement, `chip-${color}`, isAdd); } } - /** - * @private - */ - private deleteChip() { - this._elementRef.nativeElement.remove(); - } - - /** - * @private - */ - private _setDeletable() { - this.deletable = true; - } - - - /** - * @private - */ - private _fixContent(element: HTMLElement) { - // Take the first text node and add it to the label. - // Take the first icon or avatar and add it to the chip. - // Discard everything else. - - let childNodes: NodeList = element.childNodes; - let innerNode: Node = childNodes[0]; - let labelNode: Node = childNodes[1]; - let addedNodes: NodeList = innerNode.childNodes; - element.removeChild(innerNode); - - let missing = {image: true, text: true}; - let childNode: Node; - let imageNode: Node; - let text: string; - for (let i = 0, l = addedNodes.length; i < l; i++) { - childNode = addedNodes[i]; - if (childNode.nodeType === 3 && missing.text) { - text = childNode.textContent.trim(); - if (text !== '') { - labelNode.textContent = text; - missing.text = false; - } - } - if (childNode.nodeType === 1 && missing.image) { - name = childNode.nodeName; - if (childNode.nodeName === 'ION-ICON' || childNode.nodeName === 'ION-AVATAR') { - missing.image = false; - imageNode = childNode; - } - } - } - if (imageNode) { - element.insertBefore(imageNode, element.firstChild); - } - } } diff --git a/src/components/chip/chip.wp.scss b/src/components/chip/chip.wp.scss index 34981b1f3a..66f073a36d 100644 --- a/src/components/chip/chip.wp.scss +++ b/src/components/chip/chip.wp.scss @@ -3,17 +3,68 @@ // Windows Chip // -------------------------------------------------- +/// @prop - Margin of the chip +$chip-wp-margin: 2px 0 !default; + +/// @prop - Height of the chip +$chip-wp-height: 32px !default; + +/// @prop - Border radius of the chip +$chip-wp-border-radius: 16px !default; + +/// @prop - Font size of the chip +$chip-wp-font-size: 13px !default; + +/// @prop - Text color of the chip +$chip-wp-text-color: rgba(0, 0, 0, .87) !default; + +/// @prop - Background color of the chip +$chip-wp-background-color: rgba(0, 0, 0, .12) !default; + +/// @prop - Margin of the label in the chip +$chip-wp-label-margin: 0 10px !default; + +/// @prop - Background color of the icon in the chip +$chip-wp-icon-background-color: color($colors-wp, primary) !default; + +/// @prop - Text color of the icon in the chip +$chip-wp-icon-text-color: color-contrast($colors-wp, $chip-wp-icon-background-color) !default; + + +ion-chip { + margin: $chip-wp-margin; + + height: $chip-wp-height; + + border-radius: $chip-wp-border-radius; + font-size: $chip-wp-font-size; + line-height: $chip-wp-height; + color: $chip-wp-text-color; + background: $chip-wp-background-color; + + > ion-label { + margin: $chip-wp-label-margin; + } + + > ion-icon { + color: $chip-wp-icon-text-color; + background-color: $chip-wp-icon-background-color; + } + + .button { + border: 0; + } +} // Generate Windows Chip Colors // -------------------------------------------------- @each $color-name, $color-base, $color-contrast in get-colors($colors-wp) { - ion-chip { - ion-icon[#{$color-name}] { - color: $color-contrast; - background-color: $color-base; - } + .chip-#{$color-name}, + ion-chip .icon-#{$color-name} { + color: $color-contrast; + background-color: $color-base; } } diff --git a/src/components/chip/test/basic/index.ts b/src/components/chip/test/basic/index.ts index 7b73dae881..a8201efd55 100644 --- a/src/components/chip/test/basic/index.ts +++ b/src/components/chip/test/basic/index.ts @@ -5,7 +5,11 @@ import { ionicBootstrap } from '../../../../../src'; @Component({ templateUrl: 'main.html' }) -class E2EPage {} +class E2EPage { + delete(chip: Element) { + chip.remove(); + } +} @Component({ template: '' diff --git a/src/components/chip/test/basic/main.html b/src/components/chip/test/basic/main.html index b2eba2d36e..5ad55526df 100644 --- a/src/components/chip/test/basic/main.html +++ b/src/components/chip/test/basic/main.html @@ -1,7 +1,7 @@ - Chips With Text + Chips @@ -9,15 +9,88 @@ -

- - Default - -

-

- - Another With Longer Text - -

+

Text Chips

+ + + Default + + + + Secondary Label + + + + Another With Longer Text + + +

Color Chips

+ + + + Primary + + + + Secondary w/ Dark label + + + + Danger + + +

Icon Chips

+ + + + Default + + + + Secondary + + + +

Avatar Chips

+ + + + + + Default + + + + Right Avatar + + + + + +

Delete Chips

+ + + Default + + + + + + With Icon + + + + + + + + With Avatar + +
diff --git a/src/components/chip/test/delete/index.ts b/src/components/chip/test/delete/index.ts deleted file mode 100644 index de3edab3c3..0000000000 --- a/src/components/chip/test/delete/index.ts +++ /dev/null @@ -1,23 +0,0 @@ -import { Component } from '@angular/core'; -import { ionicBootstrap } from '../../../../../src'; - - -@Component({ - templateUrl: 'main.html' -}) -class E2EPage { - - deleteClicked() { - console.log('deleteClicked'); - } - -} - -@Component({ - template: '' -}) -class E2EApp { - rootPage = E2EPage; -} - -ionicBootstrap(E2EApp); diff --git a/src/components/chip/test/delete/main.html b/src/components/chip/test/delete/main.html deleted file mode 100644 index b970395c2b..0000000000 --- a/src/components/chip/test/delete/main.html +++ /dev/null @@ -1,48 +0,0 @@ - - - - Chips With Delete - - - - - - - -

- - Default - -

- -

- - - With Icon - -

- -

- - - - - With Avatar - -

- -

- - This Should Not Be Seen - - With Junk Elements - - - - -


- This Should Not Be Seen Either - -

- -
diff --git a/src/components/chip/test/icon/index.ts b/src/components/chip/test/icon/index.ts deleted file mode 100644 index 7b73dae881..0000000000 --- a/src/components/chip/test/icon/index.ts +++ /dev/null @@ -1,17 +0,0 @@ -import { Component } from '@angular/core'; -import { ionicBootstrap } from '../../../../../src'; - - -@Component({ - templateUrl: 'main.html' -}) -class E2EPage {} - -@Component({ - template: '' -}) -class E2EApp { - rootPage = E2EPage; -} - -ionicBootstrap(E2EApp); diff --git a/src/components/chip/test/icon/main.html b/src/components/chip/test/icon/main.html deleted file mode 100644 index e04a54e444..0000000000 --- a/src/components/chip/test/icon/main.html +++ /dev/null @@ -1,49 +0,0 @@ - - - - Chips With Icon - - - - - - - -

- - - Default - -

-

- - - Primary - -

-

- - - Secondary - -

-

- - - Danger - -

-

- - - Light - -

-

- - - Dark - -

- -
diff --git a/src/components/chip/test/image/index.ts b/src/components/chip/test/image/index.ts deleted file mode 100644 index 7b73dae881..0000000000 --- a/src/components/chip/test/image/index.ts +++ /dev/null @@ -1,17 +0,0 @@ -import { Component } from '@angular/core'; -import { ionicBootstrap } from '../../../../../src'; - - -@Component({ - templateUrl: 'main.html' -}) -class E2EPage {} - -@Component({ - template: '' -}) -class E2EApp { - rootPage = E2EPage; -} - -ionicBootstrap(E2EApp); diff --git a/src/components/chip/test/image/main.html b/src/components/chip/test/image/main.html deleted file mode 100644 index a83f99d31c..0000000000 --- a/src/components/chip/test/image/main.html +++ /dev/null @@ -1,21 +0,0 @@ - - - - Chips With Image - - - - - - - -

- - - - - Default - -

- -