|
| 1 | +/* |
| 2 | + * Copyright (c) 2024. Devtron Inc. |
| 3 | + */ |
| 4 | + |
| 5 | +import { useEffect, useMemo, useState } from 'react' |
| 6 | +import { ReactComponent as ICFilter } from '@Icons/ic-filter.svg' |
| 7 | +import { ReactComponent as ICFilterApplied } from '@Icons/ic-filter-applied.svg' |
| 8 | +import SelectPicker from './SelectPicker.component' |
| 9 | +import { FilterSelectPickerProps, SelectPickerOptionType, SelectPickerProps } from './type' |
| 10 | + |
| 11 | +const FilterSelectPicker = ({ |
| 12 | + appliedFilterOptions, |
| 13 | + handleApplyFilter, |
| 14 | + options, |
| 15 | + ...props |
| 16 | +}: FilterSelectPickerProps) => { |
| 17 | + const [isMenuOpen, setIsMenuOpen] = useState(false) |
| 18 | + const [selectedOptions, setSelectedOptions] = useState<SelectPickerOptionType[]>( |
| 19 | + structuredClone(appliedFilterOptions ?? []), |
| 20 | + ) |
| 21 | + |
| 22 | + const appliedFiltersCount = appliedFilterOptions?.length ?? 0 |
| 23 | + |
| 24 | + useEffect(() => { |
| 25 | + setSelectedOptions(appliedFilterOptions ?? []) |
| 26 | + }, [appliedFilterOptions]) |
| 27 | + |
| 28 | + const filterIcon = useMemo( |
| 29 | + () => (appliedFiltersCount ? <ICFilterApplied className="p-2" /> : <ICFilter className="p-2" />), |
| 30 | + [appliedFiltersCount], |
| 31 | + ) |
| 32 | + |
| 33 | + const openMenu = () => { |
| 34 | + setIsMenuOpen(true) |
| 35 | + } |
| 36 | + |
| 37 | + const closeMenu = () => { |
| 38 | + setIsMenuOpen(false) |
| 39 | + } |
| 40 | + |
| 41 | + const handleSelectOnChange: SelectPickerProps<number | string, true>['onChange'] = (selectedOptionsToUpdate) => { |
| 42 | + setSelectedOptions(structuredClone(selectedOptionsToUpdate)) |
| 43 | + } |
| 44 | + |
| 45 | + const handleMenuClose = () => { |
| 46 | + closeMenu() |
| 47 | + setSelectedOptions(structuredClone(appliedFilterOptions ?? [])) |
| 48 | + } |
| 49 | + |
| 50 | + const renderApplyButton = (optionsSelected: Parameters<FilterSelectPickerProps['handleApplyFilter']>[0]) => { |
| 51 | + const handleApplyClick = () => { |
| 52 | + handleApplyFilter(optionsSelected) |
| 53 | + closeMenu() |
| 54 | + } |
| 55 | + |
| 56 | + return ( |
| 57 | + <div className="p-8 dc__border-top-n1"> |
| 58 | + <button |
| 59 | + type="button" |
| 60 | + className="dc__unset-button-styles w-100 br-4 h-28 flex bcb-5 cn-0 fw-6 lh-28 fs-12 h-28 br-4 pt-5 pr-12 pb-5 pl-12" |
| 61 | + onClick={handleApplyClick} |
| 62 | + aria-label="Apply filters" |
| 63 | + > |
| 64 | + Apply |
| 65 | + </button> |
| 66 | + </div> |
| 67 | + ) |
| 68 | + } |
| 69 | + |
| 70 | + return ( |
| 71 | + <div className="dc__mxw-250"> |
| 72 | + <SelectPicker |
| 73 | + {...props} |
| 74 | + options={options} |
| 75 | + value={selectedOptions} |
| 76 | + isMulti |
| 77 | + menuIsOpen={isMenuOpen} |
| 78 | + onMenuOpen={openMenu} |
| 79 | + onMenuClose={handleMenuClose} |
| 80 | + onChange={handleSelectOnChange} |
| 81 | + renderMenuListFooter={renderApplyButton} |
| 82 | + controlShouldRenderValue={false} |
| 83 | + showSelectedOptionsCount |
| 84 | + isSearchable |
| 85 | + isClearable={false} |
| 86 | + customSelectedOptionsCount={appliedFiltersCount} |
| 87 | + icon={filterIcon} |
| 88 | + /> |
| 89 | + </div> |
| 90 | + ) |
| 91 | +} |
| 92 | + |
| 93 | +export default FilterSelectPicker |
0 commit comments