Skip to content

Commit

Permalink
Merge branch 'feat/bulk-select' into feat/build-infra
Browse files Browse the repository at this point in the history
  • Loading branch information
AbhishekA1509 committed Feb 2, 2024
2 parents 3ce9ebe + e27a6ee commit 42eea9e
Show file tree
Hide file tree
Showing 6 changed files with 92 additions and 24 deletions.
10 changes: 8 additions & 2 deletions src/Assets/Icon/ic-close.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
10 changes: 3 additions & 7 deletions src/Shared/Components/BulkSelection/BulkSelection.tsx
Original file line number Diff line number Diff line change
@@ -1,19 +1,15 @@
import BulkSelectionDropdownItems from './BulkSelectionDropdownItems'
import { CHECKBOX_VALUE, Checkbox, PopupMenu, noop } from '../../../Common'
import { useBulkSelection } from './BulkSelectionProvider'
import { BulkSelectionDropdownItemsType, BulkSelectionEvents, BulkSelectionProps } from './types'
import { BULK_DROPDOWN_TEST_ID, BulkSelectionOptionsLabels } from './constants'
import { ReactComponent as ICChevronDown } from '../../../Assets/Icon/ic-chevron-down.svg'
import { ReactComponent as ICCheckSquare } from '../../../Assets/Icon/ic-check-square.svg'
import { ReactComponent as ICCheckAll } from '../../../Assets/Icon/ic-check-all.svg'
import { ReactComponent as ICClose } from '../../../Assets/Icon/ic-close.svg'

const BulkSelection = <T,>({
checkboxValue,
isChecked,
selectedIdentifiers,
handleBulkSelection,
showPagination,
}: BulkSelectionProps<T>) => {
const BulkSelection = <T,>({ showPagination }: BulkSelectionProps) => {
const { handleBulkSelection, selectedIdentifiers, isChecked, checkboxValue } = useBulkSelection<T>()
const areOptionsSelected = Object.keys(selectedIdentifiers).length > 0
const BulkSelectionItems: BulkSelectionDropdownItemsType[] = [
{
Expand Down
Original file line number Diff line number Diff line change
@@ -1,17 +1,36 @@
import { useState } from 'react'
import { SELECT_ALL_ACROSS_PAGES_LOCATOR, getInvalidActionMessage } from './constants'
import { createContext, useContext, useMemo, useState } from 'react'
import { BULK_SELECTION_CONTEXT_ERROR, SELECT_ALL_ACROSS_PAGES_LOCATOR, getInvalidActionMessage } from './constants'
import {
BulkSelectionEvents,
GetBulkSelectionCheckboxValuesType,
HandleBulkSelectionType,
SelectAllDialogStatus,
UseBulkSelectionProps,
UseBulkSelectionReturnType,
} from './types'
import { CHECKBOX_VALUE, noop } from '../../../Common'

// giving type any here since not exporting this context, rather using it through useBulkSelection hook which is typed
const BulkSelectionContext = createContext<UseBulkSelectionReturnType<any>>({
selectedIdentifiers: {},
handleBulkSelection: noop,
isChecked: false,
checkboxValue: CHECKBOX_VALUE.CHECKED,
})

export const useBulkSelection = <T,>() => {
const context = useContext<UseBulkSelectionReturnType<T>>(BulkSelectionContext)
if (!context) {
throw new Error(BULK_SELECTION_CONTEXT_ERROR)
}
return context
}

const useBulkSelection = <T,>({
export const BulkSelectionProvider = <T,>({
children,
identifiers,
getSelectAllDialogStatus,
}: UseBulkSelectionProps<T>): UseBulkSelectionReturnType<T> => {
}: UseBulkSelectionProps<T>) => {
const [selectedIdentifiers, setSelectedIdentifiers] = useState<T>({} as T)

const setIdentifiersAfterClear = (newIdentifiers: T, selectedIds: (number | string)[]) => {
Expand Down Expand Up @@ -90,10 +109,52 @@ const useBulkSelection = <T,>({
}
}

return {
handleBulkSelection,
selectedIdentifiers,
const getBulkSelectionCheckboxValues = (): GetBulkSelectionCheckboxValuesType => {
const selectedIdentifiersArray = Object.keys(selectedIdentifiers)
if (selectedIdentifiersArray.length === 0) {
return {
isChecked: false,
checkboxValue: CHECKBOX_VALUE.CHECKED,
}
}

// if selectedIdentifiers contains select all across pages locator then it means all are selected
if (selectedIdentifiers[SELECT_ALL_ACROSS_PAGES_LOCATOR]) {
return {
isChecked: true,
checkboxValue: CHECKBOX_VALUE.BULK_CHECKED,
}
}

// if all the identifiers are selected then CHECKED else intermediate
const areAllPresentIdentifiersSelected = selectedIdentifiersArray.every(
(identifierId) => identifiers[identifierId],
)

if (areAllPresentIdentifiersSelected) {
return {
isChecked: true,
checkboxValue: CHECKBOX_VALUE.CHECKED,
}
}

return {
isChecked: true,
checkboxValue: CHECKBOX_VALUE.INTERMEDIATE,
}
}
}

export default useBulkSelection
const { isChecked, checkboxValue } = getBulkSelectionCheckboxValues()

const value = useMemo(
() => ({
selectedIdentifiers,
handleBulkSelection,
isChecked,
checkboxValue,
}),
[selectedIdentifiers, handleBulkSelection, isChecked, checkboxValue],
)

return <BulkSelectionContext.Provider value={value}>{children}</BulkSelectionContext.Provider>
}
1 change: 1 addition & 0 deletions src/Shared/Components/BulkSelection/constants.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -10,3 +10,4 @@ export const BulkSelectionOptionsLabels = {
// Considering application can not be named as *
export const SELECT_ALL_ACROSS_PAGES_LOCATOR = '*' as const
export const getInvalidActionMessage = (action: string) => `Invalid action ${action} passed to useBulkSelection`
export const BULK_SELECTION_CONTEXT_ERROR = 'useBulkSelection must be used within BulkSelectionContext'
2 changes: 1 addition & 1 deletion src/Shared/Components/BulkSelection/index.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
export { default as BulkSelection } from './BulkSelection'
export { default as useBulkSelection } from './UseBulkSelection'
export * from './BulkSelectionProvider'
export * from './types'
export * from './constants'
14 changes: 9 additions & 5 deletions src/Shared/Components/BulkSelection/types.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -18,14 +18,17 @@ export interface HandleBulkSelectionType<T> {
}
}

export interface UseBulkSelectionReturnType<T> {
export interface GetBulkSelectionCheckboxValuesType {
isChecked: boolean
checkboxValue: CHECKBOX_VALUE
}

export interface UseBulkSelectionReturnType<T> extends GetBulkSelectionCheckboxValuesType {
selectedIdentifiers: T
handleBulkSelection: ({ action, data }: HandleBulkSelectionType<T>) => void
}

export interface BulkSelectionProps<T> extends UseBulkSelectionReturnType<T> {
checkboxValue: CHECKBOX_VALUE
isChecked: boolean
export interface BulkSelectionProps {
showPagination: boolean
}

Expand All @@ -38,7 +41,7 @@ export interface BulkSelectionDropdownItemsType {

export interface BulkSelectionDropdownItemsProps<T>
extends BulkSelectionDropdownItemsType,
Pick<BulkSelectionProps<T>, 'handleBulkSelection'> {}
Pick<UseBulkSelectionReturnType<T>, 'handleBulkSelection'> {}

export enum SelectAllDialogStatus {
OPEN = 'OPEN',
Expand All @@ -58,4 +61,5 @@ export interface UseBulkSelectionProps<T> {
* Act as buffer between select all across pages and select all on page state
*/
getSelectAllDialogStatus: () => SelectAllDialogStatus
children?: React.ReactNode
}

0 comments on commit 42eea9e

Please sign in to comment.