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

Debt - 3952 - Replace primitives #4136

Merged
merged 105 commits into from
Nov 7, 2022
Merged

Debt - 3952 - Replace primitives #4136

merged 105 commits into from
Nov 7, 2022

Conversation

esizer
Copy link
Member

@esizer esizer commented Sep 30, 2022

Resolves #3952

📋 Summary

This replaces our underlying custom/reach common primitives with radix-ui

❓Rationale

Warning
Reach is not currently maintained.

Currently, we are stuck on react@17 and the only real blocker is reach-ui. After some research and looking at a number of primitive libraries, it seems as though radix is the best option because:

  • It has full keyboard navigation
  • Managed focus
  • Has proper semantics for assistive technology
  • WAI-ARIA compliant
  • Screen reader tested
  • Allows us to worry about styling rather than API
  • Exposes all sub-components for more control
  • Has a fairly large library to use

✅ TO DO

  • Fix linting
  • Translation run

🧪 Testing

Good luck! 🍀

  1. Build all projects npm run production --workspaces
  2. Bounce around the place where the components were replaced and confirm they all still work and look fine
  3. Check storybook for components and docs! npm run storybook

Places to Check

  • Admin
    • Logout
    • Edit Pool
    • Table column dialog
    • User/Pool Candidate filter dialogs
    • API Table search dropdown
    • User tabs
  • IAP
    • Dialogs on homepage
  • Talent Search
    • Employment equity form dialogs
    • Experience form delete confirmation
    • Logout
    • Role Salary form dialogs

⚛️ Components

Component Created Stories Tests Replaced
Accordion
AlertDialog
Collapsible
Dialog
DropdownMenu
ScrollArea
Separator
Switch
Tabs
ToggleGroup

Accordion

import Accordion from "@common/components/Accordion";

/**
 * Allows multiple accordions items to be open at once
 */
const ExampleAccordionMultipleOpen = () => (
  <Accordion.Root type="multiple">
    <Accordion.Item value="one">
        <Accordion.Trigger Icon={HeroIcon} subtitle="Subtitle">
          Example Accordion One Heading
        </Accordion.Trigger>
        <Accordion.Content>
          <p>Example accordion one content.
        </Accordion.Content>
      </Accordion.Item>
    <Accordion.Item value="two">
        <Accordion.Trigger Icon={HeroIcon} subtitle="Subtitle">
          Example Accordion Two Heading
        </Accordion.Trigger>
        <Accordion.Content>
          <p>Example accordion two content.
        </Accordion.Content>
      </Accordion.Item>
  </Accordion.Root>
);

/**
 * Allows only one accordions item to be open at once
 */
const ExampleAccordionSingleOpen = () => (
  <Accordion.Root type="single">
    <Accordion.Item value="one">
        <Accordion.Trigger Icon={HeroIcon} subtitle="Subtitle">
          Example Accordion One Heading
        </Accordion.Trigger>
        <Accordion.Content>
          <p>Example accordion one content.
        </Accordion.Content>
      </Accordion.Item>
  </Accordion.Root>
);

Alert Dialog

import AlertDialog from "@common/components/AlertDialog";
import Button from "@common/components/Button";

const ExampleAlertDialog = () => (
  <AlertDialog.Root>
    <AlertDialog.Trigger>
      <Button>Open Alert Dialog</Button>
    </AlertDialog.Trigger>
    <AlertDialog.Content>
      <AlertDialog.Title>Example Alert Dialog</AlertDialog.Title>
      <AlertDialog.Description>Example Alert Dialog Description</AlertDialog.Description>
      <AlertDialog.Footer>
        <AlertDialog.Cancel>
          <Button color="white">Cancel</Button>
        </AlertDialog.Cancel>
        <AlertDialog.Action>
          <Button color="cta">Action</Button>
        </AlertDialog.Action>
      </AlertDialog.Footer>
    </AlertDialog.Content>
  </AlertDialog.Root>
);

Dialog

import Dialog from "@common/components/Dialog";
import Button from "@common/components/Button";

const ExampleDialog = () => (
  <Dialog.Root>
    <Dialog.Trigger>
      <Button>Open Dialog</Button>
    </Dialog.Trigger>
    <Dialog.Content>
      <Dialog.Header subtitle="short description">
        Dialog Title
      </Dialog>
      <p>Dialog body</p>
      <Dialog.Footer>
        <Dialog.Close>
          <Button>Close</Button>
        </Dialog.Close>
      </Dialog.Footer>
    </Dialog.Content>
  </Dialog.Root>
);

Collapsible

import Collapsible from "@common/components/Collapsible";
import Button from "@common/components/Button";

const ExampleCollapsible = () => (
 <Collapsible.Root>
	 <Collapsible.Trigger asChild>
		 <Button>Open Collapsible</Button>
	 </Collapsible.Trigger>
	 <Collapsible.Content>
		 <p>Content for a Collapsible element</p>
	 </Collapsible.Content>
 </Collapsible.Root>

Dropdown Menu

import DropdownMenu from "@common/components/DropdownMenu";

const DropdownMenuExample = () => {
  const [value, setValue] = React.useState<string>("");
  return (
    <DropdownMenu.Root>
      <DropdownMenu.Trigger>
        <Button>Open Dropdown</Button>
      </DropdownMenu.Trigger>
      <DropdownMenu.Content>
        <DropdownMenu.Label>Basic Items</DropdownMenu.Label>
        <DropdownMenu.Item>Item One</DropdownMenu.Item>
        <DropdownMenu.Item>Item Two</DropdownMenu.Item>
        <DropdownMenu.Separator />
        <DropdownMenu.Label>Form Items</DropdownMenu.Label>
        <DropdownMenu.CheckboxItem>
          Basic CheckboxItem
        </DropdownMenu.CheckboxItem>
        <DropdownMenu.RadioGroup value={value} onValueChange={setValue}>
          <DropdownMenu.RadioItem value="one">
            <Check />
            RadioItem One
          </DropdownMenu.RadioItem>
          <DropdownMenu.RadioItem value="two">
            <Check />
            RadioItem Two
          </DropdownMenu.RadioItem>
          <DropdownMenu.RadioItem value="three">
            <Check />
            RadioItem Three
          </DropdownMenu.RadioItem>
        </DropdownMenu.RadioGroup>
      </DropdownMenu.Content>
    </DropdownMenu.Root>
  );
}

Scroll Area

import ScrollArea from "@common/components/ScrollArea";

const ExampleScrollArea = () => (
	<ScrollArea.Root style={{ height: 500, width: 320, }}>
		<ScrollArea.Viewport>
			<p>Content for the Scroll Area</p>
		<ScrollArea.ViewPort>
		<ScrollArea.Scrollbar orientation="vertical">
			<ScrollArea.Thumb />
		</ScrollArea.Scrollbar>
	</ScrollArea.Root>
);

Separator

import Separator from "@common/components/Separator";

const ExampleSeparator = () => (
	<Separator
		decorative
		orientation="vertical"
		color="secondary"
	/>
);

Switch

import Switch from "@common/components/Switch";

const SwitchExample = () => (
	<Switch.Root id="example-switch">
		<Switch.Thumb />
	</Switch.Root>
);

Tabs

import DropdownMenu from "@common/components/DropdownMenu";

const ExampleTabs = () => (
	<Tabs.Root defaultValue="one">
	    <Tabs.List aria-label="Tabs Nav">
			<Tabs.Trigger value="one">One</Tabs.Trigger>
			<Tabs.Trigger value="two">Two</Tabs.Trigger>
			<Tabs.Trigger value="three">Three</Tabs.Trigger>
		</Tabs.List>
		<Tabs.Content value="one">
			<p>One</p>
		</Tabs.Content>
		<Tabs.Content value="two">
			<p>Two</p>
		</Tabs.Content>
		<Tabs.Content value="three">
			<p>Three</p>
		</Tabs.Content>
	</Tabs.Root>
);

Toggle Group

import Toggle Group from "@common/components/ToggleGroup";

const ToggleGroupExample = () => (
	<ToggleGroup.Root>
		<ToggleGroup.Item value="one">One</ToggleGroup.Item>
		<ToggleGroup.Item value="two">Two</ToggleGroup.Item>
		<ToggleGroup.Item value="three">Three</ToggleGroup.Item>
	</ToggleGroup.Root>
);

@esizer
Copy link
Member Author

esizer commented Nov 2, 2022

bolding appears to have been lost

Hmm, very odd. Something else that I do not remember touching in this PR. I just merged in main to see if I'm just a few commits behind or something 🤔

@esizer
Copy link
Member Author

esizer commented Nov 2, 2022

is this change intentional? I thought the ones on the left were supposed to be worded differently intentionally

Looks like it was some bad merge conflict resolutions on my part. Should be good now in fix equity option titles

bolding appears to have been lost

I'm not sure what one is correct but main is bold so I updated it to be bold in fix regular font weight delete action

change to that dropdown makes it no longer recognizable as a dropdown, lost its little pointer

Good eye! Added chevron in fix dropdown menu styles

@vd1992
Copy link
Contributor

vd1992 commented Nov 3, 2022

is this change intentional? I thought the ones on the left were supposed to be worded differently intentionally

Looks like it was some bad merge conflict resolutions on my part. Should be good now in fix equity option titles

bolding appears to have been lost

I'm not sure what one is correct but main is bold so I updated it to be bold in fix regular font weight delete action

change to that dropdown makes it no longer recognizable as a dropdown, lost its little pointer

Good eye! Added chevron in fix dropdown menu styles

Nice! Overall it looks like things function just the same as before!
All right, I'll hand things back to Yoni, who I entirely have faith in to review this

Copy link
Contributor

@yonikid15 yonikid15 left a comment

Choose a reason for hiding this comment

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

This was a big one, but as always great work Eric 🎉 Thanks for taking this one on, and again apologies for the long wait on the review.

Manual tests:

  • Editing all touched sections of the Profile. Ensure all forms work behave and look correct.
  • Login/Logout.
  • Editing a pool.
  • Table column and filter dialogs, and search dropdowns.
  • User tabs
  • Dialogs on IAP homepage.

Bugs:

  • On the IAP homepage, the "See Eligibility Criteria" and "Learn more" dialog close buttons are not working.
  • On the IAP homepage, when closing a dialog the tab index jumps back to the first element on the page, in this case the Home link in the nav menu. This can get annoying for users with screen readers. It seems to be working correctly on the Admin and TalentSearch side though.
  • User cannot scroll when the dialog is open. This could prevent the user from seeing the entire Dialog, especially on smaller screens. For example, on the EE dialog I cannot click the Save button. Also, the "Learn more" dialog on IAP homepage is very long so most of the content is unviewable. Would adding a <ScrollArea /> within the Dialog fix this?
  • The search form dropdown is missing on Pool Candidates table. ISSUE Feature - Pool Candidate table search filter #4621
  • Clicking add user to pool breaks the page. It looks like it has something to do with the Input components (out of scope(?)). To recreate: go to Users table->View User->Click "add user to pool"

Cool stuff:

  • Thanks for adding the docs for each of the new Primitives. It will come in handy down the line when ppl are using them for the first time.
  • I like the subtle transition of color and the rotating chevron on the Accordion when opening and closing.

@esizer
Copy link
Member Author

esizer commented Nov 7, 2022

  • On the IAP homepage, the "See Eligibility Criteria" and "Learn more" dialog close buttons are not working.
  • On the IAP homepage, when closing a dialog the tab index jumps back to the first element on the page, in this case the Home link in the nav menu. This can get annoying for users with screen readers. It seems to be working correctly on the Admin and TalentSearch side though.

Good catch, fixed with fix iap dialog close + focus

  • User cannot scroll when the dialog is open. This could prevent the user from seeing the entire Dialog, especially on smaller screens. For example, on the EE dialog I cannot click the Save button. Also, the "Learn more" dialog on IAP homepage is very long so most of the content is unviewable. Would adding a <ScrollArea /> within the Dialog fix this?

Oops, this was a problem with the composition of the dialog. Thanks for catching that! Fixed in fix long content dialogs not scrolling

  • Clicking add user to pool breaks the page. It looks like it has something to do with the Input components (out of scope(?)). To recreate: go to Users table->View User->Click "add user to pool"

Looks like this was missed in the unsaved changes PR 😢 Fixed in fix add user to pool dialog

@esizer esizer requested a review from yonikid15 November 7, 2022 13:43
Copy link
Contributor

@yonikid15 yonikid15 left a comment

Choose a reason for hiding this comment

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

Almost there! The close button seems to have jumped into the top right of the screen. Was that intentional?
image

@esizer
Copy link
Member Author

esizer commented Nov 7, 2022

Almost there! The close button seems to have jumped into the top right of the screen. Was that intentional?

oohhh, good eye 🦅 Fixed with fix dialog close button position

@esizer esizer requested a review from yonikid15 November 7, 2022 18:34
Copy link
Contributor

@yonikid15 yonikid15 left a comment

Choose a reason for hiding this comment

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

Alright looks good to me! ✅

@esizer esizer merged commit bcde714 into main Nov 7, 2022
@esizer esizer deleted the debt/3952-replace-primitives branch November 7, 2022 19:39
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.

Replace Reach UI with new primitives
4 participants