From 4b186714d0491af7c6c9bc53ec046d65cca2f549 Mon Sep 17 00:00:00 2001
From: zyf <81416635+Zyf665@users.noreply.github.com>
Date: Mon, 18 Nov 2024 11:31:38 +0800
Subject: [PATCH] fix(Table): preserve custom event handlers in row selection
(#51661)
---
.../__tests__/Table.rowSelection.test.tsx | 72 +++++++++++++++++++
components/table/hooks/useSelection.tsx | 19 +++--
2 files changed, 86 insertions(+), 5 deletions(-)
diff --git a/components/table/__tests__/Table.rowSelection.test.tsx b/components/table/__tests__/Table.rowSelection.test.tsx
index 4f86b15b10..4ba6f2c8b3 100644
--- a/components/table/__tests__/Table.rowSelection.test.tsx
+++ b/components/table/__tests__/Table.rowSelection.test.tsx
@@ -1905,4 +1905,76 @@ describe('Table.rowSelection', () => {
);
});
});
+
+ it('should trigger both custom and internal checkbox events', () => {
+ const onClickMock = jest.fn();
+ const onChangeMock = jest.fn();
+
+ const getCheckboxProps = () => ({
+ onClick: onClickMock,
+ onChange: onChangeMock,
+ });
+
+ const { container } = render(
+
,
+ );
+
+ const firstRowCheckbox = container.querySelector('tbody tr:first-child input[type="checkbox"]');
+ expect(firstRowCheckbox).toBeTruthy();
+
+ fireEvent.click(firstRowCheckbox!);
+
+ expect(onClickMock).toHaveBeenCalled();
+ expect(onClickMock.mock.calls.length).toBe(1);
+
+ expect(onChangeMock).toHaveBeenCalled();
+ expect(onChangeMock.mock.calls.length).toBe(1);
+
+ const changeEvent = onChangeMock.mock.calls[0][0];
+ expect(changeEvent).toHaveProperty('target');
+ expect(changeEvent.target).toHaveProperty('checked');
+ });
+
+ it('should trigger both custom and internal radio events', () => {
+ const onClickMock = jest.fn();
+ const onChangeMock = jest.fn();
+
+ const getCheckboxProps = () => ({
+ onClick: onClickMock,
+ onChange: onChangeMock,
+ });
+
+ const { container } = render(
+ ,
+ );
+
+ const firstRowRadio = container.querySelector('tbody tr:first-child input[type="radio"]');
+ expect(firstRowRadio).toBeTruthy();
+
+ fireEvent.click(firstRowRadio!);
+
+ expect(onClickMock).toHaveBeenCalled();
+ expect(onClickMock.mock.calls.length).toBe(1);
+
+ expect(onChangeMock).toHaveBeenCalled();
+ expect(onChangeMock.mock.calls.length).toBe(1);
+
+ const changeEvent = onChangeMock.mock.calls[0][0];
+ expect(changeEvent).toHaveProperty('target');
+ expect(changeEvent.target).toHaveProperty('checked');
+ });
});
diff --git a/components/table/hooks/useSelection.tsx b/components/table/hooks/useSelection.tsx
index 8cf525fe47..0d7f77285c 100644
--- a/components/table/hooks/useSelection.tsx
+++ b/components/table/hooks/useSelection.tsx
@@ -496,17 +496,21 @@ const useSelection = (
renderCell = (_, record, index) => {
const key = getRowKey(record, index);
const checked = keySet.has(key);
-
+ const checkboxProps = checkboxPropsMap.get(key);
return {
node: (
e.stopPropagation()}
+ onClick={(e) => {
+ e.stopPropagation();
+ checkboxProps?.onClick?.(e);
+ }}
onChange={(event) => {
if (!keySet.has(key)) {
triggerSingleSelection(key, true, [key], event.nativeEvent);
}
+ checkboxProps?.onChange?.(event);
}}
/>
),
@@ -538,8 +542,12 @@ const useSelection = (
indeterminate={mergedIndeterminate}
checked={checked}
skipGroup
- onClick={(e) => e.stopPropagation()}
- onChange={({ nativeEvent }) => {
+ onClick={(e) => {
+ e.stopPropagation();
+ checkboxProps?.onClick?.(e);
+ }}
+ onChange={(event) => {
+ const { nativeEvent } = event;
const { shiftKey } = nativeEvent;
const currentSelectedIndex = recordKeys.findIndex((item) => item === key);
const isMultiple = derivedSelectedKeys.some((item) => recordKeys.includes(item));
@@ -595,6 +603,7 @@ const useSelection = (
} else {
updatePrevSelectedIndex(currentSelectedIndex);
}
+ checkboxProps?.onChange?.(event);
}}
/>
),