Skip to content

Commit

Permalink
Sidebar disclosure color (#4011)
Browse files Browse the repository at this point in the history
* refactor: extract NavigationDisclosure props into interface

* fix: fixing type issue

* fix: fixing header for unselected navigation header

* refactor: adding a styles for the unselected disclosure heading

* refactor: extracting style computation logic into a custom hook

* refactor: renaming variable

* fix: removing change

* chore: adding changeset

* chore: formatting

* feat: adding sidebar navigation item unselected styles

* feat: updating the computed styles

* chore: updating changeset message

* feat: adjusting the icon color in sidebar navigation disclosure heading

* chore: reverting changes

* chore: small changes for merging

---------

Co-authored-by: “nora <[email protected]>
Co-authored-by: Nora Krantz <[email protected]>
  • Loading branch information
3 people authored Sep 9, 2024
1 parent df4ffd6 commit 7ae14af
Show file tree
Hide file tree
Showing 3 changed files with 73 additions and 11 deletions.
6 changes: 6 additions & 0 deletions .changeset/long-moons-worry.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
---
"@twilio-paste/sidebar": patch
"@twilio-paste/core": patch
---

[Sidebar] Updating the unselected Sidebar Disclosure Header and SidebarNavigationItems.
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,55 @@ export interface SidebarNavigationDisclosureHeadingProps extends HTMLPasteProps<
icon?: React.ReactNode;
}

interface UseComputeDisclosureHeadingStylesArgs {
/** Whether the heading is selected */
selected?: boolean;
/** Whether the heading is nested within another heading */
nested: boolean;
}

/**
* Small hook that abstracts the logic of computing styles for the SidebarNavigationDisclosureHeading component.
*/
const useComputeDisclosureHeadingStyles = ({ nested, selected }: UseComputeDisclosureHeadingStylesArgs): BoxProps => {
let styles: BoxProps = {};
if (nested) {
styles = sidebarNavigationLabelNestedStyles;
} else {
styles = sidebarNavigationLabelStyles;
}
if (selected) {
styles = { ...styles, ...sidebarNavigationLabelSelectedStyles };
}
return styles;
};

interface UseAdjustIconColorArgs {
/** Icon to be displayed within the Heading. */
icon: React.ReactNode;
/** Whether the heading is selected. */
selected?: boolean;
}

/**
* Adjust the color on the icon if it is not selected. It accomplishes this by cloning the icon node and applying the colorTextIconInverse color.
* Memoized to reduce the number of times the icon is cloned.
*/
const useAdjustIconColor = ({ icon, selected }: UseAdjustIconColorArgs): Required<React.ReactNode> => {
return React.useMemo(() => {
if (!icon) {
return null;
}
if (icon && React.isValidElement(icon) && !selected) {
const iconElement = icon as React.ReactElement;
return React.cloneElement(iconElement, {
color: "colorTextIconInverse",
});
}
return icon;
}, [icon, selected]);
};

const StyledDisclosureHeading = React.forwardRef<HTMLDivElement, SidebarNavigationDisclosureHeadingProps>(
({ children, element = "SIDEBAR_NAVIGATION_DISCLOSURE_HEADING", selected, icon, ...props }, ref) => {
const { collapsed, variant } = React.useContext(SidebarContext);
Expand All @@ -63,15 +112,17 @@ const StyledDisclosureHeading = React.forwardRef<HTMLDivElement, SidebarNavigati
}, 120);
}, [collapsed, isCompact]);

const disclosureHeadingStyles = useComputeDisclosureHeadingStyles({ nested, selected });
const adjustedIcon = useAdjustIconColor({ icon, selected });

return (
<Box
{...safelySpreadBoxProps(props)}
ref={ref}
element={element}
onMouseEnter={() => setShouldIconMove(true)}
onMouseLeave={() => setShouldIconMove(false)}
{...(nested ? sidebarNavigationLabelNestedStyles : sidebarNavigationLabelStyles)}
{...(selected && sidebarNavigationLabelSelectedStyles)}
{...disclosureHeadingStyles}
>
<Box
as="span"
Expand All @@ -87,7 +138,7 @@ const StyledDisclosureHeading = React.forwardRef<HTMLDivElement, SidebarNavigati
>
<ChevronDisclosureIcon color="inherit" decorative size="sizeIcon20" />
</Box>
{icon ? icon : null}
{adjustedIcon}
<Box
as="span"
display="block"
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,14 +23,19 @@ import { SidebarAnchor } from "./SidebarAnchor";

const CY_BASE = "sidebar-disclosure";

const NavigationDisclosure: React.FC<
React.PropsWithChildren<{
children: SidebarNavigationDisclosureContentProps["children"];
categoryRoute: typeof SidebarCategoryRoutes[keyof typeof SidebarCategoryRoutes];
buttonText: string;
onClick?: SidebarNavigationDisclosureHeadingProps["onClick"];
}>
> = ({ children, categoryRoute, buttonText, onClick }) => {
interface NavigationDisclosureProps {
buttonText: string;
categoryRoute: typeof SidebarCategoryRoutes[keyof typeof SidebarCategoryRoutes];
children: SidebarNavigationDisclosureContentProps["children"];
onClick?: SidebarNavigationDisclosureHeadingProps["onClick"];
}

const NavigationDisclosure: React.FC<React.PropsWithChildren<NavigationDisclosureProps>> = ({
children,
categoryRoute,
buttonText,
onClick,
}) => {
const pathname = useLocationPathname();
const disclosure = useSidebarNavigationDisclosureState({
visible: pathname.startsWith(categoryRoute),
Expand Down

0 comments on commit 7ae14af

Please sign in to comment.