import { PureComponent } from 'react'; import Checkbox, { ICheckboxProps } from '../checkbox'; import Store from './Store'; export interface IGridSelectionAllCheckboxProps { store: Store; /** * Only includes non-disabled rows */ datasets: ReadonlyArray; /** * Only includes disabled rows. * * These are split into two arrays because of historical reasons. * It only affects non-disabled rows when select-all checkbox is checked/unchecked. */ disabledDatasets: ReadonlyArray; getDataKey: (data: Data, rowIndex: number | string) => string; disabled: boolean; onSelect: ( type: 'selectAll' | 'removeAll', /** * Only includes non-disabled rows because we cannot toggle disabled rows. */ datasets: ReadonlyArray ) => void; } interface IGridSelectionAllCheckboxState { checked: boolean; indeterminate: boolean; } class SelectionCheckboxAll extends PureComponent< IGridSelectionAllCheckboxProps, IGridSelectionAllCheckboxState > { constructor(props: IGridSelectionAllCheckboxProps) { super(props); this.state = { checked: this.getCheckState(props), indeterminate: this.getIndeterminateState(props), }; } unsubscribe: any; subscribe = () => { const { store } = this.props; this.unsubscribe = store.subscribe('selectedRowKeys', () => { this.setCheckState(this.props); }); }; getCheckBoxState = ( props: IGridSelectionAllCheckboxProps, type: 'every' | 'some' ) => { const { datasets, disabledDatasets, store, getDataKey } = props; // Use `datasets` if it's non empty, otherwise use `disabledDatasets` const activeDatasets = datasets?.length ? datasets : disabledDatasets; const selectedRowKeys = store.getState('selectedRowKeys') ?? []; if (selectedRowKeys.length === 0) return false; if (type === 'every') { return activeDatasets.every( (data, index) => selectedRowKeys.indexOf(getDataKey(data, index)) !== -1 ); } return activeDatasets.some( (data, index) => selectedRowKeys.indexOf(getDataKey(data, index)) !== -1 ); }; getCheckState = (props: IGridSelectionAllCheckboxProps) => { return this.getCheckBoxState(props, 'every'); }; getIndeterminateState = (props: IGridSelectionAllCheckboxProps) => { return this.getCheckBoxState(props, 'some'); }; setCheckState = (props: IGridSelectionAllCheckboxProps) => { const checked = this.getCheckState(props); const indeterminate = this.getIndeterminateState(props); this.setState({ checked, indeterminate, }); }; onChange: ICheckboxProps['onChange'] = e => { const { datasets } = this.props; const checked = e.target.checked; this.props.onSelect(checked ? 'selectAll' : 'removeAll', datasets); }; componentDidMount() { this.subscribe(); } // 等重构再删了吧,改不动 // eslint-disable-next-line react/no-deprecated componentWillReceiveProps(nextProps: IGridSelectionAllCheckboxProps) { this.setCheckState(nextProps); } componentWillUnmount() { if (this.unsubscribe) { this.unsubscribe(); } } render() { const { checked, indeterminate } = this.state; const { disabled } = this.props; const props = { checked, indeterminate: indeterminate && checked ? false : indeterminate, }; return ; } } export default SelectionCheckboxAll;