diff --git a/src/components/EditableTable.tsx b/src/components/EditableTable.tsx index f79fd6fd..37565104 100644 --- a/src/components/EditableTable.tsx +++ b/src/components/EditableTable.tsx @@ -27,6 +27,13 @@ const createGlobalStyleOverride = () => css` border: none; } + .rdg-checkbox { + --rdg-selection-color: none; + background-color: var(--rdg-header-background-color); + display: flex; + align-items: center; + } + .rdg-cell:first-child { border-left: 1px solid var(--chakra-colors-gray-100); } @@ -40,7 +47,7 @@ const createGlobalStyleOverride = () => css` } .rdg-row[aria-selected="true"]:hover { - background-color: var(--chakra-colors-blue-100); + background-color: var(--rdg-row-selected-background-color); } .rdg-cell[aria-selected="true"] { @@ -57,13 +64,14 @@ const createGlobalStyleOverride = () => css` contain: size layout style paint; border-radius: 8px; border: none; - --color: var(--chakra-colors-gray-800); + --rdg-color: var(--chakra-colors-gray-800); --background-color: #fff; - --header-background-color: var(--chakra-colors-primary-50); + --rdg-header-background-color: var(--chakra-colors-gray-50); --rdg-row-hover-background-color: var(--chakra-colors-white); --rdg-selection-color: var(--chakra-colors-blue-400); - --row-selected-background-color: var(--chakra-colors-gray-50); - --font-size: 14px; + --rdg-row-selected-background-color: var(--chakra-colors-rsi-50); + --rdg-frozen-cell-box-shadow: none; + --rdg-font-size: 14px; } ` const ROW_HEIGHT = 42 diff --git a/src/stories/Table.stories.tsx b/src/stories/Table.stories.tsx index 6fb8c474..36437ad2 100644 --- a/src/stories/Table.stories.tsx +++ b/src/stories/Table.stories.tsx @@ -1,33 +1,72 @@ -import { Box, ChakraProvider, extendTheme, Input, Select, Switch } from "@chakra-ui/react" +import { Box, ChakraProvider, Checkbox, extendTheme, Input, Select, Switch } from "@chakra-ui/react" import { EditableTable } from "../components/EditableTable" import { connect, useLape } from "lape" import type { ChangeEvent } from "react" import { colorSchemeOverrides, themeOverrides } from "../theme" import type { Field, Fields } from "../types" +import type { Column, FormatterProps } from "react-data-grid" +import { useRowSelection } from "react-data-grid" export default { title: "React spreadsheet import", } +export const SELECT_COLUMN_KEY = "select-row" + +function SelectFormatter(props: FormatterProps) { + const [isRowSelected, onRowSelectionChange] = useRowSelection() + + return ( + { + onRowSelectionChange({ + row: props.row, + checked: Boolean(event.target.checked), + isShiftClick: (event.nativeEvent as MouseEvent).shiftKey, + }) + }} + /> + ) +} + +const SelectColumn: Column = { + key: SELECT_COLUMN_KEY, + name: "", + width: 35, + maxWidth: 35, + resizable: false, + sortable: false, + frozen: true, + cellClass: "rdg-checkbox", + formatter: SelectFormatter, +} + const theme = extendTheme(colorSchemeOverrides, themeOverrides) const TableComponent = connect(() => { const data = [ { + id: 0, test: "Hello", second: "one", bool: true, }, { + id: 1, test: "Hello", second: "two", bool: true, }, { + id: 2, test: "Hello", second: "one", bool: false, }, { + id: 3, test: "Hello", second: "two", bool: true, @@ -62,10 +101,12 @@ const TableComponent = connect(() => { data: any[] errorCount: number filterErrors: boolean + selectedRows: ReadonlySet }>({ data: data, errorCount: 0, filterErrors: false, + selectedRows: new Set(), }) const updateSelect = (row: any, key: string) => (event: ChangeEvent) => { @@ -75,55 +116,68 @@ const TableComponent = connect(() => { row[key] = event.target.value } const updateSwitch = () => {} - const columns = fields.map((column: Field) => ({ - key: column.key, - name: column.label, - resizable: true, - editable: column.fieldType.type !== "checkbox", - editor: ({ row }: any) => - column.fieldType.type === "select" ? ( - - - - ) : ( - - - - ), - editorOptions: { - editOnClick: true, - }, - formatter: ({ row }: any) => - column.fieldType.type === "checkbox" ? ( - - - - ) : column.fieldType.type === "select" ? ( - column.fieldType.options.find((option) => option.value === row[column.key])?.label - ) : ( - row[column.key] - ), - cellClass: (row: { _errors: any[] | null; id: string }) => - row._errors?.length && row._errors.find((err) => err.fieldName === column.key) ? "rdg-cell-error" : "", - })) + const columns = [ + SelectColumn, + ...fields.map((column: Field) => ({ + key: column.key, + name: column.label, + resizable: true, + editable: column.fieldType.type !== "checkbox", + editor: ({ row }: any) => + column.fieldType.type === "select" ? ( + + + + ) : ( + + + + ), + editorOptions: { + editOnClick: true, + }, + formatter: ({ row }: any) => + column.fieldType.type === "checkbox" ? ( + + + + ) : column.fieldType.type === "select" ? ( + column.fieldType.options.find((option) => option.value === row[column.key])?.label + ) : ( + row[column.key] + ), + cellClass: (row: { _errors: any[] | null; id: string }) => + row._errors?.length && row._errors.find((err) => err.fieldName === column.key) ? "rdg-cell-error" : "", + })), + ] - return + return ( + row.id} + rows={state.data} + columns={columns} + selectedRows={state.selectedRows} + onSelectedRowsChange={(rows) => { + state.selectedRows = rows + }} + /> + ) }) export const Table = () => (