This commit is contained in:
TimSpan 2024-09-18 10:03:57 +08:00
commit 34b1054ccc
15 changed files with 276 additions and 487 deletions

View File

@ -8,4 +8,5 @@ node_modules/
yarn.lock yarn.lock
components.d.ts components.d.ts
package-lock.json package-lock.json
.idea

View File

@ -2,7 +2,7 @@
"name": "collect_information", "name": "collect_information",
"version": "1.0.0", "version": "1.0.0",
"private": true, "private": true,
"description": "智慧派出所信息采集小程序", "description": "警保联勤联动小程序",
"templateInfo": { "templateInfo": {
"name": "default", "name": "default",
"typescript": true, "typescript": true,
@ -71,6 +71,7 @@
"@tarojs/webpack5-runner": "3.6.25", "@tarojs/webpack5-runner": "3.6.25",
"@types/jest": "^29.3.1", "@types/jest": "^29.3.1",
"@types/node": "^18.15.11", "@types/node": "^18.15.11",
"@types/qrcode": "^1.5.5",
"@types/webpack-env": "^1.13.6", "@types/webpack-env": "^1.13.6",
"@typescript-eslint/eslint-plugin": "^6.2.0", "@typescript-eslint/eslint-plugin": "^6.2.0",
"@typescript-eslint/parser": "^6.2.0", "@typescript-eslint/parser": "^6.2.0",

View File

@ -1,7 +1,7 @@
{ {
"miniprogramRoot": "dist/", "miniprogramRoot": "dist/",
"projectname": "collect_information", "projectname": "collect_information",
"description": "智慧派出所信息采集小程序", "description": "警保联勤联动小程序",
"setting": { "setting": {
"urlCheck": false, "urlCheck": false,
"es6": false, "es6": false,

View File

@ -19,7 +19,6 @@ export default defineAppConfig({
pages: [ pages: [
'pages/policeManager/index', 'pages/policeManager/index',
'pages/policeDetails/index', 'pages/policeDetails/index',
'pages/myProject/myProject', 'pages/myProject/myProject',
'pages/projectDetails/projectDetails', 'pages/projectDetails/projectDetails',
'pages/form/form' 'pages/form/form'

View File

@ -10,25 +10,25 @@ const pinia = createPinia()
// pinia.use(piniaPluginPersistedstate) // pinia.use(piniaPluginPersistedstate)
const App = createApp({ const App = createApp({
onShow(options) { onShow(options) {
try { // try {
const store = useCounterStore() // const store = useCounterStore()
const token = Taro.getStorageSync('token') // const token = Taro.getStorageSync('token')
console.log(token) // console.log(token)
if (token) { // if (token) {
Taro.switchTab({ // Taro.switchTab({
url: '/pages/mine/mine' // url: '/pages/mine/mine'
// url: '/pages/projectManager/index/index' // // url: '/pages/projectManager/index/index'
//
}) // })
store.setSelected(2) // store.setSelected(2)
} else { // } else {
console.log(2222) // console.log(2222)
} // }
console.log('App onShow.') // console.log('App onShow.')
} catch (err) { // } catch (err) {
console.log(err) // console.log(err)
//
} // }
}, },
// 入口组件不需要实现 render 方法,即使实现了也会被 taro 所覆盖 // 入口组件不需要实现 render 方法,即使实现了也会被 taro 所覆盖

View File

@ -1,225 +0,0 @@
<template>
<view>
<nut-form ref="formRef" :model-value="formParams" :rules="rules">
<nut-form-item label="街道/社区:" prop="streetCommunity">
<view @click="streetCommunitySmallCommunityVisible = true">
{{ streetCommunitySmallCommunityLabel || "请选择街道/小区" }}
</view>
</nut-form-item>
<nut-form-item label="楼栋/门户:" prop="residentialDivision">
<view @click="buildingFloorHouseVisible = true">
{{ buildingFloorHouseLabel || "请选择楼栋/门户" }}
</view>
</nut-form-item>
<nut-form-item label="姓名:" prop="name">
<nut-input
v-model="formParams.name"
placeholder="请输入姓名"
type="text"
/>
</nut-form-item>
<nut-form-item label="性别:" prop="sex">
<nut-radio-group v-model="formParams.sex" direction="horizontal">
<nut-radio v-for="item in SEX" :key="item.value" :label="item.value"
>{{ item.label }}
</nut-radio>
</nut-radio-group>
</nut-form-item>
<nut-form-item label="出生日期:" prop="dataOfBirth">
<view @click="dataOfBirthVisible = true">
{{
dayjs(formParams.dataOfBirth).format("YYYY-MM-DD") ||
"请选择出生日期"
}}
</view>
</nut-form-item>
<nut-form-item label="身份证:" prop="idCard">
<nut-input
v-model="formParams.idCard"
placeholder="请输入身份证"
type="text"
/>
</nut-form-item>
<nut-form-item label="手机号:" prop="phone">
<nut-input
v-model="formParams.phone"
placeholder="请输入手机号码"
type="text"
/>
</nut-form-item>
<nut-form-item label="户籍地:" prop="householdRegistrationAddress">
<nut-input
v-model="formParams.householdRegistrationAddress"
placeholder="请输入户籍地"
type="text"
/>
</nut-form-item>
</nut-form>
<nut-cascader
v-model:visible="streetCommunitySmallCommunityVisible"
v-model="formParams.streetCommunitySmallCommunityIds"
:options="streetCommunitySmallCommunityTreeData"
title="选择街道/社区"
text-key="label"
@change="streetCommunitySmallCommunityChange"
></nut-cascader>
<nut-cascader
v-model:visible="buildingFloorHouseVisible"
v-model="formParams.buildingFloorHouseIds"
:options="buildingFloorHouseTreeData"
title="选择楼栋/门户"
text-key="label"
@change="buildingFloorHouseChange"
></nut-cascader>
<nut-popup v-model:visible="dataOfBirthVisible" position="bottom">
<nut-date-picker
v-model="formParams.dataOfBirth"
:min-date="min"
:max-date="max"
:three-dimensional="false"
@confirm="dataOfBirthVisible = false"
></nut-date-picker>
</nut-popup>
</view>
</template>
<script setup lang="ts">
import { SEX } from "@/enums";
import dayjs from "dayjs";
import { ref, watch } from "vue";
import type { FormRules } from "@nutui/nutui-taro/dist/types/__VUE/form/types";
import api from "@/request";
import type { FormInstance } from "@nutui/nutui-taro";
import { useLoad } from "@tarojs/taro";
const emits = defineEmits(["update:modelValue"]);
const props = withDefaults(
defineProps<{
modelValue: PersonnelInformation;
}>(),
{
modelValue: () => {
return {
name: "",
sex: 0,
dataOfBirth: new Date(),
idCard: "",
phone: "",
householdRegistrationAddress: "",
streetCommunitySmallCommunityIds: [],
buildingFloorHouseIds: [],
} as PersonnelInformation;
},
}
);
const defaultParams = { ...props.modelValue };
const formRef = ref<FormInstance>();
const formParams = ref<PersonnelInformation>({
...props.modelValue,
});
const rules: FormRules = {
name: [
{ required: true, message: "请输入姓名" },
{
validator: (value) => {
return !(value.length < 2 || value.length >= 20);
},
message: "名字在2~20字符之间",
},
],
sex: [{ required: true, message: "请选择性别" }],
idCard: [
{ required: true, message: "请输入身份证" },
{
regex:
/^[1-9]\d{5}(18|19|([23]\d))\d{2}((0[1-9])|(10|11|12))(([0-2][1-9])|10|20|30|31)\d{3}[0-9Xx]$/,
message: "身份证格式错误",
},
],
phone: [
{ required: true, message: "请输入手机号码" },
{
regex: /^400(-?)[0-9]{7}$|^1\d{10}$|^0[0-9]{2,3}-[0-9]{7,8}$/,
message: "手机格式错误",
},
],
};
watch(formParams.value, (n) => {
emits("update:modelValue", n);
});
const dataOfBirthVisible = ref(false);
const min = new Date(1920, 0, 1);
const max = new Date(2025, 10, 1);
defineExpose<{
validate: () => Promise<unknown>;
resetForm: () => void;
}>({
validate: async (): Promise<unknown> => {
const result = (await formRef.value?.validate()) as any;
if (result.valid) {
return Promise.resolve("校验通过");
}
return Promise.reject("校验不通过");
},
resetForm: () => {
for (let key in defaultParams) {
formParams.value[key] = defaultParams[key];
}
streetCommunitySmallCommunityLabel.value = "";
buildingFloorHouseLabel.value = "";
buildingFloorHouseTreeData.value = [];
},
});
const streetCommunitySmallCommunityTreeData = ref<TreeNode<string>[]>([]);
const streetCommunitySmallCommunityVisible = ref<boolean>(false);
const streetCommunitySmallCommunityLabel = ref<string>("");
const streetCommunitySmallCommunityChange = (
value: string,
pathNodes: Record<string, any>[]
) => {
buildingFloorHouseLabel.value = "";
formParams.value.buildingFloorHouseIds = [];
buildingFloorHouseTreeData.value = [];
streetCommunitySmallCommunityLabel.value = pathNodes
.map((e) => e.text)
.join(",");
getBuildingFloorHouseTreeBySmallCommunityId(value[value.length - 1]);
};
const buildingFloorHouseVisible = ref<boolean>(false);
const buildingFloorHouseLabel = ref<string>("");
const buildingFloorHouseChange = (
value: string,
pathNodes: Record<string, any>[]
) => (buildingFloorHouseLabel.value = pathNodes.map((e) => e.text).join(","));
const buildingFloorHouseTreeData = ref<TreeNode<string>[]>([]);
const getBuildingFloorHouseTreeBySmallCommunityId = (
smallCommunityId: string
) => {
api
.get<TreeNode<string>[]>(
"/residentialDivision/getBuildingFloorHouseTreeBySmallCommunityId",
{ smallCommunityId }
)
.then((resp) => {
buildingFloorHouseTreeData.value = resp.data as TreeNode<string>[];
});
};
useLoad(() => {
api
.get<TreeNode<string>[]>(
"/residentialDivision/streetCommunitySmallCommunityTree"
)
.then((resp) => {
streetCommunitySmallCommunityTreeData.value =
resp.data as TreeNode<string>[];
});
});
</script>

View File

@ -8,7 +8,7 @@ const requestInterceptor = (chain: Taro.Chain) => {
if (token) { if (token) {
requestParams.header = { requestParams.header = {
...requestParams.header, ...requestParams.header,
token:token.value token: token.value
} }
} }
return chain.proceed(requestParams) return chain.proceed(requestParams)
@ -30,7 +30,6 @@ class CustomRequest {
}).then() }).then()
} }
console.log(params,method)
Taro.request<JsonResult<T>, object>({ Taro.request<JsonResult<T>, object>({
url: this.BASE_API + url, url: this.BASE_API + url,
data: params, data: params,
@ -62,7 +61,7 @@ class CustomRequest {
duration: 2000 duration: 2000
}).then() }).then()
reject(res.errMsg); reject(res.errMsg);
console.log(res.errMsg,'000') console.log(res.errMsg, '000')
} }
}) })
}) })

View File

@ -1,90 +1,78 @@
<template> <template>
<view class="form"> <view class="form">
<nut-form ref="formRef" :model-value="formData" :rules="rules"> <nut-form ref="formRef" :model-value="formData" :rules="rules">
<nut-form-item label="姓名" prop="name"> <nut-form-item label="姓名" prop="name">
<nut-input v-model="formData.name" placeholder="请输入姓名" type="text" /> <nut-input v-model="formData.name" placeholder="请输入姓名" type="text"/>
</nut-form-item> </nut-form-item>
<nut-form-item label="年龄" prop="sex" > <nut-form-item label="性别" prop="sex">
<nut-radio-group v-model="formData.sex" direction="horizontal"> <nut-radio-group v-model="formData.sex" direction="horizontal">
<nut-radio v-for="item in SEX" :key="item.value" :label="item.value" <nut-radio v-for="item in SEX" :key="item.value" :label="item.value"
>{{ item.label }} >{{ item.label }}
</nut-radio> </nut-radio>
</nut-radio-group> </nut-radio-group>
</nut-form-item> </nut-form-item>
<nut-form-item label="身份证" prop="idCard"> <nut-form-item label="身份证" prop="idCard">
<nut-input v-model="formData.idCard" placeholder="请填写身份证" type="text" @blur="idCardBlur"/> <nut-input v-model="formData.idCard" placeholder="请填写身份证" type="text" @blur="idCardBlur"/>
</nut-form-item> </nut-form-item>
<nut-form-item label="出生日期" prop="dateOfBirth" > <nut-form-item label="出生日期" prop="dateOfBirth">
<nut-input @click="openDate" :disabled="true" v-model="formData.dateOfBirth" placeholder="请填写身份证" type="text" /> <view @click="showPicker = true">
</nut-form-item> {{
<nut-form-item label="工作岗位" prop="workPost"> dayjs(formData.dateOfBirth).isValid() ? dayjs(formData.dateOfBirth).format('YYYY-MM-DD') : '请选择出生年月'
<nut-input v-model="formData.workPost" placeholder="请输入工作岗位" type="text" /> }}
</nut-form-item> </view>
<nut-form-item label="籍贯" prop="nativePlace"> </nut-form-item>
<nut-input v-model="formData.nativePlace" placeholder="请输入籍贯" type="text" /> <nut-form-item label="工作岗位" prop="workPost">
</nut-form-item> <nut-input v-model="formData.workPost" placeholder="请输入工作岗位" type="text"/>
<nut-form-item label="地址" prop="homeAddress"> </nut-form-item>
<nut-input v-model="formData.homeAddress" placeholder="请输入地址" type="text"/> <nut-form-item label="籍贯" prop="nativePlace">
</nut-form-item> <nut-input v-model="formData.nativePlace" placeholder="请输入籍贯" type="text"/>
<nut-form-item label="保安证号" prop="securityNumber"> </nut-form-item>
<nut-input v-model="formData.securityNumber" placeholder="请输入保安证号" type="text" /> <nut-form-item label="地址" prop="homeAddress">
</nut-form-item> <nut-input v-model="formData.homeAddress" placeholder="请输入地址" type="text"/>
<nut-form-item label="备注" prop="remark"> </nut-form-item>
<nut-input v-model="formData.remark" placeholder="请填写备注" type="text" /> <nut-form-item label="保安证号" prop="securityNumber">
</nut-form-item> <nut-input v-model="formData.securityNumber" placeholder="请输入保安证号" type="text"/>
</nut-form> </nut-form-item>
<view class="formButton"> <nut-form-item label="备注" prop="remark">
<nut-button style="width: 45%" type="success" size="small" @click="submit">提交</nut-button> <nut-input v-model="formData.remark" placeholder="请填写备注" type="text"/>
<nut-button style="width: 45%" size="small" @click="reset">重置提示状态</nut-button> </nut-form-item>
</view> </nut-form>
<nut-popup v-model:visible="showPicker" position="bottom"> <view class="formButton">
<nut-date-picker <nut-button style="width: 45%" type="success" size="small" @click="submit">提交</nut-button>
v-model="pickerValue" <nut-button style="width: 45%" size="small" @click="formRef.value?.reset()">重置表单</nut-button>
:three-dimensional="false" </view>
:min-date="new Date(1900,1,1)" <nut-popup v-model:visible="showPicker" position="bottom">
:max-date="new Date(2100,1,1)" <nut-date-picker
@confirm="confirm" v-model="formData.dateOfBirth"
@cancel="showPicker = false" :three-dimensional="false"
></nut-date-picker> :min-date="new Date(1900,1,1)"
</nut-popup> :max-date="new Date(2100,1,1)"
</view> @confirm="showPicker = false"
@cancel="showPicker = false"
></nut-date-picker>
</nut-popup>
</view>
</template> </template>
<script setup lang="ts"> <script setup lang="ts">
import {onMounted, ref, watch} from "vue"; import {ref} from "vue";
import {SEX} from "@/enums"; import {SEX} from "@/enums";
import {FormRules} from "@nutui/nutui-taro/dist/types/__VUE/form/types"; import {FormRules} from "@nutui/nutui-taro/dist/types/__VUE/form/types";
import api from "@/request"; import api from "@/request";
import './form.scss' import './form.scss'
import Taro, {useLoad} from "@tarojs/taro"; import Taro, {useLoad} from "@tarojs/taro";
import dayjs from "dayjs";
const showPicker = ref(false) const showPicker = ref(false)
const formData = ref<formDate>({
snowFlakeId:'', const formData = ref<formDate>({} as any)
name: '',
workPost:'',
sex:0,
nativePlace:'',
idCard:'',
dateOfBirth:'',
securityNumber:'',
remark:'',
homeAddress: ''
})
const serviceProjectId = ref('') //id
const pickerValue = ref(new Date())
const formRef = ref(null) const formRef = ref(null)
const rules: FormRules = { const rules: FormRules = {
name: [ name: [
{ required: true, message: "请输入姓名" }, {required: true, message: "请输入姓名"},
{
validator: (value) => {
return !(value.length < 2 || value.length >= 20);
},
message: "名字在2~20字符之间",
},
], ],
sex: [{ required: true, message: "请选择性别" }], sex: [{required: true, message: "请选择性别"}],
idCard:[ idCard: [
{required: true, message: "请输入身份证号"}, {required: true, message: "请输入身份证号"},
{ {
regex: /^(^[1-9]\d{5}(18|19|([23]\d))\d{2}((0[1-9])|(10|11|12))((0[1-9])|([12][0-9])|(30|31))\d{3}(\d|X)$)/, regex: /^(^[1-9]\d{5}(18|19|([23]\d))\d{2}((0[1-9])|(10|11|12))((0[1-9])|([12][0-9])|(30|31))\d{3}(\d|X)$)/,
@ -93,72 +81,47 @@ const rules: FormRules = {
] ]
}; };
useLoad((options)=>{ useLoad((options) => {
formData.value = JSON.parse(options.item) formData.value = JSON.parse(options.item)
serviceProjectId.value = JSON.parse(options.item).snowFlakeId
console.log(serviceProjectId.value)
}) })
watch(()=>formData.value,(res)=>{ const idCardBlur = (e: any) => {
console.log(res)
})
const openDate = ()=>{
showPicker.value = true
}
const confirm = ({selectedValue })=>{
showPicker.value = false
formData.value.dateOfBirth =selectedValue[0] + '年' + selectedValue[1] +'月' + selectedValue[2] + ' 日'
}
const reset = () => {
formRef.value?.reset()
}
const idCardBlur = (e:string)=>{
const value = e.detail.value const value = e.detail.value
if (!value?.length || value.length < 18) {
formData.value.dateOfBirth = null;
return
}
const birthDate = value.substring(6, 14); const birthDate = value.substring(6, 14);
const year = birthDate.substring(0, 4); const year = birthDate.substring(0, 4);
const month = birthDate.substring(4, 6); const month = birthDate.substring(4, 6);
const day = birthDate.substring(6, 8); const day = birthDate.substring(6, 8);
// formData.value.dateOfBirth = new Date(parseInt(year), parseInt(month) - 1, parseInt(day))
formData.value.dateOfBirth = `${year}${month}${day}`
pickerValue.value = new Date(parseInt(year),parseInt(month) - 1,parseInt(day))
} }
const submit = () => { const submit = () => {
formRef.value?.validate().then(({valid, errors}) => { formRef.value?.validate().then(async ({valid}) => {
if (valid) { if (valid) {
const saveOrUpdateSecurityUserParams = { const resp = await api.post('/projectManageIndex/saveOrUpdateSecurityUser', formData.value)
serviceProjectId:serviceProjectId.value,
name: formData.value.name,
workPost:formData.value.workPost,
sex:formData.value.sex,
nativePlace: formData.value.nativePlace,
idCard: formData.value.idCard,
dateOfBirth: pickerValue.value,
securityNumber: formData.value.securityNumber,
homeAddress: formData.value.homeAddress,
remark: formData.value.remark
}
const resp = api.post('/projectManageIndex/saveOrUpdateSecurityUser',saveOrUpdateSecurityUserParams)
Taro.showToast({ Taro.showToast({
title: '项目人员录入成功', title: resp.message,
icon: 'success', icon: 'success',
duration: 2000, duration: 2000,
mask: true, mask: true,
}).then() }).then()
formData.value = { formData.value = {
snowFlakeId:'', snowFlakeId: undefined,
name: '', serviceProjectId: formData.value.serviceProjectId,
workPost:'', name: '',
sex:0, workPost: '',
nativePlace:'', telephone: '',
idCard:'', sex: 0,
dateOfBirth:'', nativePlace: '',
securityNumber:'', idCard: '',
remark:'', dateOfBirth: null,
homeAddress: '' securityNumber: '',
} remark: '',
} else { homeAddress: ''
console.warn('error:', errors) }
} }
}) })
} }

View File

@ -1,23 +1,31 @@
<template> <template>
<view class="myProject"> <view class="myProject">
<view class="myProjectItem" v-for="(item,index) in myProjectList" :key="index"> <view v-if="number !== 0">
<view style="display: flex;justify-content: space-between"> <view class="myProjectItem" v-for="(item,index) in myProjectList" :key="index">
<text>{{ item?.name }}</text> <view style="display: flex;justify-content: space-between">
<!--<text>进行中</text>--> <text>{{ item?.name }}</text>
</view> <!--<text>进行中</text>-->
<view class="myProjectIndex">地址 </view>
<text>{{ item?.provinceName }}{{ item.cityName }}{{ item.districtsName }}{{ item.streetName }}</text> <view class="myProjectIndex">地址
</view> <text>{{ item?.provinceName }}{{ item.cityName }}{{ item.districtsName }}{{ item.streetName }}</text>
<view style="display: flex;justify-content: space-between"> </view>
<text>联系人{{ item?.contactPersonInfo.name }}</text> <view style="display: flex;justify-content: space-between">
<text>电话{{ item?.contactPersonInfo.telephone }}</text> <text>联系人{{ item?.contactPersonInfo.name }}</text>
</view> <text>电话{{ item?.contactPersonInfo.telephone }}</text>
<view class="project"> </view>
<view @click="projectClick(items,item?.name)" v-for="(items,index) in item.serviceProjectList" :key="index"> <view class="project">
{{ items.name }} <view @click="projectClick(items,item?.name)" v-for="(items,index) in item.serviceProjectList" :key="index">
{{ items.name }}
</view>
</view> </view>
</view> </view>
</view> </view>
<view v-else class="myProject" >
<nut-empty image="empty" description="暂无项目">
<div style="margin-top: 10px">
</div>
</nut-empty>
</view>
</view> </view>
</template> </template>
@ -28,9 +36,12 @@ import Taro from "@tarojs/taro";
import './myproject.scss' import './myproject.scss'
const myProjectList = ref<MyProjectList[]>() const myProjectList = ref<MyProjectList[]>()
const number = ref(0)
const getMyServiceProject = async () => { const getMyServiceProject = async () => {
const resp = await api.get<MyProjectList[]>(`/projectManageIndex/getMyServiceProject`) const resp = await api.get<MyProjectList[]>(`/projectManageIndex/getMyServiceProject`)
myProjectList.value = resp.data myProjectList.value = resp.data
number.value = resp.data.length
} }
const projectClick = (items: ServiceProjectList, name: string) => { const projectClick = (items: ServiceProjectList, name: string) => {

View File

@ -2,76 +2,81 @@
<view class="projectDetails"> <view class="projectDetails">
<view class="projectDetailsItem" style="line-height: 50rpx"> <view class="projectDetailsItem" style="line-height: 50rpx">
<view> <view>
<view style="display: flex;justify-content: space-between"> <view style="display: flex;justify-content: space-between">
<text style="font-size: 18px">{{ nameValue ? nameValue : '' }}{{ '-----' + detailsList?.name }}项目</text> <text style="font-size: 18px">{{ nameValue ? nameValue : '' }}{{
<text>进行中</text> '-----' + serviceProjectDetails?.name
</view> }}项目
<view> </text>
<view style="float: left;width: 50%;" class="content">经理名称:{{ detailsList?.projectManagerMiniProgramUserInfo.name }}</view> <text>进行中</text>
<view class="content">手机号:{{ detailsList?.projectManagerMiniProgramUserInfo.telephone }}</view> </view>
<view>
<view style="float: left;width: 50%;" class="content">
经理名称:{{ serviceProjectDetails?.projectManagerMiniProgramUserInfo.name }}
</view> </view>
<view class="content">手机号:{{ serviceProjectDetails?.projectManagerMiniProgramUserInfo.telephone }}</view>
</view>
</view> </view>
</view> </view>
<view class="projectDetailsItem"> <view class="projectDetailsItem">
<view class="projectDetailsIndex"> <view class="projectDetailsIndex">
<nut-row> <nut-row>
<nut-col :span="24"> <nut-col :span="24">
<view class="content">保安证件号{{ detailsList?.idNumber }}</view> <view class="content">保安证件号{{ serviceProjectDetails?.idNumber }}</view>
</nut-col> </nut-col>
</nut-row> </nut-row>
<nut-row> <nut-row>
<nut-col :span="12"> <nut-col :span="12">
<view class="content">工作人员数量:{{ detailsList?.staffTotal }}</view> <view class="content">工作人员数量:{{ serviceProjectDetails?.staffTotal }}</view>
</nut-col> </nut-col>
<nut-col :span="12"> <nut-col :span="12">
<view class="content">保安人员数量:{{ detailsList?.securityUserTotal }}</view> <view class="content">保安人员数量:{{ serviceProjectDetails?.securityUserTotal }}</view>
</nut-col> </nut-col>
</nut-row> </nut-row>
<nut-row> <nut-row>
<nut-col :span="12"> <nut-col :span="12">
<view class="content">服务区域面积:{{ detailsList?.serviceArea }}</view> <view class="content">服务区域面积:{{ serviceProjectDetails?.serviceArea }}</view>
</nut-col> </nut-col>
<nut-col :span="12"> <nut-col :span="12">
<view class="content">楼栋数量:{{ detailsList?.buildingTotal }}</view> <view class="content">楼栋数量:{{ serviceProjectDetails?.buildingTotal }}</view>
</nut-col> </nut-col>
</nut-row> </nut-row>
<nut-row> <nut-row>
<nut-col :span="4"> <nut-col :span="4">
<view class="content">户数:{{ detailsList?.houseTotal }}</view> <view class="content">户数:{{ serviceProjectDetails?.houseTotal }}</view>
</nut-col> </nut-col>
</nut-row> </nut-row>
</view> </view>
</view> </view>
<!--表格--> <!--表格-->
<view class="projectDetailsTableDrop"> <view class="projectDetailsTableDrop">
<view style="padding: 0 12px">项目人员({{total}})</view> <view style="padding: 0 12px">项目人员({{ total }})</view>
<scroll-view :scroll-y="true" style="height: 80%;" @scrolltolower="lower" <scroll-view :scroll-y="true" style="height: 80%;" @scrolltolower="lower"
:scroll-into-view="toView" :scroll-top="scrollTop" :refresherEnabled="true" :scroll-into-view="toView" :scroll-top="scrollTop" :refresherEnabled="true"
@refresherrefresh="onRefresherRefresh" :refresher-triggered="isRefresher" @refresherrefresh="onRefresherRefresh" :refresher-triggered="isRefresher"
> >
<view class="projectDetailsTable" v-for="(item,index) in projectData" :key="index"> <view class="projectDetailsTable" v-for="(item,index) in projectData" :key="index">
<view> <view>
<view class="projectDetailsTableItem"> <view class="projectDetailsTableItem">
<view> <view>
<view style="display: flex;justify-content: space-between"> <view style="display: flex;justify-content: space-between">
<text>姓名:{{ item?.name?item?.name:'创建者' }}</text> <text>姓名:{{ item?.name ? item?.name : '创建者' }}</text>
<text>性别:{{ item.sex?.label?item.sex?.label:' 隐藏' }}</text> <text>性别:{{ item.sex?.label ? item.sex?.label : ' 隐藏' }}</text>
<text>职位:{{ item.workPost?item.workPost:'无' }}</text> <text>职位:{{ item.workPost ? item.workPost : '无' }}</text>
</view>
<view style="display: flex;justify-content: space-between">
<text>保安证件:{{ item.securityNumber?item.securityNumber:'125241256451' }}</text>
<text>出生年月:{{ dayjs(item.dateOfBirth).format('YYYY-MM-DD')}}</text>
</view>
<view style="display: flex;justify-content: space-between">
<text>创建时间:{{ item.createTime }}</text>
<text>身份证:{{ item.idCard }}</text>
</view>
</view> </view>
<view class="projectDetailsTableIndex" > <view style="display: flex;justify-content: space-between">
<view style="color: #3a6bbe" @click="detail(item)">详情</view> <text>保安证件:{{ item.securityNumber ? item.securityNumber : '125241256451' }}</text>
<view style="color: #ffa60d" @click="projectEdit(item)">编辑</view> <text>出生年月:{{ dayjs(item.dateOfBirth).format('YYYY-MM-DD') }}</text>
<view style="color: red" @click="deleteUssrID(item.snowFlakeId)">删除</view> </view>
</view> <view style="display: flex;justify-content: space-between">
<text>创建时间:{{ item.createTime }}</text>
<text>身份证:{{ item.idCard }}</text>
</view>
</view>
<view class="projectDetailsTableIndex">
<view style="color: #3a6bbe" @click="detail(item)">详情</view>
<view style="color: #ffa60d" @click="projectEdit(item)">编辑</view>
<view style="color: red" @click="deleteUssrID(item.snowFlakeId)">删除</view>
</view>
</view> </view>
</view> </view>
@ -83,57 +88,58 @@
<nut-button style="width: 45%" type="info">二维码录入</nut-button> <nut-button style="width: 45%" type="info">二维码录入</nut-button>
</view> </view>
<view>
<nut-dialog
content="是否确认删除该用户?"
:onOk="dialogOk"
v-model:visible="confirmVisible"
/>
</view>
<view> <view>
<nut-dialog no-cancel-btn content="详情" v-model:visible="detailVisible"> <nut-dialog
<slot> content="是否确认删除该用户?"
<view style="margin-bottom: 5px"> :onOk="dialogOk"
<view>籍贯{{content.nativePlace}}</view> v-model:visible="confirmVisible"
<view>公司{{content.securityUnitName}}</view> />
<view>家庭地址{{content.homeAddress}}</view> </view>
<view>备注{{content.remark}}</view> <view>
</view> <nut-dialog no-cancel-btn content="详情" v-model:visible="detailVisible">
</slot> <slot>
</nut-dialog> <view style="margin-bottom: 5px">
<view>籍贯{{ content.nativePlace }}</view>
<view>公司{{ content.securityUnitName }}</view>
<view>家庭地址{{ content.homeAddress }}</view>
<view>备注{{ content.remark }}</view>
</view>
</slot>
</nut-dialog>
</view> </view>
</view> </view>
</template> </template>
<script setup lang="ts"> <script setup lang="ts">
import Taro, {useLoad,useDidShow} from "@tarojs/taro"; import Taro, {useDidShow, useLoad} from "@tarojs/taro";
import './projectDetails.scss' import './projectDetails.scss'
import {ref} from "vue"; import {ref} from "vue";
import api from "@/request/index"; import api from "@/request/index";
import * as dayjs from 'dayjs' import * as dayjs from 'dayjs'
import {type} from "os";
const detailsList = ref()
const serviceProjectDetails = ref()
const nameValue = ref('') const nameValue = ref('')
const projectData = ref<Records[]>([]) const projectData = ref<Records[]>([])
const content = ref<Records>({} as any) const content = ref<Records>({} as any)
// //
const confirmVisible = ref(false); const confirmVisible = ref(false);
const detailVisible = ref(false) const detailVisible = ref(false)
useLoad(async (options: MyProjectList) => { useLoad(async (options: MyProjectList) => {
console.log(JSON.parse(options.item),'111111111111',options.name)
nameValue.value = options.name nameValue.value = options.name
detailsList.value = await JSON.parse(options.item) serviceProjectDetails.value = await JSON.parse(options.item)
}) })
useDidShow(async () => { useDidShow(async () => {
initServiceProjectSecurityUserList() initServiceProjectSecurityUserList()
}) })
const projectDetailsTable = async () => { const projectDetailsTable = async () => {
await Taro.showLoading({ await Taro.showLoading({
title: '加载中', title: '加载中',
}) })
const queryParams = { const queryParams = {
params: { params: {
serviceProjectId: detailsList.value?.snowFlakeId, serviceProjectId: serviceProjectDetails.value?.snowFlakeId,
}, },
page: { page: {
size: 4, size: 4,
@ -147,7 +153,20 @@ const projectDetailsTable = async () => {
Taro.hideLoading() Taro.hideLoading()
} }
const formAdd = () => { const formAdd = () => {
Taro.navigateTo({url: `/subPages/pages/form/form?item=${JSON.stringify(detailsList.value)}`}) const params = {
serviceProjectId: serviceProjectDetails.value.snowFlakeId,
snowFlakeId: undefined,
name: '',
workPost: '',
sex: 0,
nativePlace: '',
idCard: '',
dateOfBirth: null,
securityNumber: '',
remark: '',
homeAddress: ''
}
Taro.navigateTo({url: `/subPages/pages/form/form?item=${JSON.stringify(params)}`})
} }
const total = ref<any>(null) const total = ref<any>(null)
const current = ref(1) const current = ref(1)
@ -178,32 +197,32 @@ const onRefresherRefresh = (e) => {
const securityUserId = ref<string>('') const securityUserId = ref<string>('')
// //
const deleteUssrID = (snowFlakeId:string)=>{ const deleteUssrID = (snowFlakeId: string) => {
confirmVisible.value = true confirmVisible.value = true
securityUserId.value = snowFlakeId securityUserId.value = snowFlakeId
} }
// //
const dialogOk = async ()=>{ const dialogOk = async () => {
await api.delete(`/projectManageIndex/deleteSecurityUserByServiceProjectId`,{securityUserId:securityUserId.value},{ await api.delete(`/projectManageIndex/deleteSecurityUserByServiceProjectId`, {securityUserId: securityUserId.value}, {
header:{ header: {
"content-type":'application/x-www-form-urlencoded' "content-type": 'application/x-www-form-urlencoded'
} }
}) })
initServiceProjectSecurityUserList() initServiceProjectSecurityUserList()
} }
// //
const detail = (item)=>{ const detail = (item) => {
detailVisible.value = true detailVisible.value = true
content.value = item content.value = item
} }
const projectEdit = (item)=>{ const projectEdit = (item) => {
console.log(111) const params = {...item, sex: item.sex.value}
Taro.navigateTo({url: `/subPages/pages/form/form?item=${JSON.stringify(item)}`}) Taro.navigateTo({url: `/subPages/pages/form/form?item=${JSON.stringify(params)}`})
} }
</script> </script>
<style scoped lang="scss"> <style scoped lang="scss">

View File

@ -11,17 +11,25 @@
"outDir": "lib", "outDir": "lib",
"noUnusedLocals": false, "noUnusedLocals": false,
"noUnusedParameters": false, "noUnusedParameters": false,
"strictNullChecks": true, "strictNullChecks": false,
"sourceMap": true, "sourceMap": true,
"rootDir": ".", "rootDir": ".",
"jsx": "preserve", "jsx": "preserve",
"allowJs": true, "allowJs": true,
"resolveJsonModule": true, "resolveJsonModule": true,
"typeRoots": ["node_modules/@types"], "typeRoots": [
"node_modules/@types"
],
"paths": { "paths": {
"@/*": ["src/*"] "@/*": [
"src/*"
]
} }
}, },
"include": ["./src", "./types", "./config"], "include": [
"./src",
"./types",
"./config"
],
"compileOnSave": false "compileOnSave": false
} }

View File

@ -1,12 +1,14 @@
interface formDate { interface formDate {
snowFlakeId?:string; snowFlakeId?: string;
name: string; serviceProjectId: string;
workPost?:string; name?: string;
sex:number; workPost?: string;
nativePlace?:string; telephone?: string;
idCard:string; sex: number;
dateOfBirth?:string; nativePlace?: string;
securityNumber?:string; idCard: string;
remark?:string; dateOfBirth?: Date;
homeAddress?: string securityNumber?: string;
remark?: string;
homeAddress?: string
} }

View File

@ -1,5 +1,6 @@
package com.changhu.module.miniProgram.pojo.vo; package com.changhu.module.miniProgram.pojo.vo;
import cn.hutool.core.lang.Dict;
import com.changhu.common.db.enums.IsOrNot; import com.changhu.common.db.enums.IsOrNot;
import com.changhu.common.db.enums.ServiceProjectType; import com.changhu.common.db.enums.ServiceProjectType;
import com.changhu.module.management.pojo.model.ContactPersonInfo; import com.changhu.module.management.pojo.model.ContactPersonInfo;
@ -52,6 +53,8 @@ public class IndexServiceProjectListVo {
static class ServiceProjectVo { static class ServiceProjectVo {
@Schema(description = "服务项目id") @Schema(description = "服务项目id")
private Long snowFlakeId; private Long snowFlakeId;
@Schema(description = "项目经理信息")
private Dict projectManagerMiniProgramUserInfo;
@Schema(description = "服务项目名称") @Schema(description = "服务项目名称")
private String name; private String name;
@Schema(description = "服务项目类型") @Schema(description = "服务项目类型")

View File

@ -57,9 +57,14 @@
'houseTotal', sp.house_total, 'houseTotal', sp.house_total,
'staffTotal', sp.staff_total, 'staffTotal', sp.staff_total,
'securityUserTotal', sp.security_user_total, 'securityUserTotal', sp.security_user_total,
'projectManagerMiniProgramUserInfo',JSON_OBJECT(
'name',mpu.name,
'telephone',mpu.telephone,
'idCard',mpu.id_card),
'remark', sp.remark)) as 'service_project_list' 'remark', sp.remark)) as 'service_project_list'
from enterprises_unit eu from enterprises_unit eu
join service_project sp on eu.snow_flake_id = sp.enterprises_unit_id and sp.delete_flag = 0 join service_project sp on eu.snow_flake_id = sp.enterprises_unit_id and sp.delete_flag = 0
left join mini_program_user mpu on sp.project_manager_mini_program_user_id = mpu.snow_flake_id and mpu.delete_flag = 0
left join administrative_division ad1 on eu.province = ad1.code and ad1.delete_flag = 0 left join administrative_division ad1 on eu.province = ad1.code and ad1.delete_flag = 0
left join administrative_division ad2 on eu.city = ad2.code and ad2.delete_flag = 0 left join administrative_division ad2 on eu.city = ad2.code and ad2.delete_flag = 0
left join administrative_division ad3 on eu.districts = ad3.code and ad3.delete_flag = 0 left join administrative_division ad3 on eu.districts = ad3.code and ad3.delete_flag = 0

View File

@ -113,7 +113,8 @@ const columns: TableProps['columns'] = [
dataIndex: 'enterprisesUnitName', dataIndex: 'enterprisesUnitName',
title: '企事业单位名称', title: '企事业单位名称',
width: 150, width: 150,
ellipsis: true ellipsis: true,
}, },
{ {
dataIndex:'type', dataIndex:'type',
@ -192,7 +193,7 @@ const columns: TableProps['columns'] = [
<a-button type="primary" danger>删除</a-button> <a-button type="primary" danger>删除</a-button>
</a-popconfirm> </a-popconfirm>
<a-button type="primary" onClick={ async ()=>{ <a-button type="primary" onClick={ async ()=>{
console.log(record) // console.log(record)
visible.value = true visible.value = true
serviceTitle.value = '编辑服务项目' serviceTitle.value = '编辑服务项目'
if(record.isRecruitSecurity === null ){ if(record.isRecruitSecurity === null ){
@ -207,7 +208,7 @@ const columns: TableProps['columns'] = [
idNumberDisabled.value = true idNumberDisabled.value = true
} }
} }
formParams.value.projectManagerMiniProgramUserId = record.projectManagerMiniProgramUserName formParams.value.projectManagerMiniProgramUserId = record.projectManagerMiniProgramUserId
formParams.value.snowFlakeId = record.snowFlakeId formParams.value.snowFlakeId = record.snowFlakeId
formParams.value.name = record.name formParams.value.name = record.name
formParams.value.type = record.type.value formParams.value.type = record.type.value
@ -218,9 +219,7 @@ const columns: TableProps['columns'] = [
formParams.value.houseTotal = record.houseTotal formParams.value.houseTotal = record.houseTotal
formParams.value.staffTotal = record.staffTotal formParams.value.staffTotal = record.staffTotal
formParams.value. securityUserTotal = record.securityUserTotal formParams.value. securityUserTotal = record.securityUserTotal
formParams.value.enterprisesUnitId = record.enterprisesUnitName formParams.value.enterprisesUnitId = record.enterprisesUnitName
enterprisesUnitId.value = record.enterprisesUnitId
formParams.value.administrativeDivisionCodes = record.enterprisesUnitAdministrativeDivisionCodes formParams.value.administrativeDivisionCodes = record.enterprisesUnitAdministrativeDivisionCodes
}}>编辑</a-button> }}>编辑</a-button>
</a-space> </a-space>
@ -278,7 +277,11 @@ const formItemOptions = ref<FormProMaxItemOptions<serviceProjectSaveOrUpdatePara
label:'企事业单位', label:'企事业单位',
options:enterprisesUnitIdList, options:enterprisesUnitIdList,
componentsProps:{ componentsProps:{
allowClear:true allowClear:true,
onChange:async (value:string)=>{
console.log(value)
enterprisesUnitId.value = value
}
} }
}, },
type: { type: {
@ -368,10 +371,10 @@ const formItemOptions = ref<FormProMaxItemOptions<serviceProjectSaveOrUpdatePara
label: '备注', label: '备注',
} }
}) })
const UnitId = ref('')
const submit = async()=>{ const submit = async()=>{
await formRef.value.validate() await formRef.value.validate()
const snowFlakeId = ref('') const snowFlakeId = ref('')
const UnitId = ref('')
if (serviceTitle.value === '新增服务项目') { if (serviceTitle.value === '新增服务项目') {
snowFlakeId.value = '' snowFlakeId.value = ''
UnitId.value = formParams.value.enterprisesUnitId UnitId.value = formParams.value.enterprisesUnitId