From b24cc949976c93a422bf294698e5a0b5941d4f8c Mon Sep 17 00:00:00 2001 From: Maria Hutt Date: Mon, 24 Feb 2025 16:34:56 -0800 Subject: [PATCH 01/15] feat(searchbar): add sizes for ionic theme --- core/src/components.d.ts | 8 ++ .../components/searchbar/searchbar.ionic.scss | 95 +++++++++++++------ core/src/components/searchbar/searchbar.tsx | 25 +++++ .../components/searchbar/test/size/index.html | 31 ++++++ packages/angular/src/directives/proxies.ts | 4 +- packages/vue/src/proxies.ts | 1 + 6 files changed, 133 insertions(+), 31 deletions(-) create mode 100644 core/src/components/searchbar/test/size/index.html diff --git a/core/src/components.d.ts b/core/src/components.d.ts index fa663fea9fe..038c7d1f976 100644 --- a/core/src/components.d.ts +++ b/core/src/components.d.ts @@ -3115,6 +3115,10 @@ export namespace Components { * Sets the behavior for the clear button. Defaults to `"focus"`. Setting to `"focus"` shows the clear button on focus if the input is not empty. Setting to `"never"` hides the clear button. Setting to `"always"` shows the clear button regardless of focus state, but only if the input is not empty. */ "showClearButton": 'never' | 'focus' | 'always'; + /** + * Set to `"large"` for a searchbar with an increase in height, or `"medium"` for a searchbar with a medium height. Defaults to `"medium"` for the ionic theme, and `undefined` for all other themes. + */ + "size"?: 'medium' | 'large'; /** * If `true`, enable spellcheck on the input. */ @@ -8522,6 +8526,10 @@ declare namespace LocalJSX { * Sets the behavior for the clear button. Defaults to `"focus"`. Setting to `"focus"` shows the clear button on focus if the input is not empty. Setting to `"never"` hides the clear button. Setting to `"always"` shows the clear button regardless of focus state, but only if the input is not empty. */ "showClearButton"?: 'never' | 'focus' | 'always'; + /** + * Set to `"large"` for a searchbar with an increase in height, or `"medium"` for a searchbar with a medium height. Defaults to `"medium"` for the ionic theme, and `undefined` for all other themes. + */ + "size"?: 'medium' | 'large'; /** * If `true`, enable spellcheck on the input. */ diff --git a/core/src/components/searchbar/searchbar.ionic.scss b/core/src/components/searchbar/searchbar.ionic.scss index 0e009634e94..4e7e694678a 100644 --- a/core/src/components/searchbar/searchbar.ionic.scss +++ b/core/src/components/searchbar/searchbar.ionic.scss @@ -28,9 +28,6 @@ // ----------------------------------------- .searchbar-search-icon { - // Position is based on the size of the search icon. - @include globals.position(globals.$ion-scale-400, null, null, globals.$ion-scale-400); - width: globals.$ion-scale-400; height: globals.$ion-scale-400; } @@ -50,14 +47,7 @@ * the size of the clear icon, * and the gap between the icon and the input. */ - @include globals.padding( - globals.$ion-space-300, - calc(globals.$ion-space-400 + globals.$ion-scale-400 + globals.$ion-space-200), - globals.$ion-space-300, - calc(globals.$ion-space-400 + globals.$ion-scale-400 + globals.$ion-space-200) - ); - - min-height: globals.$ion-scale-1200; + @include globals.padding(globals.$ion-space-300, null); contain: strict; } @@ -66,9 +56,6 @@ // ----------------------------------------- .searchbar-clear-button { - // Position is based on the size of the clear icon. - @include globals.position(globals.$ion-scale-400, globals.$ion-scale-400, null, null); - width: globals.$ion-scale-400; height: globals.$ion-scale-400; @@ -83,14 +70,6 @@ // ----------------------------------------- .searchbar-cancel-button { - /** - * The left edge of the cancel button - * should align with the left edge - * of the back button if the searchbar - * is used in a toolbar. - */ - @include globals.position(0, null, null, 9px); - background-color: transparent; font-size: globals.$ion-font-size-400; @@ -102,7 +81,11 @@ .searchbar-search-icon, .searchbar-clear-button, .searchbar-cancel-button { + @include globals.position(50%, null); + position: absolute; + + transform: translateY(-50%); } // Clear Icon & Cancel Icon @@ -117,13 +100,6 @@ opacity: 1; } -// Searchbar in Toolbar -// ----------------------------------------- - -:host-context(ion-toolbar) { - min-height: globals.$ion-scale-1200; -} - // Searchbar States // -------------------------------------------------- @@ -157,3 +133,64 @@ cursor: default; pointer-events: none; } + +// Searchbar Sizes +// -------------------------------------------------- + +/* Medium */ +:host(.searchbar-size-medium) .searchbar-input { + /** + * Padding start is based on + * desired padding from design, + * the size of the search icon, + * and the gap between the icon and the input. + * + * Padding end is based on + * desired padding from design, + * the size of the clear icon, + * and the gap between the icon and the input. + */ + @include globals.padding-horizontal(calc(globals.$ion-space-400 + globals.$ion-scale-400 + globals.$ion-space-200)); + + min-height: globals.$ion-scale-1200; +} + +:host(.searchbar-size-medium) .searchbar-search-icon, +:host(.searchbar-size-medium) .searchbar-cancel-button { + // Start is based on the desired padding start from design. + @include globals.position-horizontal(globals.$ion-space-400, null); +} + +:host(.searchbar-size-medium) .searchbar-clear-button { + // End is based on the desired padding end from design. + @include globals.position-horizontal(null, globals.$ion-scale-400); +} + +/* Large */ +:host(.searchbar-size-large) .searchbar-input { + /** + * Padding start is based on + * desired padding from design, + * the size of the search icon, + * and the gap between the icon and the input. + * + * Padding end is based on + * desired padding from design, + * the size of the clear icon, + * and the gap between the icon and the input. + */ + @include globals.padding-horizontal(calc(globals.$ion-space-500 + globals.$ion-scale-400 + globals.$ion-space-200)); + + min-height: globals.$ion-scale-1400; +} + +:host(.searchbar-size-large) .searchbar-search-icon, +:host(.searchbar-size-large) .searchbar-cancel-button { + // Start is based on the desired padding start from design. + @include globals.position-horizontal(globals.$ion-space-500, null); +} + +:host(.searchbar-size-large) .searchbar-clear-button { + // End is based on the desired padding end from design. + @include globals.position-horizontal(null, globals.$ion-scale-500); +} diff --git a/core/src/components/searchbar/searchbar.tsx b/core/src/components/searchbar/searchbar.tsx index 868cd067049..d6fbb4473a5 100644 --- a/core/src/components/searchbar/searchbar.tsx +++ b/core/src/components/searchbar/searchbar.tsx @@ -216,6 +216,13 @@ export class Searchbar implements ComponentInterface { */ @Prop({ mutable: true }) value?: string | null = ''; + /** + * Set to `"large"` for a searchbar with an increase in height, + * or `"medium"` for a searchbar with a medium height. + * Defaults to `"medium"` for the ionic theme, and `undefined` for all other themes. + */ + @Prop() size?: 'medium' | 'large'; + /** * Emitted when the `value` of the `ion-searchbar` element has changed. */ @@ -612,6 +619,22 @@ export class Searchbar implements ComponentInterface { return true; } + private getSize(): string | undefined { + const theme = getIonTheme(this); + const { size } = this; + + // TODO(ROU-11678): Remove theme check when sizes are defined for all themes. + if (theme !== 'ionic') { + return undefined; + } + + if (size === undefined) { + return 'medium'; + } + + return size; + } + /** * Get the icon to use for the clear icon. * If an icon is set on the component, use that. @@ -698,6 +721,7 @@ export class Searchbar implements ComponentInterface { const animated = this.animated && config.getBoolean('animated', true); const theme = getIonTheme(this); const shouldShowCancelButton = this.shouldShowCancelButton(); + const size = this.getSize(); const cancelButton = this.showCancelButton !== 'never' && (