提交 a2051f08 作者: ZhangLingKun

功能:签到领取积分

上级 efd91138
......@@ -39,3 +39,33 @@ export type activityDataType = InterFunction<
>;
// 活动-编辑
export type activityEditType = InterFunction<addActivityItemType & { id: number }, null>;
// 后台——签到调整
export type DataInfoType = InterFunction<
{
id: number;
integral: number;
period: number;
status: boolean;
userContinuousCheckInVO: Array<{
bonusPoints: number;
numberOfDays: number;
}>;
},
NonNullable<unknown>
>;
// 小程序签到列表
export type SignInListType = InterFunction<
NonNullable<unknown>,
{
id: number;
integral: number;
period: number;
status: boolean;
userContinuousCheckInVO: Array<{
bonusPoints: number;
numberOfDays: number;
id: number;
signInId: number;
}>;
}[]
>;
......@@ -3,7 +3,9 @@ import {
activityDataType,
activityEditType,
addActivityType,
DataInfoType,
endActivityType,
SignInListType,
splitCouponDownType,
} from '../interface/activityManage';
import axios from '../request';
......@@ -40,4 +42,11 @@ export class ActivityManageAPI {
static getActivityData: activityDataType = (params) => {
return axios.get('malluser/activity/dataInfo', { params });
};
// 活动后台——签到调整
static DataInfo: DataInfoType = (params) => {
return axios.post('/userapp/insertSignIn', params);
};
// 小程序签到列表
static SignInList: SignInListType = (params) => axios.get('/userapp/SignInList', { params });
}
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
// @ts-ignore
import { limitEntity } from '@/api/modules/role';
function useOptionShow(id: number) {
......
/* eslint-disable */
// @ts-nocheck
import { FC, ForwardedRef, forwardRef, useState, useImperativeHandle } from 'react';
import { DatePicker, Form, Input, message, Modal, Radio, Select, Upload } from 'antd';
import { PlusOutlined } from '@ant-design/icons';
......
......@@ -13,7 +13,7 @@ import useOperate from '~/common/hook/optionHook';
// 活动数据-类型
type dataType = (ReturnType<activityDataType> extends Promise<infer T> ? T : never)['result'];
const ActivityList: FC<{}> = () => {
const ActivityList: FC = () => {
const activityRef = useRef();
const tableColumns: ColumnsType<activityItemType> = [
......@@ -31,21 +31,21 @@ const ActivityList: FC<{}> = () => {
title: '活动类型',
align: 'center',
dataIndex: 'activityType',
render: (text: string, record: activityItemType) => (
render: (_text: string, record: activityItemType) => (
<div>{record.activityType === 1 ? '裂变活动' : '普通活动'}</div>
),
},
{
title: '是否展示',
align: 'center',
render: (text: number, record: activityItemType) => (
render: (_text: number, record: activityItemType) => (
<div>{record.show ? '展示' : '隐藏'}</div>
),
},
{
title: '推广简图',
align: 'center',
render: (text: string, record: activityItemType) => (
render: (_text: string, record: activityItemType) => (
<Image src={record.activityImg} width={50} />
),
},
......@@ -62,13 +62,13 @@ const ActivityList: FC<{}> = () => {
{
title: '状态',
align: 'center',
render: (text: string, record: activityItemType) =>
render: (_text: string, record: activityItemType) =>
record.activityStatus === 1 ? '进行中' : '已下线',
},
{
title: '有效期',
align: 'center',
render: (text: string, record: activityItemType) => (
render: (_text: string, record: activityItemType) => (
<div>
<div>起:{record.startTime}</div>
<div>止:{record.endTime}</div>
......@@ -78,7 +78,7 @@ const ActivityList: FC<{}> = () => {
{
title: '操作',
align: 'center',
render: (text: string, record: activityItemType, index: number) => (
render: (_text: string, record: activityItemType, _index: number) => (
<>
<Button
type='link'
......
import React, { FC, useEffect } from 'react';
import { Form, InputNumber, Modal, ModalProps } from 'antd';
import { InterDataType } from '~/api/interface';
import { SignInListType } from '~/api/interface/activityManage';
// 参数
interface selfProps {
data?: InterDataType<SignInListType>[0]['userContinuousCheckInVO'][0];
onSubmit: (data: InterDataType<SignInListType>[0]['userContinuousCheckInVO'][0]) => void;
}
const AddOrEditModal: FC<ModalProps & selfProps> = ({ open, onCancel, title, data, onSubmit }) => {
// 表单钩子
const [editForm] = Form.useForm();
// 提交数据
const handleSubmit = async () => {
const valid = await editForm.validateFields();
if (!valid) return;
onSubmit(valid);
};
// 关闭弹窗
const handleCancel = (e: React.MouseEvent<HTMLButtonElement, MouseEvent>) => {
editForm.resetFields();
onCancel?.(e);
};
// 组件挂载
useEffect(() => {
if (!data) return;
editForm.setFieldsValue(data);
console.log('组件挂载 --->', data);
}, [open]);
return (
<Modal open={open} onCancel={(e) => handleCancel(e)} title={title} onOk={handleSubmit}>
<Form labelCol={{ span: 6 }} wrapperCol={{ span: 16 }} form={editForm}>
<Form.Item
label='连续签到天数'
name='numberOfDays'
rules={[
{ required: true, message: '请输入连续签到天数' },
{ pattern: /^[0-9]*$/g, message: '请输入整数' },
]}
>
<InputNumber min={1} max={100} placeholder='请输入连续签到天数' addonAfter={'天'} />
</Form.Item>
<Form.Item
label='奖励积分'
name='bonusPoints'
rules={[
{ required: true, message: '请输入奖励积分' },
{ pattern: /^[0-9]*$/g, message: '请输入整数' },
]}
>
<InputNumber min={1} max={10000} placeholder='请输入奖励积分' addonAfter={'积分'} />
</Form.Item>
</Form>
</Modal>
);
};
export default AddOrEditModal;
import { useEffect, useState } from 'react';
import { Button, Form, InputNumber, message, Modal, Switch, Table } from 'antd';
import { PlusOutlined } from '@ant-design/icons';
import AddOrEditModal from './comp/addOrEditModal';
import { ActivityManageAPI } from '~/api';
import { InterDataType } from '~/api/interface';
import { SignInListType } from '~/api/interface/activityManage';
const RewardsManageView = () => {
// 表单钩子
const [formRefs] = Form.useForm();
// 连续签到信息
const [signInfoList, setSignInfoList] =
useState<InterDataType<SignInListType>[0]['userContinuousCheckInVO']>();
// 签到信息
const [signData, setSignData] = useState<InterDataType<SignInListType>[0]>();
// 获取签到设置
const getDataInfo = async () => {
const res = await ActivityManageAPI.SignInList();
if (res && res.code === '200') {
if (!res.result?.length) return;
setSignInfoList(res.result[0]?.userContinuousCheckInVO || []);
setSignData(res.result[0]);
formRefs.setFieldsValue({
period: res.result[0].period,
integral: res.result[0].integral,
status: res.result[0].status,
});
}
};
// 需要编辑的数据
const [editData, setEditData] =
useState<InterDataType<SignInListType>[0]['userContinuousCheckInVO'][0]>();
// 编辑弹窗是否展示
const [addEditShow, setAddEditShow] = useState(false);
// 提交数据
const handleSubmit = async () => {
const valid = await formRefs.validateFields();
if (!valid) return;
const res = await ActivityManageAPI.DataInfo({
...valid,
userContinuousCheckInVO: signInfoList,
id: signData?.id,
});
if (res && res.code === '200') {
message.success('操作成功');
await getDataInfo();
}
// console.log('提价数据 --->', valid);
};
// 删除数据
const handleDelete = (record: InterDataType<SignInListType>[0]) => {
Modal.confirm({
title: '提示',
content: '请确认是否删除?',
onOk: () => {
setSignInfoList(signInfoList?.filter((item) => item.id !== record.id));
message.success('删除成功').then();
},
});
};
// 组件挂载
useEffect(() => {
getDataInfo().then();
}, []);
return (
<>
<div className='rewards-form' style={{ width: '90%' }}>
<Form
labelCol={{ span: 3 }}
wrapperCol={{ offset: 1 }}
form={formRefs}
initialValues={{ show: 1, activityType: 1 }}
>
<Form.Item
label='是否启用'
name='status'
rules={[{ required: true, message: '请选择是否启用' }]}
valuePropName='checked'
>
<Switch />
</Form.Item>
<Form.Item
label='签到周期'
name='period'
rules={[
{ required: true, message: '请输入签到周期' },
{ pattern: /^[0-9]*$/g, message: '请输入整数' },
]}
>
<InputNumber min={7} max={100} placeholder='请输入签到周期' addonAfter={'天'} />
</Form.Item>
<Form.Item
label='每日奖励'
name='integral'
rules={[
{ required: true, message: '请输入每日签到奖励' },
{ pattern: /^[0-9]*$/g, message: '请输入整数' },
]}
>
<InputNumber min={1} max={10000} placeholder='请输入每日签到奖励' addonAfter={'积分'} />
</Form.Item>
<Form.Item label='连续签到' wrapperCol={{ offset: 1, span: 20 }}>
<Button
type={'primary'}
icon={<PlusOutlined />}
style={{ marginBottom: '16px' }}
onClick={() => setAddEditShow(true)}
>
添加连续签到奖励
</Button>
<Table
size={'small'}
bordered
rowKey='id'
columns={[
{
title: '连续签到天数',
dataIndex: 'numberOfDays',
align: 'center',
width: '100px',
render: (text: string) => `${text}天`,
},
{
title: '奖励积分',
dataIndex: 'bonusPoints',
align: 'center',
width: '100px',
render: (text: string) => `${text}分`,
},
{
title: '操作',
dataIndex: 'action',
align: 'center',
width: '100px',
fixed: 'right',
render: (_value, record) => (
<>
<Button
type={'link'}
onClick={() => {
setEditData(record);
setAddEditShow(true);
}}
>
编辑
</Button>
<Button
type={'link'}
danger
onClick={() =>
handleDelete(record as unknown as InterDataType<SignInListType>[0])
}
>
删除
</Button>
</>
),
},
]}
dataSource={signInfoList}
/>
</Form.Item>
</Form>
</div>
<div
className='rewards-action'
style={{ width: '100%', display: 'flex', justifyContent: 'center' }}
>
<Button type={'primary'} onClick={handleSubmit}>
保存
</Button>
</div>
<AddOrEditModal
open={addEditShow}
title={editData ? '编辑' : '添加'}
data={editData}
onCancel={() => {
setAddEditShow(false);
setEditData(undefined);
}}
onSubmit={(e) => {
setSignInfoList([...(signInfoList || []), e]);
setAddEditShow(false);
setEditData(undefined);
}}
/>
</>
);
};
export default RewardsManageView;
......@@ -2,6 +2,7 @@ import { FC } from 'react';
import { Form, Input, Modal, ModalProps, Select } from 'antd';
import { Uploader } from '~/components/uploader';
import { UploadOutlined } from '@ant-design/icons';
// eslint-disable-next-line @typescript-eslint/no-empty-interface
interface selfProps {}
const AddOrEditTagModal: FC<ModalProps & selfProps> = ({ open, onCancel }) => {
......
......@@ -37,6 +37,8 @@ import {
AccountBookOutlined,
EnvironmentOutlined,
BarChartOutlined,
FireOutlined,
InsertRowAboveOutlined,
} from '@ant-design/icons';
import { Spin } from 'antd';
......@@ -169,6 +171,7 @@ import AccountLimit from '~/pages/systemManage/limitManage/roleList'; //账号
import LimitInfo from '~/pages/systemManage/limitManage/limitInfo';
import CustomListDetail from '~/pages/customManage/customList/detail';
import ServiceCategoryDetail from '~/pages/categoryManage/serviceCategoryList/detail';
import RewardsManageView from '~/pages/activityManage/rewardsManage';
const AddressManageView = React.lazy(() => import('~/pages/systemManage/addressManage'));
// const IndustryListView = React.lazy(() => import('~/pages/mallManage/industryManage/industryList')); //行业列表
......@@ -506,6 +509,30 @@ export const routerList: Array<RouteObjectType> = [
],
},
{
path: '/activityManage',
element: <LayoutView />,
errorElement: <ErrorPage />,
meta: {
id: 1100,
icon: <FireOutlined />,
title: '营销管理',
develop: true,
},
children: [
{
path: '/activityManage/rewardsManage',
element: withLoadingComponent(<RewardsManageView />),
errorElement: <ErrorPage />,
meta: {
id: 1110,
title: '签到奖励',
icon: <InsertRowAboveOutlined />,
develop: true,
},
},
],
},
{
path: '/forumManage',
element: <LayoutView />,
errorElement: <ErrorPage />,
......
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论