Skip to content

Replace all instances of Dropdown with ListBox, and remove the Dropdown component #173

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

Draft
wants to merge 34 commits into
base: master
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
34 commits
Select commit Hold shift + click to select a range
484cd26
Simplify Breadcrumbs styling to fix link colors.
mkrause Feb 27, 2025
79cb285
Implement ListBox component (initial prototype).
mkrause Mar 1, 2025
1263dc6
Implement requireIntent.
mkrause Mar 1, 2025
ff2f4b9
ListBox: implement type ahead.
mkrause Mar 1, 2025
b348aea
Implement ListBox.Header and ListBox.Action.
mkrause Mar 1, 2025
e052962
ListBox: implement disabled + 'sticky' prop for Action.
mkrause Mar 1, 2025
c2198dc
Add example of ListBox in a <form> element.
mkrause Mar 1, 2025
52b4ca0
Implement ListBoxLazy (initial prototype).
mkrause Mar 2, 2025
ec8c57d
ListBoxLazy: implement infinite scroll.
mkrause Mar 3, 2025
a4f23f0
ListBox: before zustand migration.
mkrause Mar 8, 2025
fa0f544
ListBoxStore: before removing ItemTarget.
mkrause Mar 11, 2025
7447da3
Work on ListBoxLazy.
mkrause Mar 13, 2025
b1321c1
ListBox: Before going back to 'virtual focus' on the parent list box.
mkrause Mar 23, 2025
3430a0e
Switching back to roving tabindex.
mkrause Mar 24, 2025
58da207
ListBoxLazy: always render the focused item.
mkrause Apr 8, 2025
ab42320
Implement VirtualItemKeys.
mkrause Apr 14, 2025
8d8d943
VirtualItemKeys: fixes.
mkrause Apr 14, 2025
8ca50e7
Fix issues with elements not focusing on keyboard navigation.
mkrause Apr 15, 2025
31b88d1
ListBox: Clean up code.
mkrause Apr 16, 2025
59a0b1b
Merge branch 'master' into feature/gh-165-implement-list-box
mkrause Apr 16, 2025
7e3a561
Update package lock.
mkrause Apr 16, 2025
adad805
Add missing license headers.
mkrause Apr 16, 2025
850fd73
Merge branch 'master' into feature/gh-165-implement-list-box
mkrause Apr 17, 2025
c46b053
ListBox: fix disabled state, use in <form> elements.
mkrause Apr 18, 2025
2906323
ListBox: Fix sticky headers.
mkrause Apr 18, 2025
1d45e77
ListBox: Implement workaround for sticky actions 'bleed through'.
mkrause Apr 18, 2025
55b9b2b
Remove comment.
mkrause Apr 18, 2025
e853ad9
ListBox: make 'virtualItemKeys' an optional prop.
mkrause Apr 20, 2025
0579d2e
ListBox: implement onToggle event handler for focus management with p…
mkrause Apr 20, 2025
32da639
Replace all instances of Dropdown with ListBox, and remove the Dropdo…
mkrause Apr 20, 2025
410f988
Switch to logical properties for overflow: overflow-block/inline.
mkrause Apr 23, 2025
be9c96a
Select: display the human-readable label for the selected option.
mkrause Apr 26, 2025
de348f7
Work on migrating DropdownMenu/Select to use ListBox.
mkrause Apr 30, 2025
c8b132f
ListBox: update styling.
mkrause May 5, 2025
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions .storybook/preview-head.html
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
<!-- <script src="https://unpkg.com/react-scan/dist/auto.global.js"></script> -->

<style>
/* This should be the same as the ordering in `layers.css`. */
@layer reset, baklava, app, accessibility, storybook;
Expand Down
2 changes: 2 additions & 0 deletions .storybook/preview.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -118,6 +118,8 @@ const preview = {
'InputPassword',
],
'TextArea',
'ListBox',
'ListBoxLazy',
'Select',
'DatePicker',
'DatePickerRange',
Expand Down
4 changes: 3 additions & 1 deletion .vscode/custom.css-data.json
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,9 @@
"version": 1.1,
"properties": [
{ "name": "interpolate-size" },
{ "name": "position-try-fallbacks" }
{ "name": "position-try-fallbacks" },
{ "name": "reading-flow" },
{ "name": "reading-order" }
],
"atDirectives": [
{
Expand Down
4 changes: 3 additions & 1 deletion app/Demo.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,9 @@
<Header slot="actions">
<UserMenu userName="Anand Kashyap"/>
{/* <UserMenu userName="Anand Kashyap – Very Long Name That Will Overflow"/> */}
<AccountSelector className="select-action"/>
<AccountSelector className="select-action" accounts={null}>
{accountSelected => accountSelected ?? 'Accounts'}

Check failure on line 31 in app/Demo.tsx

View workflow job for this annotation

GitHub Actions / build (22.x)

Type 'ItemDetails | "Accounts"' is not assignable to type 'ReactNode'.
</AccountSelector>
<SolutionSelector className="select-action"/>
</Header>
</AppLayout.Header>
Expand Down
3 changes: 2 additions & 1 deletion app/lib.ts
Original file line number Diff line number Diff line change
Expand Up @@ -51,6 +51,8 @@ export { TextArea } from '../src/components/forms/controls/TextArea/TextArea.tsx
export { DatePicker } from '../src/components/forms/controls/DatePicker/DatePicker.tsx';
export { TimePicker } from '../src/components/forms/controls/TimePicker/TimePicker.tsx';
export { DatePickerRange } from '../src/components/forms/controls/DatePickerRange/DatePickerRange.tsx';
export { ListBox } from '../src/components/forms/controls/ListBox/ListBox.tsx';
export { ListBoxLazy } from '../src/components/forms/controls/ListBoxLazy/ListBoxLazy.tsx';
export { Select } from '../src/components/forms/controls/Select/Select.tsx';

// Forms > Fields
Expand All @@ -77,7 +79,6 @@ export { Tab, Tabs } from '../src/components/navigations/Tabs/Tabs.tsx';
export { SpinnerModal } from '../src/components/overlays/SpinnerModal/SpinnerModal.tsx';
export { DialogModal } from '../src/components/overlays/DialogModal/DialogModal.tsx';
export { DialogOverlay } from '../src/components/overlays/DialogOverlay/DialogOverlay.tsx';
export { DropdownMenu } from '../src/components/overlays/DropdownMenu/DropdownMenu.tsx';
export { DropdownMenuProvider } from '../src/components/overlays/DropdownMenu/DropdownMenuProvider.tsx';
export { ToastProvider, notify } from '../src/components/overlays/ToastProvider/ToastProvider.tsx';
export { Tooltip } from '../src/components/overlays/Tooltip/Tooltip.tsx';
Expand Down
64 changes: 61 additions & 3 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

4 changes: 3 additions & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -110,15 +110,17 @@
"dependencies": {
"date-fns": "^4.1.0",
"message-tag": "^0.10.0",
"classnames": "^2.5.1",
"react": "^19.0.0",
"react-dom": "^19.0.0",
"react-error-boundary": "^5.0.0",
"classnames": "^2.5.1",
"zustand": "^5.0.3",
"@floating-ui/react": "^0.27.6",
"react-table": "^7.8.0",
"react-datepicker": "^8.0.0",
"effect": "^3.12.9",
"react-hook-form": "^7.54.2",
"@tanstack/react-virtual": "^3.13.2",
"optics-ts": "^2.4.1"
},
"peerDependencies": {
Expand Down
5 changes: 3 additions & 2 deletions package.json.js
Original file line number Diff line number Diff line change
Expand Up @@ -171,18 +171,19 @@ const packageConfig = {
'message-tag': '^0.10.0',

// React
'classnames': '^2.5.1',
'react': '^19.0.0',
'react-dom': '^19.0.0',
'react-error-boundary': '^5.0.0',
//'@uidotdev/usehooks': '^2.4.1',
'classnames': '^2.5.1',
'zustand': '^5.0.3',

'@floating-ui/react': '^0.27.6',
'react-table': '^7.8.0',
'react-datepicker': '^8.0.0',

'effect': '^3.12.9',
'react-hook-form': '^7.54.2',
'@tanstack/react-virtual': '^3.13.2',

'optics-ts': '^2.4.1',
},
Expand Down
4 changes: 4 additions & 0 deletions scripts/import.ts
Original file line number Diff line number Diff line change
Expand Up @@ -216,6 +216,10 @@ const runImportColorsSemantic = async (args: ScriptArgs) => {
throw new Error(`Should not happen`);
}

if (tokenValue.match(/#[a-z0-9]{3,6}/i)) {
throw new Error(`Found semantic color token defined using a hardcoded hex color: '${tokenName}'`);
}

// Replace references to primitive color tokens with their Sass variable equivalent
const color = tokenValue.replaceAll(/var\(--(.+?)-(\d+)\)/g, '\$color-$1-$2');

Expand Down
2 changes: 1 addition & 1 deletion src/components/actions/Button/Button.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -147,7 +147,7 @@ export const Button = (props: ButtonProps) => {
return (
<button
aria-label={accessibleName}
aria-disabled={!isInteractive}
aria-disabled={isInteractive ? undefined : true}
disabled={disabled}
{...propsRest}
type={buttonType} // Not overridable
Expand Down
17 changes: 7 additions & 10 deletions src/components/containers/Banner/Banner.module.scss
Original file line number Diff line number Diff line change
Expand Up @@ -34,26 +34,22 @@
color: bk.$theme-banner-text-default;

.bk-banner__header {
display: flex;
flex-direction: row;
@include bk.flex-row;
align-items: flex-start;
gap: bk.$spacing-4;

.bk-banner__header__text {
margin-inline-end: auto; // Space between text and actions

min-inline-size: 0;
display: flex;
flex-flow: row wrap;
@include bk.flex-row;
flex-wrap: wrap;
gap: bk.$spacing-1;

.bk-banner__title {
$icon-size: 1.3em;
margin-inline-start: calc(-1 * (bk.$spacing-2 + $icon-size));

min-inline-size: 0;
display: flex;
flex-direction: row;
@include bk.flex-row;
gap: bk.$spacing-2;
align-items: center;

Expand All @@ -73,8 +69,9 @@
}
}
.bk-banner__actions {
display: flex;
flex-direction: row;
flex-shrink: 0;

@include bk.flex-row;
align-items: center;
gap: bk.$spacing-3 calc(bk.$spacing-6 / 2);

Expand Down
10 changes: 4 additions & 6 deletions src/components/containers/Dialog/Dialog.module.scss
Original file line number Diff line number Diff line change
Expand Up @@ -67,19 +67,17 @@
margin-block: calc(bk.$spacing-7 / 2) calc(bk.$spacing-7 / 2);
padding-inline: var(--bk-dialog-padding-inline);

display: flex;
flex-direction: row;
gap: bk.$spacing-3;
@include bk.flex($dir: row, $gap: bk.$spacing-3);
}

.bk-dialog__content__icon-aside {
align-self: flex-start;

display: flex;
flex-direction: row;
gap: bk.$spacing-3;
@include bk.flex-row($gap: bk.$spacing-3);
}

.bk-dialog__content__body { --keep: ; }

.bk-dialog__actions {
position: sticky;
inset-block-end: -1px; // -1px to prevent bleed through due to pixel rounding
Expand Down
1 change: 1 addition & 0 deletions src/components/containers/Dialog/Dialog.stories.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -97,6 +97,7 @@ export const DialogWithAside: Story = {
</FieldLayout>
</FormLayout>
</Form>
<p>ThisIsAVeryLongStringOfTextWithoutAnySpacesToTestWhetherWeHandleWordBreaksCorrectlyWhenTheTextOverflowsTheContainingElement</p>
</Dialog>
);
},
Expand Down
2 changes: 1 addition & 1 deletion src/components/containers/Dialog/Dialog.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -182,7 +182,7 @@ export const Dialog = Object.assign(
role="document" // https://developer.mozilla.org/en-US/docs/Web/Accessibility/ARIA/Roles/document_role
// FIXME: make this focusable instead of the <dialog> as per guidelines on MDN?
//tabIndex={0}
className={cx('bk-prose')}
className={cx(cl['bk-dialog__content__body'], 'bk-prose')}
>
{children}
</section>
Expand Down
Loading
Loading