完成:黄家明项目的开发并存档
This commit is contained in:
@@ -52,6 +52,8 @@ export interface HjmCar {
|
|||||||
address?: string,
|
address?: string,
|
||||||
// 用户ID
|
// 用户ID
|
||||||
userId?: number;
|
userId?: number;
|
||||||
|
// 认领状态
|
||||||
|
claim?: number;
|
||||||
// 排序(数字越小越靠前)
|
// 排序(数字越小越靠前)
|
||||||
sortNumber?: number;
|
sortNumber?: number;
|
||||||
// 备注
|
// 备注
|
||||||
|
|||||||
101
src/api/hjm/hjmViolation/index.ts
Normal file
101
src/api/hjm/hjmViolation/index.ts
Normal file
@@ -0,0 +1,101 @@
|
|||||||
|
import request from '@/utils/request';
|
||||||
|
import type { ApiResult, PageResult } from '@/api/index';
|
||||||
|
import type { HjmViolation, HjmViolationParam } from './model';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 分页查询黄家明_违章记录
|
||||||
|
*/
|
||||||
|
export async function pageHjmViolation(params: HjmViolationParam) {
|
||||||
|
const res = await request.get<ApiResult<PageResult<HjmViolation>>>(
|
||||||
|
'/hjm/hjm-violation/page',
|
||||||
|
params
|
||||||
|
);
|
||||||
|
if (res.code === 0) {
|
||||||
|
return res.data;
|
||||||
|
}
|
||||||
|
return Promise.reject(new Error(res.message));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 查询黄家明_违章记录列表
|
||||||
|
*/
|
||||||
|
export async function listHjmViolation(params?: HjmViolationParam) {
|
||||||
|
const res = await request.get<ApiResult<HjmViolation[]>>(
|
||||||
|
'/hjm/hjm-violation',
|
||||||
|
params
|
||||||
|
);
|
||||||
|
if (res.code === 0 && res.data) {
|
||||||
|
return res.data;
|
||||||
|
}
|
||||||
|
return Promise.reject(new Error(res.message));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 添加黄家明_违章记录
|
||||||
|
*/
|
||||||
|
export async function addHjmViolation(data: HjmViolation) {
|
||||||
|
const res = await request.post<ApiResult<unknown>>(
|
||||||
|
'/hjm/hjm-violation',
|
||||||
|
data
|
||||||
|
);
|
||||||
|
if (res.code === 0) {
|
||||||
|
return res.message;
|
||||||
|
}
|
||||||
|
return Promise.reject(new Error(res.message));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 修改黄家明_违章记录
|
||||||
|
*/
|
||||||
|
export async function updateHjmViolation(data: HjmViolation) {
|
||||||
|
const res = await request.put<ApiResult<unknown>>(
|
||||||
|
'/hjm/hjm-violation',
|
||||||
|
data
|
||||||
|
);
|
||||||
|
if (res.code === 0) {
|
||||||
|
return res.message;
|
||||||
|
}
|
||||||
|
return Promise.reject(new Error(res.message));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 删除黄家明_违章记录
|
||||||
|
*/
|
||||||
|
export async function removeHjmViolation(id?: number) {
|
||||||
|
const res = await request.del<ApiResult<unknown>>(
|
||||||
|
'/hjm/hjm-violation/' + id
|
||||||
|
);
|
||||||
|
if (res.code === 0) {
|
||||||
|
return res.message;
|
||||||
|
}
|
||||||
|
return Promise.reject(new Error(res.message));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 批量删除黄家明_违章记录
|
||||||
|
*/
|
||||||
|
export async function removeBatchHjmViolation(data: (number | undefined)[]) {
|
||||||
|
const res = await request.del<ApiResult<unknown>>(
|
||||||
|
'/hjm/hjm-violation/batch',
|
||||||
|
{
|
||||||
|
data
|
||||||
|
}
|
||||||
|
);
|
||||||
|
if (res.code === 0) {
|
||||||
|
return res.message;
|
||||||
|
}
|
||||||
|
return Promise.reject(new Error(res.message));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 根据id查询黄家明_违章记录
|
||||||
|
*/
|
||||||
|
export async function getHjmViolation(id: number) {
|
||||||
|
const res = await request.get<ApiResult<HjmViolation>>(
|
||||||
|
'/hjm/hjm-violation/' + id
|
||||||
|
);
|
||||||
|
if (res.code === 0 && res.data) {
|
||||||
|
return res.data;
|
||||||
|
}
|
||||||
|
return Promise.reject(new Error(res.message));
|
||||||
|
}
|
||||||
43
src/api/hjm/hjmViolation/model/index.ts
Normal file
43
src/api/hjm/hjmViolation/model/index.ts
Normal file
@@ -0,0 +1,43 @@
|
|||||||
|
import type { PageParam } from '@/api/index';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 黄家明_违章记录
|
||||||
|
*/
|
||||||
|
export interface HjmViolation {
|
||||||
|
// 自增ID
|
||||||
|
id?: number;
|
||||||
|
// 车辆编号
|
||||||
|
code?: string;
|
||||||
|
// 标题
|
||||||
|
title?: string;
|
||||||
|
// 文章分类ID
|
||||||
|
categoryId?: number;
|
||||||
|
// 处罚金额
|
||||||
|
money?: string;
|
||||||
|
// 扣分
|
||||||
|
score?: string;
|
||||||
|
// 录入员
|
||||||
|
adminId?: number;
|
||||||
|
// 用户ID
|
||||||
|
userId?: number;
|
||||||
|
// 排序(数字越小越靠前)
|
||||||
|
sortNumber?: number;
|
||||||
|
// 备注
|
||||||
|
comments?: string;
|
||||||
|
// 状态, 0未处理, 1已处理
|
||||||
|
status?: number;
|
||||||
|
// 租户id
|
||||||
|
tenantId?: number;
|
||||||
|
// 创建时间
|
||||||
|
createTime?: string;
|
||||||
|
// 修改时间
|
||||||
|
updateTime?: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 黄家明_违章记录搜索条件
|
||||||
|
*/
|
||||||
|
export interface HjmViolationParam extends PageParam {
|
||||||
|
id?: number;
|
||||||
|
keywords?: string;
|
||||||
|
}
|
||||||
@@ -15,7 +15,8 @@ export default defineAppConfig({
|
|||||||
"register",
|
"register",
|
||||||
"forget",
|
"forget",
|
||||||
"setting",
|
"setting",
|
||||||
"agreement"
|
"agreement",
|
||||||
|
"sms-login"
|
||||||
]
|
]
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
@@ -34,7 +35,8 @@ export default defineAppConfig({
|
|||||||
"company/company",
|
"company/company",
|
||||||
"profile/profile",
|
"profile/profile",
|
||||||
"setting/setting",
|
"setting/setting",
|
||||||
"userVerify/index"
|
"userVerify/index",
|
||||||
|
"userVerify/admin"
|
||||||
]
|
]
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
@@ -48,6 +50,8 @@ export default defineAppConfig({
|
|||||||
"exam/exam",
|
"exam/exam",
|
||||||
"bx/bx",
|
"bx/bx",
|
||||||
"bx/bx-add",
|
"bx/bx-add",
|
||||||
|
"violation/add",
|
||||||
|
"violation/list",
|
||||||
"trajectory/trajectory",
|
"trajectory/trajectory",
|
||||||
"gps-log/gps-log"
|
"gps-log/gps-log"
|
||||||
// "bx/bx-list",
|
// "bx/bx-list",
|
||||||
|
|||||||
@@ -21,7 +21,7 @@ const List = () => {
|
|||||||
|
|
||||||
const reload = () => {
|
const reload = () => {
|
||||||
// 搜索条件
|
// 搜索条件
|
||||||
const where = {status: 1,deleted: 0, keywords}
|
const where = {status: 1, deleted: 0, keywords}
|
||||||
// 判断身份
|
// 判断身份
|
||||||
const roleCode = Taro.getStorageSync('RoleCode');
|
const roleCode = Taro.getStorageSync('RoleCode');
|
||||||
if(roleCode == 'kuaidiyuan'){
|
if(roleCode == 'kuaidiyuan'){
|
||||||
@@ -33,8 +33,13 @@ const List = () => {
|
|||||||
where.organizationId = Taro.getStorageSync('OrganizationId');
|
where.organizationId = Taro.getStorageSync('OrganizationId');
|
||||||
}
|
}
|
||||||
if(roleCode == 'kuaidi'){
|
if(roleCode == 'kuaidi'){
|
||||||
// @ts-ignore
|
if(Taro.getStorageSync('OrganizationId') == Taro.getStorageSync('OrganizationParentId')){
|
||||||
where.organizationParentId = Taro.getStorageSync('OrganizationParentId');
|
// @ts-ignore
|
||||||
|
where.organizationParentId = Taro.getStorageSync('OrganizationParentId');
|
||||||
|
}else {
|
||||||
|
// @ts-ignore
|
||||||
|
where.organizationId = Taro.getStorageSync('OrganizationId');
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// 获取车辆列表
|
// 获取车辆列表
|
||||||
|
|||||||
@@ -115,7 +115,7 @@ const Query = () => {
|
|||||||
title: '请上传车辆图片',
|
title: '请上传车辆图片',
|
||||||
icon: 'error'
|
icon: 'error'
|
||||||
});
|
});
|
||||||
// return false
|
return false
|
||||||
}
|
}
|
||||||
if (!FormData.gpsNo) {
|
if (!FormData.gpsNo) {
|
||||||
Taro.showToast({
|
Taro.showToast({
|
||||||
@@ -130,7 +130,7 @@ const Query = () => {
|
|||||||
...FormData,
|
...FormData,
|
||||||
status: 1
|
status: 1
|
||||||
}).then(() => {
|
}).then(() => {
|
||||||
Taro.showToast({title: `绑定成功`, icon: 'success'})
|
Taro.showToast({title: `安装成功`, icon: 'success'})
|
||||||
setTimeout(() => {
|
setTimeout(() => {
|
||||||
return Taro.navigateBack()
|
return Taro.navigateBack()
|
||||||
}, 1000)
|
}, 1000)
|
||||||
@@ -311,7 +311,7 @@ const Query = () => {
|
|||||||
const onClaimVehicle = () => {
|
const onClaimVehicle = () => {
|
||||||
updateHjmCar({
|
updateHjmCar({
|
||||||
...FormData,
|
...FormData,
|
||||||
status: 2,
|
claim: 1,
|
||||||
driverId: Taro.getStorageSync('UserId'),
|
driverId: Taro.getStorageSync('UserId'),
|
||||||
driverName: Taro.getStorageSync('RealName')
|
driverName: Taro.getStorageSync('RealName')
|
||||||
}).then(() => {
|
}).then(() => {
|
||||||
@@ -361,6 +361,7 @@ const Query = () => {
|
|||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// 4.查询角色
|
// 4.查询角色
|
||||||
const role = await listUserRole({userId: Taro.getStorageSync('UserId')})
|
const role = await listUserRole({userId: Taro.getStorageSync('UserId')})
|
||||||
const roleCode = role[0].roleCode;
|
const roleCode = role[0].roleCode;
|
||||||
@@ -394,9 +395,15 @@ const Query = () => {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
// 1.已认领则展示车辆
|
||||||
// 1.符合条件则由安装人员安装车辆,否则提示无权限
|
if (carInfo.status == 2) {
|
||||||
console.log(roleCode,'roleCode..')
|
setClaimVehicle(false)
|
||||||
|
Taro.setNavigationBarTitle({
|
||||||
|
title: '车辆信息'
|
||||||
|
})
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
// 2.符合条件则由安装人员安装车辆,否则提示无权限
|
||||||
if (carInfo.status == 0 && roleCode != 'Installer') {
|
if (carInfo.status == 0 && roleCode != 'Installer') {
|
||||||
Taro.setNavigationBarTitle({
|
Taro.setNavigationBarTitle({
|
||||||
title: '安装设备'
|
title: '安装设备'
|
||||||
@@ -408,24 +415,29 @@ const Query = () => {
|
|||||||
setDisabled(true)
|
setDisabled(true)
|
||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
// 2.如果已安装,则判断是否已认领车辆
|
// 3.如果已安装,则判断是否已认领车辆
|
||||||
if (carInfo.status == 1 && roleCode == 'kuaidiyuan') {
|
if (carInfo.status == 1 && roleCode == 'kuaidiyuan') {
|
||||||
// 2.1先查询名下有多少辆车
|
// 2.1先查询名下有多少辆车
|
||||||
const carCount = await pageHjmCar({driverId: Taro.getStorageSync('UserId')})
|
const carCount = await pageHjmCar({driverId: Taro.getStorageSync('UserId')})
|
||||||
if (carCount?.count && carCount?.count == 0) {
|
if (carCount?.count == 0) {
|
||||||
// 2.2无车辆则认领
|
// 2.2无车辆则认领
|
||||||
setClaimVehicle(true)
|
setClaimVehicle(true)
|
||||||
Taro.setNavigationBarTitle({
|
Taro.setNavigationBarTitle({
|
||||||
title: '认领车辆'
|
title: '认领车辆'
|
||||||
})
|
})
|
||||||
} else {
|
|
||||||
// 2.3存在车辆则展示车辆信息
|
|
||||||
setClaimVehicle(false)
|
|
||||||
Taro.setNavigationBarTitle({
|
|
||||||
title: '车辆信息'
|
|
||||||
})
|
|
||||||
}
|
}
|
||||||
|
return false
|
||||||
}
|
}
|
||||||
|
// if(carInfo.status == 1 && Taro.getStorageSync('UserId') != carInfo.driverId){
|
||||||
|
// Taro.showToast({
|
||||||
|
// title: '暂无权限',
|
||||||
|
// icon: 'error'
|
||||||
|
// })
|
||||||
|
// setTimeout(() => {
|
||||||
|
// Taro.navigateBack()
|
||||||
|
// },2000)
|
||||||
|
// return false
|
||||||
|
// }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -448,6 +460,8 @@ const Query = () => {
|
|||||||
})
|
})
|
||||||
}, [])
|
}, [])
|
||||||
|
|
||||||
|
// @ts-ignore
|
||||||
|
// @ts-ignore
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
{/* 未安装 */}
|
{/* 未安装 */}
|
||||||
@@ -539,10 +553,11 @@ const Query = () => {
|
|||||||
onChange={(value) => setFormData({...FormData, gpsNo: value})}
|
onChange={(value) => setFormData({...FormData, gpsNo: value})}
|
||||||
/>
|
/>
|
||||||
<div
|
<div
|
||||||
className="right"
|
className="right p-1"
|
||||||
style={{display: 'flex', alignItems: 'center'}}
|
style={{display: 'flex', alignItems: 'center'}}
|
||||||
|
onClick={saveGpsNo}
|
||||||
>
|
>
|
||||||
<Scan onClick={saveGpsNo}/>
|
<Scan />
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</Form.Item>
|
</Form.Item>
|
||||||
@@ -637,7 +652,6 @@ const Query = () => {
|
|||||||
)}
|
)}
|
||||||
</div>
|
</div>
|
||||||
</Form.Item>
|
</Form.Item>
|
||||||
|
|
||||||
<Form.Item
|
<Form.Item
|
||||||
label={'操作员'}
|
label={'操作员'}
|
||||||
name="driver"
|
name="driver"
|
||||||
@@ -648,10 +662,7 @@ const Query = () => {
|
|||||||
</Form>
|
</Form>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
) : ''}
|
) : (
|
||||||
|
|
||||||
{/* 已安装 */}
|
|
||||||
{FormData?.status != 0 ? (
|
|
||||||
<div className={'car-info w-full bg-white'}>
|
<div className={'car-info w-full bg-white'}>
|
||||||
{/* 显示多张图片 */}
|
{/* 显示多张图片 */}
|
||||||
<div style={{
|
<div style={{
|
||||||
@@ -705,6 +716,9 @@ const Query = () => {
|
|||||||
<Cell className={'car-info-item-content'}>
|
<Cell className={'car-info-item-content'}>
|
||||||
电子围栏:{FormData.fenceName}
|
电子围栏:{FormData.fenceName}
|
||||||
</Cell>
|
</Cell>
|
||||||
|
<Cell className={'car-info-item-content'}>
|
||||||
|
安装状态:{FormData.status == 2 ? '已绑定' : '未绑定'}
|
||||||
|
</Cell>
|
||||||
<Cell className={'car-info-item-content'}>
|
<Cell className={'car-info-item-content'}>
|
||||||
操作员:{FormData.status == 2 ? FormData.driver : '-'}
|
操作员:{FormData.status == 2 ? FormData.driver : '-'}
|
||||||
</Cell>
|
</Cell>
|
||||||
@@ -754,7 +768,7 @@ const Query = () => {
|
|||||||
}
|
}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
) : ''}
|
)}
|
||||||
</>
|
</>
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|||||||
3
src/hjm/violation/add.config.ts
Normal file
3
src/hjm/violation/add.config.ts
Normal file
@@ -0,0 +1,3 @@
|
|||||||
|
export default definePageConfig({
|
||||||
|
navigationBarTitleText: '添加违章记录'
|
||||||
|
})
|
||||||
244
src/hjm/violation/add.tsx
Normal file
244
src/hjm/violation/add.tsx
Normal file
@@ -0,0 +1,244 @@
|
|||||||
|
import {useEffect, useState} from "react";
|
||||||
|
import Taro from '@tarojs/taro'
|
||||||
|
import {
|
||||||
|
Button,
|
||||||
|
TextArea,
|
||||||
|
Cell,
|
||||||
|
Input,
|
||||||
|
} from '@nutui/nutui-react-taro'
|
||||||
|
import {addHjmViolation} from "@/api/hjm/hjmViolation";
|
||||||
|
import {HjmViolation} from "@/api/hjm/hjmViolation/model";
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 添加违章记录页面
|
||||||
|
*/
|
||||||
|
function Add() {
|
||||||
|
const [loading, setLoading] = useState<boolean>(false)
|
||||||
|
const [lastSubmitTime, setLastSubmitTime] = useState<number>(0) // 最后提交时间
|
||||||
|
const [formData, setFormData] = useState<HjmViolation>({
|
||||||
|
code: '',
|
||||||
|
title: '',
|
||||||
|
money: '',
|
||||||
|
score: '',
|
||||||
|
comments: ''
|
||||||
|
})
|
||||||
|
|
||||||
|
// 初始化页面数据
|
||||||
|
const initPageData = async () => {
|
||||||
|
try {
|
||||||
|
setLoading(false)
|
||||||
|
} catch (error) {
|
||||||
|
console.error('初始化失败:', error)
|
||||||
|
Taro.showToast({
|
||||||
|
title: '初始化失败',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// 提交表单
|
||||||
|
const handleSubmit = async () => {
|
||||||
|
// 防止重复提交 - 检查loading状态
|
||||||
|
if (loading) {
|
||||||
|
Taro.showToast({
|
||||||
|
title: '正在提交中,请稍候...',
|
||||||
|
icon: 'loading'
|
||||||
|
})
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
// 防止快速连续点击 - 2秒内不允许重复提交
|
||||||
|
const now = Date.now()
|
||||||
|
if (now - lastSubmitTime < 2000) {
|
||||||
|
Taro.showToast({
|
||||||
|
title: '请勿频繁提交',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
return
|
||||||
|
}
|
||||||
|
setLastSubmitTime(now)
|
||||||
|
|
||||||
|
// 表单验证
|
||||||
|
if (!formData.code?.trim()) {
|
||||||
|
Taro.showToast({
|
||||||
|
title: '请输入车辆编号',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!formData.title?.trim()) {
|
||||||
|
Taro.showToast({
|
||||||
|
title: '请输入违章标题',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
// if (!formData.money?.trim()) {
|
||||||
|
// Taro.showToast({
|
||||||
|
// title: '请输入处罚金额',
|
||||||
|
// icon: 'none'
|
||||||
|
// })
|
||||||
|
// return
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// if (!formData.score?.trim()) {
|
||||||
|
// Taro.showToast({
|
||||||
|
// title: '请输入扣分',
|
||||||
|
// icon: 'none'
|
||||||
|
// })
|
||||||
|
// return
|
||||||
|
// }
|
||||||
|
|
||||||
|
setLoading(true)
|
||||||
|
|
||||||
|
// 构建提交数据
|
||||||
|
const submitData: HjmViolation = {
|
||||||
|
...formData,
|
||||||
|
status: 0 // 0未处理, 1已处理
|
||||||
|
}
|
||||||
|
|
||||||
|
addHjmViolation(submitData).then((res) => {
|
||||||
|
console.log(res)
|
||||||
|
Taro.showToast({
|
||||||
|
title: '提交成功',
|
||||||
|
icon: 'success'
|
||||||
|
})
|
||||||
|
// 清空表单
|
||||||
|
setFormData({
|
||||||
|
code: '',
|
||||||
|
title: '',
|
||||||
|
money: '',
|
||||||
|
score: '',
|
||||||
|
comments: ''
|
||||||
|
})
|
||||||
|
|
||||||
|
setTimeout(() => {
|
||||||
|
Taro.navigateBack()
|
||||||
|
}, 2000)
|
||||||
|
}).finally(() => {
|
||||||
|
setLoading(false)
|
||||||
|
})
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
initPageData().then(r => {
|
||||||
|
console.log(r, 'rr')
|
||||||
|
})
|
||||||
|
}, [])
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div style={{
|
||||||
|
backgroundColor: '#f5f5f5',
|
||||||
|
minHeight: '100vh',
|
||||||
|
paddingBottom: '80px'
|
||||||
|
}}>
|
||||||
|
{/* 页面标题 */}
|
||||||
|
{/*<div style={{*/}
|
||||||
|
{/* backgroundColor: '#fff',*/}
|
||||||
|
{/* margin: '16px',*/}
|
||||||
|
{/* borderRadius: '12px',*/}
|
||||||
|
{/* padding: '16px',*/}
|
||||||
|
{/* boxShadow: '0 2px 8px rgba(0,0,0,0.06)'*/}
|
||||||
|
{/*}}>*/}
|
||||||
|
{/* <div style={{*/}
|
||||||
|
{/* display: 'flex',*/}
|
||||||
|
{/* alignItems: 'center',*/}
|
||||||
|
{/* gap: '8px',*/}
|
||||||
|
{/* marginBottom: '12px'*/}
|
||||||
|
{/* }}>*/}
|
||||||
|
{/* <Truck size={18} color="#1890ff"/>*/}
|
||||||
|
{/* <span style={{fontSize: '16px', fontWeight: 'bold'}}>添加违章记录</span>*/}
|
||||||
|
{/* </div>*/}
|
||||||
|
{/*</div>*/}
|
||||||
|
|
||||||
|
|
||||||
|
{/* 违章信息表单 */}
|
||||||
|
<div style={{
|
||||||
|
backgroundColor: '#fff',
|
||||||
|
margin: '16px 16px 16px',
|
||||||
|
borderRadius: '12px',
|
||||||
|
overflow: 'hidden'
|
||||||
|
}}>
|
||||||
|
<div style={{
|
||||||
|
padding: '16px',
|
||||||
|
borderBottom: '1px solid #f0f0f0'
|
||||||
|
}}>
|
||||||
|
<span style={{fontSize: '16px', fontWeight: 'bold'}}>违章信息</span>
|
||||||
|
</div>
|
||||||
|
<Cell.Group>
|
||||||
|
<Cell title="车辆编号" style={{padding: '12px 16px'}}>
|
||||||
|
<Input
|
||||||
|
placeholder="YT000001"
|
||||||
|
value={formData.code}
|
||||||
|
onChange={(value) => setFormData({...formData, code: value})}
|
||||||
|
style={{backgroundColor: '#ffffff', borderRadius: '8px'}}
|
||||||
|
/>
|
||||||
|
</Cell>
|
||||||
|
<Cell title="违章标题" style={{padding: '12px 16px'}}>
|
||||||
|
<Input
|
||||||
|
placeholder="不按规定停车"
|
||||||
|
value={formData.title}
|
||||||
|
onChange={(value) => setFormData({...formData, title: value})}
|
||||||
|
style={{backgroundColor: '#ffffff', borderRadius: '8px'}}
|
||||||
|
/>
|
||||||
|
</Cell>
|
||||||
|
<Cell title="违章描述" style={{padding: '12px 16px'}}>
|
||||||
|
<TextArea
|
||||||
|
placeholder={'XX路1号...'}
|
||||||
|
value={formData.comments}
|
||||||
|
onChange={(value) => setFormData({...formData, comments: value})}
|
||||||
|
style={{backgroundColor: '#ffffff', borderRadius: '8px'}}
|
||||||
|
/>
|
||||||
|
</Cell>
|
||||||
|
<Cell title="处罚金额" style={{padding: '12px 16px'}}>
|
||||||
|
<Input
|
||||||
|
type="number"
|
||||||
|
placeholder="200(元)"
|
||||||
|
maxLength={3}
|
||||||
|
value={formData.money}
|
||||||
|
onChange={(value) => setFormData({...formData, money: value})}
|
||||||
|
style={{backgroundColor: '#ffffff', borderRadius: '8px'}}
|
||||||
|
/>
|
||||||
|
</Cell>
|
||||||
|
<Cell title="扣分" style={{padding: '12px 16px'}}>
|
||||||
|
<Input
|
||||||
|
type="number"
|
||||||
|
maxLength={2}
|
||||||
|
placeholder="2(分)"
|
||||||
|
value={formData.score}
|
||||||
|
onChange={(value) => setFormData({...formData, score: value})}
|
||||||
|
style={{backgroundColor: '#ffffff', borderRadius: '8px'}}
|
||||||
|
/>
|
||||||
|
</Cell>
|
||||||
|
</Cell.Group>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
{/* 提交按钮 */}
|
||||||
|
<div style={{
|
||||||
|
position: 'fixed',
|
||||||
|
bottom: 0,
|
||||||
|
left: 0,
|
||||||
|
right: 0,
|
||||||
|
backgroundColor: '#fff',
|
||||||
|
padding: '16px',
|
||||||
|
borderTop: '1px solid #f0f0f0'
|
||||||
|
}}>
|
||||||
|
<Button
|
||||||
|
type="primary"
|
||||||
|
block
|
||||||
|
loading={loading}
|
||||||
|
disabled={loading}
|
||||||
|
onClick={handleSubmit}
|
||||||
|
>
|
||||||
|
{loading ? '提交中...' : '提交违章记录'}
|
||||||
|
</Button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
export default Add
|
||||||
3
src/hjm/violation/list.config.ts
Normal file
3
src/hjm/violation/list.config.ts
Normal file
@@ -0,0 +1,3 @@
|
|||||||
|
export default definePageConfig({
|
||||||
|
navigationBarTitleText: '违章记录'
|
||||||
|
})
|
||||||
260
src/hjm/violation/list.tsx
Normal file
260
src/hjm/violation/list.tsx
Normal file
@@ -0,0 +1,260 @@
|
|||||||
|
import React, {useEffect, useState} from "react";
|
||||||
|
import {
|
||||||
|
Loading,
|
||||||
|
Empty,
|
||||||
|
Button,
|
||||||
|
Input,
|
||||||
|
Tag,
|
||||||
|
Space
|
||||||
|
} from '@nutui/nutui-react-taro'
|
||||||
|
import {Search, Calendar, Truck, File, AddCircle} from '@nutui/icons-react-taro'
|
||||||
|
import Taro from '@tarojs/taro'
|
||||||
|
import {pageHjmViolation} from "@/api/hjm/hjmViolation";
|
||||||
|
import {HjmViolation} from "@/api/hjm/hjmViolation/model";
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 报险记录列表页面
|
||||||
|
*/
|
||||||
|
const List: React.FC = () => {
|
||||||
|
const [list, setList] = useState<HjmViolation[]>([])
|
||||||
|
const [loading, setLoading] = useState<boolean>(false)
|
||||||
|
const [keywords, setKeywords] = useState<string>('')
|
||||||
|
const [refreshing, setRefreshing] = useState<boolean>(false)
|
||||||
|
console.log(refreshing)
|
||||||
|
// 获取状态显示
|
||||||
|
const getStatusDisplay = (status?: number) => {
|
||||||
|
switch (status) {
|
||||||
|
case 0:
|
||||||
|
return {text: '未处理', color: '#faad14', bgColor: '#fffbe6'}
|
||||||
|
case 1:
|
||||||
|
return {text: '已处理', color: '#52c41a', bgColor: '#f6ffed'}
|
||||||
|
case 2:
|
||||||
|
return {text: '已驳回', color: '#ff4d4f', bgColor: '#fff2f0'}
|
||||||
|
default:
|
||||||
|
return {text: '未知', color: '#8c8c8c', bgColor: '#f5f5f5'}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const reload = async (showLoading = true) => {
|
||||||
|
try {
|
||||||
|
if (showLoading) setLoading(true)
|
||||||
|
setRefreshing(true)
|
||||||
|
|
||||||
|
const res = await pageHjmViolation({
|
||||||
|
keywords: keywords.trim(),
|
||||||
|
})
|
||||||
|
|
||||||
|
setList(res?.list || [])
|
||||||
|
} catch (error) {
|
||||||
|
console.error('获取报险记录失败:', error)
|
||||||
|
Taro.showToast({
|
||||||
|
title: '获取报险记录失败',
|
||||||
|
icon: 'error'
|
||||||
|
})
|
||||||
|
} finally {
|
||||||
|
setLoading(false)
|
||||||
|
setRefreshing(false)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const onSearch = () => {
|
||||||
|
reload()
|
||||||
|
}
|
||||||
|
|
||||||
|
const onKeywordsChange = (value: string) => {
|
||||||
|
setKeywords(value)
|
||||||
|
}
|
||||||
|
|
||||||
|
const onAddInsurance = () => {
|
||||||
|
Taro.navigateTo({
|
||||||
|
url: '/hjm/violation/add'
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
reload().then()
|
||||||
|
}, [])
|
||||||
|
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
{/* 搜索栏 */}
|
||||||
|
<div style={{
|
||||||
|
position: 'fixed',
|
||||||
|
top: '20px',
|
||||||
|
left: 0,
|
||||||
|
right: 0,
|
||||||
|
display: "none",
|
||||||
|
zIndex: 20,
|
||||||
|
padding: '0 16px',
|
||||||
|
backgroundColor: '#f5f5f5'
|
||||||
|
}}>
|
||||||
|
<div style={{
|
||||||
|
display: 'flex',
|
||||||
|
alignItems: 'center',
|
||||||
|
backgroundColor: '#fff',
|
||||||
|
padding: '8px 12px',
|
||||||
|
borderRadius: '20px',
|
||||||
|
boxShadow: '0 2px 8px rgba(0,0,0,0.1)'
|
||||||
|
}}>
|
||||||
|
<Search size={16} color="#999"/>
|
||||||
|
<Input
|
||||||
|
placeholder="搜索报险记录"
|
||||||
|
value={keywords}
|
||||||
|
onChange={onKeywordsChange}
|
||||||
|
onConfirm={onSearch}
|
||||||
|
style={{
|
||||||
|
border: 'none',
|
||||||
|
backgroundColor: 'transparent',
|
||||||
|
flex: 1,
|
||||||
|
marginLeft: '8px'
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
<Button
|
||||||
|
type="primary"
|
||||||
|
size="small"
|
||||||
|
onClick={onSearch}
|
||||||
|
loading={loading}
|
||||||
|
>
|
||||||
|
搜索
|
||||||
|
</Button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
{/* 报险记录列表 */}
|
||||||
|
<div style={{
|
||||||
|
marginTop: '10px',
|
||||||
|
paddingBottom: '80px'
|
||||||
|
}}>
|
||||||
|
{loading && list.length === 0 ? (
|
||||||
|
<div style={{
|
||||||
|
display: 'flex',
|
||||||
|
justifyContent: 'center',
|
||||||
|
alignItems: 'center',
|
||||||
|
height: '200px'
|
||||||
|
}}>
|
||||||
|
<Loading type="spinner">加载中...</Loading>
|
||||||
|
</div>
|
||||||
|
) : list.length === 0 ? (
|
||||||
|
<Empty description="暂无报险记录">
|
||||||
|
<Button type="primary" onClick={onAddInsurance}>
|
||||||
|
立即报险
|
||||||
|
</Button>
|
||||||
|
</Empty>
|
||||||
|
) : (
|
||||||
|
<div style={{padding: '0 16px'}}>
|
||||||
|
{list.map((item, index) => {
|
||||||
|
const statusDisplay = getStatusDisplay(item.status)
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div
|
||||||
|
key={index}
|
||||||
|
style={{
|
||||||
|
backgroundColor: '#fff',
|
||||||
|
borderRadius: '12px',
|
||||||
|
padding: '16px',
|
||||||
|
marginBottom: '12px',
|
||||||
|
boxShadow: '0 2px 8px rgba(0,0,0,0.06)',
|
||||||
|
border: '1px solid #f0f0f0'
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
<div style={{
|
||||||
|
display: 'flex',
|
||||||
|
justifyContent: 'space-between',
|
||||||
|
alignItems: 'flex-start',
|
||||||
|
marginBottom: '12px'
|
||||||
|
}}>
|
||||||
|
<div style={{flex: 1}}>
|
||||||
|
<div style={{
|
||||||
|
display: 'flex',
|
||||||
|
alignItems: 'center',
|
||||||
|
gap: '8px',
|
||||||
|
marginBottom: '8px'
|
||||||
|
}}>
|
||||||
|
<File size={16} color="#1890ff"/>
|
||||||
|
<span style={{
|
||||||
|
fontSize: '16px',
|
||||||
|
fontWeight: 'bold',
|
||||||
|
color: '#262626'
|
||||||
|
}}>
|
||||||
|
{item.title}
|
||||||
|
</span>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<Space direction="vertical">
|
||||||
|
<div style={{
|
||||||
|
display: 'flex',
|
||||||
|
alignItems: 'center',
|
||||||
|
gap: '8px'
|
||||||
|
}}>
|
||||||
|
<Truck size={14} color="#8c8c8c"/>
|
||||||
|
<span style={{fontSize: '13px', color: '#8c8c8c'}}>
|
||||||
|
车辆编号:{item.code}
|
||||||
|
</span>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div style={{
|
||||||
|
display: 'flex',
|
||||||
|
alignItems: 'center',
|
||||||
|
gap: '8px'
|
||||||
|
}}>
|
||||||
|
<Calendar size={14} color="#8c8c8c"/>
|
||||||
|
<span style={{fontSize: '13px', color: '#8c8c8c'}}>
|
||||||
|
提交时间:{item.createTime}
|
||||||
|
</span>
|
||||||
|
</div>
|
||||||
|
</Space>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<Tag
|
||||||
|
color={statusDisplay.color}
|
||||||
|
style={{
|
||||||
|
backgroundColor: statusDisplay.bgColor,
|
||||||
|
border: `1px solid ${statusDisplay.color}`,
|
||||||
|
fontSize: '12px'
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
{statusDisplay.text}
|
||||||
|
</Tag>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
{/* 备注信息 */}
|
||||||
|
{item.comments && (
|
||||||
|
<div style={{
|
||||||
|
backgroundColor: '#f8f9fa',
|
||||||
|
padding: '8px 12px',
|
||||||
|
borderRadius: '6px',
|
||||||
|
fontSize: '13px',
|
||||||
|
color: '#595959',
|
||||||
|
lineHeight: '1.4'
|
||||||
|
}}>
|
||||||
|
{item.comments.length > 50
|
||||||
|
? `${item.comments.substring(0, 50)}...`
|
||||||
|
: item.comments
|
||||||
|
}
|
||||||
|
</div>
|
||||||
|
)}
|
||||||
|
</div>
|
||||||
|
)
|
||||||
|
})}
|
||||||
|
</div>
|
||||||
|
)}
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div style={{
|
||||||
|
position: 'fixed',
|
||||||
|
bottom: '20px',
|
||||||
|
right: '20px',
|
||||||
|
zIndex: 30,
|
||||||
|
padding: '8px',
|
||||||
|
borderRadius: '20px',
|
||||||
|
overflow: "hidden",
|
||||||
|
backgroundColor: '#ff0000',
|
||||||
|
}}>
|
||||||
|
<AddCircle size={28} color={'#ffffff'} onClick={onAddInsurance} />
|
||||||
|
</div>
|
||||||
|
</>
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
export default List
|
||||||
@@ -39,6 +39,12 @@ const ExpirationTime = () => {
|
|||||||
if(data.certification){
|
if(data.certification){
|
||||||
setIsAdmin( true)
|
setIsAdmin( true)
|
||||||
}
|
}
|
||||||
|
if(Taro.getStorageSync('certification') == 'jj'){
|
||||||
|
setIsAdmin(true)
|
||||||
|
}
|
||||||
|
if(Taro.getStorageSync('certification') == 'yz'){
|
||||||
|
setIsAdmin(true)
|
||||||
|
}
|
||||||
data.roles?.map((item, index) => {
|
data.roles?.map((item, index) => {
|
||||||
if (index == 0) {
|
if (index == 0) {
|
||||||
setRoleName(item.roleCode)
|
setRoleName(item.roleCode)
|
||||||
|
|||||||
@@ -65,6 +65,7 @@ const Header = (props: any) => {
|
|||||||
setRoleName('交警')
|
setRoleName('交警')
|
||||||
Taro.setStorageSync('RoleName', '交警')
|
Taro.setStorageSync('RoleName', '交警')
|
||||||
Taro.setStorageSync('RoleCode', 'jiaojing')
|
Taro.setStorageSync('RoleCode', 'jiaojing')
|
||||||
|
Taro.setStorageSync('certification', 'jj')
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
// 邮政协会/管局
|
// 邮政协会/管局
|
||||||
@@ -73,6 +74,7 @@ const Header = (props: any) => {
|
|||||||
setRoleName('邮政协会/管局')
|
setRoleName('邮政协会/管局')
|
||||||
Taro.setStorageSync('RoleName', '邮政协会/管局')
|
Taro.setStorageSync('RoleName', '邮政协会/管局')
|
||||||
Taro.setStorageSync('RoleCode', 'youzheng')
|
Taro.setStorageSync('RoleCode', 'youzheng')
|
||||||
|
Taro.setStorageSync('certification', 'yz')
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
// 快递公司
|
// 快递公司
|
||||||
|
|||||||
@@ -116,16 +116,15 @@ function Home() {
|
|||||||
setLongitude(res.longitude)
|
setLongitude(res.longitude)
|
||||||
}
|
}
|
||||||
|
|
||||||
console.log(Taro.getStorageSync('RoleName'))
|
|
||||||
// 已认证用户
|
// 已认证用户
|
||||||
if(Taro.getStorageSync('Certification')){
|
if (Taro.getStorageSync('certification')) {
|
||||||
setIsAdmin(true)
|
setIsAdmin(true)
|
||||||
setScale(11)
|
setScale(11)
|
||||||
pageHjmCarByMap(res.latitude,res.longitude)
|
pageHjmCarByMap(res.latitude, res.longitude)
|
||||||
}
|
}
|
||||||
|
|
||||||
// 游客
|
// 游客
|
||||||
if(!Taro.getStorageSync('access_token') || Taro.getStorageSync('RoleName') == '注册用户'){
|
if (!Taro.getStorageSync('access_token') || Taro.getStorageSync('RoleName') == '注册用户') {
|
||||||
setScale(15)
|
setScale(15)
|
||||||
const arr = []
|
const arr = []
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
@@ -145,7 +144,7 @@ function Home() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
const onQuery = () => {
|
const onQuery = () => {
|
||||||
if(!keywords){
|
if (!keywords) {
|
||||||
Taro.showToast({
|
Taro.showToast({
|
||||||
title: '请输入关键字',
|
title: '请输入关键字',
|
||||||
icon: 'none'
|
icon: 'none'
|
||||||
@@ -155,36 +154,36 @@ function Home() {
|
|||||||
reload();
|
reload();
|
||||||
}
|
}
|
||||||
|
|
||||||
const pageHjmCarByMap = (latitude?: any,longitude?: any) => {
|
const pageHjmCarByMap = (latitude?: any, longitude?: any) => {
|
||||||
// 搜索条件
|
// 搜索条件
|
||||||
const where = {}
|
const where = {}
|
||||||
|
|
||||||
if(latitude){
|
if (latitude) {
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
where.latitude = latitude
|
where.latitude = latitude
|
||||||
}
|
}
|
||||||
if(longitude){
|
if (longitude) {
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
where.longitude = longitude
|
where.longitude = longitude
|
||||||
}
|
}
|
||||||
// 判断身份
|
// 判断身份
|
||||||
const roleCode = Taro.getStorageSync('RoleCode');
|
const roleCode = Taro.getStorageSync('RoleCode');
|
||||||
if(roleCode == 'kuaidiyuan'){
|
if (roleCode == 'kuaidiyuan') {
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
where.driverId = Taro.getStorageSync('UserId')
|
where.driverId = Taro.getStorageSync('UserId')
|
||||||
}
|
}
|
||||||
if(roleCode == 'zhandian'){
|
if (roleCode == 'zhandian') {
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
where.organizationId = Taro.getStorageSync('OrganizationId');
|
where.organizationId = Taro.getStorageSync('OrganizationId');
|
||||||
}
|
}
|
||||||
if(roleCode == 'kuaidi'){
|
if (roleCode == 'kuaidi') {
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
where.organizationParentId = Taro.getStorageSync('OrganizationParentId');
|
where.organizationParentId = Taro.getStorageSync('OrganizationParentId');
|
||||||
}
|
}
|
||||||
|
|
||||||
pageByQQMap(where).then(res => {
|
pageByQQMap(where).then(res => {
|
||||||
console.log(res,'pageByQQMap')
|
console.log(res, 'pageByQQMap')
|
||||||
if(res?.count == 0){
|
if (res?.count == 0) {
|
||||||
const arr = []
|
const arr = []
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
arr.push({
|
arr.push({
|
||||||
@@ -226,16 +225,16 @@ function Home() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
const reload = () => {
|
const reload = () => {
|
||||||
if(!Taro.getStorageSync('access_token')){
|
if (!Taro.getStorageSync('access_token')) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
if(!isAdmin){
|
if (!isAdmin) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
setMarkers([])
|
setMarkers([])
|
||||||
setScale(12)
|
setScale(12)
|
||||||
pageHjmCar({keywords,deleted: 0}).then(res => {
|
pageHjmCar({keywords, deleted: 0}).then(res => {
|
||||||
if(res?.count == 0){
|
if (res?.count == 0) {
|
||||||
Taro.showToast({
|
Taro.showToast({
|
||||||
title: '没有搜索结果',
|
title: '没有搜索结果',
|
||||||
icon: 'none'
|
icon: 'none'
|
||||||
@@ -247,7 +246,7 @@ function Home() {
|
|||||||
const data = res?.list[0];
|
const data = res?.list[0];
|
||||||
setLongitude(data?.longitude)
|
setLongitude(data?.longitude)
|
||||||
setLatitude(data?.latitude)
|
setLatitude(data?.latitude)
|
||||||
if(isAdmin){
|
if (isAdmin) {
|
||||||
setMarkers([{
|
setMarkers([{
|
||||||
id: data.id,
|
id: data.id,
|
||||||
latitude: data.latitude,
|
latitude: data.latitude,
|
||||||
@@ -268,7 +267,7 @@ function Home() {
|
|||||||
}])
|
}])
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
console.log(list.length,'carList.length')
|
console.log(list.length, 'carList.length')
|
||||||
})
|
})
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -308,8 +307,12 @@ function Home() {
|
|||||||
getUserInfo().then((data) => {
|
getUserInfo().then((data) => {
|
||||||
if (data) {
|
if (data) {
|
||||||
// 是否管理员
|
// 是否管理员
|
||||||
console.log(data.certification, 'certification')
|
if (data.certification) {
|
||||||
if(data.certification){
|
setIsAdmin(true)
|
||||||
|
}
|
||||||
|
// 是否交警
|
||||||
|
if (Taro.getStorageSync('certification') == 'jj') {
|
||||||
|
console.log('交警', '12312')
|
||||||
setIsAdmin(true)
|
setIsAdmin(true)
|
||||||
}
|
}
|
||||||
setUserInfo(data)
|
setUserInfo(data)
|
||||||
@@ -319,8 +322,11 @@ function Home() {
|
|||||||
if (!data.openid) {
|
if (!data.openid) {
|
||||||
Taro.login({
|
Taro.login({
|
||||||
success: (res) => {
|
success: (res) => {
|
||||||
getWxOpenId({code: res.code}).then(() => {
|
// 排查交警和邮政角色不保存openid
|
||||||
})
|
if (Taro.getStorageSync('RoleCode') !== 'jiaojing' || Taro.getStorageSync('RoleCode') !== 'youzheng' || Taro.getStorageSync('RoleCode') !== 'Installer') {
|
||||||
|
getWxOpenId({code: res.code}).then(() => {
|
||||||
|
})
|
||||||
|
}
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -3,9 +3,10 @@ import navTo from "@/utils/common";
|
|||||||
import UserFooter from "./UserFooter";
|
import UserFooter from "./UserFooter";
|
||||||
import Taro from '@tarojs/taro'
|
import Taro from '@tarojs/taro'
|
||||||
import {ArrowRight, ShieldCheck, Truck, LogisticsError} from '@nutui/icons-react-taro'
|
import {ArrowRight, ShieldCheck, Truck, LogisticsError} from '@nutui/icons-react-taro'
|
||||||
import {CSSProperties} from "react";
|
import {CSSProperties, useEffect, useState} from "react";
|
||||||
|
|
||||||
const UserCell = () => {
|
const UserCell = () => {
|
||||||
|
const [roleName, setRoleName] = useState<string>('')
|
||||||
const InfiniteUlStyle: CSSProperties = {
|
const InfiniteUlStyle: CSSProperties = {
|
||||||
height: '88vh',
|
height: '88vh',
|
||||||
padding: '16px',
|
padding: '16px',
|
||||||
@@ -30,6 +31,10 @@ const UserCell = () => {
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
setRoleName(Taro.getStorageSync('RoleCode'))
|
||||||
|
}, []);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<div style={InfiniteUlStyle} id="scroll">
|
<div style={InfiniteUlStyle} id="scroll">
|
||||||
@@ -50,38 +55,85 @@ const UserCell = () => {
|
|||||||
}}
|
}}
|
||||||
/>
|
/>
|
||||||
</Cell.Group>
|
</Cell.Group>
|
||||||
<Cell.Group divider={true}>
|
{
|
||||||
<Cell
|
roleName === 'kuaidi' && (
|
||||||
className="nutui-cell-clickable"
|
<Cell.Group divider={true}>
|
||||||
title={
|
<Cell
|
||||||
<div style={{display: 'inline-flex', alignItems: 'center'}}>
|
className="nutui-cell-clickable"
|
||||||
<Truck size={16}/>
|
title={
|
||||||
<span className={'pl-3 text-sm'}>车辆信息</span>
|
<div style={{display: 'inline-flex', alignItems: 'center'}}>
|
||||||
</div>
|
<ShieldCheck size={16}/>
|
||||||
}
|
<span className={'pl-3 text-sm'}>实名认证审核</span>
|
||||||
align="center"
|
</div>
|
||||||
extra={<ArrowRight color="#cccccc" size={18}/>}
|
}
|
||||||
onClick={() => {
|
align="center"
|
||||||
navTo('/user/car/index', true)
|
extra={<ArrowRight color="#cccccc" size={18}/>}
|
||||||
}}
|
onClick={() => {
|
||||||
/>
|
navTo('/user/userVerify/admin', true)
|
||||||
</Cell.Group>
|
}}
|
||||||
<Cell.Group divider={true}>
|
/>
|
||||||
<Cell
|
</Cell.Group>
|
||||||
className="nutui-cell-clickable"
|
)
|
||||||
title={
|
}
|
||||||
<div style={{display: 'inline-flex', alignItems: 'center'}}>
|
{
|
||||||
<LogisticsError size={16}/>
|
roleName === 'kuaidiyuan' && (
|
||||||
<span className={'pl-3 text-sm'}>报险记录</span>
|
<>
|
||||||
</div>
|
<Cell.Group divider={true}>
|
||||||
}
|
<Cell
|
||||||
align="center"
|
className="nutui-cell-clickable"
|
||||||
extra={<ArrowRight color="#cccccc" size={18}/>}
|
title={
|
||||||
onClick={() => {
|
<div style={{display: 'inline-flex', alignItems: 'center'}}>
|
||||||
navTo('/hjm/bx/bx', true)
|
<Truck size={16}/>
|
||||||
}}
|
<span className={'pl-3 text-sm'}>车辆信息</span>
|
||||||
/>
|
</div>
|
||||||
</Cell.Group>
|
}
|
||||||
|
align="center"
|
||||||
|
extra={<ArrowRight color="#cccccc" size={18}/>}
|
||||||
|
onClick={() => {
|
||||||
|
navTo('/user/car/index', true)
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
</Cell.Group>
|
||||||
|
<Cell.Group divider={true}>
|
||||||
|
<Cell
|
||||||
|
className="nutui-cell-clickable"
|
||||||
|
title={
|
||||||
|
<div style={{display: 'inline-flex', alignItems: 'center'}}>
|
||||||
|
<LogisticsError size={16}/>
|
||||||
|
<span className={'pl-3 text-sm'}>报险记录</span>
|
||||||
|
</div>
|
||||||
|
}
|
||||||
|
align="center"
|
||||||
|
extra={<ArrowRight color="#cccccc" size={18}/>}
|
||||||
|
onClick={() => {
|
||||||
|
navTo('/hjm/bx/bx', true)
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
</Cell.Group>
|
||||||
|
</>
|
||||||
|
)
|
||||||
|
}
|
||||||
|
{
|
||||||
|
roleName === 'jiaojing' && (
|
||||||
|
<Cell.Group divider={true}>
|
||||||
|
<Cell
|
||||||
|
className="nutui-cell-clickable"
|
||||||
|
title={
|
||||||
|
<div style={{display: 'inline-flex', alignItems: 'center'}}>
|
||||||
|
<Truck size={16}/>
|
||||||
|
<span className={'pl-3 text-sm'}>违章记录</span>
|
||||||
|
</div>
|
||||||
|
}
|
||||||
|
align="center"
|
||||||
|
extra={<ArrowRight color="#cccccc" size={18}/>}
|
||||||
|
onClick={() => {
|
||||||
|
navTo('/hjm/violation/list', true)
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
</Cell.Group>
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
{/*<Cell.Group divider={true} description={*/}
|
{/*<Cell.Group divider={true} description={*/}
|
||||||
{/* <div style={{display: 'inline-flex', alignItems: 'center'}}>*/}
|
{/* <div style={{display: 'inline-flex', alignItems: 'center'}}>*/}
|
||||||
{/* <span style={{marginTop: '12px'}}>管理</span>*/}
|
{/* <span style={{marginTop: '12px'}}>管理</span>*/}
|
||||||
@@ -171,7 +223,14 @@ const UserCell = () => {
|
|||||||
title="账号安全"
|
title="账号安全"
|
||||||
align="center"
|
align="center"
|
||||||
extra={<ArrowRight color="#cccccc" size={18}/>}
|
extra={<ArrowRight color="#cccccc" size={18}/>}
|
||||||
onClick={() => navTo('/user/profile/profile',true)}
|
onClick={() => navTo('/user/profile/profile', true)}
|
||||||
|
/>
|
||||||
|
<Cell
|
||||||
|
className="nutui-cell-clickable"
|
||||||
|
title="短信登录"
|
||||||
|
align="center"
|
||||||
|
extra={<ArrowRight color="#cccccc" size={18}/>}
|
||||||
|
onClick={() => navTo('/passport/sms-login', true)}
|
||||||
/>
|
/>
|
||||||
<Cell
|
<Cell
|
||||||
className="nutui-cell-clickable"
|
className="nutui-cell-clickable"
|
||||||
|
|||||||
4
src/passport/sms-login.config.ts
Normal file
4
src/passport/sms-login.config.ts
Normal file
@@ -0,0 +1,4 @@
|
|||||||
|
export default definePageConfig({
|
||||||
|
navigationBarTitleText: '验证码登录',
|
||||||
|
navigationBarTextStyle: 'black'
|
||||||
|
})
|
||||||
204
src/passport/sms-login.tsx
Normal file
204
src/passport/sms-login.tsx
Normal file
@@ -0,0 +1,204 @@
|
|||||||
|
import {useEffect, useState} from "react";
|
||||||
|
import Taro from '@tarojs/taro'
|
||||||
|
import {Input, Button} from '@nutui/nutui-react-taro'
|
||||||
|
import {loginBySms, sendSmsCaptcha} from "@/api/passport/login";
|
||||||
|
import {LoginParam} from "@/api/passport/login/model";
|
||||||
|
|
||||||
|
const SmsLogin = () => {
|
||||||
|
const [loading, setLoading] = useState<boolean>(false)
|
||||||
|
const [sendingCode, setSendingCode] = useState<boolean>(false)
|
||||||
|
const [countdown, setCountdown] = useState<number>(0)
|
||||||
|
const [formData, setFormData] = useState<LoginParam>({
|
||||||
|
phone: '',
|
||||||
|
code: ''
|
||||||
|
})
|
||||||
|
|
||||||
|
const reload = () => {
|
||||||
|
Taro.hideTabBar()
|
||||||
|
}
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
reload()
|
||||||
|
}, [])
|
||||||
|
|
||||||
|
// 倒计时效果
|
||||||
|
useEffect(() => {
|
||||||
|
let timer: NodeJS.Timeout
|
||||||
|
if (countdown > 0) {
|
||||||
|
timer = setTimeout(() => {
|
||||||
|
setCountdown(countdown - 1)
|
||||||
|
}, 1000)
|
||||||
|
}
|
||||||
|
return () => {
|
||||||
|
if (timer) clearTimeout(timer)
|
||||||
|
}
|
||||||
|
}, [countdown])
|
||||||
|
|
||||||
|
// 验证手机号格式
|
||||||
|
const validatePhone = (phone: string): boolean => {
|
||||||
|
const phoneRegex = /^1[3-9]\d{9}$/
|
||||||
|
return phoneRegex.test(phone)
|
||||||
|
}
|
||||||
|
|
||||||
|
// 发送短信验证码
|
||||||
|
const handleSendCode = async () => {
|
||||||
|
if (!formData.phone) {
|
||||||
|
Taro.showToast({
|
||||||
|
title: '请输入手机号码',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!validatePhone(formData.phone)) {
|
||||||
|
Taro.showToast({
|
||||||
|
title: '请输入正确的手机号码',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
if (sendingCode || countdown > 0) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
setSendingCode(true)
|
||||||
|
await sendSmsCaptcha({ phone: formData.phone })
|
||||||
|
|
||||||
|
Taro.showToast({
|
||||||
|
title: '验证码已发送',
|
||||||
|
icon: 'success'
|
||||||
|
})
|
||||||
|
|
||||||
|
// 开始60秒倒计时
|
||||||
|
setCountdown(60)
|
||||||
|
} catch (error: any) {
|
||||||
|
Taro.showToast({
|
||||||
|
title: error.message || '发送失败',
|
||||||
|
icon: 'error'
|
||||||
|
})
|
||||||
|
} finally {
|
||||||
|
setSendingCode(false)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 处理登录
|
||||||
|
const handleLogin = async () => {
|
||||||
|
// 防止重复提交
|
||||||
|
if (loading) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
// 表单验证
|
||||||
|
if (!formData.phone) {
|
||||||
|
Taro.showToast({
|
||||||
|
title: '请输入手机号码',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!validatePhone(formData.phone)) {
|
||||||
|
Taro.showToast({
|
||||||
|
title: '请输入正确的手机号码',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!formData.code) {
|
||||||
|
Taro.showToast({
|
||||||
|
title: '请输入验证码',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
if (formData.code.length !== 6) {
|
||||||
|
Taro.showToast({
|
||||||
|
title: '请输入6位验证码',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
setLoading(true)
|
||||||
|
|
||||||
|
await loginBySms({
|
||||||
|
phone: formData.phone,
|
||||||
|
code: formData.code
|
||||||
|
})
|
||||||
|
|
||||||
|
Taro.showToast({
|
||||||
|
title: '登录成功',
|
||||||
|
icon: 'success'
|
||||||
|
})
|
||||||
|
|
||||||
|
// 延迟跳转到首页
|
||||||
|
setTimeout(() => {
|
||||||
|
Taro.reLaunch({
|
||||||
|
url: '/pages/index/index'
|
||||||
|
})
|
||||||
|
}, 1500)
|
||||||
|
|
||||||
|
} catch (error: any) {
|
||||||
|
Taro.showToast({
|
||||||
|
title: error.message || '登录失败',
|
||||||
|
icon: 'error'
|
||||||
|
})
|
||||||
|
} finally {
|
||||||
|
setLoading(false)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
<div className={'flex flex-col justify-center px-5 pt-3'}>
|
||||||
|
<div className={'flex flex-col justify-between items-center my-2'}>
|
||||||
|
<Input
|
||||||
|
type="number"
|
||||||
|
placeholder="请输入手机号码"
|
||||||
|
maxLength={11}
|
||||||
|
value={formData.phone}
|
||||||
|
onChange={(value) => setFormData({...formData, phone: value})}
|
||||||
|
style={{backgroundColor: '#ffffff', borderRadius: '8px'}}
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
<div className={'flex justify-between items-center bg-white rounded-lg my-2 pr-2'}>
|
||||||
|
<Input
|
||||||
|
type="number"
|
||||||
|
placeholder="请输入6位验证码"
|
||||||
|
maxLength={6}
|
||||||
|
value={formData.code}
|
||||||
|
onChange={(value) => setFormData({...formData, code: value})}
|
||||||
|
style={{ backgroundColor: '#ffffff', borderRadius: '8px'}}
|
||||||
|
/>
|
||||||
|
<Button
|
||||||
|
size="small"
|
||||||
|
type={countdown > 0 ? "default" : "primary"}
|
||||||
|
loading={sendingCode}
|
||||||
|
disabled={sendingCode || countdown > 0}
|
||||||
|
onClick={handleSendCode}
|
||||||
|
>
|
||||||
|
{countdown > 0 ? `${countdown}s` : sendingCode ? '发送中...' : '获取验证码'}
|
||||||
|
</Button>
|
||||||
|
</div>
|
||||||
|
<div className={'flex justify-center my-5'}>
|
||||||
|
<Button
|
||||||
|
type="info"
|
||||||
|
size={'large'}
|
||||||
|
className={'w-full rounded-lg p-2'}
|
||||||
|
loading={loading}
|
||||||
|
disabled={loading}
|
||||||
|
onClick={handleLogin}
|
||||||
|
>
|
||||||
|
{loading ? '登录中...' : '登录'}
|
||||||
|
</Button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</>
|
||||||
|
)
|
||||||
|
}
|
||||||
|
export default SmsLogin
|
||||||
3
src/user/userVerify/admin.config.ts
Normal file
3
src/user/userVerify/admin.config.ts
Normal file
@@ -0,0 +1,3 @@
|
|||||||
|
export default definePageConfig({
|
||||||
|
navigationBarTitleText: '实名认证管理'
|
||||||
|
})
|
||||||
248
src/user/userVerify/admin.tsx
Normal file
248
src/user/userVerify/admin.tsx
Normal file
@@ -0,0 +1,248 @@
|
|||||||
|
import React, {useEffect, useState} from "react";
|
||||||
|
import {
|
||||||
|
Loading,
|
||||||
|
Empty,
|
||||||
|
Button,
|
||||||
|
Input,
|
||||||
|
Tag,
|
||||||
|
Space
|
||||||
|
} from '@nutui/nutui-react-taro'
|
||||||
|
import {Search, Calendar, Truck, File, AddCircle} from '@nutui/icons-react-taro'
|
||||||
|
import Taro from '@tarojs/taro'
|
||||||
|
import {pageHjmViolation} from "@/api/hjm/hjmViolation";
|
||||||
|
import {UserVerify} from "@/api/system/userVerify/model";
|
||||||
|
import {pageUserVerify} from "@/api/system/userVerify";
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 报险记录列表页面
|
||||||
|
*/
|
||||||
|
const List: React.FC = () => {
|
||||||
|
const [list, setList] = useState<UserVerify[]>([])
|
||||||
|
const [loading, setLoading] = useState<boolean>(false)
|
||||||
|
const [keywords, setKeywords] = useState<string>('')
|
||||||
|
const [refreshing, setRefreshing] = useState<boolean>(false)
|
||||||
|
console.log(refreshing)
|
||||||
|
// 获取状态显示
|
||||||
|
const getStatusDisplay = (status?: number) => {
|
||||||
|
switch (status) {
|
||||||
|
case 0:
|
||||||
|
return {text: '未处理', color: '#faad14', bgColor: '#fffbe6'}
|
||||||
|
case 1:
|
||||||
|
return {text: '已处理', color: '#52c41a', bgColor: '#f6ffed'}
|
||||||
|
case 2:
|
||||||
|
return {text: '已驳回', color: '#ff4d4f', bgColor: '#fff2f0'}
|
||||||
|
default:
|
||||||
|
return {text: '未知', color: '#8c8c8c', bgColor: '#f5f5f5'}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const reload = async (showLoading = true) => {
|
||||||
|
try {
|
||||||
|
if (showLoading) setLoading(true)
|
||||||
|
setRefreshing(true)
|
||||||
|
|
||||||
|
const res = await pageUserVerify({
|
||||||
|
keywords: keywords.trim(),
|
||||||
|
})
|
||||||
|
|
||||||
|
setList(res?.list || [])
|
||||||
|
} catch (error) {
|
||||||
|
console.error('获取报险记录失败:', error)
|
||||||
|
Taro.showToast({
|
||||||
|
title: '获取报险记录失败',
|
||||||
|
icon: 'error'
|
||||||
|
})
|
||||||
|
} finally {
|
||||||
|
setLoading(false)
|
||||||
|
setRefreshing(false)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const onSearch = () => {
|
||||||
|
reload()
|
||||||
|
}
|
||||||
|
|
||||||
|
const onKeywordsChange = (value: string) => {
|
||||||
|
setKeywords(value)
|
||||||
|
}
|
||||||
|
|
||||||
|
const onAddInsurance = () => {
|
||||||
|
Taro.navigateTo({
|
||||||
|
url: '/hjm/violation/add'
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
reload().then()
|
||||||
|
}, [])
|
||||||
|
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
{/* 搜索栏 */}
|
||||||
|
<div style={{
|
||||||
|
position: 'fixed',
|
||||||
|
top: '20px',
|
||||||
|
left: 0,
|
||||||
|
right: 0,
|
||||||
|
display: "none",
|
||||||
|
zIndex: 20,
|
||||||
|
padding: '0 16px',
|
||||||
|
backgroundColor: '#f5f5f5'
|
||||||
|
}}>
|
||||||
|
<div style={{
|
||||||
|
display: 'flex',
|
||||||
|
alignItems: 'center',
|
||||||
|
backgroundColor: '#fff',
|
||||||
|
padding: '8px 12px',
|
||||||
|
borderRadius: '20px',
|
||||||
|
boxShadow: '0 2px 8px rgba(0,0,0,0.1)'
|
||||||
|
}}>
|
||||||
|
<Search size={16} color="#999"/>
|
||||||
|
<Input
|
||||||
|
placeholder="搜索报险记录"
|
||||||
|
value={keywords}
|
||||||
|
onChange={onKeywordsChange}
|
||||||
|
onConfirm={onSearch}
|
||||||
|
style={{
|
||||||
|
border: 'none',
|
||||||
|
backgroundColor: 'transparent',
|
||||||
|
flex: 1,
|
||||||
|
marginLeft: '8px'
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
<Button
|
||||||
|
type="primary"
|
||||||
|
size="small"
|
||||||
|
onClick={onSearch}
|
||||||
|
loading={loading}
|
||||||
|
>
|
||||||
|
搜索
|
||||||
|
</Button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
{/* 报险记录列表 */}
|
||||||
|
<div style={{
|
||||||
|
marginTop: '10px',
|
||||||
|
paddingBottom: '80px'
|
||||||
|
}}>
|
||||||
|
{loading && list.length === 0 ? (
|
||||||
|
<div style={{
|
||||||
|
display: 'flex',
|
||||||
|
justifyContent: 'center',
|
||||||
|
alignItems: 'center',
|
||||||
|
height: '200px'
|
||||||
|
}}>
|
||||||
|
<Loading type="spinner">加载中...</Loading>
|
||||||
|
</div>
|
||||||
|
) : list.length === 0 ? (
|
||||||
|
<Empty description="暂无报险记录">
|
||||||
|
<Button type="primary" onClick={onAddInsurance}>
|
||||||
|
立即报险
|
||||||
|
</Button>
|
||||||
|
</Empty>
|
||||||
|
) : (
|
||||||
|
<div style={{padding: '0 16px'}}>
|
||||||
|
{list.map((item, index) => {
|
||||||
|
const statusDisplay = getStatusDisplay(item.status)
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div
|
||||||
|
key={index}
|
||||||
|
style={{
|
||||||
|
backgroundColor: '#fff',
|
||||||
|
borderRadius: '12px',
|
||||||
|
padding: '16px',
|
||||||
|
marginBottom: '12px',
|
||||||
|
boxShadow: '0 2px 8px rgba(0,0,0,0.06)',
|
||||||
|
border: '1px solid #f0f0f0'
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
<div style={{
|
||||||
|
display: 'flex',
|
||||||
|
justifyContent: 'space-between',
|
||||||
|
alignItems: 'flex-start',
|
||||||
|
marginBottom: '12px'
|
||||||
|
}}>
|
||||||
|
<div style={{flex: 1}}>
|
||||||
|
<div style={{
|
||||||
|
display: 'flex',
|
||||||
|
alignItems: 'center',
|
||||||
|
gap: '8px',
|
||||||
|
marginBottom: '8px'
|
||||||
|
}}>
|
||||||
|
<File size={16} color="#1890ff"/>
|
||||||
|
<span style={{
|
||||||
|
fontSize: '16px',
|
||||||
|
fontWeight: 'bold',
|
||||||
|
color: '#262626'
|
||||||
|
}}>
|
||||||
|
{item.realName}
|
||||||
|
</span>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<Space direction="vertical">
|
||||||
|
<div style={{
|
||||||
|
display: 'flex',
|
||||||
|
alignItems: 'center',
|
||||||
|
gap: '8px'
|
||||||
|
}}>
|
||||||
|
<Truck size={14} color="#8c8c8c"/>
|
||||||
|
<span style={{fontSize: '13px', color: '#8c8c8c'}}>
|
||||||
|
手机号码:{item.phone}
|
||||||
|
</span>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div style={{
|
||||||
|
display: 'flex',
|
||||||
|
alignItems: 'center',
|
||||||
|
gap: '8px'
|
||||||
|
}}>
|
||||||
|
<Calendar size={14} color="#8c8c8c"/>
|
||||||
|
<span style={{fontSize: '13px', color: '#8c8c8c'}}>
|
||||||
|
提交时间:{item.createTime}
|
||||||
|
</span>
|
||||||
|
</div>
|
||||||
|
</Space>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<Tag
|
||||||
|
color={statusDisplay.color}
|
||||||
|
style={{
|
||||||
|
backgroundColor: statusDisplay.bgColor,
|
||||||
|
border: `1px solid ${statusDisplay.color}`,
|
||||||
|
fontSize: '12px'
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
{item.statusText}
|
||||||
|
</Tag>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
{/* 备注信息 */}
|
||||||
|
{item.comments && (
|
||||||
|
<div style={{
|
||||||
|
backgroundColor: '#f8f9fa',
|
||||||
|
padding: '8px 12px',
|
||||||
|
borderRadius: '6px',
|
||||||
|
fontSize: '13px',
|
||||||
|
color: '#595959',
|
||||||
|
lineHeight: '1.4'
|
||||||
|
}}>
|
||||||
|
{item.comments.length > 50
|
||||||
|
? `${item.comments.substring(0, 50)}...`
|
||||||
|
: item.comments
|
||||||
|
}
|
||||||
|
</div>
|
||||||
|
)}
|
||||||
|
</div>
|
||||||
|
)
|
||||||
|
})}
|
||||||
|
</div>
|
||||||
|
)}
|
||||||
|
</div>
|
||||||
|
</>
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
export default List
|
||||||
Reference in New Issue
Block a user