Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix: fixing the non selectable issue #4306

Closed
wants to merge 3 commits into from
Closed

fix: fixing the non selectable issue #4306

wants to merge 3 commits into from

Conversation

macci001
Copy link
Contributor

@macci001 macci001 commented Dec 10, 2024

📝 Description

  • The pr reverts fix(touch): fixing the selection functionality on touch #4220
  • There will be issue in touch due to usePress update. The usePress update prevents the default behavior of the touch to tackle the chromium bug (ref). Due to this the touch events were not triggering.
  • The pr makes changes to fix the above issue. (the aprroach is similar to one I am planning to use in the rating component)

⛳️ Current behavior (updates)

  • Multiselect on table not functioning
  • Parent was receiving more than one click.

🚀 New behavior

  • Fixed: Multiselect on table not functioning
  • Fixed: Parent was receiving more than one click.

💣 Is this a breaking change (Yes/No):

📝 Additional Information

Summary by CodeRabbit

Release Notes

  • New Features

    • Enhanced touch responsiveness for Checkbox, Switch, and Radio components.
  • Bug Fixes

    • Improved accessibility by removing the VisuallyHidden component from Checkbox, Switch, and Radio implementations.
  • Tests

    • Added new test cases to verify focus behavior for Checkbox, Switch, and Radio components.
  • Documentation

    • Updated stories for Checkbox, Switch, and Radio components to reflect recent changes and improve usability.

Copy link

changeset-bot bot commented Dec 10, 2024

🦋 Changeset detected

Latest commit: 8dc580a

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 5 packages
Name Type
@nextui-org/checkbox Patch
@nextui-org/switch Patch
@nextui-org/radio Patch
@nextui-org/table Patch
@nextui-org/react Patch

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

Copy link

vercel bot commented Dec 10, 2024

The latest updates on your projects. Learn more about Vercel for Git ↗︎

Name Status Preview Comments Updated (UTC)
nextui-docs-v2 ✅ Ready (Inspect) Visit Preview 💬 Add feedback Dec 10, 2024 11:21am
nextui-storybook-v2 ✅ Ready (Inspect) Visit Preview 💬 Add feedback Dec 10, 2024 11:21am

Copy link
Contributor

coderabbitai bot commented Dec 10, 2024

Walkthrough

This pull request introduces patches for the checkbox, switch, and radio components from the @nextui-org library, addressing touch interaction issues as noted in issue #4252. The changes involve the removal of the VisuallyHidden component in favor of directly rendering input elements styled to be visually hidden yet interactive. Additionally, enhancements to state management and interaction handling are made through the introduction of new state variables and hooks, improving the usability of these components in touch-enabled environments.

Changes

File Change Summary
.changeset/eighty-fireants-give.md Patches for @nextui-org/checkbox, @nextui-org/switch, and @nextui-org/radio to fix touch interactions.
apps/docs/content/components/checkbox/custom-implementation.raw.jsx Removed VisuallyHidden, replaced with styled input.
apps/docs/content/components/radio-group/custom-impl.raw.jsx Removed VisuallyHidden, replaced with styled input.
apps/docs/content/components/radio-group/custom-impl.raw.tsx Removed VisuallyHidden, replaced with styled input.
apps/docs/content/components/switch/custom-impl.raw.jsx Removed VisuallyHidden, replaced with styled input.
apps/docs/content/components/switch/custom-impl.raw.tsx Removed VisuallyHidden, replaced with styled input.
packages/components/checkbox/tests/checkbox.test.tsx Added test for focus behavior on parent element when Checkbox is clicked.
packages/components/checkbox/src/checkbox.tsx Removed VisuallyHidden, directly rendered input.
packages/components/checkbox/src/use-checkbox.ts Added isPressed state and integrated usePress for better interaction handling.
packages/components/radio/tests/radio.test.tsx Added test for focus behavior on parent element when Radio is clicked.
packages/components/radio/src/radio.tsx Removed VisuallyHidden, directly rendered input.
packages/components/radio/src/use-radio.ts Enhanced functionality with useState and usePress for better interaction handling.
packages/components/radio/stories/radio.stories.tsx Removed VisuallyHidden, updated templates for improved usability and validation.
packages/components/switch/tests/switch.test.tsx Added test for focus behavior on parent element when Switch is clicked.
packages/components/switch/src/switch.tsx Removed VisuallyHidden, directly rendered input.
packages/components/switch/src/use-switch.ts Enhanced functionality with useState and usePress for better interaction handling.
packages/components/switch/stories/switch.stories.tsx Removed VisuallyHidden, updated templates for improved usability and validation.

Possibly related PRs

Suggested labels

👀 Status: In Review

Suggested reviewers

  • wingkwong
  • jrgarciadev

Thank you for using CodeRabbit. We offer it for free to the OSS community and would appreciate your support in helping us grow. If you find it useful, would you consider giving us a shout-out on your favorite social media?

❤️ Share
🪧 Tips

Chat

There are 3 ways to chat with CodeRabbit:

  • Review comments: Directly reply to a review comment made by CodeRabbit. Example:
    • I pushed a fix in commit <commit_id>, please review it.
    • Generate unit testing code for this file.
    • Open a follow-up GitHub issue for this discussion.
  • Files and specific lines of code (under the "Files changed" tab): Tag @coderabbitai in a new review comment at the desired location with your query. Examples:
    • @coderabbitai generate unit testing code for this file.
    • @coderabbitai modularize this function.
  • PR comments: Tag @coderabbitai in a new PR comment to ask questions about the PR branch. For the best results, please provide a very specific query, as very limited context is provided in this mode. Examples:
    • @coderabbitai gather interesting stats about this repository and render them as a table. Additionally, render a pie chart showing the language distribution in the codebase.
    • @coderabbitai read src/utils.ts and generate unit testing code.
    • @coderabbitai read the files in the src/scheduler package and generate a class diagram using mermaid and a README in the markdown format.
    • @coderabbitai help me debug CodeRabbit configuration file.

Note: Be mindful of the bot's finite context window. It's strongly recommended to break down tasks such as reading entire modules into smaller chunks. For a focused discussion, use review comments to chat about specific files and their changes, instead of using the PR comments.

CodeRabbit Commands (Invoked using PR comments)

  • @coderabbitai pause to pause the reviews on a PR.
  • @coderabbitai resume to resume the paused reviews.
  • @coderabbitai review to trigger an incremental review. This is useful when automatic reviews are disabled for the repository.
  • @coderabbitai full review to do a full review from scratch and review all the files again.
  • @coderabbitai summary to regenerate the summary of the PR.
  • @coderabbitai generate docstrings to generate docstrings for this PR. (Experiment)
  • @coderabbitai resolve resolve all the CodeRabbit review comments.
  • @coderabbitai configuration to show the current CodeRabbit configuration for the repository.
  • @coderabbitai help to get help.

Other keywords and placeholders

  • Add @coderabbitai ignore anywhere in the PR description to prevent this PR from being reviewed.
  • Add @coderabbitai summary to generate the high-level summary at a specific location in the PR description.
  • Add @coderabbitai anywhere in the PR title to generate the title automatically.

Documentation and Community

  • Visit our Documentation for detailed information on how to use CodeRabbit.
  • Join our Discord Community to get help, request features, and share feedback.
  • Follow us on X/Twitter for updates and announcements.

Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

🧹 Outside diff range and nitpick comments (7)
packages/components/checkbox/src/use-checkbox.ts (1)

331-331: Consider adding screen reader focus indication

While the current implementation correctly handles touch interactions with absolute positioning and proper z-index, consider adding focus:ring utility classes for better screen reader focus indication.

-      className: "absolute inset-0 opacity-0 z-50 cursor-pointer",
+      className: "absolute inset-0 opacity-0 z-50 cursor-pointer focus:ring-2 focus:ring-offset-2 focus:ring-primary",
packages/components/radio/src/use-radio.ts (1)

142-143: Correct the reference in the comment from useCheckbox to useRadio.

The comment incorrectly mentions useCheckbox; it should refer to useReactAriaRadio to accurately reflect the function being used.

Apply this diff to fix the comment:

- // Handle press state for full label. Keyboard press state is returned by useCheckbox
+ // Handle press state for full label. Keyboard press state is returned by useReactAriaRadio
.changeset/eighty-fireants-give.md (1)

7-7: Hyphenate "non touchable" to "non-touchable".

Per standard spelling, "non-touchable" should be hyphenated.

Apply this diff to correct the spelling:

-Fixing the non touchable components issue(#4252)
+Fixing the non-touchable components issue (#4252)
🧰 Tools
🪛 LanguageTool

[grammar] ~7-~7: This expression is usually spelled with a hyphen.
Context: ...extui-org/radio": patch --- Fixing the non touchable components issue(#4252)

(NON_ANTI_JJ)

apps/docs/content/components/radio-group/custom-impl.raw.jsx (1)

Line range hint 15-21: Optimize touch interaction area

The custom radio implementation uses padding and gap for spacing, which affects the touch target area.

Consider adjusting the layout to ensure consistent touch targets:

-"max-w-[300px] cursor-pointer border-2 border-default rounded-lg gap-4 p-4",
+"max-w-[300px] cursor-pointer border-2 border-default rounded-lg gap-4 p-4 min-h-[48px]",
packages/components/switch/__tests__/switch.test.tsx (1)

188-202: Consider adding more edge cases to the focus test

While the current test verifies basic focus behavior, consider adding tests for:

  • Multiple rapid clicks
  • Focus behavior with disabled state
  • Focus behavior with readonly state
+ it("should not trigger focus on parent when disabled", async () => {
+   const onFocus = jest.fn();
+   const wrapper = render(
+     <div tabIndex={-1} onFocus={onFocus}>
+       <Switch isDisabled data-testid="switch-test">Switch</Switch>
+     </div>
+   );
+   const label = wrapper.getByTestId("switch-test");
+   await user.click(label);
+   expect(onFocus).not.toHaveBeenCalled();
+ });
packages/components/checkbox/__tests__/checkbox.test.tsx (1)

93-107: Consider enhancing test robustness

While the test correctly verifies the focus behavior, consider these enhancements for better reliability:

  1. Add assertion to verify the checkbox state after click
  2. Add negative test case to ensure focus isn't triggered when parent isn't focusable
 it("should trigger focus on focusable parent once after click", async () => {
   const onFocus = jest.fn();
+  const onChange = jest.fn();

   const wrapper = render(
     <div tabIndex={-1} onFocus={onFocus}>
-      <Checkbox data-testid="checkbox-test">Checkbox</Checkbox>
+      <Checkbox data-testid="checkbox-test" onChange={onChange}>Checkbox</Checkbox>
     </div>,
   );

   const label = wrapper.getByTestId("checkbox-test");
+  const input = wrapper.container.querySelector("input");

   await user.click(label);

   expect(onFocus).toHaveBeenCalledTimes(1);
+  expect(onChange).toHaveBeenCalledTimes(1);
+  expect(input).toBeChecked();
 });

+it("should not trigger focus on non-focusable parent after click", async () => {
+  const onFocus = jest.fn();
+
+  const wrapper = render(
+    <div onFocus={onFocus}>
+      <Checkbox data-testid="checkbox-test">Checkbox</Checkbox>
+    </div>,
+  );
+
+  const label = wrapper.getByTestId("checkbox-test");
+
+  await user.click(label);
+
+  expect(onFocus).not.toHaveBeenCalled();
+});
packages/components/radio/__tests__/radio.test.tsx (1)

145-163: Enhance test coverage for radio focus behavior

While the test verifies basic focus behavior, consider these enhancements for more comprehensive coverage:

  1. Verify radio selection state remains unchanged after focus
  2. Test focus behavior when switching between radio options
 it("should trigger focus on focusable parent once after click", async () => {
   const onFocus = jest.fn();
+  const onValueChange = jest.fn();

   const wrapper = render(
     <div tabIndex={-1} onFocus={onFocus}>
-      <RadioGroup defaultValue="1" label="Options">
+      <RadioGroup defaultValue="1" label="Options" onValueChange={onValueChange}>
         <Radio data-testid="radio-test-1" value="1">
           Option 1
         </Radio>
+        <Radio data-testid="radio-test-2" value="2">
+          Option 2
+        </Radio>
       </RadioGroup>
     </div>,
   );

   const label = wrapper.getByTestId("radio-test-1");
+  const radio1 = wrapper.container.querySelector('input[value="1"]');
+  const radio2 = wrapper.container.querySelector('input[value="2"]');

   await user.click(label);

   expect(onFocus).toHaveBeenCalledTimes(1);
+  expect(radio1).toBeChecked();
+  expect(radio2).not.toBeChecked();
+
+  // Test focus behavior when switching options
+  await user.click(wrapper.getByTestId("radio-test-2"));
+  expect(onFocus).toHaveBeenCalledTimes(2);
+  expect(onValueChange).toHaveBeenCalledWith("2");
+  expect(radio1).not.toBeChecked();
+  expect(radio2).toBeChecked();
 });
📜 Review details

Configuration used: .coderabbit.yaml
Review profile: CHILL

📥 Commits

Reviewing files that changed from the base of the PR and between 1485eca and 8dc580a.

📒 Files selected for processing (17)
  • .changeset/eighty-fireants-give.md (1 hunks)
  • apps/docs/content/components/checkbox/custom-implementation.raw.jsx (2 hunks)
  • apps/docs/content/components/radio-group/custom-impl.raw.jsx (2 hunks)
  • apps/docs/content/components/radio-group/custom-impl.raw.tsx (2 hunks)
  • apps/docs/content/components/switch/custom-impl.raw.jsx (2 hunks)
  • apps/docs/content/components/switch/custom-impl.raw.tsx (2 hunks)
  • packages/components/checkbox/__tests__/checkbox.test.tsx (1 hunks)
  • packages/components/checkbox/src/checkbox.tsx (1 hunks)
  • packages/components/checkbox/src/use-checkbox.ts (6 hunks)
  • packages/components/radio/__tests__/radio.test.tsx (1 hunks)
  • packages/components/radio/src/radio.tsx (1 hunks)
  • packages/components/radio/src/use-radio.ts (5 hunks)
  • packages/components/radio/stories/radio.stories.tsx (1 hunks)
  • packages/components/switch/__tests__/switch.test.tsx (1 hunks)
  • packages/components/switch/src/switch.tsx (1 hunks)
  • packages/components/switch/src/use-switch.ts (4 hunks)
  • packages/components/switch/stories/switch.stories.tsx (1 hunks)
🧰 Additional context used
🪛 LanguageTool
.changeset/eighty-fireants-give.md

[grammar] ~7-~7: This expression is usually spelled with a hyphen.
Context: ...extui-org/radio": patch --- Fixing the non touchable components issue(#4252)

(NON_ANTI_JJ)

🔇 Additional comments (14)
packages/components/checkbox/src/use-checkbox.ts (3)

215-230: Well-implemented press state management for touch interactions!

The separation of keyboard and mouse/touch press states is cleanly implemented, directly addressing the touch event issues mentioned in the PR objectives. The implementation correctly handles press state updates only for non-keyboard interactions.


232-232: Clean implementation of combined press state!

The press state combination elegantly handles both keyboard and mouse/touch interactions while respecting the disabled state, providing a single source of truth for the UI.


296-296: Verify touch event handling across different devices

The press event handlers are correctly merged with other props. However, let's verify the touch event behavior across different devices and browsers.

Also applies to: 312-312

✅ Verification successful

Let me gather more specific information about the touch event handling in the checkbox component.


Touch event handling implementation is properly integrated

The implementation shows correct touch event handling through React Aria's usePress hook:

  • Press state is properly managed for non-keyboard interactions
  • The pressProps are correctly merged with other props
  • Touch events are handled through the abstraction provided by React Aria's interactions
  • Data attributes are properly set for pressed state

The implementation follows best practices for touch interactions and accessibility:

  • Disabled state is respected for touch interactions
  • Keyboard vs touch/pointer interactions are properly distinguished
  • Press state is correctly synchronized with the component's visual feedback
🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Search for touch event related tests and implementations

# Look for touch event related tests
echo "Searching for touch event related tests..."
rg -l "touch|press|pointer" --glob "**/*.{test,spec}.{ts,tsx,js,jsx}"

# Look for touch event implementations
echo "Searching for touch event implementations..."
ast-grep --pattern 'usePress|onTouchStart|onTouchEnd|onPointerDown|onPointerUp'

Length of output: 915


Script:

#!/bin/bash
# Search for touch/press event handling in checkbox component and its tests
echo "Searching checkbox component tests..."
rg -l "touch|press|pointer" packages/components/checkbox/__tests__/

echo "Searching checkbox implementation for press handlers..."
rg -C 5 "press" packages/components/checkbox/src/use-checkbox.ts

echo "Looking for usePress hook implementation..."
rg -C 5 "usePress" packages/components/checkbox/src/use-checkbox.ts

echo "Checking for touch event related aria attributes..."
rg "aria-(pressed|touchstart|touchend)" packages/components/checkbox/

Length of output: 3466

packages/components/switch/src/use-switch.ts (1)

158-162: LGTM!

The integration of usePress and management of isPressed state enhances the switch component's interaction handling.

packages/components/radio/src/radio.tsx (1)

23-23: Change is acceptable; ensures accessibility without VisuallyHidden.

The removal of the VisuallyHidden component in favor of styling the input element directly maintains accessibility while simplifying the DOM structure.

packages/components/checkbox/src/checkbox.tsx (1)

28-28: Verify accessibility after VisuallyHidden removal

While removing the VisuallyHidden wrapper might improve touch interactions, we need to ensure the input remains accessible to screen readers while being visually hidden.

Consider adding a CSS utility class for visually hidden elements that maintains accessibility:

.visually-hidden {
  position: absolute;
  width: 1px;
  height: 1px;
  padding: 0;
  margin: -1px;
  overflow: hidden;
  clip: rect(0, 0, 0, 0);
  white-space: nowrap;
  border: 0;
}
✅ Verification successful

Let me gather more information about the checkbox component and its styling to better understand how visual hiding is handled.


Let me check the useCheckbox hook implementation to understand how the styling and accessibility attributes are handled.


Let me check the theme implementation for the checkbox to understand how the input is styled.


Input is properly hidden while maintaining accessibility

The checkbox input is correctly implemented with proper accessibility considerations:

  1. The input is visually hidden using CSS positioning and opacity:
className: "absolute inset-0 opacity-0 z-50 cursor-pointer"
  1. The input remains interactive and focusable due to:
    • Maintaining its presence in the DOM
    • Having z-50 to ensure it's clickable
    • Keeping cursor-pointer
  2. The implementation uses React Aria's useCheckbox hook which provides proper ARIA attributes and keyboard interactions

The removal of VisuallyHidden wrapper is actually an improvement as it simplifies the implementation while maintaining accessibility through CSS.

🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Search for CSS classes that might handle visual hiding
rg -g '*.{css,scss}' 'visually-hidden|sr-only|hidden' 

# Check if the input receives necessary ARIA attributes
ast-grep --pattern 'input {...$_}'

Length of output: 390


Script:

#!/bin/bash
# Check the checkbox component's styling
rg -g '*.{css,scss,ts,tsx}' -C 5 'checkbox.*input'

# Look for any CSS-in-JS styling related to the checkbox input
ast-grep --pattern 'const $_ = styled($$$)input'

# Check if there's any style prop passed to input
ast-grep --pattern '<input style={$_}'

# Check the complete checkbox component implementation
cat packages/components/checkbox/src/checkbox.tsx

Length of output: 5946


Script:

#!/bin/bash
# Check the useCheckbox hook implementation
cat packages/components/checkbox/src/use-checkbox.ts

# Look for any styled components related to checkbox
rg -g '*.{ts,tsx}' -C 5 'styled.*checkbox'

# Check if there are any CSS modules
fd -e module.css -e module.scss . packages/components/checkbox/

Length of output: 10648


Script:

#!/bin/bash
# Check the checkbox theme implementation
cat packages/components/theme/src/components/checkbox.ts

# Look for any base styles that might handle input visibility
rg -g '*.{ts,tsx}' -C 5 'absolute.*opacity-0|opacity-0.*absolute'

Length of output: 17131

packages/components/switch/src/switch.tsx (1)

37-37: Ensure adequate touch target size

The switch component should maintain proper touch target dimensions (minimum 44x44px for iOS, 48x48px for Android) for optimal touch interaction.

Consider adding touch-specific styles:

.touch-target {
  min-width: 48px;
  min-height: 48px;
  touch-action: manipulation;
}
✅ Verification successful

Let me gather more specific information about the switch component's styles and dimensions.


Let me check the switch component's implementation more specifically.


Touch target size is adequately handled by the component

The switch component already implements proper touch target sizes through its theme configuration:

  • Small (sm): 40px × 24px (w-10 h-6)
  • Medium (md): 48px × 28px (w-12 h-7) - default size
  • Large (lg): 56px × 32px (w-14 h-8)

The default medium size (48px × 28px) meets the recommended touch target dimensions for both iOS (44px) and Android (48px). Additionally, the component:

  • Uses proper cursor and touch handling with cursor-pointer touch-none
  • Implements tap highlight transparency for better mobile experience
  • Includes proper focus management and keyboard interaction
🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Search for touch-related styles and dimensions
rg -g '*.{css,scss}' 'min-(width|height)|touch-action'

# Look for existing touch event handlers
ast-grep --pattern 'onTouchStart|onTouchEnd|onClick'

Length of output: 161


Script:

#!/bin/bash
# Search for switch-specific styles and dimensions
rg -g '*.{css,scss,ts,tsx}' -A 5 'switch|Switch' --ignore-case

# Look for style-related props or CSS classes in the switch component
ast-grep --pattern 'className|style'

# Check if there are any size-related constants or utilities
rg -g '*.{ts,tsx}' 'size|dimension|width|height' --ignore-case

Length of output: 67339


Script:

#!/bin/bash
# Look for switch-specific styles and dimensions in the toggle theme
cat packages/core/theme/src/components/toggle.ts

# Check the switch implementation for any size-related props or styles
cat packages/components/switch/src/switch.tsx

Length of output: 6720

apps/docs/content/components/radio-group/custom-impl.raw.tsx (2)

21-21: Ensure proper touch target size with relative positioning

The addition of relative positioning is necessary for absolute positioning of the input, but we should verify the touch target size meets accessibility standards.

✅ Verification successful

Touch target size meets accessibility standards

The implementation includes sufficient padding and dimensions:

  • Uses p-4 (16px padding) on all sides
  • Has a minimum width of 300px (max-w-[300px])
  • Full element is clickable due to inset-0 on the input
  • Includes proper spacing with gap-4 between elements

The touch target implementation is actually more accessible than a standard radio button as it makes the entire container clickable while maintaining proper visual feedback through hover states and borders.

🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Check if there are any existing touch target size specifications
rg -i "touch-target|tap-target" .

Length of output: 35


Script:

#!/bin/bash
# Let's check the actual dimensions and spacing classes used in the radio implementation
rg -A 5 -B 5 "relative group inline-flex" .

# Also check for any size-related classes or styles
ast-grep --pattern 'className={`$$$`}'

Length of output: 2123


26-26: Verify input element accessibility

The replacement of VisuallyHidden with direct styling maintains functionality but requires verification of:

  1. Screen reader compatibility
  2. Focus visibility
  3. Touch event propagation

Consider adding explicit ARIA attributes to enhance screen reader compatibility:

-<input {...getInputProps()} className="absolute inset-0 z-50 cursor-pointer opacity-0" />
+<input {...getInputProps()} className="absolute inset-0 z-50 cursor-pointer opacity-0" aria-hidden="false" />
apps/docs/content/components/checkbox/custom-implementation.raw.jsx (1)

53-53: ⚠️ Potential issue

Verify touch event propagation with Chip component

The absolute positioning of the input over the Chip component could affect touch event handling. We need to ensure that:

  1. Touch events properly trigger both the input and Chip state changes
  2. No double-triggering occurs
  3. The z-index of 50 doesn't interfere with other interactive elements

Consider adding event stopping to prevent propagation issues:

-<input {...getInputProps()} className="absolute inset-0 z-50 cursor-pointer opacity-0" />
+<input {...getInputProps()} 
+  className="absolute inset-0 z-50 cursor-pointer opacity-0"
+  onClick={(e) => e.stopPropagation()} 
/>
apps/docs/content/components/switch/custom-impl.raw.jsx (1)

48-48: Ensure consistent behavior across all form controls

The implementation follows the same pattern as radio and checkbox, but we should ensure consistent behavior:

  1. Touch event handling
  2. Focus state management
  3. Icon switching animation

Consider extracting the common input styling to a shared utility:

const visuallyHiddenInputClass = "absolute inset-0 z-50 cursor-pointer opacity-0";

This would ensure consistency across all form control implementations and make future updates easier to maintain.

apps/docs/content/components/switch/custom-impl.raw.tsx (1)

49-49: Verify touch event handling with the new input implementation

The direct input element with z-50 ensures it remains interactive while being visually hidden. However, we should verify that this doesn't interfere with other touch interactions.

✅ Verification successful

No z-index conflicts found with the input implementation

The search results show that z-50 is consistently used across similar interactive form elements (checkbox, radio, switch) and UI components that need to be on top. The pattern of using z-50 with opacity-0 for accessible but visually hidden inputs is an established pattern in the codebase, and there are no higher z-index values that would interfere with the touch interactions.

🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Check for potential z-index conflicts in the codebase
rg -g '*.{css,scss,tsx,jsx}' 'z-[5-9][0-9]|z-\[([5-9][0-9]|100)\]' --type-add 'css:*.{css,scss}'

Length of output: 3230

packages/components/switch/stories/switch.stories.tsx (1)

114-114: LGTM! Consistent implementation across components

The implementation matches the approach used in custom implementation, ensuring consistent behavior across different usage patterns.

packages/components/radio/stories/radio.stories.tsx (1)

423-423: LGTM: Improved accessibility and touch interaction

The changes properly handle input positioning and touch events:

  1. Added relative positioning to the container
  2. Properly positioned input element with z-index for touch interaction

Also applies to: 429-429

@macci001 macci001 marked this pull request as draft December 10, 2024 11:43
@wingkwong wingkwong added this to the v2.6.6 milestone Dec 10, 2024
Copy link
Member

@wingkwong wingkwong left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

image

@jrgarciadev
Copy link
Member

Closing this in favor of this PR #4311

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
3 participants