feat(input): add clearInputIcon property (#29246)

Issue number: resolves #26974

---------

<!-- Please do not submit updates to dependencies unless it fixes an
issue. -->

<!-- Please try to limit your pull request to one type (bugfix, feature,
etc). Submit multiple pull requests if needed. -->

## What is the current behavior?
<!-- Please describe the current behavior that you are modifying. -->

In https://github.com/ionic-team/ionic-framework/pull/26354 we updated
the clear icon to use an ionicon instead of an hardcoded SVG. This has
made it challenging to customize the icon.

## What is the new behavior?
<!-- Please describe the behavior or changes that are being added by
this PR. -->

- Added `clearInputIcon` property to allow developers to customize the
ionicon used.

## Does this introduce a breaking change?

- [ ] Yes
- [x] No

<!--
  If this introduces a breaking change:
1. Describe the impact and migration path for existing applications
below.
  2. Update the BREAKING.md file with the breaking change.
3. Add "BREAKING CHANGE: [...]" to the commit description when merging.
See
https://github.com/ionic-team/ionic-framework/blob/main/.github/CONTRIBUTING.md#footer
for more information.
-->


## Other information

<!-- Any other information that is important to this PR such as
screenshots of how the component looks before and after the change. -->
This commit is contained in:
Liam DeBeasi
2024-04-02 10:30:33 -04:00
parent 4b79bbef7d
commit 0f5d1c02d2
6 changed files with 37 additions and 4 deletions

View File

@ -92,6 +92,11 @@ export class Input implements ComponentInterface {
*/
@Prop() clearInput = false;
/**
* The icon to use for the clear button. Only applies when `clearInput` is set to `true`.
*/
@Prop() clearInputIcon?: string;
/**
* If `true`, the value will be cleared after focus upon edit. Defaults to `true` when `type` is `"password"`, `false` for all other types.
*/
@ -681,11 +686,13 @@ export class Input implements ComponentInterface {
}
render() {
const { disabled, fill, readonly, shape, inputId, labelPlacement, el, hasFocus } = this;
const { disabled, fill, readonly, shape, inputId, labelPlacement, el, hasFocus, clearInputIcon } = this;
const mode = getIonMode(this);
const value = this.getValue();
const inItem = hostContext('ion-item', this.el);
const shouldRenderHighlight = mode === 'md' && fill !== 'outline' && !inItem;
const defaultClearIcon = mode === 'ios' ? closeCircle : closeSharp;
const clearIconData = clearInputIcon ?? defaultClearIcon;
const hasValue = this.hasValue();
const hasStartEndSlots = el.querySelector('[slot="start"], [slot="end"]') !== null;
@ -784,7 +791,7 @@ export class Input implements ComponentInterface {
}}
onClick={this.clearTextInput}
>
<ion-icon aria-hidden="true" icon={mode === 'ios' ? closeCircle : closeSharp}></ion-icon>
<ion-icon aria-hidden="true" icon={clearIconData}></ion-icon>
</button>
)}
<slot name="end"></slot>

View File

@ -99,3 +99,19 @@ describe('input: label rendering', () => {
expect(labelText.textContent).toBe('Label Prop Text');
});
});
// https://github.com/ionic-team/ionic-framework/issues/26974
describe('input: clear icon', () => {
it('should render custom icon', async () => {
const page = await newSpecPage({
components: [Input],
html: `
<ion-input clear-input-icon="foo" clear-input="true"></ion-input>
`,
});
const icon = page.body.querySelector<HTMLIonIconElement>('ion-input ion-icon')!;
expect(icon.getAttribute('icon')).toBe('foo');
});
});