new
This commit is contained in:
319
src/pages/rules/components/CopyRule/MultiCopyPopup.tsx
Normal file
319
src/pages/rules/components/CopyRule/MultiCopyPopup.tsx
Normal file
@@ -0,0 +1,319 @@
|
||||
import {
|
||||
type ProFormInstance,
|
||||
StepsForm,
|
||||
useBreakpoint,
|
||||
} from '@ant-design/pro-components';
|
||||
import { Button, Divider, Flex, Input, Modal, Space, Typography } from 'antd';
|
||||
import { createContext, useMemo, useRef, useState } from 'react';
|
||||
import useRichFormat from '@/hooks/useRichI18n';
|
||||
import { $t } from '@/utils/i18n';
|
||||
import '../style.less';
|
||||
import { flushSync } from 'react-dom';
|
||||
import { type SchemaType, schemaMap } from '../../ruleFormSchema';
|
||||
import { handleEmptyValuesFunc } from '../../utils';
|
||||
import BatchCloneModal from './comp/BatchCloneModal';
|
||||
import Step1 from './comp/Step1';
|
||||
import Step2 from './comp/Step2';
|
||||
|
||||
const { Text, Title } = Typography;
|
||||
type MultiCopyPopupContextValue = {
|
||||
ruleMeta: Record<string, any>;
|
||||
dataSourceList: API.DataSourceListItem[];
|
||||
currentRuleType: number;
|
||||
targetDataSourceId: string | number | null;
|
||||
selectRules: API.RuleListItem[];
|
||||
setSelectRules: (rules: API.RuleListItem[]) => void;
|
||||
currentSchemaMap: Record<string, any>;
|
||||
};
|
||||
export const MultiCopyPopupContext = createContext<MultiCopyPopupContextValue>({
|
||||
ruleMeta: {},
|
||||
dataSourceList: [],
|
||||
currentRuleType: 0,
|
||||
targetDataSourceId: null,
|
||||
selectRules: [],
|
||||
setSelectRules: () => {},
|
||||
currentSchemaMap: {},
|
||||
});
|
||||
type MultiCopyPopupProps = {
|
||||
visible: boolean;
|
||||
ruleMeta: Record<string, any>;
|
||||
dataSourceList: API.DataSourceListItem[];
|
||||
currentRuleType: number;
|
||||
onDone: (refresh?: boolean) => void;
|
||||
};
|
||||
|
||||
const MultiCopyPopup = ({
|
||||
visible,
|
||||
ruleMeta,
|
||||
onDone,
|
||||
currentRuleType,
|
||||
dataSourceList,
|
||||
}: MultiCopyPopupProps) => {
|
||||
const { richFormat } = useRichFormat();
|
||||
const screens = useBreakpoint();
|
||||
|
||||
const currentSchemaMap =
|
||||
schemaMap[currentRuleType as unknown as SchemaType]?.({ richFormat }) || {};
|
||||
const formMapRef = useRef<
|
||||
React.RefObject<ProFormInstance<any> | undefined>[]
|
||||
>([]);
|
||||
const [targetDataSourceId, setTargetDataSourceId] = useState<
|
||||
string | number | null
|
||||
>(null);
|
||||
const [selectRules, setSelectRules] = useState<API.RuleListItem[]>([]);
|
||||
const [checkedIdsList, setCheckedIdsList] = useState<Array<string | number>>(
|
||||
[],
|
||||
);
|
||||
const [inputValue, setInputValue] = useState('');
|
||||
const [batchCloneModalVisible, setBatchCloneModalVisible] = useState(false);
|
||||
const [selectedRows, setSelectedRows] = useState<Partial<API.RuleListItem>[]>(
|
||||
[],
|
||||
);
|
||||
|
||||
const submitRuleList = useMemo(() => {
|
||||
return selectRules.filter((item) => checkedIdsList.includes(item.id));
|
||||
}, [selectRules, checkedIdsList]);
|
||||
|
||||
const targetDataSource = useMemo(() => {
|
||||
return dataSourceList.find((item) => item.id === targetDataSourceId);
|
||||
}, [targetDataSourceId, dataSourceList]);
|
||||
|
||||
const handleCancel = () => {
|
||||
setBatchCloneModalVisible(false);
|
||||
setSelectedRows([]);
|
||||
setSelectRules([]);
|
||||
setCheckedIdsList([]);
|
||||
setInputValue('');
|
||||
setTargetDataSourceId(null);
|
||||
};
|
||||
|
||||
return (
|
||||
<Modal
|
||||
width={['xl', 'xxl'].includes(screens || '') ? '50%' : '95%'}
|
||||
open={visible}
|
||||
centered
|
||||
destroyOnHidden
|
||||
onCancel={() => {
|
||||
handleCancel();
|
||||
onDone();
|
||||
}}
|
||||
title={$t('pages.clones.title')}
|
||||
footer={null}
|
||||
maskClosable={false}
|
||||
styles={{
|
||||
body: {
|
||||
maxHeight: '90vh',
|
||||
overflowY: 'auto',
|
||||
overflowX: 'hidden',
|
||||
marginRight: -10,
|
||||
paddingRight: 8,
|
||||
},
|
||||
}}
|
||||
>
|
||||
<MultiCopyPopupContext.Provider
|
||||
value={{
|
||||
ruleMeta,
|
||||
dataSourceList,
|
||||
currentRuleType,
|
||||
targetDataSourceId,
|
||||
selectRules,
|
||||
setSelectRules,
|
||||
currentSchemaMap,
|
||||
}}
|
||||
>
|
||||
<StepsForm
|
||||
formMapRef={formMapRef}
|
||||
onFinish={async (values) => {
|
||||
const editNameRules = values?.step2 || {};
|
||||
|
||||
const submitValues = submitRuleList.map((item) => {
|
||||
const tmpValues = handleEmptyValuesFunc(item);
|
||||
const tmpValues2 =
|
||||
currentSchemaMap?.transformSubmitValue?.(tmpValues) ||
|
||||
tmpValues;
|
||||
const submitValues = {
|
||||
...tmpValues2,
|
||||
dataSourceId: targetDataSourceId,
|
||||
name:
|
||||
editNameRules[item.id] ||
|
||||
`${item.name || ruleMeta?.title || ''} - ${targetDataSource?.sourceName || ''}`,
|
||||
id: void 0,
|
||||
groupFilter: '',
|
||||
};
|
||||
|
||||
if (currentSchemaMap?.symbolFormShow) {
|
||||
submitValues.param2 = '';
|
||||
}
|
||||
if (currentSchemaMap?.assetFormShow) {
|
||||
submitValues.param1 = '';
|
||||
}
|
||||
|
||||
const tmp: Record<string, any> = {
|
||||
companyId: submitValues.companyId,
|
||||
dataSourceId: submitValues.dataSourceId,
|
||||
groupFilter: submitValues.groupFilter,
|
||||
name: submitValues.name,
|
||||
type: submitValues.type,
|
||||
};
|
||||
for (const key in submitValues) {
|
||||
if (key.indexOf('param') !== -1) {
|
||||
tmp[key] = submitValues[key];
|
||||
}
|
||||
}
|
||||
return tmp;
|
||||
});
|
||||
|
||||
setSelectedRows(submitValues);
|
||||
setBatchCloneModalVisible(true);
|
||||
}}
|
||||
submitter={{
|
||||
render: (props) => {
|
||||
if (props.step === 0) {
|
||||
return [
|
||||
<Button key="cancel" onClick={() => onDone()}>
|
||||
{$t('pages.model.cancel')}
|
||||
</Button>,
|
||||
<Button
|
||||
disabled={selectRules.length === 0}
|
||||
key="goToTree"
|
||||
type="primary"
|
||||
onClick={() => props.onSubmit?.()}
|
||||
>
|
||||
{$t('pages.clones.step1.confirm')}
|
||||
</Button>,
|
||||
];
|
||||
}
|
||||
|
||||
if (props.step === 1) {
|
||||
return [
|
||||
<Button key="pre" onClick={() => props.onPre?.()}>
|
||||
← {$t('pages.clones.back')}
|
||||
</Button>,
|
||||
<Button
|
||||
disabled={checkedIdsList.length === 0}
|
||||
type="primary"
|
||||
key="goToTree"
|
||||
onClick={() => props.onSubmit?.()}
|
||||
>
|
||||
{$t('pages.clones.step2.confirm')}
|
||||
</Button>,
|
||||
];
|
||||
}
|
||||
|
||||
return [
|
||||
<Button
|
||||
key="gotoTwo"
|
||||
onClick={() => {
|
||||
setInputValue('');
|
||||
props.onPre?.();
|
||||
}}
|
||||
>
|
||||
← {$t('pages.clones.backPreview')}
|
||||
</Button>,
|
||||
<Button
|
||||
disabled={
|
||||
submitRuleList.length === 0 ||
|
||||
inputValue !== targetDataSource?.sourceName
|
||||
}
|
||||
variant="solid"
|
||||
color="danger"
|
||||
key="goToTree"
|
||||
onClick={() => props.onSubmit?.()}
|
||||
>
|
||||
{$t('pages.clones.step3.confirm')}
|
||||
</Button>,
|
||||
];
|
||||
},
|
||||
}}
|
||||
>
|
||||
<StepsForm.StepForm
|
||||
name="step1"
|
||||
title={$t('pages.clones.step1.title')}
|
||||
onValuesChange={({ sourceDataSourceId }) => {
|
||||
if (sourceDataSourceId) {
|
||||
const curFormRef = formMapRef?.current?.[0]?.current;
|
||||
const curTargetDataSourceId =
|
||||
curFormRef?.getFieldValue('targetDataSourceId');
|
||||
if (curTargetDataSourceId === sourceDataSourceId) {
|
||||
let targetDataSourceId: string | number | null = null;
|
||||
for (const item of dataSourceList) {
|
||||
if (item.id !== sourceDataSourceId) {
|
||||
targetDataSourceId = item.id;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (targetDataSourceId) {
|
||||
curFormRef?.setFieldsValue({
|
||||
targetDataSourceId,
|
||||
});
|
||||
setTargetDataSourceId(targetDataSourceId);
|
||||
}
|
||||
}
|
||||
}
|
||||
}}
|
||||
>
|
||||
<Step1
|
||||
formMapRef={formMapRef}
|
||||
setTargetDataSourceId={setTargetDataSourceId}
|
||||
/>
|
||||
</StepsForm.StepForm>
|
||||
<StepsForm.StepForm
|
||||
name="step2"
|
||||
title={$t('pages.clones.step2.title')}
|
||||
>
|
||||
<Step2 setCheckedIdsList={setCheckedIdsList} />
|
||||
</StepsForm.StepForm>
|
||||
<StepsForm.StepForm
|
||||
name="time"
|
||||
title={$t('pages.clones.step3.title')}
|
||||
>
|
||||
<div className="confirm-container">
|
||||
<Flex className="confirm-space" align="center" justify="center">
|
||||
<Space direction="vertical" align="center">
|
||||
<Title level={5}>
|
||||
{$t('pages.clones.step3.confirmTitle', {
|
||||
cloneCount: checkedIdsList.length,
|
||||
target: targetDataSource?.sourceName || '',
|
||||
})}
|
||||
</Title>
|
||||
<Text type="secondary">
|
||||
{$t('pages.clones.step3.confirmTips')}
|
||||
</Text>
|
||||
<Input
|
||||
placeholder={targetDataSource?.sourceName || ''}
|
||||
className="text-center"
|
||||
size="large"
|
||||
value={inputValue}
|
||||
onChange={(e) => setInputValue(e.target.value)}
|
||||
/>
|
||||
<Text type="secondary">
|
||||
{$t('pages.clones.step3.confirmTips2')}
|
||||
</Text>
|
||||
</Space>
|
||||
</Flex>
|
||||
</div>
|
||||
<Divider style={{ margin: '16px 0' }} />
|
||||
</StepsForm.StepForm>
|
||||
</StepsForm>
|
||||
</MultiCopyPopupContext.Provider>
|
||||
|
||||
<BatchCloneModal
|
||||
visible={batchCloneModalVisible}
|
||||
selectedRows={selectedRows}
|
||||
onClose={(cb) => {
|
||||
setBatchCloneModalVisible(false);
|
||||
cb?.();
|
||||
}}
|
||||
onFinish={(cb) => {
|
||||
flushSync(() => {
|
||||
setBatchCloneModalVisible(false);
|
||||
});
|
||||
cb?.();
|
||||
handleCancel();
|
||||
onDone?.(true);
|
||||
}}
|
||||
/>
|
||||
</Modal>
|
||||
);
|
||||
};
|
||||
export default MultiCopyPopup;
|
||||
Reference in New Issue
Block a user