From 4e6ebf59c55abd442b8ce31a1e2438e7dbeea360 Mon Sep 17 00:00:00 2001 From: "Manu Mtz.-Almeida" Date: Wed, 7 Feb 2018 19:05:39 +0100 Subject: [PATCH] feat(ion-router): adds ion-router --- .gitignore | 1 + packages/core/package-lock.json | 6 +- packages/core/package.json | 1 + .../src/components/page-one/page-one.tsx | 22 + .../src/components/page-two/page-two.tsx | 22 + .../scripts/test-components/stencil.config.js | 5 + .../scripts/test-components/tsconfig.json | 22 + packages/core/src/components.d.ts | 24 +- packages/core/src/components.d.ts.orig | 3430 +++++++++++++++++ packages/core/src/components/nav/nav-utils.ts | 12 +- packages/core/src/components/nav/nav.tsx | 62 +- packages/core/src/components/nav/readme.md | 21 +- .../src/components/nav/test/basic/index.html | 22 +- .../src/components/nav/test/routing/e2e.js | 52 + .../components/nav/test/routing/index.html | 46 + packages/core/src/components/route/readme.md | 5 - packages/core/src/components/route/route.tsx | 12 +- .../router-controller/router-controller.tsx | 105 - .../router-controller/router-utils.ts | 183 - .../{router-controller => router}/readme.md | 24 + .../src/components/router/router-utils.ts | 224 ++ .../core/src/components/router/router.tsx | 91 + .../test/router-utils.spec.tsx} | 150 +- packages/core/src/components/tabs/readme.md | 9 + packages/core/src/components/tabs/tabs.tsx | 46 +- packages/core/src/index.d.ts | 7 +- packages/core/stencil.config.js | 2 +- 27 files changed, 4113 insertions(+), 493 deletions(-) create mode 100644 packages/core/scripts/test-components/src/components/page-one/page-one.tsx create mode 100644 packages/core/scripts/test-components/src/components/page-two/page-two.tsx create mode 100644 packages/core/scripts/test-components/stencil.config.js create mode 100644 packages/core/scripts/test-components/tsconfig.json create mode 100644 packages/core/src/components.d.ts.orig create mode 100644 packages/core/src/components/nav/test/routing/e2e.js create mode 100644 packages/core/src/components/nav/test/routing/index.html delete mode 100644 packages/core/src/components/router-controller/router-controller.tsx delete mode 100644 packages/core/src/components/router-controller/router-utils.ts rename packages/core/src/components/{router-controller => router}/readme.md (56%) create mode 100644 packages/core/src/components/router/router-utils.ts create mode 100644 packages/core/src/components/router/router.tsx rename packages/core/src/components/{route/test/router-utils.spec.ts => router/test/router-utils.spec.tsx} (58%) diff --git a/.gitignore b/.gitignore index 6ef0abc5fe..92b3f84761 100644 --- a/.gitignore +++ b/.gitignore @@ -19,6 +19,7 @@ node_modules/ tmp/ temp/ packages/core/theme-builder/ +packages/core/test-components/ $RECYCLE.BIN/ .DS_Store diff --git a/packages/core/package-lock.json b/packages/core/package-lock.json index 7da1a998d1..a24915761b 100644 --- a/packages/core/package-lock.json +++ b/packages/core/package-lock.json @@ -14,9 +14,9 @@ } }, "@stencil/core": { - "version": "0.4.0-0", - "resolved": "https://registry.npmjs.org/@stencil/core/-/core-0.4.0-0.tgz", - "integrity": "sha512-s5/dfezhD2PZoeHevxZRe7GNLmOL+vf/MRtngZCUOjFrdswwCAEnURnhTTQMh+CQi6r6cdKIgdEzzMI9WGI/rA==", + "version": "0.4.0-1", + "resolved": "https://registry.npmjs.org/@stencil/core/-/core-0.4.0-1.tgz", + "integrity": "sha512-VgjzNx28O27Hd32LEf5dirJJnOUyq+MZdLpIWuaTZtAkj6EWGgIqw0ZOs0j0XzopIOJ25BqBk6nVS1xLaaqrzg==", "dev": true, "requires": { "chokidar": "2.0.0", diff --git a/packages/core/package.json b/packages/core/package.json index a03f0104dd..d8c92bb16a 100644 --- a/packages/core/package.json +++ b/packages/core/package.json @@ -38,6 +38,7 @@ "snapshot": "node ./scripts/e2e --snapshot", "test": "jest --no-cache", "test.watch": "jest --watch --no-cache", + "build-test-cmp": "stencil build --dev --config scripts/test-components/stencil.config.js", "theme-app-build": "stencil build --dev --config scripts/theme-builder/stencil.config.js", "theme-builder": "npm run theme-app-build && sd concurrent \"stencil build --dev --watch\" \"stencil-dev-server\" \"npm run theme-server\" ", "theme-server": "node scripts/theme-builder/server.js", diff --git a/packages/core/scripts/test-components/src/components/page-one/page-one.tsx b/packages/core/scripts/test-components/src/components/page-one/page-one.tsx new file mode 100644 index 0000000000..fa460b3f67 --- /dev/null +++ b/packages/core/scripts/test-components/src/components/page-one/page-one.tsx @@ -0,0 +1,22 @@ +import { Component } from '@stencil/core'; + +@Component({ + tag: 'page-one', +}) +export class PageOne { + + render() { + return [ + + + + Page One + + + + page one + + + ]; + } +} diff --git a/packages/core/scripts/test-components/src/components/page-two/page-two.tsx b/packages/core/scripts/test-components/src/components/page-two/page-two.tsx new file mode 100644 index 0000000000..077562bb9f --- /dev/null +++ b/packages/core/scripts/test-components/src/components/page-two/page-two.tsx @@ -0,0 +1,22 @@ +import { Component } from '@stencil/core'; + +@Component({ + tag: 'page-two', +}) +export class PageTwo { + + render() { + return [ + + + + Page Two + + + + this is page two + + + ]; + } +} diff --git a/packages/core/scripts/test-components/stencil.config.js b/packages/core/scripts/test-components/stencil.config.js new file mode 100644 index 0000000000..c22efbec48 --- /dev/null +++ b/packages/core/scripts/test-components/stencil.config.js @@ -0,0 +1,5 @@ +exports.config = { + generateWWW: true, + wwwDir: '../../test-components', + serviceWorker: false +}; diff --git a/packages/core/scripts/test-components/tsconfig.json b/packages/core/scripts/test-components/tsconfig.json new file mode 100644 index 0000000000..6da84ddecc --- /dev/null +++ b/packages/core/scripts/test-components/tsconfig.json @@ -0,0 +1,22 @@ +{ + "compilerOptions": { + "allowSyntheticDefaultImports": true, + "allowUnreachableCode": false, + "declaration": false, + "experimentalDecorators": true, + "lib": [ + "dom", + "es2015" + ], + "moduleResolution": "node", + "module": "es2015", + "target": "es2015", + "noUnusedLocals": true, + "noUnusedParameters": true, + "jsx": "react", + "jsxFactory": "h" + }, + "include": [ + "src" + ] +} diff --git a/packages/core/src/components.d.ts b/packages/core/src/components.d.ts index 46f722368a..040d8f7ca5 100644 --- a/packages/core/src/components.d.ts +++ b/packages/core/src/components.d.ts @@ -1834,6 +1834,7 @@ declare global { lazy?: boolean; mode?: string; root?: any; + swipeBackEnabled?: boolean; useUrls?: boolean; } } @@ -2442,30 +2443,31 @@ declare global { import { - RouterController as IonRouterController -} from './components/router-controller/router-controller'; + Router as IonRouter +} from './components/router/router'; declare global { - interface HTMLIonRouterControllerElement extends IonRouterController, HTMLStencilElement { + interface HTMLIonRouterElement extends IonRouter, HTMLStencilElement { } - var HTMLIonRouterControllerElement: { - prototype: HTMLIonRouterControllerElement; - new (): HTMLIonRouterControllerElement; + var HTMLIonRouterElement: { + prototype: HTMLIonRouterElement; + new (): HTMLIonRouterElement; }; interface HTMLElementTagNameMap { - "ion-router-controller": HTMLIonRouterControllerElement; + "ion-router": HTMLIonRouterElement; } interface ElementTagNameMap { - "ion-router-controller": HTMLIonRouterControllerElement; + "ion-router": HTMLIonRouterElement; } namespace JSX { interface IntrinsicElements { - "ion-router-controller": JSXElements.IonRouterControllerAttributes; + "ion-router": JSXElements.IonRouterAttributes; } } namespace JSXElements { - export interface IonRouterControllerAttributes extends HTMLAttributes { - + export interface IonRouterAttributes extends HTMLAttributes { + base?: string; + useHash?: boolean; } } } diff --git a/packages/core/src/components.d.ts.orig b/packages/core/src/components.d.ts.orig new file mode 100644 index 0000000000..aaa27b6587 --- /dev/null +++ b/packages/core/src/components.d.ts.orig @@ -0,0 +1,3430 @@ +/** + * This is an autogenerated file created by the Stencil build process. + * It contains typing information for all components that exist in this project + * and imports for stencil collections that might be configured in your stencil.config.js file + */ + +import 'ionicons'; + +import { + ActionSheetButton, +} from './components/action-sheet/action-sheet'; +import { + AnimationBuilder, + FrameworkDelegate, + PickerColumn, + PickerOptions, +} from './index'; +import { + AlertButton, + AlertInput, +} from './components/alert/alert'; +import { + ElementRef, + Side, +} from './utils/helpers'; +import { + GestureCallback, + GestureDetail, +} from './components/gesture/gesture'; +import { + PickerButton, + PickerColumn as PickerColumn2, +} from './components/picker/picker'; +import { + Event, +} from '@stencil/core'; +import { + ScrollCallback, +} from './components/scroll/scroll'; +import { + SelectPopoverOption, +} from './components/select-popover/select-popover'; +import { + DomRenderFn, + HeaderFn, + ItemHeightFn, + ItemRenderFn, + NodeHeightFn, +} from './components/virtual-scroll/virtual-scroll-utils'; + +declare global { + interface HTMLStencilElement extends HTMLElement { + componentOnReady(): Promise; + componentOnReady(done: (ele?: this) => void): void; + } +} + + + +import { + ActionSheetController as IonActionSheetController +} from './components/action-sheet-controller/action-sheet-controller'; + +declare global { + interface HTMLIonActionSheetControllerElement extends IonActionSheetController, HTMLStencilElement { + } + var HTMLIonActionSheetControllerElement: { + prototype: HTMLIonActionSheetControllerElement; + new (): HTMLIonActionSheetControllerElement; + }; + interface HTMLElementTagNameMap { + "ion-action-sheet-controller": HTMLIonActionSheetControllerElement; + } + interface ElementTagNameMap { + "ion-action-sheet-controller": HTMLIonActionSheetControllerElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-action-sheet-controller": JSXElements.IonActionSheetControllerAttributes; + } + } + namespace JSXElements { + export interface IonActionSheetControllerAttributes extends HTMLAttributes { + + } + } +} + + +import { + ActionSheet as IonActionSheet +} from './components/action-sheet/action-sheet'; + +declare global { + interface HTMLIonActionSheetElement extends IonActionSheet, HTMLStencilElement { + } + var HTMLIonActionSheetElement: { + prototype: HTMLIonActionSheetElement; + new (): HTMLIonActionSheetElement; + }; + interface HTMLElementTagNameMap { + "ion-action-sheet": HTMLIonActionSheetElement; + } + interface ElementTagNameMap { + "ion-action-sheet": HTMLIonActionSheetElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-action-sheet": JSXElements.IonActionSheetAttributes; + } + } + namespace JSXElements { + export interface IonActionSheetAttributes extends HTMLAttributes { + buttons?: ActionSheetButton[]; + cssClass?: string; + enableBackdropDismiss?: boolean; + enterAnimation?: AnimationBuilder; + leaveAnimation?: AnimationBuilder; + subTitle?: string; + title?: string; + translucent?: boolean; + willAnimate?: boolean; + } + } +} + + +import { + AlertController as IonAlertController +} from './components/alert-controller/alert-controller'; + +declare global { + interface HTMLIonAlertControllerElement extends IonAlertController, HTMLStencilElement { + } + var HTMLIonAlertControllerElement: { + prototype: HTMLIonAlertControllerElement; + new (): HTMLIonAlertControllerElement; + }; + interface HTMLElementTagNameMap { + "ion-alert-controller": HTMLIonAlertControllerElement; + } + interface ElementTagNameMap { + "ion-alert-controller": HTMLIonAlertControllerElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-alert-controller": JSXElements.IonAlertControllerAttributes; + } + } + namespace JSXElements { + export interface IonAlertControllerAttributes extends HTMLAttributes { + + } + } +} + + +import { + Alert as IonAlert +} from './components/alert/alert'; + +declare global { + interface HTMLIonAlertElement extends IonAlert, HTMLStencilElement { + } + var HTMLIonAlertElement: { + prototype: HTMLIonAlertElement; + new (): HTMLIonAlertElement; + }; + interface HTMLElementTagNameMap { + "ion-alert": HTMLIonAlertElement; + } + interface ElementTagNameMap { + "ion-alert": HTMLIonAlertElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-alert": JSXElements.IonAlertAttributes; + } + } + namespace JSXElements { + export interface IonAlertAttributes extends HTMLAttributes { + buttons?: AlertButton[]; + cssClass?: string; + enableBackdropDismiss?: boolean; + enterAnimation?: AnimationBuilder; + inputs?: AlertInput[]; + leaveAnimation?: AnimationBuilder; + message?: string; + subTitle?: string; + title?: string; + translucent?: boolean; + willAnimate?: boolean; + } + } +} + + +import { + AnimationControllerImpl as IonAnimationController +} from './components/animation-controller/animation-controller'; + +declare global { + interface HTMLIonAnimationControllerElement extends IonAnimationController, HTMLStencilElement { + } + var HTMLIonAnimationControllerElement: { + prototype: HTMLIonAnimationControllerElement; + new (): HTMLIonAnimationControllerElement; + }; + interface HTMLElementTagNameMap { + "ion-animation-controller": HTMLIonAnimationControllerElement; + } + interface ElementTagNameMap { + "ion-animation-controller": HTMLIonAnimationControllerElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-animation-controller": JSXElements.IonAnimationControllerAttributes; + } + } + namespace JSXElements { + export interface IonAnimationControllerAttributes extends HTMLAttributes { + + } + } +} + + +import { + App as IonApp +} from './components/app/app'; + +declare global { + interface HTMLIonAppElement extends IonApp, HTMLStencilElement { + } + var HTMLIonAppElement: { + prototype: HTMLIonAppElement; + new (): HTMLIonAppElement; + }; + interface HTMLElementTagNameMap { + "ion-app": HTMLIonAppElement; + } + interface ElementTagNameMap { + "ion-app": HTMLIonAppElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-app": JSXElements.IonAppAttributes; + } + } + namespace JSXElements { + export interface IonAppAttributes extends HTMLAttributes { + + } + } +} + + +import { + Avatar as IonAvatar +} from './components/avatar/avatar'; + +declare global { + interface HTMLIonAvatarElement extends IonAvatar, HTMLStencilElement { + } + var HTMLIonAvatarElement: { + prototype: HTMLIonAvatarElement; + new (): HTMLIonAvatarElement; + }; + interface HTMLElementTagNameMap { + "ion-avatar": HTMLIonAvatarElement; + } + interface ElementTagNameMap { + "ion-avatar": HTMLIonAvatarElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-avatar": JSXElements.IonAvatarAttributes; + } + } + namespace JSXElements { + export interface IonAvatarAttributes extends HTMLAttributes { + + } + } +} + + +import { + BackButton as IonBackButton +} from './components/back-button/back-button'; + +declare global { + interface HTMLIonBackButtonElement extends IonBackButton, HTMLStencilElement { + } + var HTMLIonBackButtonElement: { + prototype: HTMLIonBackButtonElement; + new (): HTMLIonBackButtonElement; + }; + interface HTMLElementTagNameMap { + "ion-back-button": HTMLIonBackButtonElement; + } + interface ElementTagNameMap { + "ion-back-button": HTMLIonBackButtonElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-back-button": JSXElements.IonBackButtonAttributes; + } + } + namespace JSXElements { + export interface IonBackButtonAttributes extends HTMLAttributes { + + } + } +} + + +import { + Backdrop as IonBackdrop +} from './components/backdrop/backdrop'; + +declare global { + interface HTMLIonBackdropElement extends IonBackdrop, HTMLStencilElement { + } + var HTMLIonBackdropElement: { + prototype: HTMLIonBackdropElement; + new (): HTMLIonBackdropElement; + }; + interface HTMLElementTagNameMap { + "ion-backdrop": HTMLIonBackdropElement; + } + interface ElementTagNameMap { + "ion-backdrop": HTMLIonBackdropElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-backdrop": JSXElements.IonBackdropAttributes; + } + } + namespace JSXElements { + export interface IonBackdropAttributes extends HTMLAttributes { + mode?: 'ios' | 'md'; + } + } +} + + +import { + Badge as IonBadge +} from './components/badge/badge'; + +declare global { + interface HTMLIonBadgeElement extends IonBadge, HTMLStencilElement { + } + var HTMLIonBadgeElement: { + prototype: HTMLIonBadgeElement; + new (): HTMLIonBadgeElement; + }; + interface HTMLElementTagNameMap { + "ion-badge": HTMLIonBadgeElement; + } + interface ElementTagNameMap { + "ion-badge": HTMLIonBadgeElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-badge": JSXElements.IonBadgeAttributes; + } + } + namespace JSXElements { + export interface IonBadgeAttributes extends HTMLAttributes { + color?: string; + mode?: 'ios' | 'md'; + } + } +} + + +import { + Button as IonButton +} from './components/button/button'; + +declare global { + interface HTMLIonButtonElement extends IonButton, HTMLStencilElement { + } + var HTMLIonButtonElement: { + prototype: HTMLIonButtonElement; + new (): HTMLIonButtonElement; + }; + interface HTMLElementTagNameMap { + "ion-button": HTMLIonButtonElement; + } + interface ElementTagNameMap { + "ion-button": HTMLIonButtonElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-button": JSXElements.IonButtonAttributes; + } + } + namespace JSXElements { + export interface IonButtonAttributes extends HTMLAttributes { + buttonType?: string; + color?: string; + disabled?: boolean; + expand?: 'full' | 'block'; + fill?: 'clear' | 'outline' | 'solid' | 'default'; + href?: string; + mode?: 'ios' | 'md'; + round?: boolean; + size?: 'small' | 'default' | 'large'; + strong?: boolean; + } + } +} + + +import { + Buttons as IonButtons +} from './components/buttons/buttons'; + +declare global { + interface HTMLIonButtonsElement extends IonButtons, HTMLStencilElement { + } + var HTMLIonButtonsElement: { + prototype: HTMLIonButtonsElement; + new (): HTMLIonButtonsElement; + }; + interface HTMLElementTagNameMap { + "ion-buttons": HTMLIonButtonsElement; + } + interface ElementTagNameMap { + "ion-buttons": HTMLIonButtonsElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-buttons": JSXElements.IonButtonsAttributes; + } + } + namespace JSXElements { + export interface IonButtonsAttributes extends HTMLAttributes { + + } + } +} + + +import { + CardContent as IonCardContent +} from './components/card-content/card-content'; + +declare global { + interface HTMLIonCardContentElement extends IonCardContent, HTMLStencilElement { + } + var HTMLIonCardContentElement: { + prototype: HTMLIonCardContentElement; + new (): HTMLIonCardContentElement; + }; + interface HTMLElementTagNameMap { + "ion-card-content": HTMLIonCardContentElement; + } + interface ElementTagNameMap { + "ion-card-content": HTMLIonCardContentElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-card-content": JSXElements.IonCardContentAttributes; + } + } + namespace JSXElements { + export interface IonCardContentAttributes extends HTMLAttributes { + color?: string; + mode?: 'ios' | 'md'; + } + } +} + + +import { + CardHeader as IonCardHeader +} from './components/card-header/card-header'; + +declare global { + interface HTMLIonCardHeaderElement extends IonCardHeader, HTMLStencilElement { + } + var HTMLIonCardHeaderElement: { + prototype: HTMLIonCardHeaderElement; + new (): HTMLIonCardHeaderElement; + }; + interface HTMLElementTagNameMap { + "ion-card-header": HTMLIonCardHeaderElement; + } + interface ElementTagNameMap { + "ion-card-header": HTMLIonCardHeaderElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-card-header": JSXElements.IonCardHeaderAttributes; + } + } + namespace JSXElements { + export interface IonCardHeaderAttributes extends HTMLAttributes { + color?: string; + mode?: 'ios' | 'md'; + translucent?: boolean; + } + } +} + + +import { + CardSubtitle as IonCardSubtitle +} from './components/card-subtitle/card-subtitle'; + +declare global { + interface HTMLIonCardSubtitleElement extends IonCardSubtitle, HTMLStencilElement { + } + var HTMLIonCardSubtitleElement: { + prototype: HTMLIonCardSubtitleElement; + new (): HTMLIonCardSubtitleElement; + }; + interface HTMLElementTagNameMap { + "ion-card-subtitle": HTMLIonCardSubtitleElement; + } + interface ElementTagNameMap { + "ion-card-subtitle": HTMLIonCardSubtitleElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-card-subtitle": JSXElements.IonCardSubtitleAttributes; + } + } + namespace JSXElements { + export interface IonCardSubtitleAttributes extends HTMLAttributes { + color?: string; + mode?: 'ios' | 'md'; + } + } +} + + +import { + CardTitle as IonCardTitle +} from './components/card-title/card-title'; + +declare global { + interface HTMLIonCardTitleElement extends IonCardTitle, HTMLStencilElement { + } + var HTMLIonCardTitleElement: { + prototype: HTMLIonCardTitleElement; + new (): HTMLIonCardTitleElement; + }; + interface HTMLElementTagNameMap { + "ion-card-title": HTMLIonCardTitleElement; + } + interface ElementTagNameMap { + "ion-card-title": HTMLIonCardTitleElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-card-title": JSXElements.IonCardTitleAttributes; + } + } + namespace JSXElements { + export interface IonCardTitleAttributes extends HTMLAttributes { + color?: string; + mode?: 'ios' | 'md'; + } + } +} + + +import { + Card as IonCard +} from './components/card/card'; + +declare global { + interface HTMLIonCardElement extends IonCard, HTMLStencilElement { + } + var HTMLIonCardElement: { + prototype: HTMLIonCardElement; + new (): HTMLIonCardElement; + }; + interface HTMLElementTagNameMap { + "ion-card": HTMLIonCardElement; + } + interface ElementTagNameMap { + "ion-card": HTMLIonCardElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-card": JSXElements.IonCardAttributes; + } + } + namespace JSXElements { + export interface IonCardAttributes extends HTMLAttributes { + color?: string; + mode?: 'ios' | 'md'; + } + } +} + + +import { + Checkbox as IonCheckbox +} from './components/checkbox/checkbox'; + +declare global { + interface HTMLIonCheckboxElement extends IonCheckbox, HTMLStencilElement { + } + var HTMLIonCheckboxElement: { + prototype: HTMLIonCheckboxElement; + new (): HTMLIonCheckboxElement; + }; + interface HTMLElementTagNameMap { + "ion-checkbox": HTMLIonCheckboxElement; + } + interface ElementTagNameMap { + "ion-checkbox": HTMLIonCheckboxElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-checkbox": JSXElements.IonCheckboxAttributes; + } + } + namespace JSXElements { + export interface IonCheckboxAttributes extends HTMLAttributes { + checked?: boolean; + color?: string; + disabled?: boolean; + mode?: 'ios' | 'md'; + name?: string; + value?: string; + } + } +} + + +import { + ChipButton as IonChipButton +} from './components/chip-button/chip-button'; + +declare global { + interface HTMLIonChipButtonElement extends IonChipButton, HTMLStencilElement { + } + var HTMLIonChipButtonElement: { + prototype: HTMLIonChipButtonElement; + new (): HTMLIonChipButtonElement; + }; + interface HTMLElementTagNameMap { + "ion-chip-button": HTMLIonChipButtonElement; + } + interface ElementTagNameMap { + "ion-chip-button": HTMLIonChipButtonElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-chip-button": JSXElements.IonChipButtonAttributes; + } + } + namespace JSXElements { + export interface IonChipButtonAttributes extends HTMLAttributes { + color?: string; + disabled?: boolean; + fill?: string; + href?: string; + mode?: 'ios' | 'md'; + } + } +} + + +import { + Chip as IonChip +} from './components/chip/chip'; + +declare global { + interface HTMLIonChipElement extends IonChip, HTMLStencilElement { + } + var HTMLIonChipElement: { + prototype: HTMLIonChipElement; + new (): HTMLIonChipElement; + }; + interface HTMLElementTagNameMap { + "ion-chip": HTMLIonChipElement; + } + interface ElementTagNameMap { + "ion-chip": HTMLIonChipElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-chip": JSXElements.IonChipAttributes; + } + } + namespace JSXElements { + export interface IonChipAttributes extends HTMLAttributes { + color?: string; + mode?: 'ios' | 'md'; + } + } +} + + +import { + Col as IonCol +} from './components/col/col'; + +declare global { + interface HTMLIonColElement extends IonCol, HTMLStencilElement { + } + var HTMLIonColElement: { + prototype: HTMLIonColElement; + new (): HTMLIonColElement; + }; + interface HTMLElementTagNameMap { + "ion-col": HTMLIonColElement; + } + interface ElementTagNameMap { + "ion-col": HTMLIonColElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-col": JSXElements.IonColAttributes; + } + } + namespace JSXElements { + export interface IonColAttributes extends HTMLAttributes { + + } + } +} + + +import { + Content as IonContent +} from './components/content/content'; + +declare global { + interface HTMLIonContentElement extends IonContent, HTMLStencilElement { + } + var HTMLIonContentElement: { + prototype: HTMLIonContentElement; + new (): HTMLIonContentElement; + }; + interface HTMLElementTagNameMap { + "ion-content": HTMLIonContentElement; + } + interface ElementTagNameMap { + "ion-content": HTMLIonContentElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-content": JSXElements.IonContentAttributes; + } + } + namespace JSXElements { + export interface IonContentAttributes extends HTMLAttributes { + fullscreen?: boolean; + ionScroll?: Function; + ionScrollEnd?: Function; + ionScrollStart?: Function; + } + } +} + + +import { + CordovaPlatform as IonCordovaPlatform +} from './components/cordova-platform/cordova-platform'; + +declare global { + interface HTMLIonCordovaPlatformElement extends IonCordovaPlatform, HTMLStencilElement { + } + var HTMLIonCordovaPlatformElement: { + prototype: HTMLIonCordovaPlatformElement; + new (): HTMLIonCordovaPlatformElement; + }; + interface HTMLElementTagNameMap { + "ion-cordova-platform": HTMLIonCordovaPlatformElement; + } + interface ElementTagNameMap { + "ion-cordova-platform": HTMLIonCordovaPlatformElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-cordova-platform": JSXElements.IonCordovaPlatformAttributes; + } + } + namespace JSXElements { + export interface IonCordovaPlatformAttributes extends HTMLAttributes { + + } + } +} + + +import { + Datetime as IonDatetime +} from './components/datetime/datetime'; + +declare global { + interface HTMLIonDatetimeElement extends IonDatetime, HTMLStencilElement { + } + var HTMLIonDatetimeElement: { + prototype: HTMLIonDatetimeElement; + new (): HTMLIonDatetimeElement; + }; + interface HTMLElementTagNameMap { + "ion-datetime": HTMLIonDatetimeElement; + } + interface ElementTagNameMap { + "ion-datetime": HTMLIonDatetimeElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-datetime": JSXElements.IonDatetimeAttributes; + } + } + namespace JSXElements { + export interface IonDatetimeAttributes extends HTMLAttributes { + cancelText?: string; + dayNames?: string[] | string; + dayShortNames?: string[] | string; + dayValues?: number[] | number | string; + disabled?: boolean; + displayFormat?: string; + doneText?: string; + hourValues?: number[] | number | string; + max?: string; + min?: string; + minuteValues?: number[] | number | string; + monthNames?: string[] | string; + monthShortNames?: string[] | string; + monthValues?: number[] | number | string; + pickerFormat?: string; + pickerOptions?: PickerOptions; + placeholder?: string; + value?: string; + yearValues?: number[] | number | string; + } + } +} + + +import { + Events as IonEvents +} from './components/events/events'; + +declare global { + interface HTMLIonEventsElement extends IonEvents, HTMLStencilElement { + } + var HTMLIonEventsElement: { + prototype: HTMLIonEventsElement; + new (): HTMLIonEventsElement; + }; + interface HTMLElementTagNameMap { + "ion-events": HTMLIonEventsElement; + } + interface ElementTagNameMap { + "ion-events": HTMLIonEventsElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-events": JSXElements.IonEventsAttributes; + } + } + namespace JSXElements { + export interface IonEventsAttributes extends HTMLAttributes { + + } + } +} + + +import { + FabButton as IonFabButton +} from './components/fab-button/fab-button'; + +declare global { + interface HTMLIonFabButtonElement extends IonFabButton, HTMLStencilElement { + } + var HTMLIonFabButtonElement: { + prototype: HTMLIonFabButtonElement; + new (): HTMLIonFabButtonElement; + }; + interface HTMLElementTagNameMap { + "ion-fab-button": HTMLIonFabButtonElement; + } + interface ElementTagNameMap { + "ion-fab-button": HTMLIonFabButtonElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-fab-button": JSXElements.IonFabButtonAttributes; + } + } + namespace JSXElements { + export interface IonFabButtonAttributes extends HTMLAttributes { + activated?: boolean; + color?: string; + disabled?: boolean; + href?: string; + mode?: 'ios' | 'md'; + show?: boolean; + toggleActive?: Function; + translucent?: boolean; + } + } +} + + +import { + FabList as IonFabList +} from './components/fab-list/fab-list'; + +declare global { + interface HTMLIonFabListElement extends IonFabList, HTMLStencilElement { + } + var HTMLIonFabListElement: { + prototype: HTMLIonFabListElement; + new (): HTMLIonFabListElement; + }; + interface HTMLElementTagNameMap { + "ion-fab-list": HTMLIonFabListElement; + } + interface ElementTagNameMap { + "ion-fab-list": HTMLIonFabListElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-fab-list": JSXElements.IonFabListAttributes; + } + } + namespace JSXElements { + export interface IonFabListAttributes extends HTMLAttributes { + activated?: boolean; + } + } +} + + +import { + Fab as IonFab +} from './components/fab/fab'; + +declare global { + interface HTMLIonFabElement extends IonFab, HTMLStencilElement { + } + var HTMLIonFabElement: { + prototype: HTMLIonFabElement; + new (): HTMLIonFabElement; + }; + interface HTMLElementTagNameMap { + "ion-fab": HTMLIonFabElement; + } + interface ElementTagNameMap { + "ion-fab": HTMLIonFabElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-fab": JSXElements.IonFabAttributes; + } + } + namespace JSXElements { + export interface IonFabAttributes extends HTMLAttributes { + + } + } +} + + +import { + Footer as IonFooter +} from './components/footer/footer'; + +declare global { + interface HTMLIonFooterElement extends IonFooter, HTMLStencilElement { + } + var HTMLIonFooterElement: { + prototype: HTMLIonFooterElement; + new (): HTMLIonFooterElement; + }; + interface HTMLElementTagNameMap { + "ion-footer": HTMLIonFooterElement; + } + interface ElementTagNameMap { + "ion-footer": HTMLIonFooterElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-footer": JSXElements.IonFooterAttributes; + } + } + namespace JSXElements { + export interface IonFooterAttributes extends HTMLAttributes { + translucent?: boolean; + } + } +} + + +import { + Gesture as IonGesture +} from './components/gesture/gesture'; + +declare global { + interface HTMLIonGestureElement extends IonGesture, HTMLStencilElement { + } + var HTMLIonGestureElement: { + prototype: HTMLIonGestureElement; + new (): HTMLIonGestureElement; + }; + interface HTMLElementTagNameMap { + "ion-gesture": HTMLIonGestureElement; + } + interface ElementTagNameMap { + "ion-gesture": HTMLIonGestureElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-gesture": JSXElements.IonGestureAttributes; + } + } + namespace JSXElements { + export interface IonGestureAttributes extends HTMLAttributes { + attachTo?: ElementRef; + autoBlockAll?: boolean; + block?: string; + canStart?: GestureCallback; + direction?: string; + disabled?: boolean; + disableScroll?: boolean; + gestureName?: string; + gesturePriority?: number; + maxAngle?: number; + notCaptured?: GestureCallback; + onEnd?: GestureCallback; + onMove?: GestureCallback; + onPress?: GestureCallback; + onStart?: GestureCallback; + onWillStart?: (_: GestureDetail) => Promise; + passive?: boolean; + threshold?: number; + type?: string; + } + } +} + + +import { + Grid as IonGrid +} from './components/grid/grid'; + +declare global { + interface HTMLIonGridElement extends IonGrid, HTMLStencilElement { + } + var HTMLIonGridElement: { + prototype: HTMLIonGridElement; + new (): HTMLIonGridElement; + }; + interface HTMLElementTagNameMap { + "ion-grid": HTMLIonGridElement; + } + interface ElementTagNameMap { + "ion-grid": HTMLIonGridElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-grid": JSXElements.IonGridAttributes; + } + } + namespace JSXElements { + export interface IonGridAttributes extends HTMLAttributes { + + } + } +} + + +import { + Header as IonHeader +} from './components/header/header'; + +declare global { + interface HTMLIonHeaderElement extends IonHeader, HTMLStencilElement { + } + var HTMLIonHeaderElement: { + prototype: HTMLIonHeaderElement; + new (): HTMLIonHeaderElement; + }; + interface HTMLElementTagNameMap { + "ion-header": HTMLIonHeaderElement; + } + interface ElementTagNameMap { + "ion-header": HTMLIonHeaderElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-header": JSXElements.IonHeaderAttributes; + } + } + namespace JSXElements { + export interface IonHeaderAttributes extends HTMLAttributes { + translucent?: boolean; + } + } +} + + +import { + InfiniteScrollContent as IonInfiniteScrollContent +} from './components/infinite-scroll-content/infinite-scroll-content'; + +declare global { + interface HTMLIonInfiniteScrollContentElement extends IonInfiniteScrollContent, HTMLStencilElement { + } + var HTMLIonInfiniteScrollContentElement: { + prototype: HTMLIonInfiniteScrollContentElement; + new (): HTMLIonInfiniteScrollContentElement; + }; + interface HTMLElementTagNameMap { + "ion-infinite-scroll-content": HTMLIonInfiniteScrollContentElement; + } + interface ElementTagNameMap { + "ion-infinite-scroll-content": HTMLIonInfiniteScrollContentElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-infinite-scroll-content": JSXElements.IonInfiniteScrollContentAttributes; + } + } + namespace JSXElements { + export interface IonInfiniteScrollContentAttributes extends HTMLAttributes { + loadingSpinner?: string; + loadingText?: string; + } + } +} + + +import { + InfiniteScroll as IonInfiniteScroll +} from './components/infinite-scroll/infinite-scroll'; + +declare global { + interface HTMLIonInfiniteScrollElement extends IonInfiniteScroll, HTMLStencilElement { + } + var HTMLIonInfiniteScrollElement: { + prototype: HTMLIonInfiniteScrollElement; + new (): HTMLIonInfiniteScrollElement; + }; + interface HTMLElementTagNameMap { + "ion-infinite-scroll": HTMLIonInfiniteScrollElement; + } + interface ElementTagNameMap { + "ion-infinite-scroll": HTMLIonInfiniteScrollElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-infinite-scroll": JSXElements.IonInfiniteScrollAttributes; + } + } + namespace JSXElements { + export interface IonInfiniteScrollAttributes extends HTMLAttributes { + disabled?: boolean; + position?: string; + threshold?: string; + } + } +} + + +import { + Input as IonInput +} from './components/input/input'; + +declare global { + interface HTMLIonInputElement extends IonInput, HTMLStencilElement { + } + var HTMLIonInputElement: { + prototype: HTMLIonInputElement; + new (): HTMLIonInputElement; + }; + interface HTMLElementTagNameMap { + "ion-input": HTMLIonInputElement; + } + interface ElementTagNameMap { + "ion-input": HTMLIonInputElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-input": JSXElements.IonInputAttributes; + } + } + namespace JSXElements { + export interface IonInputAttributes extends HTMLAttributes { + accept?: string; + autocapitalize?: string; + autocomplete?: string; + autocorrect?: string; + autofocus?: boolean; + checked?: boolean; + clearInput?: boolean; + clearOnEdit?: boolean; + debounce?: number; + disabled?: boolean; + inputmode?: string; + max?: string; + maxlength?: number; + min?: string; + minlength?: number; + multiple?: boolean; + name?: string; + pattern?: string; + placeholder?: string; + readonly?: boolean; + required?: boolean; + results?: number; + size?: number; + spellcheck?: boolean; + step?: string; + type?: string; + value?: string; + } + } +} + + +import { + ItemDivider as IonItemDivider +} from './components/item-divider/item-divider'; + +declare global { + interface HTMLIonItemDividerElement extends IonItemDivider, HTMLStencilElement { + } + var HTMLIonItemDividerElement: { + prototype: HTMLIonItemDividerElement; + new (): HTMLIonItemDividerElement; + }; + interface HTMLElementTagNameMap { + "ion-item-divider": HTMLIonItemDividerElement; + } + interface ElementTagNameMap { + "ion-item-divider": HTMLIonItemDividerElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-item-divider": JSXElements.IonItemDividerAttributes; + } + } + namespace JSXElements { + export interface IonItemDividerAttributes extends HTMLAttributes { + color?: string; + mode?: 'ios' | 'md'; + } + } +} + + +import { + ItemGroup as IonItemGroup +} from './components/item-group/item-group'; + +declare global { + interface HTMLIonItemGroupElement extends IonItemGroup, HTMLStencilElement { + } + var HTMLIonItemGroupElement: { + prototype: HTMLIonItemGroupElement; + new (): HTMLIonItemGroupElement; + }; + interface HTMLElementTagNameMap { + "ion-item-group": HTMLIonItemGroupElement; + } + interface ElementTagNameMap { + "ion-item-group": HTMLIonItemGroupElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-item-group": JSXElements.IonItemGroupAttributes; + } + } + namespace JSXElements { + export interface IonItemGroupAttributes extends HTMLAttributes { + + } + } +} + + +import { + ItemOption as IonItemOption +} from './components/item-option/item-option'; + +declare global { + interface HTMLIonItemOptionElement extends IonItemOption, HTMLStencilElement { + } + var HTMLIonItemOptionElement: { + prototype: HTMLIonItemOptionElement; + new (): HTMLIonItemOptionElement; + }; + interface HTMLElementTagNameMap { + "ion-item-option": HTMLIonItemOptionElement; + } + interface ElementTagNameMap { + "ion-item-option": HTMLIonItemOptionElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-item-option": JSXElements.IonItemOptionAttributes; + } + } + namespace JSXElements { + export interface IonItemOptionAttributes extends HTMLAttributes { + color?: string; + disabled?: boolean; + href?: string; + mode?: 'ios' | 'md'; + } + } +} + + +import { + ItemOptions as IonItemOptions +} from './components/item-options/item-options'; + +declare global { + interface HTMLIonItemOptionsElement extends IonItemOptions, HTMLStencilElement { + } + var HTMLIonItemOptionsElement: { + prototype: HTMLIonItemOptionsElement; + new (): HTMLIonItemOptionsElement; + }; + interface HTMLElementTagNameMap { + "ion-item-options": HTMLIonItemOptionsElement; + } + interface ElementTagNameMap { + "ion-item-options": HTMLIonItemOptionsElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-item-options": JSXElements.IonItemOptionsAttributes; + } + } + namespace JSXElements { + export interface IonItemOptionsAttributes extends HTMLAttributes { + side?: Side; + } + } +} + + +import { + ItemSliding as IonItemSliding +} from './components/item-sliding/item-sliding'; + +declare global { + interface HTMLIonItemSlidingElement extends IonItemSliding, HTMLStencilElement { + } + var HTMLIonItemSlidingElement: { + prototype: HTMLIonItemSlidingElement; + new (): HTMLIonItemSlidingElement; + }; + interface HTMLElementTagNameMap { + "ion-item-sliding": HTMLIonItemSlidingElement; + } + interface ElementTagNameMap { + "ion-item-sliding": HTMLIonItemSlidingElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-item-sliding": JSXElements.IonItemSlidingAttributes; + } + } + namespace JSXElements { + export interface IonItemSlidingAttributes extends HTMLAttributes { + + } + } +} + + +import { + Item as IonItem +} from './components/item/item'; + +declare global { + interface HTMLIonItemElement extends IonItem, HTMLStencilElement { + } + var HTMLIonItemElement: { + prototype: HTMLIonItemElement; + new (): HTMLIonItemElement; + }; + interface HTMLElementTagNameMap { + "ion-item": HTMLIonItemElement; + } + interface ElementTagNameMap { + "ion-item": HTMLIonItemElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-item": JSXElements.IonItemAttributes; + } + } + namespace JSXElements { + export interface IonItemAttributes extends HTMLAttributes { + color?: string; + href?: string; + mode?: 'ios' | 'md'; + onclick?: (this: HTMLElement, ev: MouseEvent) => any; + tappable?: boolean; + } + } +} + + +import { + KeyboardController as IonKeyboardController +} from './components/keyboard-controller/keyboard-controller'; + +declare global { + interface HTMLIonKeyboardControllerElement extends IonKeyboardController, HTMLStencilElement { + } + var HTMLIonKeyboardControllerElement: { + prototype: HTMLIonKeyboardControllerElement; + new (): HTMLIonKeyboardControllerElement; + }; + interface HTMLElementTagNameMap { + "ion-keyboard-controller": HTMLIonKeyboardControllerElement; + } + interface ElementTagNameMap { + "ion-keyboard-controller": HTMLIonKeyboardControllerElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-keyboard-controller": JSXElements.IonKeyboardControllerAttributes; + } + } + namespace JSXElements { + export interface IonKeyboardControllerAttributes extends HTMLAttributes { + + } + } +} + + +import { + Label as IonLabel +} from './components/label/label'; + +declare global { + interface HTMLIonLabelElement extends IonLabel, HTMLStencilElement { + } + var HTMLIonLabelElement: { + prototype: HTMLIonLabelElement; + new (): HTMLIonLabelElement; + }; + interface HTMLElementTagNameMap { + "ion-label": HTMLIonLabelElement; + } + interface ElementTagNameMap { + "ion-label": HTMLIonLabelElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-label": JSXElements.IonLabelAttributes; + } + } + namespace JSXElements { + export interface IonLabelAttributes extends HTMLAttributes { + color?: string; + fixed?: boolean; + floating?: boolean; + mode?: 'ios' | 'md'; + stacked?: boolean; + } + } +} + + +import { + ListHeader as IonListHeader +} from './components/list-header/list-header'; + +declare global { + interface HTMLIonListHeaderElement extends IonListHeader, HTMLStencilElement { + } + var HTMLIonListHeaderElement: { + prototype: HTMLIonListHeaderElement; + new (): HTMLIonListHeaderElement; + }; + interface HTMLElementTagNameMap { + "ion-list-header": HTMLIonListHeaderElement; + } + interface ElementTagNameMap { + "ion-list-header": HTMLIonListHeaderElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-list-header": JSXElements.IonListHeaderAttributes; + } + } + namespace JSXElements { + export interface IonListHeaderAttributes extends HTMLAttributes { + color?: string; + mode?: 'ios' | 'md'; + } + } +} + + +import { + List as IonList +} from './components/list/list'; + +declare global { + interface HTMLIonListElement extends IonList, HTMLStencilElement { + } + var HTMLIonListElement: { + prototype: HTMLIonListElement; + new (): HTMLIonListElement; + }; + interface HTMLElementTagNameMap { + "ion-list": HTMLIonListElement; + } + interface ElementTagNameMap { + "ion-list": HTMLIonListElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-list": JSXElements.IonListAttributes; + } + } + namespace JSXElements { + export interface IonListAttributes extends HTMLAttributes { + + } + } +} + + +import { + LoadingController as IonLoadingController +} from './components/loading-controller/loading-controller'; + +declare global { + interface HTMLIonLoadingControllerElement extends IonLoadingController, HTMLStencilElement { + } + var HTMLIonLoadingControllerElement: { + prototype: HTMLIonLoadingControllerElement; + new (): HTMLIonLoadingControllerElement; + }; + interface HTMLElementTagNameMap { + "ion-loading-controller": HTMLIonLoadingControllerElement; + } + interface ElementTagNameMap { + "ion-loading-controller": HTMLIonLoadingControllerElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-loading-controller": JSXElements.IonLoadingControllerAttributes; + } + } + namespace JSXElements { + export interface IonLoadingControllerAttributes extends HTMLAttributes { + + } + } +} + + +import { + Loading as IonLoading +} from './components/loading/loading'; + +declare global { + interface HTMLIonLoadingElement extends IonLoading, HTMLStencilElement { + } + var HTMLIonLoadingElement: { + prototype: HTMLIonLoadingElement; + new (): HTMLIonLoadingElement; + }; + interface HTMLElementTagNameMap { + "ion-loading": HTMLIonLoadingElement; + } + interface ElementTagNameMap { + "ion-loading": HTMLIonLoadingElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-loading": JSXElements.IonLoadingAttributes; + } + } + namespace JSXElements { + export interface IonLoadingAttributes extends HTMLAttributes { + content?: string; + cssClass?: string; + dismissOnPageChange?: boolean; + duration?: number; + enterAnimation?: AnimationBuilder; + leaveAnimation?: AnimationBuilder; + showBackdrop?: boolean; + spinner?: string; + translucent?: boolean; + willAnimate?: boolean; + } + } +} + + +import { + MenuController as IonMenuController +} from './components/menu-controller/menu-controller'; + +declare global { + interface HTMLIonMenuControllerElement extends IonMenuController, HTMLStencilElement { + } + var HTMLIonMenuControllerElement: { + prototype: HTMLIonMenuControllerElement; + new (): HTMLIonMenuControllerElement; + }; + interface HTMLElementTagNameMap { + "ion-menu-controller": HTMLIonMenuControllerElement; + } + interface ElementTagNameMap { + "ion-menu-controller": HTMLIonMenuControllerElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-menu-controller": JSXElements.IonMenuControllerAttributes; + } + } + namespace JSXElements { + export interface IonMenuControllerAttributes extends HTMLAttributes { + + } + } +} + + +import { + MenuToggle as IonMenuToggle +} from './components/menu-toggle/menu-toggle'; + +declare global { + interface HTMLIonMenuToggleElement extends IonMenuToggle, HTMLStencilElement { + } + var HTMLIonMenuToggleElement: { + prototype: HTMLIonMenuToggleElement; + new (): HTMLIonMenuToggleElement; + }; + interface HTMLElementTagNameMap { + "ion-menu-toggle": HTMLIonMenuToggleElement; + } + interface ElementTagNameMap { + "ion-menu-toggle": HTMLIonMenuToggleElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-menu-toggle": JSXElements.IonMenuToggleAttributes; + } + } + namespace JSXElements { + export interface IonMenuToggleAttributes extends HTMLAttributes { + menu?: string; + } + } +} + + +import { + Menu as IonMenu +} from './components/menu/menu'; + +declare global { + interface HTMLIonMenuElement extends IonMenu, HTMLStencilElement { + } + var HTMLIonMenuElement: { + prototype: HTMLIonMenuElement; + new (): HTMLIonMenuElement; + }; + interface HTMLElementTagNameMap { + "ion-menu": HTMLIonMenuElement; + } + interface ElementTagNameMap { + "ion-menu": HTMLIonMenuElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-menu": JSXElements.IonMenuAttributes; + } + } + namespace JSXElements { + export interface IonMenuAttributes extends HTMLAttributes { + content?: string; + disabled?: boolean; + maxEdgeStart?: number; + menuId?: string; + persistent?: boolean; + side?: Side; + swipeEnabled?: boolean; + type?: string; + } + } +} + + +import { + ModalController as IonModalController +} from './components/modal-controller/modal-controller'; + +declare global { + interface HTMLIonModalControllerElement extends IonModalController, HTMLStencilElement { + } + var HTMLIonModalControllerElement: { + prototype: HTMLIonModalControllerElement; + new (): HTMLIonModalControllerElement; + }; + interface HTMLElementTagNameMap { + "ion-modal-controller": HTMLIonModalControllerElement; + } + interface ElementTagNameMap { + "ion-modal-controller": HTMLIonModalControllerElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-modal-controller": JSXElements.IonModalControllerAttributes; + } + } + namespace JSXElements { + export interface IonModalControllerAttributes extends HTMLAttributes { + + } + } +} + + +import { + Modal as IonModal +} from './components/modal/modal'; + +declare global { + interface HTMLIonModalElement extends IonModal, HTMLStencilElement { + } + var HTMLIonModalElement: { + prototype: HTMLIonModalElement; + new (): HTMLIonModalElement; + }; + interface HTMLElementTagNameMap { + "ion-modal": HTMLIonModalElement; + } + interface ElementTagNameMap { + "ion-modal": HTMLIonModalElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-modal": JSXElements.IonModalAttributes; + } + } + namespace JSXElements { + export interface IonModalAttributes extends HTMLAttributes { + color?: string; + component?: any; + cssClass?: string; + data?: any; + delegate?: FrameworkDelegate; + enableBackdropDismiss?: boolean; + enterAnimation?: AnimationBuilder; + leaveAnimation?: AnimationBuilder; + modalId?: number; + mode?: 'ios' | 'md'; + showBackdrop?: boolean; + willAnimate?: boolean; + } + } +} + + +import { + NavPop as IonNavPop +} from './components/nav-pop/nav-pop'; + +declare global { + interface HTMLIonNavPopElement extends IonNavPop, HTMLStencilElement { + } + var HTMLIonNavPopElement: { + prototype: HTMLIonNavPopElement; + new (): HTMLIonNavPopElement; + }; + interface HTMLElementTagNameMap { + "ion-nav-pop": HTMLIonNavPopElement; + } + interface ElementTagNameMap { + "ion-nav-pop": HTMLIonNavPopElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-nav-pop": JSXElements.IonNavPopAttributes; + } + } + namespace JSXElements { + export interface IonNavPopAttributes extends HTMLAttributes { + + } + } +} + + +import { + Nav as IonNav +} from './components/nav/nav'; + +declare global { + interface HTMLIonNavElement extends IonNav, HTMLStencilElement { + } + var HTMLIonNavElement: { + prototype: HTMLIonNavElement; + new (): HTMLIonNavElement; + }; + interface HTMLElementTagNameMap { + "ion-nav": HTMLIonNavElement; + } + interface ElementTagNameMap { + "ion-nav": HTMLIonNavElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-nav": JSXElements.IonNavAttributes; + } + } + namespace JSXElements { + export interface IonNavAttributes extends HTMLAttributes { + delegate?: FrameworkDelegate; + lazy?: boolean; + mode?: string; + root?: any; + swipeBackEnabled?: boolean; + useUrls?: boolean; + } + } +} + + +import { + Note as IonNote +} from './components/note/note'; + +declare global { + interface HTMLIonNoteElement extends IonNote, HTMLStencilElement { + } + var HTMLIonNoteElement: { + prototype: HTMLIonNoteElement; + new (): HTMLIonNoteElement; + }; + interface HTMLElementTagNameMap { + "ion-note": HTMLIonNoteElement; + } + interface ElementTagNameMap { + "ion-note": HTMLIonNoteElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-note": JSXElements.IonNoteAttributes; + } + } + namespace JSXElements { + export interface IonNoteAttributes extends HTMLAttributes { + color?: string; + mode?: 'ios' | 'md'; + } + } +} + + +import { + Page as IonPage +} from './components/page/page'; + +declare global { + interface HTMLIonPageElement extends IonPage, HTMLStencilElement { + } + var HTMLIonPageElement: { + prototype: HTMLIonPageElement; + new (): HTMLIonPageElement; + }; + interface HTMLElementTagNameMap { + "ion-page": HTMLIonPageElement; + } + interface ElementTagNameMap { + "ion-page": HTMLIonPageElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-page": JSXElements.IonPageAttributes; + } + } + namespace JSXElements { + export interface IonPageAttributes extends HTMLAttributes { + + } + } +} + + +import { + PickerColumnCmp as IonPickerColumn +} from './components/picker-column/picker-column'; + +declare global { + interface HTMLIonPickerColumnElement extends IonPickerColumn, HTMLStencilElement { + } + var HTMLIonPickerColumnElement: { + prototype: HTMLIonPickerColumnElement; + new (): HTMLIonPickerColumnElement; + }; + interface HTMLElementTagNameMap { + "ion-picker-column": HTMLIonPickerColumnElement; + } + interface ElementTagNameMap { + "ion-picker-column": HTMLIonPickerColumnElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-picker-column": JSXElements.IonPickerColumnAttributes; + } + } + namespace JSXElements { + export interface IonPickerColumnAttributes extends HTMLAttributes { + col?: PickerColumn; + } + } +} + + +import { + PickerController as IonPickerController +} from './components/picker-controller/picker-controller'; + +declare global { + interface HTMLIonPickerControllerElement extends IonPickerController, HTMLStencilElement { + } + var HTMLIonPickerControllerElement: { + prototype: HTMLIonPickerControllerElement; + new (): HTMLIonPickerControllerElement; + }; + interface HTMLElementTagNameMap { + "ion-picker-controller": HTMLIonPickerControllerElement; + } + interface ElementTagNameMap { + "ion-picker-controller": HTMLIonPickerControllerElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-picker-controller": JSXElements.IonPickerControllerAttributes; + } + } + namespace JSXElements { + export interface IonPickerControllerAttributes extends HTMLAttributes { + + } + } +} + + +import { + Picker as IonPicker +} from './components/picker/picker'; + +declare global { + interface HTMLIonPickerElement extends IonPicker, HTMLStencilElement { + } + var HTMLIonPickerElement: { + prototype: HTMLIonPickerElement; + new (): HTMLIonPickerElement; + }; + interface HTMLElementTagNameMap { + "ion-picker": HTMLIonPickerElement; + } + interface ElementTagNameMap { + "ion-picker": HTMLIonPickerElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-picker": JSXElements.IonPickerAttributes; + } + } + namespace JSXElements { + export interface IonPickerAttributes extends HTMLAttributes { + buttons?: PickerButton[]; + columns?: PickerColumn[]; + content?: string; + cssClass?: string; + dismissOnPageChange?: boolean; + duration?: number; + enableBackdropDismiss?: boolean; + enterAnimation?: AnimationBuilder; + leaveAnimation?: AnimationBuilder; + pickerId?: number; + showBackdrop?: boolean; + willAnimate?: boolean; + } + } +} + + +import { + PopoverController as IonPopoverController +} from './components/popover-controller/popover-controller'; + +declare global { + interface HTMLIonPopoverControllerElement extends IonPopoverController, HTMLStencilElement { + } + var HTMLIonPopoverControllerElement: { + prototype: HTMLIonPopoverControllerElement; + new (): HTMLIonPopoverControllerElement; + }; + interface HTMLElementTagNameMap { + "ion-popover-controller": HTMLIonPopoverControllerElement; + } + interface ElementTagNameMap { + "ion-popover-controller": HTMLIonPopoverControllerElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-popover-controller": JSXElements.IonPopoverControllerAttributes; + } + } + namespace JSXElements { + export interface IonPopoverControllerAttributes extends HTMLAttributes { + + } + } +} + + +import { + Popover as IonPopover +} from './components/popover/popover'; + +declare global { + interface HTMLIonPopoverElement extends IonPopover, HTMLStencilElement { + } + var HTMLIonPopoverElement: { + prototype: HTMLIonPopoverElement; + new (): HTMLIonPopoverElement; + }; + interface HTMLElementTagNameMap { + "ion-popover": HTMLIonPopoverElement; + } + interface ElementTagNameMap { + "ion-popover": HTMLIonPopoverElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-popover": JSXElements.IonPopoverAttributes; + } + } + namespace JSXElements { + export interface IonPopoverAttributes extends HTMLAttributes { + color?: string; + component?: string; + cssClass?: string; + data?: any; + delegate?: FrameworkDelegate; + enableBackdropDismiss?: boolean; + enterAnimation?: AnimationBuilder; + ev?: Event; + leaveAnimation?: AnimationBuilder; + mode?: 'ios' | 'md'; + popoverId?: number; + showBackdrop?: boolean; + translucent?: boolean; + willAnimate?: boolean; + } + } +} + + +import { + RadioGroup as IonRadioGroup +} from './components/radio-group/radio-group'; + +declare global { + interface HTMLIonRadioGroupElement extends IonRadioGroup, HTMLStencilElement { + } + var HTMLIonRadioGroupElement: { + prototype: HTMLIonRadioGroupElement; + new (): HTMLIonRadioGroupElement; + }; + interface HTMLElementTagNameMap { + "ion-radio-group": HTMLIonRadioGroupElement; + } + interface ElementTagNameMap { + "ion-radio-group": HTMLIonRadioGroupElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-radio-group": JSXElements.IonRadioGroupAttributes; + } + } + namespace JSXElements { + export interface IonRadioGroupAttributes extends HTMLAttributes { + allowEmptySelection?: boolean; + disabled?: boolean; + name?: string; + value?: string; + } + } +} + + +import { + Radio as IonRadio +} from './components/radio/radio'; + +declare global { + interface HTMLIonRadioElement extends IonRadio, HTMLStencilElement { + } + var HTMLIonRadioElement: { + prototype: HTMLIonRadioElement; + new (): HTMLIonRadioElement; + }; + interface HTMLElementTagNameMap { + "ion-radio": HTMLIonRadioElement; + } + interface ElementTagNameMap { + "ion-radio": HTMLIonRadioElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-radio": JSXElements.IonRadioAttributes; + } + } + namespace JSXElements { + export interface IonRadioAttributes extends HTMLAttributes { + checked?: boolean; + color?: string; + disabled?: boolean; + mode?: 'ios' | 'md'; + name?: string; + value?: string; + } + } +} + + +import { + RangeKnob as IonRangeKnob +} from './components/range-knob/range-knob'; + +declare global { + interface HTMLIonRangeKnobElement extends IonRangeKnob, HTMLStencilElement { + } + var HTMLIonRangeKnobElement: { + prototype: HTMLIonRangeKnobElement; + new (): HTMLIonRangeKnobElement; + }; + interface HTMLElementTagNameMap { + "ion-range-knob": HTMLIonRangeKnobElement; + } + interface ElementTagNameMap { + "ion-range-knob": HTMLIonRangeKnobElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-range-knob": JSXElements.IonRangeKnobAttributes; + } + } + namespace JSXElements { + export interface IonRangeKnobAttributes extends HTMLAttributes { + disabled?: boolean; + knob?: string; + labelId?: string; + max?: number; + min?: number; + pin?: boolean; + pressed?: boolean; + ratio?: number; + val?: number; + } + } +} + + +import { + Range as IonRange +} from './components/range/range'; + +declare global { + interface HTMLIonRangeElement extends IonRange, HTMLStencilElement { + } + var HTMLIonRangeElement: { + prototype: HTMLIonRangeElement; + new (): HTMLIonRangeElement; + }; + interface HTMLElementTagNameMap { + "ion-range": HTMLIonRangeElement; + } + interface ElementTagNameMap { + "ion-range": HTMLIonRangeElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-range": JSXElements.IonRangeAttributes; + } + } + namespace JSXElements { + export interface IonRangeAttributes extends HTMLAttributes { + color?: string; + debounce?: number; + disabled?: boolean; + dualKnobs?: boolean; + max?: number; + min?: number; + mode?: 'ios' | 'md'; + pin?: boolean; + snaps?: boolean; + step?: number; + value?: any; + } + } +} + + +import { + RefresherContent as IonRefresherContent +} from './components/refresher-content/refresher-content'; + +declare global { + interface HTMLIonRefresherContentElement extends IonRefresherContent, HTMLStencilElement { + } + var HTMLIonRefresherContentElement: { + prototype: HTMLIonRefresherContentElement; + new (): HTMLIonRefresherContentElement; + }; + interface HTMLElementTagNameMap { + "ion-refresher-content": HTMLIonRefresherContentElement; + } + interface ElementTagNameMap { + "ion-refresher-content": HTMLIonRefresherContentElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-refresher-content": JSXElements.IonRefresherContentAttributes; + } + } + namespace JSXElements { + export interface IonRefresherContentAttributes extends HTMLAttributes { + pullingIcon?: string; + pullingText?: string; + refreshingSpinner?: string; + refreshingText?: string; + } + } +} + + +import { + Refresher as IonRefresher +} from './components/refresher/refresher'; + +declare global { + interface HTMLIonRefresherElement extends IonRefresher, HTMLStencilElement { + } + var HTMLIonRefresherElement: { + prototype: HTMLIonRefresherElement; + new (): HTMLIonRefresherElement; + }; + interface HTMLElementTagNameMap { + "ion-refresher": HTMLIonRefresherElement; + } + interface ElementTagNameMap { + "ion-refresher": HTMLIonRefresherElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-refresher": JSXElements.IonRefresherAttributes; + } + } + namespace JSXElements { + export interface IonRefresherAttributes extends HTMLAttributes { + closeDuration?: string; + disabled?: boolean; + pullMax?: any; + pullMin?: number; + snapbackDuration?: string; + } + } +} + + +import { + ReorderGroup as IonReorderGroup +} from './components/reorder-group/reorder-group'; + +declare global { + interface HTMLIonReorderGroupElement extends IonReorderGroup, HTMLStencilElement { + } + var HTMLIonReorderGroupElement: { + prototype: HTMLIonReorderGroupElement; + new (): HTMLIonReorderGroupElement; + }; + interface HTMLElementTagNameMap { + "ion-reorder-group": HTMLIonReorderGroupElement; + } + interface ElementTagNameMap { + "ion-reorder-group": HTMLIonReorderGroupElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-reorder-group": JSXElements.IonReorderGroupAttributes; + } + } + namespace JSXElements { + export interface IonReorderGroupAttributes extends HTMLAttributes { + disabled?: boolean; + } + } +} + + +import { + Reorder as IonReorder +} from './components/reorder/reorder'; + +declare global { + interface HTMLIonReorderElement extends IonReorder, HTMLStencilElement { + } + var HTMLIonReorderElement: { + prototype: HTMLIonReorderElement; + new (): HTMLIonReorderElement; + }; + interface HTMLElementTagNameMap { + "ion-reorder": HTMLIonReorderElement; + } + interface ElementTagNameMap { + "ion-reorder": HTMLIonReorderElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-reorder": JSXElements.IonReorderAttributes; + } + } + namespace JSXElements { + export interface IonReorderAttributes extends HTMLAttributes { + + } + } +} + + +import { + RippleEffect as IonRippleEffect +} from './components/ripple-effect/ripple-effect'; + +declare global { + interface HTMLIonRippleEffectElement extends IonRippleEffect, HTMLStencilElement { + } + var HTMLIonRippleEffectElement: { + prototype: HTMLIonRippleEffectElement; + new (): HTMLIonRippleEffectElement; + }; + interface HTMLElementTagNameMap { + "ion-ripple-effect": HTMLIonRippleEffectElement; + } + interface ElementTagNameMap { + "ion-ripple-effect": HTMLIonRippleEffectElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-ripple-effect": JSXElements.IonRippleEffectAttributes; + } + } + namespace JSXElements { + export interface IonRippleEffectAttributes extends HTMLAttributes { + useTapClick?: boolean; + } + } +} + + +import { + RouteLink as IonRouteLink +} from './components/route-link/route-link'; + +declare global { + interface HTMLIonRouteLinkElement extends IonRouteLink, HTMLStencilElement { + } + var HTMLIonRouteLinkElement: { + prototype: HTMLIonRouteLinkElement; + new (): HTMLIonRouteLinkElement; + }; + interface HTMLElementTagNameMap { + "ion-route-link": HTMLIonRouteLinkElement; + } + interface ElementTagNameMap { + "ion-route-link": HTMLIonRouteLinkElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-route-link": JSXElements.IonRouteLinkAttributes; + } + } + namespace JSXElements { + export interface IonRouteLinkAttributes extends HTMLAttributes { + router?: any; + url?: string; + } + } +} + + +import { + Route as IonRoute +} from './components/route/route'; + +declare global { + interface HTMLIonRouteElement extends IonRoute, HTMLStencilElement { + } + var HTMLIonRouteElement: { + prototype: HTMLIonRouteElement; + new (): HTMLIonRouteElement; + }; + interface HTMLElementTagNameMap { + "ion-route": HTMLIonRouteElement; + } + interface ElementTagNameMap { + "ion-route": HTMLIonRouteElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-route": JSXElements.IonRouteAttributes; + } + } + namespace JSXElements { + export interface IonRouteAttributes extends HTMLAttributes { + component?: string; + path?: string; + props?: any; + } + } +} + + +import { + Router as IonRouter +} from './components/router/router'; + +declare global { +<<<<<<< Updated upstream + interface HTMLIonRouterControllerElement extends IonRouterController, HTMLStencilElement { +======= + interface HTMLIonRouterElement extends IonRouter, HTMLElement { +>>>>>>> Stashed changes + } + var HTMLIonRouterElement: { + prototype: HTMLIonRouterElement; + new (): HTMLIonRouterElement; + }; + interface HTMLElementTagNameMap { + "ion-router": HTMLIonRouterElement; + } + interface ElementTagNameMap { + "ion-router": HTMLIonRouterElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-router": JSXElements.IonRouterAttributes; + } + } + namespace JSXElements { + export interface IonRouterAttributes extends HTMLAttributes { + base?: string; + useHash?: boolean; + } + } +} + + +import { + Row as IonRow +} from './components/row/row'; + +declare global { + interface HTMLIonRowElement extends IonRow, HTMLStencilElement { + } + var HTMLIonRowElement: { + prototype: HTMLIonRowElement; + new (): HTMLIonRowElement; + }; + interface HTMLElementTagNameMap { + "ion-row": HTMLIonRowElement; + } + interface ElementTagNameMap { + "ion-row": HTMLIonRowElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-row": JSXElements.IonRowAttributes; + } + } + namespace JSXElements { + export interface IonRowAttributes extends HTMLAttributes { + + } + } +} + + +import { + Scroll as IonScroll +} from './components/scroll/scroll'; + +declare global { + interface HTMLIonScrollElement extends IonScroll, HTMLStencilElement { + } + var HTMLIonScrollElement: { + prototype: HTMLIonScrollElement; + new (): HTMLIonScrollElement; + }; + interface HTMLElementTagNameMap { + "ion-scroll": HTMLIonScrollElement; + } + interface ElementTagNameMap { + "ion-scroll": HTMLIonScrollElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-scroll": JSXElements.IonScrollAttributes; + } + } + namespace JSXElements { + export interface IonScrollAttributes extends HTMLAttributes { + disabled?: boolean; + onionScroll?: ScrollCallback; + onionScrollEnd?: ScrollCallback; + onionScrollStart?: ScrollCallback; + } + } +} + + +import { + Searchbar as IonSearchbar +} from './components/searchbar/searchbar'; + +declare global { + interface HTMLIonSearchbarElement extends IonSearchbar, HTMLStencilElement { + } + var HTMLIonSearchbarElement: { + prototype: HTMLIonSearchbarElement; + new (): HTMLIonSearchbarElement; + }; + interface HTMLElementTagNameMap { + "ion-searchbar": HTMLIonSearchbarElement; + } + interface ElementTagNameMap { + "ion-searchbar": HTMLIonSearchbarElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-searchbar": JSXElements.IonSearchbarAttributes; + } + } + namespace JSXElements { + export interface IonSearchbarAttributes extends HTMLAttributes { + animated?: boolean; + autocomplete?: string; + autocorrect?: string; + cancelButtonText?: string; + color?: string; + debounce?: number; + mode?: 'ios' | 'md'; + placeholder?: string; + showCancelButton?: boolean; + spellcheck?: boolean; + type?: string; + value?: string; + } + } +} + + +import { + SegmentButton as IonSegmentButton +} from './components/segment-button/segment-button'; + +declare global { + interface HTMLIonSegmentButtonElement extends IonSegmentButton, HTMLStencilElement { + } + var HTMLIonSegmentButtonElement: { + prototype: HTMLIonSegmentButtonElement; + new (): HTMLIonSegmentButtonElement; + }; + interface HTMLElementTagNameMap { + "ion-segment-button": HTMLIonSegmentButtonElement; + } + interface ElementTagNameMap { + "ion-segment-button": HTMLIonSegmentButtonElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-segment-button": JSXElements.IonSegmentButtonAttributes; + } + } + namespace JSXElements { + export interface IonSegmentButtonAttributes extends HTMLAttributes { + activated?: boolean; + checked?: boolean; + color?: string; + disabled?: boolean; + href?: string; + mode?: 'ios' | 'md'; + value?: string; + } + } +} + + +import { + Segment as IonSegment +} from './components/segment/segment'; + +declare global { + interface HTMLIonSegmentElement extends IonSegment, HTMLStencilElement { + } + var HTMLIonSegmentElement: { + prototype: HTMLIonSegmentElement; + new (): HTMLIonSegmentElement; + }; + interface HTMLElementTagNameMap { + "ion-segment": HTMLIonSegmentElement; + } + interface ElementTagNameMap { + "ion-segment": HTMLIonSegmentElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-segment": JSXElements.IonSegmentAttributes; + } + } + namespace JSXElements { + export interface IonSegmentAttributes extends HTMLAttributes { + color?: string; + disabled?: boolean; + mode?: 'ios' | 'md'; + value?: string; + } + } +} + + +import { + SelectOption as IonSelectOption +} from './components/select-option/select-option'; + +declare global { + interface HTMLIonSelectOptionElement extends IonSelectOption, HTMLStencilElement { + } + var HTMLIonSelectOptionElement: { + prototype: HTMLIonSelectOptionElement; + new (): HTMLIonSelectOptionElement; + }; + interface HTMLElementTagNameMap { + "ion-select-option": HTMLIonSelectOptionElement; + } + interface ElementTagNameMap { + "ion-select-option": HTMLIonSelectOptionElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-select-option": JSXElements.IonSelectOptionAttributes; + } + } + namespace JSXElements { + export interface IonSelectOptionAttributes extends HTMLAttributes { + disabled?: boolean; + selected?: boolean; + value?: string; + } + } +} + + +import { + SelectPopover as IonSelectPopover +} from './components/select-popover/select-popover'; + +declare global { + interface HTMLIonSelectPopoverElement extends IonSelectPopover, HTMLStencilElement { + } + var HTMLIonSelectPopoverElement: { + prototype: HTMLIonSelectPopoverElement; + new (): HTMLIonSelectPopoverElement; + }; + interface HTMLElementTagNameMap { + "ion-select-popover": HTMLIonSelectPopoverElement; + } + interface ElementTagNameMap { + "ion-select-popover": HTMLIonSelectPopoverElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-select-popover": JSXElements.IonSelectPopoverAttributes; + } + } + namespace JSXElements { + export interface IonSelectPopoverAttributes extends HTMLAttributes { + message?: string; + options?: SelectPopoverOption[]; + subTitle?: string; + title?: string; + } + } +} + + +import { + Select as IonSelect +} from './components/select/select'; + +declare global { + interface HTMLIonSelectElement extends IonSelect, HTMLStencilElement { + } + var HTMLIonSelectElement: { + prototype: HTMLIonSelectElement; + new (): HTMLIonSelectElement; + }; + interface HTMLElementTagNameMap { + "ion-select": HTMLIonSelectElement; + } + interface ElementTagNameMap { + "ion-select": HTMLIonSelectElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-select": JSXElements.IonSelectAttributes; + } + } + namespace JSXElements { + export interface IonSelectAttributes extends HTMLAttributes { + cancelText?: string; + disabled?: boolean; + interface?: string; + interfaceOptions?: any; + multiple?: boolean; + name?: string; + okText?: string; + placeholder?: string; + selectedText?: string; + value?: string | string[]; + } + } +} + + +import { + SkeletonText as IonSkeletonText +} from './components/skeleton-text/skeleton-text'; + +declare global { + interface HTMLIonSkeletonTextElement extends IonSkeletonText, HTMLStencilElement { + } + var HTMLIonSkeletonTextElement: { + prototype: HTMLIonSkeletonTextElement; + new (): HTMLIonSkeletonTextElement; + }; + interface HTMLElementTagNameMap { + "ion-skeleton-text": HTMLIonSkeletonTextElement; + } + interface ElementTagNameMap { + "ion-skeleton-text": HTMLIonSkeletonTextElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-skeleton-text": JSXElements.IonSkeletonTextAttributes; + } + } + namespace JSXElements { + export interface IonSkeletonTextAttributes extends HTMLAttributes { + width?: string; + } + } +} + + +import { + Slide as IonSlide +} from './components/slide/slide'; + +declare global { + interface HTMLIonSlideElement extends IonSlide, HTMLStencilElement { + } + var HTMLIonSlideElement: { + prototype: HTMLIonSlideElement; + new (): HTMLIonSlideElement; + }; + interface HTMLElementTagNameMap { + "ion-slide": HTMLIonSlideElement; + } + interface ElementTagNameMap { + "ion-slide": HTMLIonSlideElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-slide": JSXElements.IonSlideAttributes; + } + } + namespace JSXElements { + export interface IonSlideAttributes extends HTMLAttributes { + + } + } +} + + +import { + Slides as IonSlides +} from './components/slides/slides'; + +declare global { + interface HTMLIonSlidesElement extends IonSlides, HTMLStencilElement { + } + var HTMLIonSlidesElement: { + prototype: HTMLIonSlidesElement; + new (): HTMLIonSlidesElement; + }; + interface HTMLElementTagNameMap { + "ion-slides": HTMLIonSlidesElement; + } + interface ElementTagNameMap { + "ion-slides": HTMLIonSlidesElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-slides": JSXElements.IonSlidesAttributes; + } + } + namespace JSXElements { + export interface IonSlidesAttributes extends HTMLAttributes { + options?: any; + pager?: boolean; + } + } +} + + +import { + Spinner as IonSpinner +} from './components/spinner/spinner'; + +declare global { + interface HTMLIonSpinnerElement extends IonSpinner, HTMLStencilElement { + } + var HTMLIonSpinnerElement: { + prototype: HTMLIonSpinnerElement; + new (): HTMLIonSpinnerElement; + }; + interface HTMLElementTagNameMap { + "ion-spinner": HTMLIonSpinnerElement; + } + interface ElementTagNameMap { + "ion-spinner": HTMLIonSpinnerElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-spinner": JSXElements.IonSpinnerAttributes; + } + } + namespace JSXElements { + export interface IonSpinnerAttributes extends HTMLAttributes { + color?: string; + duration?: number; + mode?: 'ios' | 'md'; + name?: string; + paused?: boolean; + } + } +} + + +import { + SplitPane as IonSplitPane +} from './components/split-pane/split-pane'; + +declare global { + interface HTMLIonSplitPaneElement extends IonSplitPane, HTMLStencilElement { + } + var HTMLIonSplitPaneElement: { + prototype: HTMLIonSplitPaneElement; + new (): HTMLIonSplitPaneElement; + }; + interface HTMLElementTagNameMap { + "ion-split-pane": HTMLIonSplitPaneElement; + } + interface ElementTagNameMap { + "ion-split-pane": HTMLIonSplitPaneElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-split-pane": JSXElements.IonSplitPaneAttributes; + } + } + namespace JSXElements { + export interface IonSplitPaneAttributes extends HTMLAttributes { + disabled?: boolean; + when?: string | boolean; + } + } +} + + +import { + StatusTap as IonStatusTap +} from './components/status-tap/status-tap'; + +declare global { + interface HTMLIonStatusTapElement extends IonStatusTap, HTMLStencilElement { + } + var HTMLIonStatusTapElement: { + prototype: HTMLIonStatusTapElement; + new (): HTMLIonStatusTapElement; + }; + interface HTMLElementTagNameMap { + "ion-status-tap": HTMLIonStatusTapElement; + } + interface ElementTagNameMap { + "ion-status-tap": HTMLIonStatusTapElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-status-tap": JSXElements.IonStatusTapAttributes; + } + } + namespace JSXElements { + export interface IonStatusTapAttributes extends HTMLAttributes { + duration?: number; + } + } +} + + +import { + TabButton as IonTabButton +} from './components/tab-button/tab-button'; + +declare global { + interface HTMLIonTabButtonElement extends IonTabButton, HTMLStencilElement { + } + var HTMLIonTabButtonElement: { + prototype: HTMLIonTabButtonElement; + new (): HTMLIonTabButtonElement; + }; + interface HTMLElementTagNameMap { + "ion-tab-button": HTMLIonTabButtonElement; + } + interface ElementTagNameMap { + "ion-tab-button": HTMLIonTabButtonElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-tab-button": JSXElements.IonTabButtonAttributes; + } + } + namespace JSXElements { + export interface IonTabButtonAttributes extends HTMLAttributes { + mode?: 'ios' | 'md'; + selected?: boolean; + tab?: HTMLIonTabElement; + } + } +} + + +import { + Tab as IonTab +} from './components/tab/tab'; + +declare global { + interface HTMLIonTabElement extends IonTab, HTMLStencilElement { + } + var HTMLIonTabElement: { + prototype: HTMLIonTabElement; + new (): HTMLIonTabElement; + }; + interface HTMLElementTagNameMap { + "ion-tab": HTMLIonTabElement; + } + interface ElementTagNameMap { + "ion-tab": HTMLIonTabElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-tab": JSXElements.IonTabAttributes; + } + } + namespace JSXElements { + export interface IonTabAttributes extends HTMLAttributes { + badge?: string; + badgeStyle?: string; + btnId?: string; + disabled?: boolean; + icon?: string; + path?: string; + selected?: boolean; + show?: boolean; + tabsHideOnSubPages?: boolean; + title?: string; + } + } +} + + +import { + Tabbar as IonTabbar +} from './components/tabbar/tabbar'; + +declare global { + interface HTMLIonTabbarElement extends IonTabbar, HTMLStencilElement { + } + var HTMLIonTabbarElement: { + prototype: HTMLIonTabbarElement; + new (): HTMLIonTabbarElement; + }; + interface HTMLElementTagNameMap { + "ion-tabbar": HTMLIonTabbarElement; + } + interface ElementTagNameMap { + "ion-tabbar": HTMLIonTabbarElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-tabbar": JSXElements.IonTabbarAttributes; + } + } + namespace JSXElements { + export interface IonTabbarAttributes extends HTMLAttributes { + highlight?: boolean; + layout?: string; + placement?: string; + scrollable?: Boolean; + selectedTab?: HTMLIonTabElement; + tabs?: HTMLIonTabElement[]; + translucent?: boolean; + } + } +} + + +import { + Tabs as IonTabs +} from './components/tabs/tabs'; + +declare global { + interface HTMLIonTabsElement extends IonTabs, HTMLStencilElement { + } + var HTMLIonTabsElement: { + prototype: HTMLIonTabsElement; + new (): HTMLIonTabsElement; + }; + interface HTMLElementTagNameMap { + "ion-tabs": HTMLIonTabsElement; + } + interface ElementTagNameMap { + "ion-tabs": HTMLIonTabsElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-tabs": JSXElements.IonTabsAttributes; + } + } + namespace JSXElements { + export interface IonTabsAttributes extends HTMLAttributes { + color?: string; + name?: string; + scrollable?: boolean; + tabbarHidden?: boolean; + tabbarHighlight?: boolean; + tabbarLayout?: string; + tabbarPlacement?: string; + translucent?: boolean; + } + } +} + + +import { + TapClick as IonTapClick +} from './components/tap-click/tap-click'; + +declare global { + interface HTMLIonTapClickElement extends IonTapClick, HTMLStencilElement { + } + var HTMLIonTapClickElement: { + prototype: HTMLIonTapClickElement; + new (): HTMLIonTapClickElement; + }; + interface HTMLElementTagNameMap { + "ion-tap-click": HTMLIonTapClickElement; + } + interface ElementTagNameMap { + "ion-tap-click": HTMLIonTapClickElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-tap-click": JSXElements.IonTapClickAttributes; + } + } + namespace JSXElements { + export interface IonTapClickAttributes extends HTMLAttributes { + + } + } +} + + +import { + Text as IonText +} from './components/text/text'; + +declare global { + interface HTMLIonTextElement extends IonText, HTMLStencilElement { + } + var HTMLIonTextElement: { + prototype: HTMLIonTextElement; + new (): HTMLIonTextElement; + }; + interface HTMLElementTagNameMap { + "ion-text": HTMLIonTextElement; + } + interface ElementTagNameMap { + "ion-text": HTMLIonTextElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-text": JSXElements.IonTextAttributes; + } + } + namespace JSXElements { + export interface IonTextAttributes extends HTMLAttributes { + color?: string; + mode?: 'ios' | 'md'; + } + } +} + + +import { + Textarea as IonTextarea +} from './components/textarea/textarea'; + +declare global { + interface HTMLIonTextareaElement extends IonTextarea, HTMLStencilElement { + } + var HTMLIonTextareaElement: { + prototype: HTMLIonTextareaElement; + new (): HTMLIonTextareaElement; + }; + interface HTMLElementTagNameMap { + "ion-textarea": HTMLIonTextareaElement; + } + interface ElementTagNameMap { + "ion-textarea": HTMLIonTextareaElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-textarea": JSXElements.IonTextareaAttributes; + } + } + namespace JSXElements { + export interface IonTextareaAttributes extends HTMLAttributes { + autocapitalize?: string; + autocomplete?: string; + autofocus?: boolean; + clearOnEdit?: boolean; + cols?: number; + debounce?: number; + disabled?: boolean; + maxlength?: number; + minlength?: number; + name?: string; + placeholder?: string; + readonly?: boolean; + required?: boolean; + rows?: number; + spellcheck?: boolean; + value?: string; + wrap?: string; + } + } +} + + +import { + Thumbnail as IonThumbnail +} from './components/thumbnail/thumbnail'; + +declare global { + interface HTMLIonThumbnailElement extends IonThumbnail, HTMLStencilElement { + } + var HTMLIonThumbnailElement: { + prototype: HTMLIonThumbnailElement; + new (): HTMLIonThumbnailElement; + }; + interface HTMLElementTagNameMap { + "ion-thumbnail": HTMLIonThumbnailElement; + } + interface ElementTagNameMap { + "ion-thumbnail": HTMLIonThumbnailElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-thumbnail": JSXElements.IonThumbnailAttributes; + } + } + namespace JSXElements { + export interface IonThumbnailAttributes extends HTMLAttributes { + + } + } +} + + +import { + ToolbarTitle as IonTitle +} from './components/title/title'; + +declare global { + interface HTMLIonTitleElement extends IonTitle, HTMLStencilElement { + } + var HTMLIonTitleElement: { + prototype: HTMLIonTitleElement; + new (): HTMLIonTitleElement; + }; + interface HTMLElementTagNameMap { + "ion-title": HTMLIonTitleElement; + } + interface ElementTagNameMap { + "ion-title": HTMLIonTitleElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-title": JSXElements.IonTitleAttributes; + } + } + namespace JSXElements { + export interface IonTitleAttributes extends HTMLAttributes { + + } + } +} + + +import { + ToastController as IonToastController +} from './components/toast-controller/toast-controller'; + +declare global { + interface HTMLIonToastControllerElement extends IonToastController, HTMLStencilElement { + } + var HTMLIonToastControllerElement: { + prototype: HTMLIonToastControllerElement; + new (): HTMLIonToastControllerElement; + }; + interface HTMLElementTagNameMap { + "ion-toast-controller": HTMLIonToastControllerElement; + } + interface ElementTagNameMap { + "ion-toast-controller": HTMLIonToastControllerElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-toast-controller": JSXElements.IonToastControllerAttributes; + } + } + namespace JSXElements { + export interface IonToastControllerAttributes extends HTMLAttributes { + + } + } +} + + +import { + Toast as IonToast +} from './components/toast/toast'; + +declare global { + interface HTMLIonToastElement extends IonToast, HTMLStencilElement { + } + var HTMLIonToastElement: { + prototype: HTMLIonToastElement; + new (): HTMLIonToastElement; + }; + interface HTMLElementTagNameMap { + "ion-toast": HTMLIonToastElement; + } + interface ElementTagNameMap { + "ion-toast": HTMLIonToastElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-toast": JSXElements.IonToastAttributes; + } + } + namespace JSXElements { + export interface IonToastAttributes extends HTMLAttributes { + closeButtonText?: string; + cssClass?: string; + dismissOnPageChange?: boolean; + duration?: number; + enterAnimation?: AnimationBuilder; + leaveAnimation?: AnimationBuilder; + message?: string; + position?: string; + showCloseButton?: boolean; + toastId?: number; + translucent?: boolean; + willAnimate?: boolean; + } + } +} + + +import { + Toggle as IonToggle +} from './components/toggle/toggle'; + +declare global { + interface HTMLIonToggleElement extends IonToggle, HTMLStencilElement { + } + var HTMLIonToggleElement: { + prototype: HTMLIonToggleElement; + new (): HTMLIonToggleElement; + }; + interface HTMLElementTagNameMap { + "ion-toggle": HTMLIonToggleElement; + } + interface ElementTagNameMap { + "ion-toggle": HTMLIonToggleElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-toggle": JSXElements.IonToggleAttributes; + } + } + namespace JSXElements { + export interface IonToggleAttributes extends HTMLAttributes { + checked?: boolean; + color?: string; + disabled?: boolean; + mode?: 'ios' | 'md'; + name?: string; + value?: string; + } + } +} + + +import { + Toolbar as IonToolbar +} from './components/toolbar/toolbar'; + +declare global { + interface HTMLIonToolbarElement extends IonToolbar, HTMLStencilElement { + } + var HTMLIonToolbarElement: { + prototype: HTMLIonToolbarElement; + new (): HTMLIonToolbarElement; + }; + interface HTMLElementTagNameMap { + "ion-toolbar": HTMLIonToolbarElement; + } + interface ElementTagNameMap { + "ion-toolbar": HTMLIonToolbarElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-toolbar": JSXElements.IonToolbarAttributes; + } + } + namespace JSXElements { + export interface IonToolbarAttributes extends HTMLAttributes { + color?: string; + mode?: 'ios' | 'md'; + translucent?: boolean; + } + } +} + + +import { + VirtualScroll as IonVirtualScroll +} from './components/virtual-scroll/virtual-scroll'; + +declare global { + interface HTMLIonVirtualScrollElement extends IonVirtualScroll, HTMLStencilElement { + } + var HTMLIonVirtualScrollElement: { + prototype: HTMLIonVirtualScrollElement; + new (): HTMLIonVirtualScrollElement; + }; + interface HTMLElementTagNameMap { + "ion-virtual-scroll": HTMLIonVirtualScrollElement; + } + interface ElementTagNameMap { + "ion-virtual-scroll": HTMLIonVirtualScrollElement; + } + namespace JSX { + interface IntrinsicElements { + "ion-virtual-scroll": JSXElements.IonVirtualScrollAttributes; + } + } + namespace JSXElements { + export interface IonVirtualScrollAttributes extends HTMLAttributes { + approxFooterHeight?: number; + approxHeaderHeight?: number; + approxItemHeight?: number; + domRender?: DomRenderFn; + footerFn?: HeaderFn; + headerFn?: HeaderFn; + itemHeight?: ItemHeightFn; + itemRender?: ItemRenderFn; + items?: any[]; + nodeHeight?: NodeHeightFn; + } + } +} + +declare global { namespace JSX { interface StencilJSX {} } } diff --git a/packages/core/src/components/nav/nav-utils.ts b/packages/core/src/components/nav/nav-utils.ts index e5fa65a43d..516b890b75 100644 --- a/packages/core/src/components/nav/nav-utils.ts +++ b/packages/core/src/components/nav/nav-utils.ts @@ -1,7 +1,13 @@ import { Transition } from './nav-interfaces'; -import { Animation, AnimationOptions, Config, Nav, RouterEntry, TransitionBuilder, ViewController } from '../../index'; +import { Animation, AnimationOptions, Config, Nav, TransitionBuilder, ViewController } from '../../index'; import { isDef } from '../../utils/helpers'; +export enum State { + New, + INITIALIZED, + ATTACHED, + DESTROYED, +} export const STATE_NEW = 1; export const STATE_INITIALIZED = 2; export const STATE_ATTACHED = 3; @@ -189,8 +195,4 @@ export function getNextNavId() { return navControllerIds++; } -export function resolveRoute(nav: Nav, component: string): RouterEntry { - return nav.routes.find(r => r.id === component); -} - let navControllerIds = NAV_ID_START; diff --git a/packages/core/src/components/nav/nav.tsx b/packages/core/src/components/nav/nav.tsx index 09258877f5..1683cc8abe 100644 --- a/packages/core/src/components/nav/nav.tsx +++ b/packages/core/src/components/nav/nav.tsx @@ -7,11 +7,10 @@ import { Config, FrameworkDelegate, NavOptions, + NavOutlet, NavResult, - NavState, PublicNav, PublicViewController, - RouterEntries, Transition, TransitionInstruction, } from '../../index'; @@ -35,7 +34,6 @@ import { getPreviousImpl, getViews, isViewController, - resolveRoute, setZIndex, toggleHidden, transitionFactory @@ -63,16 +61,14 @@ const urlMap = new Map(); tag: 'ion-nav', styleUrl: 'nav.scss' }) -export class Nav implements PublicNav { +export class Nav implements PublicNav, NavOutlet { @Element() element: HTMLElement; @Event() navInit: EventEmitter; @Event() ionNavChanged: EventEmitter; - useRouter: boolean; navId: number; init = false; - routes: RouterEntries = []; parent: Nav; views: ViewController[] = []; transitioning?: boolean; @@ -96,17 +92,12 @@ export class Nav implements PublicNav { this.navId = getNextNavId(); } - componentWillLoad() { - this.routes = Array.from(this.element.querySelectorAll('ion-route')) - .map(child => child.getRoute()); - } - componentDidLoad() { if (this.init) { return; } this.init = true; - if (!this.useRouter || !this.lazy) { + if (!this.lazy) { componentDidLoadImpl(this); } } @@ -198,15 +189,8 @@ export class Nav implements PublicNav { return getLastView(this); } - @Method() - getState(): NavState { - assert(this.useRouter, 'routing is disabled'); - return getState(this); - } - @Method() setRouteId(id: string, _: any = {}): Promise { - assert(this.useRouter, 'routing is disabled'); const active = this.getActive(); if (active && active.component === id) { return Promise.resolve(); @@ -215,9 +199,21 @@ export class Nav implements PublicNav { } @Method() - getRoutes(): RouterEntries { - assert(this.useRouter, 'routing is disabled'); - return this.routes; + getRouteId(): string | null { + const element = this.getContentElement(); + if (element) { + return element.tagName; + } + return null; + } + + @Method() + getContentElement(): HTMLElement { + const active = getActiveImpl(this); + if (active) { + active.element; + } + return null; } @Method() @@ -333,23 +329,6 @@ export class Nav implements PublicNav { } } -export function getState(nav: Nav): NavState { - const active = getActiveImpl(nav); - if (!active) { - return null; - } - const component = active.component; - const route = resolveRoute(nav, component); - if (!route) { - console.error('cant reverse route by component', component); - return null; - } - return { - path: route.path, - focusNode: active.element - }; -} - export function componentDidLoadImpl(nav: Nav) { nav.navInit.emit(); if (nav.root) { @@ -1145,7 +1124,7 @@ export function convertViewsToViewControllers(pairs: ComponentDataPair[]): ViewC }); } -export function convertComponentToViewController(nav: Nav, ti: TransitionInstruction): ViewController[] { +export function convertComponentToViewController(_: Nav, ti: TransitionInstruction): ViewController[] { if (ti.insertViews) { assert(ti.insertViews.length > 0, 'length can not be zero'); const viewControllers = convertViewsToViewControllers(ti.insertViews); @@ -1161,9 +1140,6 @@ export function convertComponentToViewController(nav: Nav, ti: TransitionInstruc if (viewController.state === STATE_DESTROYED) { throw new Error('The view has already been destroyed'); } - if (nav.useRouter && !resolveRoute(nav, viewController.component)) { - throw new Error('Route not specified for ' + viewController.component); - } } return viewControllers; } diff --git a/packages/core/src/components/nav/readme.md b/packages/core/src/components/nav/readme.md index 9b21b66b75..912de220a0 100644 --- a/packages/core/src/components/nav/readme.md +++ b/packages/core/src/components/nav/readme.md @@ -27,6 +27,11 @@ string any +#### swipeBackEnabled + +boolean + + #### useUrls boolean @@ -54,6 +59,11 @@ string any +#### swipe-back-enabled + +boolean + + #### use-urls boolean @@ -72,9 +82,6 @@ boolean #### canGoBack() -#### canSwipeBack() - - #### clearTransitionInfoForUrl() @@ -87,16 +94,16 @@ boolean #### getChildNavs() +#### getContentElement() + + #### getId() #### getPrevious() -#### getRoutes() - - -#### getState() +#### getRouteId() #### getTransitionInfoForUrl() diff --git a/packages/core/src/components/nav/test/basic/index.html b/packages/core/src/components/nav/test/basic/index.html index 634ae35350..0a9f8e0415 100644 --- a/packages/core/src/components/nav/test/basic/index.html +++ b/packages/core/src/components/nav/test/basic/index.html @@ -11,18 +11,18 @@ + f:last-of-type { + background: yellow; + } + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/core/src/components/route/readme.md b/packages/core/src/components/route/readme.md index 8192604b9f..aec9f098b8 100644 --- a/packages/core/src/components/route/readme.md +++ b/packages/core/src/components/route/readme.md @@ -39,11 +39,6 @@ string any -## Methods - -#### getRoute() - - ---------------------------------------------- diff --git a/packages/core/src/components/route/route.tsx b/packages/core/src/components/route/route.tsx index ab1606bd75..8ae3d6b60f 100644 --- a/packages/core/src/components/route/route.tsx +++ b/packages/core/src/components/route/route.tsx @@ -1,5 +1,4 @@ -import { Component, Method, Prop } from '@stencil/core'; -import { RouterEntry, parseURL } from '../router-controller/router-utils'; +import { Component, Prop } from '@stencil/core'; @Component({ @@ -11,13 +10,4 @@ export class Route { @Prop() component: string; @Prop() props: any = {}; - @Method() - getRoute(): RouterEntry { - return { - path: this.path, - segments: parseURL(this.path), - id: this.component, - props: this.props - }; - } } diff --git a/packages/core/src/components/router-controller/router-controller.tsx b/packages/core/src/components/router-controller/router-controller.tsx deleted file mode 100644 index 26e27539fe..0000000000 --- a/packages/core/src/components/router-controller/router-controller.tsx +++ /dev/null @@ -1,105 +0,0 @@ -import { Component, Listen, Prop } from '@stencil/core'; -import { RouterSegments, generateURL, parseURL, readNavState, writeNavState } from './router-utils'; -import { Config, DomController } from '../../index'; - - -@Component({ - tag: 'ion-router-controller' -}) -export class RouterController { - - private busy = false; - private enabled = false; - private basePrefix = '#'; - - @Prop({ context: 'config' }) config: Config; - @Prop({ context: 'dom' }) dom: DomController; - - componentDidLoad() { - const enabled = this.enabled = this.config.getBoolean('useRouter', false); - if (enabled) { - const base = document.querySelector('head > base'); - if (base) { - const baseURL = base.getAttribute('href'); - if (baseURL && baseURL.length > 0) { - this.basePrefix = baseURL; - } - } - - this.dom.raf(() => { - console.debug('[OUT] page load -> write nav state'); - this.writeNavStateRoot(); - }); - } - } - - @Listen('window:hashchange') - protected onURLHashChanged() { - if (!this.isBlocked()) { - console.debug('[OUT] hash changed -> write nav state'); - this.writeNavStateRoot(); - } - } - - @Listen('body:ionNavChanged') - protected onNavChanged(ev: CustomEvent) { - if (this.isBlocked()) { - return; - } - - console.debug('[IN] nav changed -> update URL'); - const { stack, pivot } = this.readNavState(); - if (pivot) { - // readNavState() found a pivot that is not initialized - console.debug('[IN] pivot uninitialized -> write partial nav state'); - this.writeNavState(pivot, []); - } - - const isPop = ev.detail.isPop === true; - this.setURL(generateURL(stack), isPop); - } - - private setURL(url: string, isPop: boolean) { - url = this.basePrefix + url; - const history = window.history; - if (isPop) { - history.back(); - history.replaceState(null, null, url); - } else { - history.pushState(null, null, url); - } - } - - private isBlocked(): boolean { - return this.busy || !this.enabled; - } - - private writeNavStateRoot(): Promise { - const node = document.querySelector('ion-app') as HTMLElement; - return this.writeNavState(node, this.readURL()); - } - - private writeNavState(node: any, url: string[]): Promise { - const segments = new RouterSegments(url); - this.busy = true; // prevents reentrance - return writeNavState(node, segments) - .catch(err => console.error(err)) - .then(() => this.busy = false); - } - - private readNavState() { - const root = document.querySelector('ion-app') as HTMLElement; - return readNavState(root); - } - - private isHash() { - return this.basePrefix.length > 0 && this.basePrefix[0] === '#'; - } - - private readURL(): string[] { - const url = this.isHash() - ? window.location.hash.substr(1) - : window.location.pathname; - return parseURL(url); - } -} diff --git a/packages/core/src/components/router-controller/router-utils.ts b/packages/core/src/components/router-controller/router-utils.ts deleted file mode 100644 index 724f36a291..0000000000 --- a/packages/core/src/components/router-controller/router-utils.ts +++ /dev/null @@ -1,183 +0,0 @@ - -export interface NavElement extends HTMLElement { - setRouteId(id: any, data?: any): Promise; - getRoutes(): RouterEntries; - getState(): NavState; - - componentOnReady(): Promise; - componentOnReady(done: (cmp?: HTMLElement) => void): void; -} - -export interface RouterEntry { - path: string; - id: any; - segments?: string[]; - props?: any; -} - -export type RouterEntries = RouterEntry[]; - -export interface NavState { - path: string; - focusNode: HTMLElement; -} - -export class RouterSegments { - constructor( - private segments: string[] - ) {} - - next(): string { - if (this.segments.length > 0) { - return this.segments.shift() as string; - } - return ''; - } -} - -export function writeNavState(root: HTMLElement, segments: RouterSegments): Promise { - const node = breadthFirstSearch(root); - if (!node) { - return Promise.resolve(); - } - return node.componentOnReady() - .then(() => node.getRoutes()) - .then(routes => mustMatchRoute(segments, routes)) - .then(route => node.setRouteId(route.id)) - .then(() => { - const state = node.getState(); - if (!state) { - throw new Error('setRouteId failed?'); - } - writeNavState(state.focusNode, segments); - }); -} - -export function readNavState(node: HTMLElement) { - const stack = []; - let pivot: NavElement | null = null; - let state: NavState; - while (true) { - pivot = breadthFirstSearch(node); - if (pivot) { - state = pivot.getState(); - if (state) { - node = state.focusNode; - stack.push(state); - } else { - break; - } - } else { - break; - } - } - return { - stack: stack, - pivot: pivot - }; -} - -function mustMatchRoute(segments: RouterSegments, routes: RouterEntries) { - const r = matchRoute(segments, routes); - if (!r) { - throw new Error('no route found'); - } - return r; -} - -export function matchRoute(segments: RouterSegments, routes: RouterEntries): RouterEntry | null { - if (!routes) { - return null; - } - let index = 0; - routes = routes.map(initRoute); - let selectedRoute: RouterEntry|null = null; - let ambiguous = false; - let segment: string; - let l: number; - - while (true) { - routes = routes.filter(r => r.segments.length > index); - if (routes.length === 0) { - break; - } - segment = segments.next(); - routes = routes.filter(r => r.segments[index] === segment); - l = routes.length; - if (l === 0) { - selectedRoute = null; - ambiguous = false; - } else { - selectedRoute = routes[0]; - ambiguous = l > 1; - } - index++; - } - if (ambiguous) { - throw new Error('ambiguious match'); - } - return selectedRoute; -} - -export function generateURL(stack: NavState[]): string { - const segments: string[] = []; - for (const state of stack) { - segments.push(...parseURL(state.path)); - } - const path = segments - .filter(s => s.length > 0) - .join('/'); - - return '/' + path; -} - -export function initRoute(route: RouterEntry): RouterEntry { - if (route.segments === undefined || route.segments === null) { - route.segments = parseURL(route.path); - } - return route; -} - -export function parseURL(url: string): string[] { - if (url === null || url === undefined) { - return ['']; - } - const segments = url.split('/') - .map(s => s.trim()) - .filter(s => s.length > 0); - - if (segments.length === 0) { - return ['']; - } else { - return segments; - } -} - -const navs = ['ION-NAV', 'ION-TABS']; -export function breadthFirstSearch(root: HTMLElement): NavElement | null { - if (!root) { - console.error('search root is null'); - return null; - } - // we do a Breadth-first search - // Breadth-first search (BFS) is an algorithm for traversing or searching tree - // or graph data structures.It starts at the tree root(or some arbitrary node of a graph, - // sometimes referred to as a 'search key'[1]) and explores the neighbor nodes - // first, before moving to the next level neighbours. - - const queue = [root]; - let node: HTMLElement | undefined; - while (node = queue.shift()) { - // visit node - if (navs.indexOf(node.tagName) >= 0) { - return node as NavElement; - } - - // queue children - const children = node.children; - for (let i = 0; i < children.length; i++) { - queue.push(children[i] as NavElement); - } - } - return null; -} diff --git a/packages/core/src/components/router-controller/readme.md b/packages/core/src/components/router/readme.md similarity index 56% rename from packages/core/src/components/router-controller/readme.md rename to packages/core/src/components/router/readme.md index 46eebe9f21..5ae07c076a 100644 --- a/packages/core/src/components/router-controller/readme.md +++ b/packages/core/src/components/router/readme.md @@ -5,6 +5,30 @@ +## Properties + +#### base + +string + + +#### useHash + +boolean + + +## Attributes + +#### base + +string + + +#### use-hash + +boolean + + ---------------------------------------------- diff --git a/packages/core/src/components/router/router-utils.ts b/packages/core/src/components/router/router-utils.ts new file mode 100644 index 0000000000..c6d89e805d --- /dev/null +++ b/packages/core/src/components/router/router-utils.ts @@ -0,0 +1,224 @@ +import { StencilElement } from '../../index'; + +export interface NavOutlet { + setRouteId(id: any, data?: any): Promise; + getRouteId(): string; + getContentElement(): HTMLElement | null; +} + +export type NavOutletElement = NavOutlet & StencilElement; + +export interface RouterEntry { + id: any; + path: string[]; + subroutes: RouterEntries; + props?: any; +} + +export type RouterEntries = RouterEntry[]; + +export class RouterSegments { + constructor( + private path: string[] + ) {} + + next(): string { + if (this.path.length > 0) { + return this.path.shift() as string; + } + return ''; + } +} + +export function writeNavState(root: HTMLElement, chain: RouterEntries, index = 0): Promise { + if (index >= chain.length) { + return Promise.resolve(); + } + + const route = chain[index]; + const node = breadthFirstSearch(root); + if (!node) { + return Promise.resolve(); + } + return node.componentOnReady() + .then(() => node.setRouteId(route.id, route.props)) + .then(() => { + const nextEl = node.getContentElement(); + if (nextEl) { + return writeNavState(nextEl, chain, index + 1); + } + return null; + }); +} + +export function readNavState(node: HTMLElement) { + const stack: string[] = []; + let pivot: NavOutlet|null; + while (true) { + pivot = breadthFirstSearch(node); + if (pivot) { + const cmp = pivot.getRouteId(); + if (cmp) { + node = pivot.getContentElement(); + stack.push(cmp.toLowerCase()); + } else { + break; + } + } else { + break; + } + } + return { + stack: stack, + pivot: pivot + }; +} + +export function matchPath(stack: string[], routes: RouterEntries): string[] { + const path: string[] = []; + for (const id of stack) { + const route = routes.find(r => r.id === id); + if (route) { + path.push(...route.path); + routes = route.subroutes; + } else { + break; + } + } + return path; +} + +export function matchRouteChain(path: string[], routes: RouterEntries): RouterEntries { + const chain = []; + const segments = new RouterSegments(path); + while (routes.length > 0) { + const route = matchRoute(segments, routes); + if (!route) { + break; + } + chain.push(route); + routes = route.subroutes; + } + return chain; +} + +export function matchRoute(segments: RouterSegments, routes: RouterEntries): RouterEntry | null { + if (!routes) { + return null; + } + let index = 0; + let selectedRoute: RouterEntry|null = null; + let ambiguous = false; + let segment: string; + let l: number; + + while (true) { + routes = routes.filter(r => r.path.length > index); + if (routes.length === 0) { + break; + } + segment = segments.next(); + routes = routes.filter(r => r.path[index] === segment); + l = routes.length; + if (l === 0) { + selectedRoute = null; + ambiguous = false; + } else { + selectedRoute = routes[0]; + ambiguous = l > 1; + } + index++; + } + if (ambiguous) { + throw new Error('ambiguious match'); + } + return selectedRoute; +} + +export function readRoutes(root: Element): RouterEntries { + return (Array.from(root.children) as HTMLIonRouteElement[]) + .filter(el => el.tagName === 'ION-ROUTE') + .map(el => ({ + path: parsePath(el.path), + id: el.component, + props: el.props, + subroutes: readRoutes(el) + })); +} + +export function generatePath(segments: string[]): string { + const path = segments + .filter(s => s.length > 0) + .join('/'); + + return '/' + path; +} + +export function parsePath(path: string): string[] { + if (path === null || path === undefined) { + return ['']; + } + const segments = path.split('/') + .map(s => s.trim()) + .filter(s => s.length > 0); + + if (segments.length === 0) { + return ['']; + } else { + return segments; + } +} + +const navs = ['ION-NAV', 'ION-TABS']; +export function breadthFirstSearch(root: HTMLElement): NavOutletElement | null { + if (!root) { + console.error('search root is null'); + return null; + } + // we do a Breadth-first search + // Breadth-first search (BFS) is an algorithm for traversing or searching tree + // or graph data structures.It starts at the tree root(or some arbitrary node of a graph, + // sometimes referred to as a 'search key'[1]) and explores the neighbor nodes + // first, before moving to the next level neighbours. + + const queue = [root]; + let node: HTMLElement | undefined; + while (node = queue.shift()) { + // visit node + if (navs.indexOf(node.tagName) >= 0) { + return node as NavOutletElement; + } + + // queue children + const children = node.children; + for (let i = 0; i < children.length; i++) { + queue.push(children[i] as NavOutletElement); + } + } + return null; +} + +export function writePath(history: History, base: string, usePath: boolean, path: string[], isPop: boolean) { + path = [base, ...path]; + let url = generatePath(path); + if (usePath) { + url = '#' + url; + } + if (isPop) { + history.back(); + history.replaceState(null, null, url); + } else { + history.pushState(null, null, url); + } +} + +export function readPath(loc: Location, base: string, useHash: boolean): string[] | null { + const path = useHash + ? loc.hash.substr(1) + : loc.pathname; + + if (path.startsWith(base)) { + return parsePath(path.slice(base.length)); + } + return null; +} diff --git a/packages/core/src/components/router/router.tsx b/packages/core/src/components/router/router.tsx new file mode 100644 index 0000000000..1c2db9f5f8 --- /dev/null +++ b/packages/core/src/components/router/router.tsx @@ -0,0 +1,91 @@ +import { Component, Element, Listen, Prop } from '@stencil/core'; +import { RouterEntries, matchPath, matchRouteChain, readNavState, readPath, readRoutes, writeNavState, writePath } from './router-utils'; +import { Config, DomController } from '../../index'; + + +@Component({ + tag: 'ion-router' +}) +export class Router { + + private routes: RouterEntries; + private busy = false; + + @Prop({ context: 'config' }) config: Config; + @Prop({ context: 'dom' }) dom: DomController; + + @Prop() base = ''; + @Prop() useHash = true; + + @Element() el: HTMLElement; + + componentDidLoad() { + // read config + this.routes = readRoutes(this.el); + + // perform first write + this.dom.raf(() => { + console.debug('[OUT] page load -> write nav state'); + this.writeNavStateRoot(); + }); + } + + @Listen('window:hashchange') + protected onURLHashChanged() { + if (!this.busy) { + console.debug('[OUT] hash changed -> write nav state'); + this.writeNavStateRoot(); + } + } + + @Listen('body:ionNavChanged') + protected onNavChanged(ev: CustomEvent) { + if (this.busy) { + return; + } + + console.debug('[IN] nav changed -> update URL'); + const { stack, pivot } = this.readNavState(); + if (pivot) { + // readNavState() found a pivot that is not initialized + console.debug('[IN] pivot uninitialized -> write partial nav state'); + this.writeNavState(pivot, []); + } + + const isPop = ev.detail.isPop === true; + const segments = matchPath(stack, this.routes); + this.writePath(segments, isPop); + } + + + private writeNavStateRoot(): Promise { + const node = document.querySelector('ion-app') as HTMLElement; + const currentPath = this.readPath(); + if (currentPath) { + return this.writeNavState(node, currentPath); + } + return Promise.resolve(); + } + + private writeNavState(node: any, path: string[]): Promise { + const chain = matchRouteChain(path, this.routes); + + this.busy = true; + return writeNavState(node, chain) + .catch(err => console.error(err)) + .then(() => this.busy = false); + } + + private readNavState() { + const root = document.querySelector('ion-app') as HTMLElement; + return readNavState(root); + } + + private writePath(path: string[], isPop: boolean) { + writePath(window.history, this.base, this.useHash, path, isPop); + } + + private readPath(): string[] | null { + return readPath(window.location, this.base, this.useHash); + } +} diff --git a/packages/core/src/components/route/test/router-utils.spec.ts b/packages/core/src/components/router/test/router-utils.spec.tsx similarity index 58% rename from packages/core/src/components/route/test/router-utils.spec.ts rename to packages/core/src/components/router/test/router-utils.spec.tsx index dbf7ab7c2e..5caaaa49bd 100644 --- a/packages/core/src/components/route/test/router-utils.spec.ts +++ b/packages/core/src/components/router/test/router-utils.spec.tsx @@ -1,7 +1,7 @@ import { - RouterEntries, RouterEntry, RouterSegments, breadthFirstSearch, - generateURL, initRoute, matchRoute, parseURL -} from '../../router-controller/router-utils'; + RouterEntries, RouterSegments, breadthFirstSearch, + generatePath, matchRoute, parsePath +} from '../router-utils'; describe('RouterSegments', () => { it ('should initialize with empty array', () => { @@ -26,74 +26,74 @@ describe('RouterSegments', () => { describe('parseURL', () => { it('should parse empty path', () => { - expect(parseURL('')).toEqual(['']); + expect(parsePath('')).toEqual(['']); }); it('should parse empty path (2)', () => { - expect(parseURL(' ')).toEqual(['']); + expect(parsePath(' ')).toEqual(['']); }); it('should parse null path', () => { - expect(parseURL(null)).toEqual(['']); + expect(parsePath(null)).toEqual(['']); }); it('should parse undefined path', () => { - expect(parseURL(undefined)).toEqual(['']); + expect(parsePath(undefined)).toEqual(['']); }); it('should parse relative path', () => { - expect(parseURL('path/to/file.js')).toEqual(['path', 'to', 'file.js']); + expect(parsePath('path/to/file.js')).toEqual(['path', 'to', 'file.js']); }); it('should parse absolute path', () => { - expect(parseURL('/path/to/file.js')).toEqual(['path', 'to', 'file.js']); + expect(parsePath('/path/to/file.js')).toEqual(['path', 'to', 'file.js']); }); it('should parse relative path', () => { - expect(parseURL('/PATH///to//file.js//')).toEqual(['PATH', 'to', 'file.js']); + expect(parsePath('/PATH///to//file.js//')).toEqual(['PATH', 'to', 'file.js']); }); }); -describe('initRoute', () => { - it('should initialize empty segments', () => { - const route: RouterEntry = { - id: 'cmp', - path: 'path/to/cmp' - }; - initRoute(route); - expect(route.segments).toEqual(['path', 'to', 'cmp']); - }); +// describe('readRoutes', () => { +// it('should read URL', () => { +// const node = (
+// +// +// +// +// +//
) as any; +// node.children = node.vchildren; - it('should not initialize valid segments', () => { - const route: RouterEntry = { - id: 'cmp', - path: 'path/to/cmp', - segments: [''] - }; - initRoute(route); - expect(route.segments).toEqual(['']); - }); -}); +// expect(readRoutes(node)).toEqual([ +// { path: [''], id: 'hola', subroutes: [] }, +// { path: ['one-page'], id: 'one-page', subroutes: [] }, +// { path: ['secondpage'], id: 'second-page', subroutes: [] }, +// { path: ['5', 'hola'], id: '4', subroutes: [] }, +// { path: ['path', 'to', 'five'], id: '5', subroutes: [] } +// ]); +// }); +// }); describe('matchRoute', () => { it('should match simple route', () => { const seg = new RouterSegments(['path', 'to', 'component']); - const routes = [ - { id: 2, path: 'to' }, - { id: 1, path: 'path' }, - { id: 3, path: 'segment' }, - { id: 4, path: '' }, + const routes: RouterEntries = [ + { id: 2, path: ['to'], subroutes: [] }, + { id: 1, path: ['path'], subroutes: [] }, + { id: 3, path: ['segment'], subroutes: [] }, + { id: 4, path: [''], subroutes: [] }, ]; const match = matchRoute(seg, routes); - expect(match).toEqual({ id: 1, path: 'path', segments: ['path'] }); + expect(match).toEqual({ id: 1, path: ['path'], subroutes: [] }); expect(seg.next()).toEqual('to'); }); it('should match default route', () => { - const routes = [ - { id: 2, path: 'to' }, - { id: 1, path: 'path' }, - { id: 3, path: 'segment' }, - { id: 4, path: '' }, + const routes: RouterEntries = [ + { id: 2, path: ['to'], subroutes: [] }, + { id: 1, path: ['path'], subroutes: [] }, + { id: 3, path: ['segment'], subroutes: [] }, + { id: 4, path: [''], subroutes: [] }, ]; const seg = new RouterSegments(['hola', 'path']); let match = matchRoute(seg, routes); @@ -108,13 +108,12 @@ describe('matchRoute', () => { } }); - it('should not match any route', () => { - const routes = [ - { id: 2, path: 'to/to/to' }, - { id: 1, path: 'adam/manu' }, - { id: 3, path: 'hola/adam' }, - { id: 4, path: '' }, + const routes: RouterEntries = [ + { id: 2, path: ['to', 'to', 'to'], subroutes: [] }, + { id: 1, path: ['adam', 'manu'], subroutes: [] }, + { id: 3, path: ['hola', 'adam'], subroutes: [] }, + { id: 4, path: [''], subroutes: [] }, ]; const seg = new RouterSegments(['hola', 'manu', 'adam']); const match = matchRoute(seg, routes); @@ -130,9 +129,9 @@ describe('matchRoute', () => { }); it('should not match any route (2)', () => { - const routes = [ - { id: 1, path: 'adam/manu' }, - { id: 3, path: 'hola/adam' }, + const routes: RouterEntries = [ + { id: 1, path: ['adam', 'manu'], subroutes: [] }, + { id: 3, path: ['hola', 'adam'], subroutes: [] }, ]; const seg = new RouterSegments(['adam']); expect(matchRoute(seg, routes)).toBeNull(); @@ -141,11 +140,11 @@ describe('matchRoute', () => { }); it ('should match multiple segments', () => { - const routes = [ - { id: 1, path: 'adam/manu' }, - { id: 2, path: 'manu/hello' }, - { id: 3, path: 'hello' }, - { id: 4, path: '' }, + const routes: RouterEntries = [ + { id: 1, path: ['adam', 'manu'], subroutes: [] }, + { id: 2, path: ['manu', 'hello'], subroutes: [] }, + { id: 3, path: ['hello'], subroutes: [] }, + { id: 4, path: [''], subroutes: [] }, ]; const seg = new RouterSegments(['adam', 'manu', 'hello', 'manu', 'hello']); let match = matchRoute(seg, routes); @@ -165,10 +164,10 @@ describe('matchRoute', () => { }); it('should match long multi segments', () => { - const routes = [ - { id: 1, path: 'adam/manu/hello/menu/hello' }, - { id: 2, path: 'adam/manu/hello/menu' }, - { id: 3, path: 'adam/manu' }, + const routes: RouterEntries = [ + { id: 1, path: ['adam', 'manu', 'hello', 'menu', 'hello'], subroutes: [] }, + { id: 2, path: ['adam', 'manu', 'hello', 'menu'], subroutes: [] }, + { id: 3, path: ['adam', 'manu'], subroutes: [] }, ]; const seg = new RouterSegments(['adam', 'manu', 'hello', 'menu', 'hello']); const match = matchRoute(seg, routes); @@ -186,26 +185,26 @@ describe('matchRoute', () => { }); -describe('generateURL', () => { +describe('generatePath', () => { it('should generate an empty URL', () => { - expect(generateURL([])).toEqual('/'); - expect(generateURL([{ path: '' } as any])).toEqual('/'); - expect(generateURL([{ path: '/' } as any])).toEqual('/'); - expect(generateURL([{ path: '//' } as any])).toEqual('/'); - expect(generateURL([{ path: ' ' } as any])).toEqual('/'); + expect(generatePath([])).toEqual('/'); + expect(generatePath([{ path: '' } as any])).toEqual('/'); + expect(generatePath([{ path: '/' } as any])).toEqual('/'); + expect(generatePath([{ path: '//' } as any])).toEqual('/'); + expect(generatePath([{ path: ' ' } as any])).toEqual('/'); }); it('should genenerate a basic url', () => { - const state = [ - { path: '/' }, - { path: '/ ' }, - { path: '' }, - { path: '/path// to/' }, - { path: '/page ' }, - { path: 'number-TWO/' }, - { path: ' / ' } + const stack = [ + '', + '', + '', + 'path/to', + 'page', + 'number-TWO', + '' ]; - expect(generateURL(state as any)).toEqual('/path/to/page/number-TWO'); + expect(generatePath(stack)).toEqual('/path/to/page/number-TWO'); }); }); @@ -234,8 +233,3 @@ describe('breadthFirstSearch', () => { }); }); -// describe('readNavState', () => { -// it('should read state', () => { - -// }); -// }); diff --git a/packages/core/src/components/tabs/readme.md b/packages/core/src/components/tabs/readme.md index 8a69b4c79b..d8376922cb 100644 --- a/packages/core/src/components/tabs/readme.md +++ b/packages/core/src/components/tabs/readme.md @@ -222,9 +222,15 @@ Emitted when the tab changes. #### getByIndex() +#### getContentElement() + + #### getIndex() +#### getRouteId() + + #### getSelected() @@ -234,6 +240,9 @@ Emitted when the tab changes. #### select() +#### setRouteId() + + ---------------------------------------------- diff --git a/packages/core/src/components/tabs/tabs.tsx b/packages/core/src/components/tabs/tabs.tsx index 22a815b14b..ba3aa0ee1e 100644 --- a/packages/core/src/components/tabs/tabs.tsx +++ b/packages/core/src/components/tabs/tabs.tsx @@ -1,5 +1,5 @@ import { Component, Element, Event, EventEmitter, Listen, Method, Prop, State } from '@stencil/core'; -import { Config } from '../../index'; +import { Config, NavOutlet } from '../../index'; @Component({ @@ -9,7 +9,7 @@ import { Config } from '../../index'; md: 'tabs.md.scss' } }) -export class Tabs { +export class Tabs implements NavOutlet { private ids = -1; private tabsId: number = (++tabIds); @@ -134,7 +134,7 @@ export class Tabs { */ @Method() getSelected(): HTMLIonTabElement | undefined { - return this.tabs.find((tab) => tab.selected); + return this.selectedTab; } @Method() @@ -147,30 +147,6 @@ export class Tabs { return this.tabs; } - /*@Method() - getState(): NavState { - const selectedTab = this.getSelected(); - if (!selectedTab) { - return null; - } - return { - path: selectedTab.getPath(), - focusNode: selectedTab - }; - } - - @Method() - getRoutes(): RouterEntries { - const a = this.tabs.map(t => { - return { - path: t.getPath(), - id: t - }; - }); - return a; - } - - @Method() setRouteId(id: any, _: any = {}): Promise { if (this.selectedTab === id) { @@ -178,7 +154,21 @@ export class Tabs { } return this.select(id); } - */ + + + @Method() + getRouteId(): string|null { + if (this.selectedTab) { + return this.selectedTab.tagName; + } + return null; + } + + + @Method() + getContentElement(): HTMLElement { + return this.selectedTab; + } private initTabs() { const tabs = this.tabs = Array.from(this.el.querySelectorAll('ion-tab')); diff --git a/packages/core/src/index.d.ts b/packages/core/src/index.d.ts index ebc3147daf..7aad822e4c 100644 --- a/packages/core/src/index.d.ts +++ b/packages/core/src/index.d.ts @@ -83,8 +83,8 @@ export { ReorderGroup } from './components/reorder-group/reorder-group'; export { RouterEntry, RouterEntries, - NavState, -} from './components/router-controller/router-utils'; + NavOutlet +} from './components/router/router-utils'; export { Row } from './components/row/row'; export { Reorder } from './components/reorder/reorder'; export { Scroll, ScrollCallback, ScrollDetail } from './components/scroll/scroll'; @@ -162,6 +162,9 @@ declare global { namespace JSXElements { export interface DOMAttributes { + // for ion-menu and ion-split-pane + main?: boolean; + padding?: boolean; ['padding-top']?: boolean; ['padding-bottom']?: boolean; diff --git a/packages/core/stencil.config.js b/packages/core/stencil.config.js index 165f7b6604..522396c264 100644 --- a/packages/core/stencil.config.js +++ b/packages/core/stencil.config.js @@ -30,7 +30,7 @@ exports.config = { { components: ['ion-popover', 'ion-popover-controller'] }, { components: ['ion-radio', 'ion-radio-group'] }, { components: ['ion-reorder', 'ion-reorder-group'] }, - { components: ['ion-route', 'ion-router-controller'] }, + { components: ['ion-route', 'ion-router'] }, { components: ['ion-searchbar'] }, { components: ['ion-segment', 'ion-segment-button'] }, { components: ['ion-select', 'ion-select-option', 'ion-select-popover'] },