Skip to content

fix(core/dropdown-button): Dropdown-button adaptions - #2711

Open
dmytro-halimov wants to merge 6 commits into
mainfrom
fix/dropdown-button-adaptions
Open

fix(core/dropdown-button): Dropdown-button adaptions#2711
dmytro-halimov wants to merge 6 commits into
mainfrom
fix/dropdown-button-adaptions

Conversation

@dmytro-halimov

@dmytro-halimov dmytro-halimov commented Aug 12, 2026

Copy link
Copy Markdown
Collaborator

🆕 What is the new behavior?

  • A story has been added where actually a dropdown opens on click
  • Added aria-hidden="true" to the decorative icon on main button
  • Fixed Storybook violation about nested interactive controls
  • Fixed the issue with dropdown-button stretching in preview examples
  • Dropdown labels are changed to show hug content behavior

Tracked under EIX-74

🏁 Checklist

A pull request can only be merged if all of these conditions are met (where applicable):

  • 🦮 Accessibility (a11y) features were implemented
  • 🗺️ Internationalization (i18n) - no hard coded strings
  • 📲 Responsiveness - components handle viewport changes and content overflow gracefully
  • 📕 Add or update a Storybook story
  • 📄 Documentation was reviewed/updated siemens/ix-docs
  • 🧪 Unit tests were added/updated and pass (pnpm test)
  • 📸 Visual regression tests were added/updated and pass (Guide)
  • 🧐 Static code analysis passes (pnpm lint)
  • 🏗️ Successful compilation (pnpm build, changes pushed)

👨‍💻 Help & support

Summary by CodeRabbit

  • Accessibility

    • Improved dropdown button semantics, accessible naming, and screen-reader announcements.
    • Decorative icons are hidden from assistive technologies, while nested controls no longer create duplicate interactions.
    • Enhanced keyboard focus behavior and accessible labeling for icon-only and open/close states.
  • Bug Fixes

    • Improved hover and active-state styling, alignment, and pointer-cursor behavior across variants.
  • Documentation

    • Clarified dropdown button examples and added a story showcasing dropdown items.

@changeset-bot

changeset-bot Bot commented Aug 12, 2026

Copy link
Copy Markdown

🦋 Changeset detected

Latest commit: d1580f8

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

This PR includes changesets to release 5 packages
Name Type
@siemens/ix Patch
@siemens/ix-angular Patch
@siemens/ix-docs Patch
@siemens/ix-react Patch
@siemens/ix-vue 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

@netlify

netlify Bot commented Aug 12, 2026

Copy link
Copy Markdown

Deploy Preview for ix-storybook ready!

Name Link
🔨 Latest commit d1580f8
🔍 Latest deploy log https://app.netlify.com/projects/ix-storybook/deploys/6a7dd2fdbb12ce000966fec5
😎 Deploy Preview https://deploy-preview-2711--ix-storybook.netlify.app
📱 Preview on mobile
Toggle QR Code...

QR Code

Use your smartphone camera to open QR code link.
🤖 Make changes Run an agent on this branch

To edit notification comments on pull requests, go to your Netlify project configuration.

@dmytro-halimov
dmytro-halimov marked this pull request as ready for review August 12, 2026 07:47
@dmytro-halimov
dmytro-halimov requested a review from a team as a code owner August 12, 2026 07:47
@coderabbitai

coderabbitai Bot commented Aug 12, 2026

Copy link
Copy Markdown

Review Change Stack

📝 Walkthrough

Walkthrough

The ix-dropdown-button now derives accessible labels, exposes the host as the interactive menu button, hides decorative content, applies variant state styling, and updates framework previews, Storybook coverage, tests, and release documentation.

Changes

Dropdown button updates

Layer / File(s) Summary
Accessible dropdown button behavior
packages/core/src/components/dropdown-button/dropdown-button.tsx, packages/core/src/components/dropdown-button/dropdown-button.ct.ts, packages/core/src/components/dropdown/test/dropdown.ct.ts, testing/visual-testing/tests/...
The component derives accessible labels, marks nested controls inert, hides decorative icons, validates keyboard focus and menu naming, and updates interaction locators to target ix-dropdown-button.
Variant state styling
packages/core/src/components/dropdown-button/dropdown-button.scss
A Sass mixin maps hover and active colors for dropdown-button variants. The component also uses a pointer cursor.
Preview examples and release documentation
.changeset/dropdown-button-decorative-icon.md, packages/*-test-app/src/preview-examples/..., packages/storybook-docs/src/stories/dropdown-button.stories.ts
Preview labels identify each variant, preview containers align items to the start, Storybook adds dropdown items, and a patch changeset records the accessibility update.

Estimated code review effort: 3 (Moderate) | ~20 minutes

Possibly related PRs

  • siemens/ix#2654: Both PRs modify dropdown-button preview CSS and accessibility behavior.
  • siemens/ix#2659: Both PRs modify ix-dropdown-button; this PR changes accessible naming and inert content.
  • siemens/ix#2683: Both PRs modify dropdown-button accessibility labeling and add ARIA regression coverage.

Suggested reviewers: alexkaduk

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title identifies a dropdown-button fix and matches the main changes, including accessibility and preview updates.
✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch fix/dropdown-button-adaptions

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Actionable comments posted: 7

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In @.changeset/dropdown-button-decorative-icon.md:
- Line 5: Update the changeset summary for ix-dropdown-button to include the
published styling changes: variant-specific hover/active state mapping and
pointer-cursor behavior. Keep the wording consumer-focused and retain the
existing accessibility impact.

In
`@packages/angular-standalone-test-app/src/preview-examples/dropdown-button.ts`:
- Around line 21-41: Remove the nested ix-dropdown-item elements from the
disabled dropdown example in the dropdown-button preview, leaving the disabled
ix-dropdown-button itself unchanged and matching the Angular, HTML, and React
examples.

In `@packages/core/src/components/dropdown-button/dropdown-button.tsx`:
- Around line 221-230: Update the public JSDoc for ariaLabelDropdownButton to
document that the resolved label is applied to the host element and that the
nested implementation button is inert. Keep the existing description of the
label’s purpose while explicitly covering both host-label behavior and the inert
control.
- Around line 221-230: Add regression coverage in dropdown-button.ct.ts using
regressionTest for label precedence, empty label handling, host focusability,
inert nested controls, hidden decorative icons, and the menu accessible name;
include hydration/render scenarios and a makeAxeBuilder accessibility check,
using accessible locators where applicable.
- Around line 221-225: Update the accessible-name fallback in the dropdown
button render logic around the ariaLabel calculation so an empty this.label is
treated as absent, allowing the open/close fallback to provide the host
accessible name. Preserve the existing precedence for non-empty hostAriaLabel,
ariaLabelDropdownButton, and label values.

In `@packages/storybook-docs/src/stories/dropdown-button.stories.ts`:
- Around line 40-50: Update the dropdown button story’s render callback to pass
an afterRender hook to genericRender, create and append the ix-dropdown-item
children through that hook, and remove the querySelector and non-null assertion
on ix-dropdown-button.

In `@packages/vue-test-app/src/preview-examples/dropdown-button.vue`:
- Line 39: Update the disabled dropdown variant in the Vue preview around
IxDropdownButton so it matches the HTML and React examples by rendering no
IxDropdownItem children; preserve the existing label, disabled prop, and icon.
🪄 Autofix

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: ASSERTIVE

Plan: Pro Plus

Run ID: 3752d26f-fef0-4512-a83a-4f34e242413c

📥 Commits

Reviewing files that changed from the base of the PR and between 6479f9d and 9b8f680.

📒 Files selected for processing (14)
  • .changeset/dropdown-button-decorative-icon.md
  • packages/angular-standalone-test-app/src/preview-examples/dropdown-button.css
  • packages/angular-standalone-test-app/src/preview-examples/dropdown-button.ts
  • packages/angular-test-app/src/preview-examples/dropdown-button.css
  • packages/angular-test-app/src/preview-examples/dropdown-button.ts
  • packages/core/src/components/dropdown-button/dropdown-button.scss
  • packages/core/src/components/dropdown-button/dropdown-button.tsx
  • packages/html-test-app/src/preview-examples/dropdown-button.css
  • packages/html-test-app/src/preview-examples/dropdown-button.html
  • packages/react-test-app/src/preview-examples/dropdown-button.scoped.css
  • packages/react-test-app/src/preview-examples/dropdown-button.tsx
  • packages/storybook-docs/src/stories/dropdown-button.stories.ts
  • packages/vue-test-app/src/preview-examples/dropdown-button.css
  • packages/vue-test-app/src/preview-examples/dropdown-button.vue

Comment thread .changeset/dropdown-button-decorative-icon.md
Comment thread packages/core/src/components/dropdown-button/dropdown-button.tsx Outdated
Comment thread packages/core/src/components/dropdown-button/dropdown-button.tsx
Comment thread packages/storybook-docs/src/stories/dropdown-button.stories.ts Outdated
Comment thread packages/vue-test-app/src/preview-examples/dropdown-button.vue Outdated
@dmytro-halimov
dmytro-halimov requested a review from a team as a code owner August 12, 2026 10:53

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
packages/core/src/components/dropdown-button/dropdown-button.tsx (1)

221-229: 🎯 Functional Correctness | 🟠 Major | ⚡ Quick win

Treat empty configured ARIA labels as absent.

If a consumer sets aria-label="" or aria-label-dropdown-button="", this expression selects the empty string. The host is the only interactive button because the nested controls are inert. The host then has no accessible name.

Normalize both configured labels before applying precedence. Add component tests for both empty configured-label cases.

Proposed fix
+    const fallbackAriaLabel = this.dropdownShow
+      ? 'Close dropdown'
+      : 'Open dropdown';
     const ariaLabel =
-      this.hostAriaLabel ??
-      this.ariaLabelDropdownButton ??
-      (this.label || (this.dropdownShow ? 'Close dropdown' : 'Open dropdown'));
+      this.hostAriaLabel ||
+      this.ariaLabelDropdownButton ||
+      this.label ||
+      fallbackAriaLabel;

As per coding guidelines, “Keep accessibility behavior … as consumer contracts.” As per path instructions, “Prioritize correctness, regressions, accessibility, release impact, and missing validation.”

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/core/src/components/dropdown-button/dropdown-button.tsx` around
lines 221 - 229, Normalize hostAriaLabel and ariaLabelDropdownButton so empty
strings are treated as absent before applying the precedence in the ariaLabel
calculation, preserving fallback to the component label or open/close text. Add
component tests covering each configured label being empty and verify the host
receives the fallback accessible name.

Sources: Coding guidelines, Path instructions

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Outside diff comments:
In `@packages/core/src/components/dropdown-button/dropdown-button.tsx`:
- Around line 221-229: Normalize hostAriaLabel and ariaLabelDropdownButton so
empty strings are treated as absent before applying the precedence in the
ariaLabel calculation, preserving fallback to the component label or open/close
text. Add component tests covering each configured label being empty and verify
the host receives the fallback accessible name.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: ASSERTIVE

Plan: Pro Plus

Run ID: c75f7c28-307e-4700-990f-a139a0439573

📥 Commits

Reviewing files that changed from the base of the PR and between 480a883 and e197f7e.

📒 Files selected for processing (4)
  • packages/core/src/components/dropdown-button/dropdown-button.ct.ts
  • packages/core/src/components/dropdown-button/dropdown-button.tsx
  • packages/storybook-docs/src/stories/dropdown-button.stories.ts
  • packages/vue-test-app/src/preview-examples/dropdown-button.vue

@sonarqubecloud

Copy link
Copy Markdown

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant