diff --git a/BREAKING.md b/BREAKING.md
index 9d14348f30a..5cf4e641be8 100644
--- a/BREAKING.md
+++ b/BREAKING.md
@@ -24,6 +24,7 @@ This is a comprehensive list of the breaking changes introduced in the major ver
- [Nav](#version-8x-nav)
- [Picker](#version-8x-picker)
- [Progress bar](#version-8x-progress-bar)
+ - [Radio](#version-8x-radio)
- [Textarea](#version-8x-textarea)
Browser and Platform Support
@@ -175,6 +176,10 @@ For more information on the dynamic font, refer to the [Dynamic Font Scaling doc
For more information on styling toast buttons, refer to the [Toast Theming documentation](https://ionicframework.com/docs/api/toast#theming).
+
Radio
+
+- The `legacy` property and support for the legacy syntax, which involved placing an `ion-radio` inside of an `ion-item` with an `ion-label`, have been removed. For more information on migrating from the legacy radio syntax, refer to the [Radio documentation](https://ionicframework.com/docs/api/radio#migrating-from-legacy-radio-syntax).
+
Textarea
- The `legacy` property and support for the legacy syntax, which involved placing an `ion-textarea` inside of an `ion-item` with an `ion-label`, have been removed. For more information on migrating from the legacy textarea syntax, refer to the [Textarea documentation](https://ionicframework.com/docs/api/textarea#migrating-from-legacy-textarea-syntax).
diff --git a/core/api.txt b/core/api.txt
index 2ac742620f6..c962ee2c2a9 100644
--- a/core/api.txt
+++ b/core/api.txt
@@ -1038,7 +1038,6 @@ ion-radio,prop,color,"danger" | "dark" | "light" | "medium" | "primary" | "secon
ion-radio,prop,disabled,boolean,false,false,false
ion-radio,prop,justify,"end" | "space-between" | "start",'space-between',false,false
ion-radio,prop,labelPlacement,"end" | "fixed" | "stacked" | "start",'start',false,false
-ion-radio,prop,legacy,boolean | undefined,undefined,false,false
ion-radio,prop,mode,"ios" | "md",undefined,false,false
ion-radio,prop,name,string,this.inputId,false,false
ion-radio,prop,value,any,undefined,false,false
diff --git a/core/src/components.d.ts b/core/src/components.d.ts
index 668cb2d85fa..fe7b0030b41 100644
--- a/core/src/components.d.ts
+++ b/core/src/components.d.ts
@@ -2257,10 +2257,6 @@ export namespace Components {
* Where to place the label relative to the radio. `"start"`: The label will appear to the left of the radio in LTR and to the right in RTL. `"end"`: The label will appear to the right of the radio in LTR and to the left in RTL. `"fixed"`: The label has the same behavior as `"start"` except it also has a fixed width. Long text will be truncated with ellipses ("..."). `"stacked"`: The label will appear above the radio regardless of the direction. The alignment of the label can be controlled with the `alignment` property.
*/
"labelPlacement": 'start' | 'end' | 'fixed' | 'stacked';
- /**
- * Set the `legacy` property to `true` to forcibly use the legacy form control markup. Ionic will only opt components in to the modern form markup when they are using either the `aria-label` attribute or the default slot that contains the label text. As a result, the `legacy` property should only be used as an escape hatch when you want to avoid this automatic opt-in behavior. Note that this property will be removed in an upcoming major release of Ionic, and all form components will be opted-in to using the modern form markup.
- */
- "legacy"?: boolean;
/**
* The mode determines which platform styles to use.
*/
@@ -4157,7 +4153,6 @@ declare global {
new (): HTMLIonProgressBarElement;
};
interface HTMLIonRadioElementEventMap {
- "ionStyle": StyleEventDetail;
"ionFocus": void;
"ionBlur": void;
}
@@ -6947,10 +6942,6 @@ declare namespace LocalJSX {
* Where to place the label relative to the radio. `"start"`: The label will appear to the left of the radio in LTR and to the right in RTL. `"end"`: The label will appear to the right of the radio in LTR and to the left in RTL. `"fixed"`: The label has the same behavior as `"start"` except it also has a fixed width. Long text will be truncated with ellipses ("..."). `"stacked"`: The label will appear above the radio regardless of the direction. The alignment of the label can be controlled with the `alignment` property.
*/
"labelPlacement"?: 'start' | 'end' | 'fixed' | 'stacked';
- /**
- * Set the `legacy` property to `true` to forcibly use the legacy form control markup. Ionic will only opt components in to the modern form markup when they are using either the `aria-label` attribute or the default slot that contains the label text. As a result, the `legacy` property should only be used as an escape hatch when you want to avoid this automatic opt-in behavior. Note that this property will be removed in an upcoming major release of Ionic, and all form components will be opted-in to using the modern form markup.
- */
- "legacy"?: boolean;
/**
* The mode determines which platform styles to use.
*/
@@ -6967,10 +6958,6 @@ declare namespace LocalJSX {
* Emitted when the radio button has focus.
*/
"onIonFocus"?: (event: IonRadioCustomEvent) => void;
- /**
- * Emitted when the styles change.
- */
- "onIonStyle"?: (event: IonRadioCustomEvent) => void;
/**
* the value of the radio.
*/
diff --git a/core/src/components/radio-group/test/legacy/basic/index.html b/core/src/components/radio-group/test/legacy/basic/index.html
deleted file mode 100644
index 5b690307e38..00000000000
--- a/core/src/components/radio-group/test/legacy/basic/index.html
+++ /dev/null
@@ -1,56 +0,0 @@
-
-
-
-
- Radio Group - Basic
-
-
-
-
-
-
-
-
-
-
-
-
- Radio Group - Basic
-
-
-
-
-
-
-
- Radio Group Header
-
-
-
- Item 1
-
-
-
-
- Item 2
-
-
-
-
- Item 3
-
-
-
-
- Item 4
-
-
-
-
-
-
-
-
diff --git a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts b/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts
deleted file mode 100644
index 470ce52bcc5..00000000000
--- a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts
+++ /dev/null
@@ -1,163 +0,0 @@
-import { expect } from '@playwright/test';
-import type { Locator } from '@playwright/test';
-import { configs, test } from '@utils/test/playwright';
-import type { E2EPage } from '@utils/test/playwright';
-
-configs().forEach(({ title, screenshot, config }) => {
- test.describe(title('radio-group: basic'), () => {
- test('should not have visual regressions', async ({ page }) => {
- await page.goto(`/src/components/radio-group/test/legacy/basic`, config);
-
- const list = page.locator('ion-list');
-
- await expect(list).toHaveScreenshot(screenshot(`radio-group-diff`));
- });
- });
-});
-
-/**
- * This behavior does not vary across modes/directions.
- */
-configs({ modes: ['ios'], directions: ['ltr'] }).forEach(({ title, config }) => {
- test.describe(title('radio-group: interaction'), () => {
- let radioFixture: RadioFixture;
-
- test.beforeEach(({ page }) => {
- radioFixture = new RadioFixture(page);
- });
-
- test('spacebar should not deselect without allowEmptySelection', async ({ page }) => {
- await page.setContent(
- `
-
-
- One
-
-
-
- `,
- config
- );
-
- await radioFixture.checkRadio('keyboard');
- await radioFixture.expectChecked(true);
- });
-
- test('spacebar should deselect with allowEmptySelection', async ({ page }) => {
- await page.setContent(
- `
-
-
- One
-
-
-
- `,
- config
- );
-
- await radioFixture.checkRadio('keyboard');
- await radioFixture.expectChecked(false);
- });
-
- test('click should not deselect without allowEmptySelection', async ({ page }) => {
- await page.setContent(
- `
-
-
- One
-
-
-
- `,
- config
- );
-
- await radioFixture.checkRadio('mouse');
- await radioFixture.expectChecked(true);
- });
-
- test('click should deselect with allowEmptySelection', async ({ page }) => {
- await page.setContent(
- `
-
-
- One
-
-
-
- `,
- config
- );
-
- await radioFixture.checkRadio('mouse');
- await radioFixture.expectChecked(false);
- });
-
- test('programmatically assigning a value should update the checked radio', async ({ page }) => {
- await page.setContent(
- `
-
-
- Item 1
-
-
-
-
- Item 2
-
-
-
-
- Item 3
-
-
-
- `,
- config
- );
-
- const radioGroup = page.locator('ion-radio-group');
- const radioOne = page.locator('ion-radio[value="1"]');
- const radioTwo = page.locator('ion-radio[value="2"]');
-
- await radioGroup.evaluate((el: HTMLIonRadioGroupElement) => (el.value = '2'));
-
- await page.waitForChanges();
-
- await expect(radioOne).not.toHaveClass(/radio-checked/);
- await expect(radioTwo).toHaveClass(/radio-checked/);
- });
- });
-});
-
-class RadioFixture {
- readonly page: E2EPage;
-
- private radio!: Locator;
-
- constructor(page: E2EPage) {
- this.page = page;
- }
-
- async checkRadio(method: 'keyboard' | 'mouse', selector = 'ion-radio') {
- const { page } = this;
- const radio = (this.radio = page.locator(selector));
-
- if (method === 'keyboard') {
- await radio.focus();
- await page.keyboard.press('Space');
- } else {
- await radio.click();
- }
-
- await page.waitForChanges();
-
- return radio;
- }
-
- async expectChecked(state: boolean) {
- const { radio } = this;
- await expect(radio.locator('input')).toHaveJSProperty('checked', state);
- }
-}
diff --git a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-ios-ltr-Mobile-Chrome-linux.png b/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-ios-ltr-Mobile-Chrome-linux.png
deleted file mode 100644
index eb0f8a78eeb..00000000000
Binary files a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-ios-ltr-Mobile-Chrome-linux.png and /dev/null differ
diff --git a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-ios-ltr-Mobile-Firefox-linux.png b/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-ios-ltr-Mobile-Firefox-linux.png
deleted file mode 100644
index 816de0abe89..00000000000
Binary files a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-ios-ltr-Mobile-Firefox-linux.png and /dev/null differ
diff --git a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-ios-ltr-Mobile-Safari-linux.png b/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-ios-ltr-Mobile-Safari-linux.png
deleted file mode 100644
index 112e95d78b9..00000000000
Binary files a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-ios-ltr-Mobile-Safari-linux.png and /dev/null differ
diff --git a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-ios-rtl-Mobile-Chrome-linux.png b/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-ios-rtl-Mobile-Chrome-linux.png
deleted file mode 100644
index c8ed6eec30a..00000000000
Binary files a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-ios-rtl-Mobile-Chrome-linux.png and /dev/null differ
diff --git a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-ios-rtl-Mobile-Firefox-linux.png b/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-ios-rtl-Mobile-Firefox-linux.png
deleted file mode 100644
index 4b10678d1fc..00000000000
Binary files a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-ios-rtl-Mobile-Firefox-linux.png and /dev/null differ
diff --git a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-ios-rtl-Mobile-Safari-linux.png b/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-ios-rtl-Mobile-Safari-linux.png
deleted file mode 100644
index 7abb3c4e106..00000000000
Binary files a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-ios-rtl-Mobile-Safari-linux.png and /dev/null differ
diff --git a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-md-ltr-Mobile-Chrome-linux.png b/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-md-ltr-Mobile-Chrome-linux.png
deleted file mode 100644
index 5b5c3c81629..00000000000
Binary files a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-md-ltr-Mobile-Chrome-linux.png and /dev/null differ
diff --git a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-md-ltr-Mobile-Firefox-linux.png b/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-md-ltr-Mobile-Firefox-linux.png
deleted file mode 100644
index 64737909dfc..00000000000
Binary files a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-md-ltr-Mobile-Firefox-linux.png and /dev/null differ
diff --git a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-md-ltr-Mobile-Safari-linux.png b/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-md-ltr-Mobile-Safari-linux.png
deleted file mode 100644
index e482a253713..00000000000
Binary files a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-md-ltr-Mobile-Safari-linux.png and /dev/null differ
diff --git a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-md-rtl-Mobile-Chrome-linux.png b/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-md-rtl-Mobile-Chrome-linux.png
deleted file mode 100644
index c6dddca74be..00000000000
Binary files a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-md-rtl-Mobile-Chrome-linux.png and /dev/null differ
diff --git a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-md-rtl-Mobile-Firefox-linux.png b/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-md-rtl-Mobile-Firefox-linux.png
deleted file mode 100644
index 3feeec34a82..00000000000
Binary files a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-md-rtl-Mobile-Firefox-linux.png and /dev/null differ
diff --git a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-md-rtl-Mobile-Safari-linux.png b/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-md-rtl-Mobile-Safari-linux.png
deleted file mode 100644
index d2ba829f7f7..00000000000
Binary files a/core/src/components/radio-group/test/legacy/basic/radio-group.e2e.ts-snapshots/radio-group-diff-md-rtl-Mobile-Safari-linux.png and /dev/null differ
diff --git a/core/src/components/radio-group/test/legacy/form/index.html b/core/src/components/radio-group/test/legacy/form/index.html
deleted file mode 100644
index 159f8c62498..00000000000
--- a/core/src/components/radio-group/test/legacy/form/index.html
+++ /dev/null
@@ -1,114 +0,0 @@
-
-
-
-
- Radio Group - Form
-
-
-
-
-
-
-
-
-
-
-
-
- Radio Group - Form
-
-
-
-
-
-
-
- Value:
-
-
-
-
- Changes:
- 0
-
-
-
-
-
-
-
-
diff --git a/core/src/components/radio-group/test/legacy/form/radio-group.e2e.ts b/core/src/components/radio-group/test/legacy/form/radio-group.e2e.ts
deleted file mode 100644
index 72e3811d1c4..00000000000
--- a/core/src/components/radio-group/test/legacy/form/radio-group.e2e.ts
+++ /dev/null
@@ -1,35 +0,0 @@
-import { expect } from '@playwright/test';
-import { configs, test } from '@utils/test/playwright';
-
-configs({ modes: ['ios'], directions: ['ltr'] }).forEach(({ title, config }) => {
- test.describe(title('radio-group: form'), () => {
- test.beforeEach(async ({ page }) => {
- await page.goto('/src/components/radio-group/test/legacy/form', config);
- });
-
- test('selecting an option should update the value', async ({ page }) => {
- const radioGroup = page.locator('ion-radio-group');
- const ionChange = await page.spyOnEvent('ionChange');
- const griffRadio = page.locator('ion-radio[value="griff"]');
- await expect(radioGroup).toHaveAttribute('value', 'biff');
-
- await griffRadio.click();
- await page.waitForChanges();
-
- await expect(ionChange).toHaveReceivedEventDetail({ value: 'griff', event: { isTrusted: true } });
- });
-
- test('selecting a disabled option should not update the value', async ({ page }) => {
- const value = page.locator('#value');
- const disabledRadio = page.locator('ion-radio[value="george"]');
-
- await expect(value).toHaveText('');
- await expect(disabledRadio).toHaveAttribute('disabled', '');
-
- await disabledRadio.click({ force: true });
- await page.waitForChanges();
-
- await expect(value).toHaveText('');
- });
- });
-});
diff --git a/core/src/components/radio-group/test/legacy/search/index.html b/core/src/components/radio-group/test/legacy/search/index.html
deleted file mode 100644
index fb0bb926f37..00000000000
--- a/core/src/components/radio-group/test/legacy/search/index.html
+++ /dev/null
@@ -1,82 +0,0 @@
-
-
-
-
- Radio Group - Search
-
-
-
-
-
-
-
-
-
-
-
-
- Radio Group - Form
-
-
-
-
-
- Current value:
-
-
-
-
-
-
-
-
-
-
-
-
diff --git a/core/src/components/radio-group/test/legacy/search/radio-group.e2e.ts b/core/src/components/radio-group/test/legacy/search/radio-group.e2e.ts
deleted file mode 100644
index ec40c756059..00000000000
--- a/core/src/components/radio-group/test/legacy/search/radio-group.e2e.ts
+++ /dev/null
@@ -1,42 +0,0 @@
-import { expect } from '@playwright/test';
-import { configs, test } from '@utils/test/playwright';
-
-/**
- * This behavior does not var across modes/directions.
- */
-configs({ modes: ['ios'], directions: ['ltr'] }).forEach(({ title, config }) => {
- test.describe(title('radio-group'), () => {
- test.beforeEach(async ({ page }) => {
- await page.goto('/src/components/radio-group/test/legacy/search', config);
- });
-
- test.describe('radio-group: state', () => {
- test('radio should remain checked after being removed/readded to the dom', async ({ page }) => {
- const radioGroup = page.locator('ion-radio-group');
- const radio = page.locator('ion-radio[value=two]');
- const searchbarInput = page.locator('ion-searchbar input');
-
- // select radio
- await radio.click();
- await expect(radio.locator('input')).toHaveJSProperty('checked', true);
-
- // filter radio so it is not in DOM
- await page.fill('ion-searchbar input', 'zero');
- await searchbarInput.evaluate((el) => el.blur());
- await page.waitForChanges();
- await expect(radio).toBeHidden();
-
- // ensure radio group has the same value
- await expect(radioGroup).toHaveJSProperty('value', 'two');
-
- // clear the search so the radio appears
- await page.fill('ion-searchbar input', '');
- await searchbarInput.evaluate((el) => el.blur());
- await page.waitForChanges();
-
- // ensure that the new radio instance is still checked
- await expect(radio.locator('input')).toHaveJSProperty('checked', true);
- });
- });
- });
-});
diff --git a/core/src/components/radio/radio.ios.scss b/core/src/components/radio/radio.ios.scss
index 958cad6ffee..775239a9ea1 100644
--- a/core/src/components/radio/radio.ios.scss
+++ b/core/src/components/radio/radio.ios.scss
@@ -8,12 +8,6 @@
--color-checked: #{ion-color(primary, base)};
}
-// TODO FW-3125: Remove styles
-:host(.legacy-radio) {
- width: $radio-ios-icon-width;
- height: $radio-ios-icon-height;
-}
-
:host(.ion-color.radio-checked) .radio-inner {
border-color: current-color(base);
}
@@ -69,30 +63,6 @@
opacity: 0.2;
}
-// iOS Radio Within An Item
-// -----------------------------------------
-
-:host(.in-item.legacy-radio) {
- @include margin(
- $radio-ios-item-end-margin-top,
- $radio-ios-item-end-margin-end,
- $radio-ios-item-end-margin-bottom,
- $radio-ios-item-end-margin-start
- );
-
- display: block;
- position: static;
-}
-
-:host(.in-item.legacy-radio[slot="start"]) {
- @include margin(
- $radio-ios-item-start-margin-top,
- $radio-ios-item-start-margin-end,
- $radio-ios-item-start-margin-bottom,
- $radio-ios-item-start-margin-start
- );
-}
-
// Radio Native Wrapper
// ----------------------------------------------------------------
diff --git a/core/src/components/radio/radio.ios.vars.scss b/core/src/components/radio/radio.ios.vars.scss
index 9d42d8ff72d..459e96dd154 100644
--- a/core/src/components/radio/radio.ios.vars.scss
+++ b/core/src/components/radio/radio.ios.vars.scss
@@ -21,27 +21,3 @@ $radio-ios-icon-border-style: solid !default;
/// @prop - Opacity of the disabled radio
$radio-ios-disabled-opacity: $form-control-ios-disabled-opacity !default;
-
-/// @prop - Margin top of the item-start in a radio
-$radio-ios-item-start-margin-top: 8px !default;
-
-/// @prop - Margin end of the item-start in a radio
-$radio-ios-item-start-margin-end: 21px !default;
-
-/// @prop - Margin bottom of the item-start in a radio
-$radio-ios-item-start-margin-bottom: 8px !default;
-
-/// @prop - Margin start of the item-start in a radio
-$radio-ios-item-start-margin-start: 3px !default;
-
-/// @prop - Margin top of the item-end in a radio
-$radio-ios-item-end-margin-top: 8px !default;
-
-/// @prop - Margin end of the item-end in a radio
-$radio-ios-item-end-margin-end: 11px !default;
-
-/// @prop - Margin bottom of the item-end in a radio
-$radio-ios-item-end-margin-bottom: $radio-ios-item-end-margin-top !default;
-
-/// @prop - Margin start of the item-end in a radio
-$radio-ios-item-end-margin-start: ($item-ios-padding-start * 0.5) !default;
diff --git a/core/src/components/radio/radio.md.scss b/core/src/components/radio/radio.md.scss
index 55db7d97c94..ba6296bcbc5 100644
--- a/core/src/components/radio/radio.md.scss
+++ b/core/src/components/radio/radio.md.scss
@@ -12,12 +12,6 @@
--border-radius: #{$radio-md-icon-border-radius};
}
-// TODO FW-3125: Remove this style
-:host(.legacy-radio) {
- width: $radio-md-icon-width;
- height: $radio-md-icon-height;
-}
-
:host(.ion-color) .radio-inner {
background: current-color(base);
}
@@ -74,7 +68,6 @@
// opacity set by its spec, while the label
// should match the other form controls
-:host(.legacy-radio.radio-disabled),
:host(.radio-disabled) .label-text-wrapper {
opacity: $radio-md-disabled-opacity;
}
@@ -86,10 +79,6 @@
// Material Design Radio: Keyboard Focus
// -----------------------------------------
-:host(.ion-focused.legacy-radio) .radio-icon::after {
- @include position(-12px, null, null, -12px);
-}
-
:host(.ion-focused) .radio-icon::after {
@include border-radius(var(--inner-border-radius));
@@ -105,30 +94,6 @@
opacity: 0.2;
}
-// Material Design Radio Within An Item
-// -----------------------------------------
-
-:host(.in-item.legacy-radio) {
- @include margin(
- $radio-md-item-end-margin-top,
- $radio-md-item-end-margin-end,
- $radio-md-item-end-margin-bottom,
- $radio-md-item-end-margin-start
- );
-
- display: block;
- position: static;
-}
-
-:host(.in-item.legacy-radio[slot="start"]) {
- @include margin(
- $radio-md-item-start-margin-top,
- $radio-md-item-start-margin-end,
- $radio-md-item-start-margin-bottom,
- $radio-md-item-start-margin-start
- );
-}
-
// Radio Native Wrapper
// ----------------------------------------------------------------
diff --git a/core/src/components/radio/radio.md.vars.scss b/core/src/components/radio/radio.md.vars.scss
index 47a6bd81ba1..1dfa6c780f1 100644
--- a/core/src/components/radio/radio.md.vars.scss
+++ b/core/src/components/radio/radio.md.vars.scss
@@ -37,30 +37,6 @@ $radio-md-transition-easing: cubic-bezier(.4, 0, .2, 1) !default;
/// @prop - Opacity of the disabled radio label
$radio-md-disabled-opacity: $form-control-md-disabled-opacity !default;
-/// @prop - Margin top of the item-start in a radio
-$radio-md-item-start-margin-top: 11px !default;
-
-/// @prop - Margin end of the item-start in a radio
-$radio-md-item-start-margin-end: 36px !default;
-
-/// @prop - Margin bottom of the item-start in a radio
-$radio-md-item-start-margin-bottom: 10px !default;
-
-/// @prop - Margin start of the item-start in a radio
-$radio-md-item-start-margin-start: 4px !default;
-
-/// @prop - Margin top of the item-end in a radio
-$radio-md-item-end-margin-top: 9px !default;
-
-/// @prop - Margin end of the item-end in a radio
-$radio-md-item-end-margin-end: 0 !default;
-
-/// @prop - Margin bottom of the item-end in a radio
-$radio-md-item-end-margin-bottom: $radio-md-item-end-margin-top !default;
-
-/// @prop - Margin start of the item-end in a radio
-$radio-md-item-end-margin-start: 0 !default;
-
/// @prop - Opacity of the disabled radio
/// This value is used because the radio color is set to
/// `rgb(0, 0, 0, 0.60)` when enabled and we need it to be
diff --git a/core/src/components/radio/radio.scss b/core/src/components/radio/radio.scss
index 5a231acad9e..0b9bc51c2d1 100644
--- a/core/src/components/radio/radio.scss
+++ b/core/src/components/radio/radio.scss
@@ -15,20 +15,17 @@
display: inline-block;
position: relative;
- box-sizing: border-box;
max-width: 100%;
min-height: inherit;
+ cursor: pointer;
+
user-select: none;
z-index: $z-index-item-input;
-}
-
-// TODO FW-3125: Remove :not selector and move styles to host
-:host(:not(.legacy-radio)) {
- cursor: pointer;
+ box-sizing: border-box;
}
:host(.radio-disabled) {
@@ -52,17 +49,6 @@
box-sizing: border-box;
}
-// TODO FW-3125: Remove this style
-:host(.legacy-radio) label {
- @include input-cover();
-
- display: flex;
-
- align-items: center;
-
- opacity: 0;
-}
-
input {
@include visually-hidden();
}
@@ -71,7 +57,7 @@ input {
outline: none;
}
-:host(.in-item:not(.legacy-radio)) {
+:host(.in-item) {
width: 100%;
height: 100%;
}
@@ -82,8 +68,8 @@ input {
* toolbar which is why we do not
* limit the below behavior to just ion-item.
*/
-:host([slot="start"]:not(.legacy-radio)),
-:host([slot="end"]:not(.legacy-radio)) {
+:host([slot="start"]),
+:host([slot="end"]) {
width: auto;
}
@@ -116,7 +102,7 @@ input {
overflow: hidden;
}
-:host(.in-item:not(.legacy-radio)) .label-text-wrapper {
+:host(.in-item) .label-text-wrapper {
@include margin($radio-item-label-margin-top, null, $radio-item-label-margin-bottom, null);
}
diff --git a/core/src/components/radio/radio.tsx b/core/src/components/radio/radio.tsx
index d19fc34d523..079f5d52c4d 100644
--- a/core/src/components/radio/radio.tsx
+++ b/core/src/components/radio/radio.tsx
@@ -1,13 +1,11 @@
import type { ComponentInterface, EventEmitter } from '@stencil/core';
import { Component, Element, Event, Host, Method, Prop, State, Watch, h } from '@stencil/core';
-import type { LegacyFormController } from '@utils/forms';
-import { createLegacyFormController, isOptionSelected } from '@utils/forms';
-import { addEventListener, getAriaLabel, removeEventListener } from '@utils/helpers';
-import { printIonWarning } from '@utils/logging';
+import { isOptionSelected } from '@utils/forms';
+import { addEventListener, removeEventListener } from '@utils/helpers';
import { createColorClasses, hostContext } from '@utils/theme';
import { getIonMode } from '../../global/ionic-global';
-import type { Color, StyleEventDetail } from '../../interface';
+import type { Color } from '../../interface';
/**
* @virtualProp {"ios" | "md"} mode - The mode determines which platform styles to use.
@@ -29,11 +27,6 @@ import type { Color, StyleEventDetail } from '../../interface';
export class Radio implements ComponentInterface {
private inputId = `ion-rb-${radioButtonIds++}`;
private radioGroup: HTMLIonRadioGroupElement | null = null;
- private nativeInput!: HTMLInputElement;
- private legacyFormController!: LegacyFormController;
-
- // This flag ensures we log the deprecation warning at most once.
- private hasLoggedDeprecationWarning = false;
@Element() el!: HTMLIonRadioElement;
@@ -89,18 +82,6 @@ export class Radio implements ComponentInterface {
*/
@Prop() labelPlacement: 'start' | 'end' | 'fixed' | 'stacked' = 'start';
- // TODO FW-3125: Remove the legacy property and implementation
- /**
- * Set the `legacy` property to `true` to forcibly use the legacy form control markup.
- * Ionic will only opt components in to the modern form markup when they are
- * using either the `aria-label` attribute or the default slot that contains
- * the label text. As a result, the `legacy` property should only be used as
- * an escape hatch when you want to avoid this automatic opt-in behavior.
- * Note that this property will be removed in an upcoming major release
- * of Ionic, and all form components will be opted-in to using the modern form markup.
- */
- @Prop() legacy?: boolean;
-
/**
* How to pack the label and radio within a line.
* `"start"`: The label and radio will appear on the left in LTR and
@@ -119,12 +100,6 @@ export class Radio implements ComponentInterface {
*/
@Prop() alignment: 'start' | 'center' = 'center';
- /**
- * Emitted when the styles change.
- * @internal
- */
- @Event() ionStyle!: EventEmitter;
-
/**
* Emitted when the radio button has focus.
*/
@@ -151,7 +126,6 @@ export class Radio implements ComponentInterface {
}
connectedCallback() {
- this.legacyFormController = createLegacyFormController(this.el);
if (this.value === undefined) {
this.value = this.inputId;
}
@@ -170,31 +144,6 @@ export class Radio implements ComponentInterface {
}
}
- componentWillLoad() {
- this.emitStyle();
- }
-
- @Watch('checked')
- @Watch('color')
- @Watch('disabled')
- protected styleChanged() {
- this.emitStyle();
- }
-
- private emitStyle() {
- const style: StyleEventDetail = {
- 'interactive-disabled': this.disabled,
- // TODO(FW-3125): remove this
- legacy: !!this.legacy,
- };
-
- if (this.legacyFormController.hasLegacyControl()) {
- style['radio-checked'] = this.checked;
- }
-
- this.ionStyle.emit(style);
- }
-
private updateState = () => {
if (this.radioGroup) {
const { compareWith, value: radioGroupValue } = this.radioGroup;
@@ -210,18 +159,6 @@ export class Radio implements ComponentInterface {
return;
}
- /**
- * The legacy control uses a native input inside
- * of the radio host, so we can set this.checked
- * to the state of the nativeInput. RadioGroup
- * will prevent the native input from checking if
- * allowEmptySelection="false" by calling ev.preventDefault().
- */
- if (this.legacyFormController.hasLegacyControl()) {
- this.checked = this.nativeInput.checked;
- return;
- }
-
/**
* The modern control does not use a native input
* inside of the radio host, so we cannot rely on the
@@ -260,12 +197,6 @@ export class Radio implements ComponentInterface {
}
render() {
- const { legacyFormController } = this;
-
- return legacyFormController.hasLegacyControl() ? this.renderLegacyRadio() : this.renderRadio();
- }
-
- private renderRadio() {
const { checked, disabled, color, el, justify, labelPlacement, hasLabel, buttonTabindex, alignment } = this;
const mode = getIonMode(this);
const inItem = hostContext('ion-item', el);
@@ -307,67 +238,6 @@ export class Radio implements ComponentInterface {
);
}
-
- private renderLegacyRadio() {
- if (!this.hasLoggedDeprecationWarning) {
- printIonWarning(
- `ion-radio now requires providing a label with either the default slot or the "aria-label" attribute. To migrate, remove any usage of "ion-label" and pass the label text to either the component or the "aria-label" attribute.
-
-Example: Option Label
-Example with aria-label:
-
-Developers can use the "legacy" property to continue using the legacy form markup. This property will be removed in an upcoming major release of Ionic where this form control will use the modern form markup.`,
- this.el
- );
-
- if (this.legacy) {
- printIonWarning(
- `ion-radio is being used with the "legacy" property enabled which will forcibly enable the legacy form markup. This property will be removed in an upcoming major release of Ionic where this form control will use the modern form markup.
-
-Developers can dismiss this warning by removing their usage of the "legacy" property and using the new radio syntax.`,
- this.el
- );
- }
-
- this.hasLoggedDeprecationWarning = true;
- }
-
- const { inputId, disabled, checked, color, el, buttonTabindex } = this;
- const mode = getIonMode(this);
- const { label, labelId, labelText } = getAriaLabel(el, inputId);
-
- return (
-
- {this.renderRadioControl()}
-
- (this.nativeInput = nativeEl as HTMLInputElement)}
- />
-
- );
- }
}
let radioButtonIds = 0;
diff --git a/packages/angular/src/directives/proxies.ts b/packages/angular/src/directives/proxies.ts
index d038c6f8700..954e5c064be 100644
--- a/packages/angular/src/directives/proxies.ts
+++ b/packages/angular/src/directives/proxies.ts
@@ -1578,14 +1578,14 @@ export declare interface IonProgressBar extends Components.IonProgressBar {}
@ProxyCmp({
- inputs: ['alignment', 'color', 'disabled', 'justify', 'labelPlacement', 'legacy', 'mode', 'name', 'value']
+ inputs: ['alignment', 'color', 'disabled', 'justify', 'labelPlacement', 'mode', 'name', 'value']
})
@Component({
selector: 'ion-radio',
changeDetection: ChangeDetectionStrategy.OnPush,
template: '',
// eslint-disable-next-line @angular-eslint/no-inputs-metadata-property
- inputs: ['alignment', 'color', 'disabled', 'justify', 'labelPlacement', 'legacy', 'mode', 'name', 'value'],
+ inputs: ['alignment', 'color', 'disabled', 'justify', 'labelPlacement', 'mode', 'name', 'value'],
})
export class IonRadio {
protected el: HTMLElement;
diff --git a/packages/angular/standalone/src/directives/proxies.ts b/packages/angular/standalone/src/directives/proxies.ts
index 749687dce03..b366f4a1a5b 100644
--- a/packages/angular/standalone/src/directives/proxies.ts
+++ b/packages/angular/standalone/src/directives/proxies.ts
@@ -1581,14 +1581,14 @@ export declare interface IonProgressBar extends Components.IonProgressBar {}
@ProxyCmp({
defineCustomElementFn: defineIonRadio,
- inputs: ['alignment', 'color', 'disabled', 'justify', 'labelPlacement', 'legacy', 'mode', 'name', 'value']
+ inputs: ['alignment', 'color', 'disabled', 'justify', 'labelPlacement', 'mode', 'name', 'value']
})
@Component({
selector: 'ion-radio',
changeDetection: ChangeDetectionStrategy.OnPush,
template: '',
// eslint-disable-next-line @angular-eslint/no-inputs-metadata-property
- inputs: ['alignment', 'color', 'disabled', 'justify', 'labelPlacement', 'legacy', 'mode', 'name', 'value'],
+ inputs: ['alignment', 'color', 'disabled', 'justify', 'labelPlacement', 'mode', 'name', 'value'],
standalone: true
})
export class IonRadio {
diff --git a/packages/vue/src/proxies.ts b/packages/vue/src/proxies.ts
index 910a609e349..c81008a9db5 100644
--- a/packages/vue/src/proxies.ts
+++ b/packages/vue/src/proxies.ts
@@ -606,10 +606,8 @@ export const IonRadio = /*@__PURE__*/ defineContainer