Skip to content

Commit

Permalink
fix: sidebar layout issues (#201)
Browse files Browse the repository at this point in the history
  • Loading branch information
Misael840 committed May 13, 2024
1 parent 020454d commit bf8c679
Show file tree
Hide file tree
Showing 4 changed files with 83 additions and 28 deletions.
16 changes: 16 additions & 0 deletions src/components/SideBar/SideBar.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -287,4 +287,20 @@ describe('<SideBar/>', () => {
renderResult.rerender(<SideBar {...props} isLoadingSideBarList />)
expect(renderResult.getAllByRole('sidebar-list-skeleton')[0]).toBeDefined()
})

it('should close dropdown when clicked outside', () => {
renderResult.rerender(<SideBar {...props} activeDropdown />)
const dropdown = renderResult.getByRole('sidebar-dropdown-header')
const sidebar = renderResult.getByRole('container-sidebar')

fireEvent.click(dropdown)

expect(renderResult.getByRole('sidebar-dropdown-list')).toBeDefined()

fireEvent.mouseDown(sidebar)

vi.advanceTimersByTime(300)

expect(renderResult.queryByRole('sidebar-dropdown-list')).toBeNull()
})
})
8 changes: 7 additions & 1 deletion src/components/SideBar/SideBar.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -127,6 +127,10 @@ export interface SideBarProps {
* Dropdown button text label
*/
dropdownButtonText?: string
/**
* Icon for the dropdown button
*/
dropdownIcon?: ReactNode
/**
* Dropdown button callback function
*/
Expand Down Expand Up @@ -159,7 +163,8 @@ const SideBar = ({
activeDropdown,
dropdownButtonText,
dropdownButtonCallback,
dropdownList
dropdownList,
dropdownIcon
}: SideBarProps) => {
const sidebarRef: MutableRefObject<HTMLDivElement | null> =
useRef<HTMLDivElement>(null)
Expand Down Expand Up @@ -280,6 +285,7 @@ const SideBar = ({
dropdownButtonText={dropdownButtonText}
dropdownButtonCallback={dropdownButtonCallback}
dropdownList={dropdownList}
dropdownIcon={dropdownIcon}
/>
) : (
<Flex
Expand Down
81 changes: 59 additions & 22 deletions src/components/SideBar/SidebarDropdown.tsx
Original file line number Diff line number Diff line change
@@ -1,15 +1,11 @@
import { Dispatch, ReactNode, SetStateAction, useEffect, useState } from 'react'
import {
OfficeBuildingIcon,
ChevronUpIcon,
ChevronDownIcon,
PlusIcon
} from '@heroicons/react/outline'
import { OfficeBuildingIcon, PlusIcon } from '@heroicons/react/outline'
import { CheckCircleIcon } from '@heroicons/react/solid'
import { composeClasses } from 'lib/classes'
import {
Button,
Circle,
Divider,
Flex,
Overflow,
SidebarDropdownListItem,
Expand Down Expand Up @@ -43,6 +39,10 @@ interface SidebarDropdownProps {
* Text for the dropdown button
*/
dropdownButtonText?: string
/**
* Icon for the dropdown button
*/
dropdownIcon?: ReactNode
/**
* Callback for the dropdown button
*/
Expand All @@ -60,11 +60,14 @@ const SidebarDropdown = ({
isLoadingHeaderInfo,
dropdownList,
dropdownButtonText,
dropdownIcon,
dropdownButtonCallback,
setExpand
}: SidebarDropdownProps) => {
const [isOpen, setIsOpen] = useState<boolean>(false)

const isEmtpyList = !dropdownList?.length

const handleToggleDropdown = () => {
if (isLoadingHeaderInfo) return
if (!expand) setExpand(true)
Expand All @@ -81,6 +84,17 @@ const SidebarDropdown = ({
if (isOpen && !expand) setIsOpen(false)
}, [expand])

useEffect(() => {
const handleClick = () => {
if (!isOpen) return
setIsOpen(false)
}
window.addEventListener('mousedown', handleClick)
return () => {
window.removeEventListener('mousedown', handleClick)
}
}, [isOpen])

return (
<div role="sidebar-dropdown" className="relative">
<div className="p-2">
Expand All @@ -96,13 +110,18 @@ const SidebarDropdown = ({
style={{ height: '60px' }}
gap={expand ? '2' : '4'}
onClick={handleToggleDropdown}
onMouseDown={(e) => e.stopPropagation()}
>
<Circle
className="p-1 text-blue-700 bg-blue-50 flex-shrink-0"
width="32px"
height="32px"
>
<OfficeBuildingIcon className="w-5 h-5 text-gray-500" />
{dropdownIcon ? (
dropdownIcon
) : (
<OfficeBuildingIcon className="w-5 h-5 text-blue-700" />
)}
</Circle>
<Flex className="flex-col w-32">
{isLoadingHeaderInfo ? (
Expand Down Expand Up @@ -133,14 +152,29 @@ const SidebarDropdown = ({
justifyContent="center"
className="flex-col"
>
<ChevronUpIcon className="w-3 h-3 text-gray-500" />
<ChevronDownIcon className="w-3 h-3 text-gray-500" />
<svg
data-slot="icon"
fill="none"
strokeWidth="1.5"
stroke="currentColor"
viewBox="0 0 24 24"
xmlns="http://www.w3.org/2000/svg"
aria-hidden="true"
className="w-4 h-4 text-gray-500"
>
<path
strokeLinecap="round"
strokeLinejoin="round"
d="M8.25 15 12 18.75 15.75 15m-7.5-6L12 5.25 15.75 9"
></path>
</svg>
</Flex>
</Flex>
</div>
<Transition show={isOpen} className="absolute top-16 w-full p-2 z-20">
<Flex
className="bg-white h-auto w-full flex-col p-2 border rounded-lg z-50"
role="sidebar-dropdown-list"
className="bg-white h-auto w-full flex-col p-2 border rounded-lg z-50 shadow-lg"
style={{ maxHeight: '224px' }}
>
<Overflow className="flex-grow">
Expand All @@ -166,23 +200,26 @@ const SidebarDropdown = ({
</Text>
<div className="w-4 flex-shrink-0">
{item.isActive && (
<CheckCircleIcon className="w-4 h-4 text-green-500" />
<CheckCircleIcon className="w-4 h-4 text-blue-500" />
)}
</div>
</Flex>
))}
</Overflow>
<Button
role="sidebar-dropdown-button"
variant="ghost"
className="flex justify-center items-center gap-2 h-8 hover:bg-blue-50 transition-all duration-300 ease-in-out cursor-pointer"
onClick={handleButtonCallback}
>
<Text size="xs" className="underline underline-space">
{dropdownButtonText}
</Text>
<PlusIcon className="w-4 h-4" />
</Button>
<Flex justifyContent="center" className="flex-col">
{!isEmtpyList && <Divider light />}
<Button
role="sidebar-dropdown-button"
variant="ghost"
className="flex justify-center items-center gap-2 h-8 hover:bg-blue-50 transition-all duration-300 ease-in-out cursor-pointer"
onClick={handleButtonCallback}
>
<Text size="xs" className="underline underline-space">
{dropdownButtonText}
</Text>
<PlusIcon className="w-4 h-4" />
</Button>
</Flex>
</Flex>
</Transition>
</div>
Expand Down
6 changes: 1 addition & 5 deletions src/components/SideBar/ToggleSideBar.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -40,11 +40,7 @@ const ToggleSideBar = ({
'focus:bg-primary focus:text-white',
'hover:bg-blue-50',
'top-1/2 transform -translate-y-1/2',
alwaysVisible
? expand
? '-right-5'
: '-right-10'
: '-right-5 opacity-0 group-hover:opacity-100',
alwaysVisible ? (expand ? '-right-5' : '-right-10') : '-right-5',
className
)}
onClick={() => setExpand((prev) => !prev)}
Expand Down

0 comments on commit bf8c679

Please sign in to comment.