Browse Source

Merge remote-tracking branch 'origin/master'

master
DX 2 months ago
parent
commit
8f1303cf13
  1. 2
      .env
  2. 4
      .env.dev
  3. 2
      .env.prod
  4. 1
      .eslintrc.js
  5. 4
      index.html
  6. 8
      src/api/enterprises/index.ts
  7. 13
      src/api/login/index.ts
  8. 7
      src/api/system/maxkb/index.ts
  9. 6
      src/api/system/user/index.ts
  10. 2
      src/layout/components/Logo/src/Logo.vue
  11. 1
      src/utils/dict.ts
  12. 326
      src/views/Home/Index.vue
  13. 3
      src/views/Login/Login.vue
  14. 12
      src/views/Login/components/LoginForm.vue
  15. 86
      src/views/Login/components/QrCodeForm.vue
  16. 138
      src/views/enterprises/components/SelectUser.vue
  17. 82
      src/views/enterprises/index.vue
  18. 211
      src/views/enterprises/update.vue
  19. 139
      src/views/task/create.vue
  20. 21
      src/views/task/index.vue

2
.env

@ -1,5 +1,5 @@
# 标题 # 标题
VITE_APP_TITLE=智慧生态管理系统 VITE_APP_TITLE=智慧生态系统
# 项目本地运行端口号 # 项目本地运行端口号
VITE_PORT=9980 VITE_PORT=9980

4
.env.dev

@ -4,7 +4,7 @@ NODE_ENV=production
VITE_DEV=true VITE_DEV=true
# 请求路径 # 请求路径
VITE_BASE_URL='http://api-dashboard.yudao.iocoder.cn' VITE_BASE_URL='http://localhost:48080'
# 文件上传类型:server - 后端上传, client - 前端直连上传,仅支持S3服务 # 文件上传类型:server - 后端上传, client - 前端直连上传,仅支持S3服务
VITE_UPLOAD_TYPE=server VITE_UPLOAD_TYPE=server
@ -31,7 +31,7 @@ VITE_OUT_DIR=dist
VITE_MALL_H5_DOMAIN='http://mall.yudao.iocoder.cn' VITE_MALL_H5_DOMAIN='http://mall.yudao.iocoder.cn'
# 验证码的开关 # 验证码的开关
VITE_APP_CAPTCHA_ENABLE=true VITE_APP_CAPTCHA_ENABLE=false
# GoView域名 # GoView域名
VITE_GOVIEW_URL='http://127.0.0.1:3000' VITE_GOVIEW_URL='http://127.0.0.1:3000'

2
.env.prod

@ -28,7 +28,7 @@ VITE_BASE_PATH=/
VITE_OUT_DIR=dist-prod VITE_OUT_DIR=dist-prod
# 商城H5会员端域名 # 商城H5会员端域名
VITE_MALL_H5_DOMAIN='http://mall.yudao.iocoder.cn' VITE_MALL_H5_DOMAIN='http://127.0.0.1:3000'
# GoView域名 # GoView域名
VITE_GOVIEW_URL='http://127.0.0.1:3000' VITE_GOVIEW_URL='http://127.0.0.1:3000'

1
.eslintrc.js

@ -7,6 +7,7 @@ module.exports = defineConfig({
node: true, node: true,
es6: true es6: true
}, },
globals:{ "qq": true,},
parser: 'vue-eslint-parser', parser: 'vue-eslint-parser',
parserOptions: { parserOptions: {
parser: '@typescript-eslint/parser', parser: '@typescript-eslint/parser',

4
index.html

@ -139,5 +139,9 @@
</div> </div>
</div> </div>
<script type="module" src="/src/main.ts"></script> <script type="module" src="/src/main.ts"></script>
<!-- <script charset="utf-8" src="https://map.qq.com/api/js?v=2.exp&key=PQ5BZ-GZ5C7-RTMXB-HSAPB-3TOAV-5CBLZ"></script> -->
<div id="app"></div>
</body> </body>
</html> </html>

8
src/api/enterprises/index.ts

@ -9,12 +9,14 @@ export interface EnterprisesVO {
region: string // 企业所属区域 region: string // 企业所属区域
enterprisesName: string // 企业名称 enterprisesName: string // 企业名称
address: string // 企业地址 address: string // 企业地址
enterprisesStatus//企业状态
contactName: string // 环保负责人姓名 contactName: string // 环保负责人姓名
environmentalContactPhone: string // 企业环保负责人联系电话 environmentalContactPhone: string // 企业环保负责人联系电话
registrationNumber: string // 企业注册号 registrationNumber: string // 企业注册号
introduction: string // 企业图文介绍 introduction: string // 企业图文介绍
establishmentDate: Date // 企业成立时间 establishmentDate: Date // 企业成立时间
gpsLocation: string // 企业经纬度 gpsLocation: string // 企业经纬度
signRadius:string//签到半径
managerDeptId: number // 管理部门 managerDeptId: number // 管理部门
} }
@ -26,7 +28,7 @@ export const EnterprisesApi = {
}, },
// 查询企业详情 // 查询企业详情
getEnterprises: async (id: number) => { getEnterprises: async (id: any) => {
return await request.get({ url: `/system/enterprise/get?id=` + id }) return await request.get({ url: `/system/enterprise/get?id=` + id })
}, },
@ -34,6 +36,10 @@ export const EnterprisesApi = {
createEnterprises: async (data: EnterprisesVO) => { createEnterprises: async (data: EnterprisesVO) => {
return await request.post({ url: `/system/enterprise/create`, data }) return await request.post({ url: `/system/enterprise/create`, data })
}, },
// PC新增企业
pccreateEnterprises: async (data: EnterprisesVO) => {
return await request.post({ url: `/system/enterprise/pccreate`, data })
},
// 修改企业 // 修改企业
updateEnterprises: async (data: EnterprisesVO) => { updateEnterprises: async (data: EnterprisesVO) => {

13
src/api/login/index.ts

@ -7,6 +7,8 @@ export interface SmsCodeVO {
scene: number scene: number
} }
export interface SmsLoginVO { export interface SmsLoginVO {
mobile: string mobile: string
code: string code: string
@ -72,10 +74,19 @@ export const socialAuthRedirect = (type: number, redirectUri: string) => {
} }
// 获取验证图片以及 token // 获取验证图片以及 token
export const getCode = (data: any) => { export const getCode = (data: any) => {
debugger
return request.postOriginal({ url: 'system/captcha/get', data }) return request.postOriginal({ url: 'system/captcha/get', data })
} }
// 获取登陆图片
export const getCodeWebPic = (data: any) => {
return request.post({ url: 'system/auth/web_code_login', data })
}
// 根据扫码生产的uuuid 进行登陆
export const qrLoginCode = (data: any) => {
return request.post({ url: 'system/auth/social-qr-login-openid', data })
}
// 滑动或者点选验证 // 滑动或者点选验证
export const reqCheck = (data: any) => { export const reqCheck = (data: any) => {
return request.postOriginal({ url: 'system/captcha/check', data }) return request.postOriginal({ url: 'system/captcha/check', data })

7
src/api/system/maxkb/index.ts

@ -0,0 +1,7 @@
import request from '@/config/axios'
// 推送maxkb知识库
export const pushWeb = async (data:any) => {
return await request.post({ url: '/system/maxkb/pushWeb',data })
}

6
src/api/system/user/index.ts

@ -25,6 +25,12 @@ export const getUserPage = (params: PageParam) => {
return request.get({ url: '/system/user/page', params }) return request.get({ url: '/system/user/page', params })
} }
// 查询专管员用户管理列表
export const getPcUserPage = (params: PageParam) => {
return request.get({ url: '/system/user/pcpage', params })
}
// 查询所有用户列表 // 查询所有用户列表
export const getAllUser = () => { export const getAllUser = () => {
return request.get({ url: '/system/user/all' }) return request.get({ url: '/system/user/all' })

2
src/layout/components/Logo/src/Logo.vue

@ -75,7 +75,7 @@ watch(
src="@/assets/imgs/logo.png" src="@/assets/imgs/logo.png"
/> />
<div <div
v-if="show" v-if="show" style="color:black"
:class="[ :class="[
'ml-10px text-16px font-700 flex-1', 'ml-10px text-16px font-700 flex-1',
{ {

1
src/utils/dict.ts

@ -115,6 +115,7 @@ export enum DICT_TYPE {
//========== 企业 ========== //========== 企业 ==========
ENTERPRISES_AREA = 'enterprises_area', ENTERPRISES_AREA = 'enterprises_area',
ENTERPRISES_TYPE = 'enterprises_type', ENTERPRISES_TYPE = 'enterprises_type',
ENTERPRISES_STATUS = 'enterprises_status',
//========== 资质 ========== //========== 资质 ==========
ENTERPRISES_QUA = 'enterprise_qua', ENTERPRISES_QUA = 'enterprise_qua',

326
src/views/Home/Index.vue

@ -1,173 +1,173 @@
<template> <template>
<div> <div>
<el-card shadow="never"> <!-- <el-card shadow="never">-->
<el-skeleton :loading="loading" animated> <!-- <el-skeleton :loading="loading" animated>-->
<el-row :gutter="16" justify="space-between"> <!-- <el-row :gutter="16" justify="space-between">-->
<el-col :xl="12" :lg="12" :md="12" :sm="24" :xs="24"> <!-- <el-col :xl="12" :lg="12" :md="12" :sm="24" :xs="24">-->
<div class="flex items-center"> <!-- <div class="flex items-center">-->
<el-avatar :src="avatar" :size="70" class="mr-16px"> <!-- <el-avatar :src="avatar" :size="70" class="mr-16px">-->
<img src="@/assets/imgs/avatar.gif" alt="" /> <!-- <img src="@/assets/imgs/avatar.gif" alt="" />-->
</el-avatar> <!-- </el-avatar>-->
<div> <!-- <div>-->
<div class="text-20px"> <!-- <div class="text-20px">-->
{{ t('workplace.welcome') }} {{ username }} {{ t('workplace.happyDay') }} <!-- {{ t('workplace.welcome') }} {{ username }} {{ t('workplace.happyDay') }}-->
</div> <!-- </div>-->
<div class="mt-10px text-14px text-gray-500"> <!-- <div class="mt-10px text-14px text-gray-500">-->
{{ t('workplace.toady') }}20 - 32 <!-- {{ t('workplace.toady') }}20 - 32-->
</div> <!-- </div>-->
</div> <!-- </div>-->
</div> <!-- </div>-->
</el-col> <!-- </el-col>-->
<el-col :xl="12" :lg="12" :md="12" :sm="24" :xs="24"> <!-- <el-col :xl="12" :lg="12" :md="12" :sm="24" :xs="24">-->
<div class="h-70px flex items-center justify-end lt-sm:mt-10px"> <!-- <div class="h-70px flex items-center justify-end lt-sm:mt-10px">-->
<div class="px-8px text-right"> <!-- <div class="px-8px text-right">-->
<div class="mb-16px text-14px text-gray-400">{{ t('workplace.project') }}</div> <!-- <div class="mb-16px text-14px text-gray-400">{{ t('workplace.project') }}</div>-->
<CountTo <!-- <CountTo-->
class="text-20px" <!-- class="text-20px"-->
:start-val="0" <!-- :start-val="0"-->
:end-val="totalSate.project" <!-- :end-val="totalSate.project"-->
:duration="2600" <!-- :duration="2600"-->
/> <!-- />-->
</div> <!-- </div>-->
<el-divider direction="vertical" /> <!-- <el-divider direction="vertical" />-->
<div class="px-8px text-right"> <!-- <div class="px-8px text-right">-->
<div class="mb-16px text-14px text-gray-400">{{ t('workplace.toDo') }}</div> <!-- <div class="mb-16px text-14px text-gray-400">{{ t('workplace.toDo') }}</div>-->
<CountTo <!-- <CountTo-->
class="text-20px" <!-- class="text-20px"-->
:start-val="0" <!-- :start-val="0"-->
:end-val="totalSate.todo" <!-- :end-val="totalSate.todo"-->
:duration="2600" <!-- :duration="2600"-->
/> <!-- />-->
</div> <!-- </div>-->
<el-divider direction="vertical" border-style="dashed" /> <!-- <el-divider direction="vertical" border-style="dashed" />-->
<div class="px-8px text-right"> <!-- <div class="px-8px text-right">-->
<div class="mb-16px text-14px text-gray-400">{{ t('workplace.access') }}</div> <!-- <div class="mb-16px text-14px text-gray-400">{{ t('workplace.access') }}</div>-->
<CountTo <!-- <CountTo-->
class="text-20px" <!-- class="text-20px"-->
:start-val="0" <!-- :start-val="0"-->
:end-val="totalSate.access" <!-- :end-val="totalSate.access"-->
:duration="2600" <!-- :duration="2600"-->
/> <!-- />-->
</div> <!-- </div>-->
</div> <!-- </div>-->
</el-col> <!-- </el-col>-->
</el-row> <!-- </el-row>-->
</el-skeleton> <!-- </el-skeleton>-->
</el-card> <!-- </el-card>-->
</div> </div>
<el-row class="mt-8px" :gutter="8" justify="space-between"> <el-row class="mt-8px" :gutter="8" justify="space-between">
<el-col :xl="16" :lg="16" :md="24" :sm="24" :xs="24" class="mb-8px"> <el-col :xl="16" :lg="16" :md="24" :sm="24" :xs="24" class="mb-8px">
<el-card shadow="never"> <!-- <el-card shadow="never">-->
<template #header> <!-- <template #header>-->
<div class="h-3 flex justify-between"> <!-- <div class="h-3 flex justify-between">-->
<span>{{ t('workplace.project') }}</span> <!-- <span>{{ t('workplace.project') }}</span>-->
<el-link <!-- <el-link-->
type="primary" <!-- type="primary"-->
:underline="false" <!-- :underline="false"-->
href="https://github.com/yudaocode" <!-- href="https://github.com/yudaocode"-->
target="_blank" <!-- target="_blank"-->
> <!-- >-->
{{ t('action.more') }} <!-- {{ t('action.more') }}-->
</el-link> <!-- </el-link>-->
</div> <!-- </div>-->
</template> <!-- </template>-->
<el-skeleton :loading="loading" animated> <!-- <el-skeleton :loading="loading" animated>-->
<el-row> <!-- <el-row>-->
<el-col <!-- <el-col-->
v-for="(item, index) in projects" <!-- v-for="(item, index) in projects"-->
:key="`card-${index}`" <!-- :key="`card-${index}`"-->
:xl="8" <!-- :xl="8"-->
:lg="8" <!-- :lg="8"-->
:md="8" <!-- :md="8"-->
:sm="24" <!-- :sm="24"-->
:xs="24" <!-- :xs="24"-->
> <!-- >-->
<el-card shadow="hover" class="mr-5px mt-5px"> <!-- <el-card shadow="hover" class="mr-5px mt-5px">-->
<div class="flex items-center"> <!-- <div class="flex items-center">-->
<Icon :icon="item.icon" :size="25" class="mr-8px" /> <!-- <Icon :icon="item.icon" :size="25" class="mr-8px" />-->
<span class="text-16px">{{ item.name }}</span> <!-- <span class="text-16px">{{ item.name }}</span>-->
</div> <!-- </div>-->
<div class="mt-12px text-9px text-gray-400">{{ t(item.message) }}</div> <!-- <div class="mt-12px text-9px text-gray-400">{{ t(item.message) }}</div>-->
<div class="mt-12px flex justify-between text-12px text-gray-400"> <!-- <div class="mt-12px flex justify-between text-12px text-gray-400">-->
<span>{{ item.personal }}</span> <!-- <span>{{ item.personal }}</span>-->
<span>{{ formatTime(item.time, 'yyyy-MM-dd') }}</span> <!-- <span>{{ formatTime(item.time, 'yyyy-MM-dd') }}</span>-->
</div> <!-- </div>-->
</el-card> <!-- </el-card>-->
</el-col> <!-- </el-col>-->
</el-row> <!-- </el-row>-->
</el-skeleton> <!-- </el-skeleton>-->
</el-card> <!-- </el-card>-->
<el-card shadow="never" class="mt-8px"> <!-- <el-card shadow="never" class="mt-8px">-->
<el-skeleton :loading="loading" animated> <!-- <el-skeleton :loading="loading" animated>-->
<el-row :gutter="20" justify="space-between"> <!-- <el-row :gutter="20" justify="space-between">-->
<el-col :xl="10" :lg="10" :md="24" :sm="24" :xs="24"> <!-- <el-col :xl="10" :lg="10" :md="24" :sm="24" :xs="24">-->
<el-card shadow="hover" class="mb-8px"> <!-- <el-card shadow="hover" class="mb-8px">-->
<el-skeleton :loading="loading" animated> <!-- <el-skeleton :loading="loading" animated>-->
<Echart :options="pieOptionsData" :height="280" /> <!-- <Echart :options="pieOptionsData" :height="280" />-->
</el-skeleton> <!-- </el-skeleton>-->
</el-card> <!-- </el-card>-->
</el-col> <!-- </el-col>-->
<el-col :xl="14" :lg="14" :md="24" :sm="24" :xs="24"> <!-- <el-col :xl="14" :lg="14" :md="24" :sm="24" :xs="24">-->
<el-card shadow="hover" class="mb-8px"> <!-- <el-card shadow="hover" class="mb-8px">-->
<el-skeleton :loading="loading" animated> <!-- <el-skeleton :loading="loading" animated>-->
<Echart :options="barOptionsData" :height="280" /> <!-- <Echart :options="barOptionsData" :height="280" />-->
</el-skeleton> <!-- </el-skeleton>-->
</el-card> <!-- </el-card>-->
</el-col> <!-- </el-col>-->
</el-row> <!-- </el-row>-->
</el-skeleton> <!-- </el-skeleton>-->
</el-card> <!-- </el-card>-->
</el-col> <!-- </el-col>-->
<el-col :xl="8" :lg="8" :md="24" :sm="24" :xs="24" class="mb-8px"> <!-- <el-col :xl="8" :lg="8" :md="24" :sm="24" :xs="24" class="mb-8px">-->
<el-card shadow="never"> <!-- <el-card shadow="never">-->
<template #header> <!-- <template #header>-->
<div class="h-3 flex justify-between"> <!-- <div class="h-3 flex justify-between">-->
<span>{{ t('workplace.shortcutOperation') }}</span> <!-- <span>{{ t('workplace.shortcutOperation') }}</span>-->
</div> <!-- </div>-->
</template> <!-- </template>-->
<el-skeleton :loading="loading" animated> <!-- <el-skeleton :loading="loading" animated>-->
<el-row> <!-- <el-row>-->
<el-col v-for="item in shortcut" :key="`team-${item.name}`" :span="8" class="mb-8px"> <!-- <el-col v-for="item in shortcut" :key="`team-${item.name}`" :span="8" class="mb-8px">-->
<div class="flex items-center"> <!-- <div class="flex items-center">-->
<Icon :icon="item.icon" class="mr-8px" /> <!-- <Icon :icon="item.icon" class="mr-8px" />-->
<el-link type="default" :underline="false" @click="setWatermark(item.name)"> <!-- <el-link type="default" :underline="false" @click="setWatermark(item.name)">-->
{{ item.name }} <!-- {{ item.name }}-->
</el-link> <!-- </el-link>-->
</div> <!-- </div>-->
</el-col> <!-- </el-col>-->
</el-row> <!-- </el-row>-->
</el-skeleton> <!-- </el-skeleton>-->
</el-card> <!-- </el-card>-->
<el-card shadow="never" class="mt-8px"> <!-- <el-card shadow="never" class="mt-8px">-->
<template #header> <!-- <template #header>-->
<div class="h-3 flex justify-between"> <!-- <div class="h-3 flex justify-between">-->
<span>{{ t('workplace.notice') }}</span> <!-- <span>{{ t('workplace.notice') }}</span>-->
<el-link type="primary" :underline="false">{{ t('action.more') }}</el-link> <!-- <el-link type="primary" :underline="false">{{ t('action.more') }}</el-link>-->
</div> <!-- </div>-->
</template> <!-- </template>-->
<el-skeleton :loading="loading" animated> <!-- <el-skeleton :loading="loading" animated>-->
<div v-for="(item, index) in notice" :key="`dynamics-${index}`"> <!-- <div v-for="(item, index) in notice" :key="`dynamics-${index}`">-->
<div class="flex items-center"> <!-- <div class="flex items-center">-->
<el-avatar :src="avatar" :size="35" class="mr-16px"> <!-- <el-avatar :src="avatar" :size="35" class="mr-16px">-->
<img src="@/assets/imgs/avatar.gif" alt="" /> <!-- <img src="@/assets/imgs/avatar.gif" alt="" />-->
</el-avatar> <!-- </el-avatar>-->
<div> <!-- <div>-->
<div class="text-14px"> <!-- <div class="text-14px">-->
<Highlight :keys="item.keys.map((v) => t(v))"> <!-- <Highlight :keys="item.keys.map((v) => t(v))">-->
{{ item.type }} : {{ item.title }} <!-- {{ item.type }} : {{ item.title }}-->
</Highlight> <!-- </Highlight>-->
</div> <!-- </div>-->
<div class="mt-16px text-12px text-gray-400"> <!-- <div class="mt-16px text-12px text-gray-400">-->
{{ formatTime(item.date, 'yyyy-MM-dd') }} <!-- {{ formatTime(item.date, 'yyyy-MM-dd') }}-->
</div> <!-- </div>-->
</div> <!-- </div>-->
</div> <!-- </div>-->
<el-divider /> <!-- <el-divider />-->
</div> <!-- </div>-->
</el-skeleton> <!-- </el-skeleton>-->
</el-card> <!-- </el-card>-->
</el-col> </el-col>
</el-row> </el-row>
</template> </template>

3
src/views/Login/Login.vue

@ -51,8 +51,7 @@
> >
<!-- 账号登录 --> <!-- 账号登录 -->
<LoginForm class="m-auto h-auto p-20px lt-xl:(rounded-3xl light:bg-white)" /> <LoginForm class="m-auto h-auto p-20px lt-xl:(rounded-3xl light:bg-white)" />
<!-- 手机登录 -->
<MobileForm class="m-auto h-auto p-20px lt-xl:(rounded-3xl light:bg-white)" />
<!-- 二维码登录 --> <!-- 二维码登录 -->
<QrCodeForm class="m-auto h-auto p-20px lt-xl:(rounded-3xl light:bg-white)" /> <QrCodeForm class="m-auto h-auto p-20px lt-xl:(rounded-3xl light:bg-white)" />
<!-- 注册 --> <!-- 注册 -->

12
src/views/Login/components/LoginForm.vue

@ -92,13 +92,13 @@
<el-col :span="24" style="padding-right: 10px; padding-left: 10px"> <el-col :span="24" style="padding-right: 10px; padding-left: 10px">
<el-form-item> <el-form-item>
<el-row :gutter="5" justify="space-between" style="width: 100%"> <el-row :gutter="5" justify="space-between" style="width: 100%">
<el-col :span="8"> <!-- <el-col :span="8">
<XButton <XButton
:title="t('login.btnMobile')" :title="t('login.btnMobile')"
class="w-[100%]" class="w-[100%]"
@click="setLoginState(LoginStateEnum.MOBILE)" @click="setLoginState(LoginStateEnum.MOBILE)"
/> />
</el-col> </el-col> -->
<el-col :span="8"> <el-col :span="8">
<XButton <XButton
:title="t('login.btnQRCode')" :title="t('login.btnQRCode')"
@ -116,7 +116,7 @@
</el-row> </el-row>
</el-form-item> </el-form-item>
</el-col> </el-col>
<el-divider content-position="center">{{ t('login.otherLogin') }}</el-divider> <!-- <el-divider content-position="center">{{ t('login.otherLogin') }}</el-divider>
<el-col :span="24" style="padding-right: 10px; padding-left: 10px"> <el-col :span="24" style="padding-right: 10px; padding-left: 10px">
<el-form-item> <el-form-item>
<div class="w-[100%] flex justify-between"> <div class="w-[100%] flex justify-between">
@ -131,8 +131,8 @@
/> />
</div> </div>
</el-form-item> </el-form-item>
</el-col> </el-col> -->
<el-divider content-position="center">萌新必读</el-divider> <!-- <el-divider content-position="center">萌新必读</el-divider>
<el-col :span="24" style="padding-right: 10px; padding-left: 10px"> <el-col :span="24" style="padding-right: 10px; padding-left: 10px">
<el-form-item> <el-form-item>
<div class="w-[100%] flex justify-between"> <div class="w-[100%] flex justify-between">
@ -146,7 +146,7 @@
</el-link> </el-link>
</div> </div>
</el-form-item> </el-form-item>
</el-col> </el-col> -->
</el-row> </el-row>
</el-form> </el-form>
</template> </template>

86
src/views/Login/components/QrCodeForm.vue

@ -5,7 +5,10 @@
</el-col> </el-col>
<el-col :span="24" style="padding-right: 10px; padding-left: 10px"> <el-col :span="24" style="padding-right: 10px; padding-left: 10px">
<el-card class="mb-10px text-center" shadow="hover"> <el-card class="mb-10px text-center" shadow="hover">
<Qrcode :logo="logoImg" /> <!-- <Qrcode :logo="logoImg" /> -->
<!-- 显示图片 -->
<img :src="imageUrl" alt="Converted Image" v-if="imageUrl" />
<XButton title="显示登陆二维码" class="w-[100%]" @click="getimg()" />
</el-card> </el-card>
</el-col> </el-col>
<el-divider class="enter-x">{{ t('login.qrcode') }}</el-divider> <el-divider class="enter-x">{{ t('login.qrcode') }}</el-divider>
@ -18,13 +21,90 @@
</template> </template>
<script lang="ts" setup> <script lang="ts" setup>
import logoImg from '@/assets/imgs/logo.png' import logoImg from '@/assets/imgs/logo.png'
import * as LoginApi from '@/api/login'
import * as authUtil from '@/utils/auth'
import LoginFormTitle from './LoginFormTitle.vue' import LoginFormTitle from './LoginFormTitle.vue'
import { LoginStateEnum, useLoginState } from './useLogin' import { LoginStateEnum, useLoginState } from './useLogin'
import router from '@/router'
defineOptions({ name: 'QrCodeForm' }) defineOptions({ name: 'QrCodeForm' })
const imageUrl = ref('');
const uuuid =ref('')
const { t } = useI18n() const { t } = useI18n()
const { handleBackLogin, getLoginState } = useLoginState() const { handleBackLogin, getLoginState } = useLoginState()
const getShow = computed(() => unref(getLoginState) === LoginStateEnum.QR_CODE) const getShow = computed(() => unref(getLoginState) === LoginStateEnum.QR_CODE)
// ID
let intervalId = ref();
const getimg =async ()=>{
const array = new Uint32Array(4);
crypto.getRandomValues(array);
let result = '';
array.forEach((value) => {
result += value.toString(16).padStart(8, '0');
});
uuuid.value = result;
var mockBinaryData = await LoginApi.getCodeWebPic({
scene:uuuid.value,
path: 'sub/common/waiting',
checkPath: false
});
// Base64
const binaryString = atob(mockBinaryData);
const len = binaryString.length;
const bytes = new Uint8Array(len);
for (let i = 0; i < len; i++) {
bytes[i] = binaryString.charCodeAt(i);
}
// Blob
const blob = new Blob([bytes], { type: 'image/png' });
// URL
imageUrl.value = URL.createObjectURL(blob);
//
refaulst();
}
//
const startTime = Date.now();
// 10
const tenMinutes = 60 * 1000;
//
const refaulst = ()=>{
//
if (intervalId) {
clearInterval(intervalId.value);
}
// 5
intervalId.value = setInterval(async () => {
try {
// 10
if (Date.now() - startTime >= tenMinutes) {
clearInterval(intervalId.value);
console.log('定时器已停止,已过去 10 分钟。');
return;
}
const res = await LoginApi.qrLoginCode({code:uuuid.value})
if(res){
clearInterval(intervalId.value);
authUtil.setToken(res)
router.push({ path: '/' })
}
} catch (error) {
console.error('获取扫码状态失败:', error);
}
}, 5000);
}
onMounted(() => {
// getCookie()
getimg()
})
</script> </script>

138
src/views/enterprises/components/SelectUser.vue

@ -0,0 +1,138 @@
<template>
<section class="select-wrapper" v-if="show">
<!-- 左侧部门树 -->
<section class="dept-wrapper">
<DeptTree @node-click="handleDeptNodeClick" />
</section>
<section class="dept-wrapper">
<el-table v-loading="loading" :data="list" @row-click="handleClickRow">
<el-table-column label="用户编号" align="center" key="id" prop="id" />
<el-table-column
label="用户名称"
align="center"
prop="username"
:show-overflow-tooltip="true"
/>
<el-table-column
label="用户昵称"
align="center"
prop="nickname"
:show-overflow-tooltip="true"
/>
<el-table-column
label="部门"
align="center"
key="deptName"
prop="deptName"
:show-overflow-tooltip="true"
/>
</el-table>
<Pagination
:total="total"
v-model:page="queryParams.pageNo"
v-model:limit="queryParams.pageSize"
@pagination="getList"
/>
<el-button type="primary" class="close" circle size="small" @click="close">
<Icon icon="ep:close" />
</el-button>
</section>
</section>
</template>
<script lang="ts" setup>
import * as UserApi from '@/api/system/user'
import DeptTree from '@/views/system/user/DeptTree.vue'
import {getPcUserPage} from "@/api/system/user";
const show = ref(false)
const loading = ref(true) //
const total = ref(0) //
const list = ref([]) //
const queryParams = reactive({
pageNo: 1,
pageSize: 10,
username: undefined,
mobile: undefined,
status: undefined,
deptId: undefined,
createTime: []
})
const emit = defineEmits(['select', 'close'])
/** 查询列表 */
const getList = async () => {
loading.value = true
try {
const data = await UserApi.getPcUserPage(queryParams)
list.value = data.list
total.value = data.total
} finally {
loading.value = false
}
}
/** 处理部门被点击 */
const handleDeptNodeClick = async (row) => {
queryParams.deptId = row.id
await getList()
}
function handleClickRow(row) {
emit('select', row)
}
function open() {
getList()
show.value = true
}
function close() {
show.value = false
emit('close')
}
defineExpose({ open })
</script>
<style lang="scss" scoped>
.select-wrapper {
display: flex;
flex-flow: row nowrap;
background-color: #fff;
padding: 10px;
padding-top: 50px;
border-radius: 6px;
min-height: 50vh;
position: relative;
.close {
position: absolute;
top: 10px;
right: 10px;
}
.selec-wrapper {
max-width: 400px;
display: flex;
flex-flow: row nowrap;
gap: 5px;
.users {
flex: 1;
display: flex;
flex-flow: row wrap;
gap: 5px;
}
.select {
cursor: pointer;
background-color: #f1faff;
border: 1px dashed #00a3ff;
padding: 0px 15px;
color: #00a3ff;
// color: #00a3ff;
// text-decoration: underline;
border-radius: 6px;
height: fit-content;
&:hover {
opacity: 0.8;
}
}
}
}
</style>

82
src/views/enterprises/index.vue

@ -79,11 +79,39 @@
/> />
</el-form-item> </el-form-item>
<el-form-item label="企业状态" prop="enterprisesStatus">
<el-select
v-model="queryParams.enterprisesStatus"
placeholder="请选择企业状态"
clearable
class="!w-240px"
>
<el-option
v-for="dict in getStrDictOptions(DICT_TYPE.ENTERPRISES_STATUS)"
:key="dict.value"
:label="dict.label"
:value="dict.value"
/>
</el-select>
</el-form-item>
<el-form-item> <el-form-item>
<el-button @click="handleQuery"><Icon icon="ep:search" class="mr-5px" /> 搜索</el-button> <el-button @click="handleQuery"><Icon icon="ep:search" class="mr-5px" /> 搜索</el-button>
<el-button @click="resetQuery"><Icon icon="ep:refresh" class="mr-5px" /> 重置</el-button> <el-button @click="resetQuery"><Icon icon="ep:refresh" class="mr-5px" /> 重置</el-button>
<el-button type="primary" plain @click="openForm('create')"> <el-button type="primary" plain @click="
<Icon icon="ep:plus" class="mr-5px" /> 新增 push({
path: 'update'
})
">
<Icon icon="ep:plus" class="mr-5px" @click="
push({
path: 'update',
query: {
id: scope.row.id
}
})
" /> 新增
</el-button> </el-button>
<el-button type="success" plain @click="handleExport" :loading="exportLoading"> <el-button type="success" plain @click="handleExport" :loading="exportLoading">
<Icon icon="ep:download" class="mr-5px" /> 导出 <Icon icon="ep:download" class="mr-5px" /> 导出
@ -96,7 +124,7 @@
<ContentWrap> <ContentWrap>
<el-table v-loading="loading" :data="list" :stripe="true" :show-overflow-tooltip="true"> <el-table v-loading="loading" :data="list" :stripe="true" :show-overflow-tooltip="true">
<el-table-column label="企业名称" align="center" fixed="left" prop="enterprisesName" /> <el-table-column label="企业名称" align="center" fixed="left" prop="enterprisesName" />
<el-table-column label="邀请人" align="center" prop="inviterName" fixed="left" /> <el-table-column label="专管员" align="center" prop="inviterName" fixed="left" />
<el-table-column label="企业类型" align="center" prop="type" fixed="left" > <el-table-column label="企业类型" align="center" prop="type" fixed="left" >
<template #default="scope"> <template #default="scope">
<dict-tag :type="DICT_TYPE.ENTERPRISES_TYPE" :value="scope.row.type" /> <dict-tag :type="DICT_TYPE.ENTERPRISES_TYPE" :value="scope.row.type" />
@ -128,13 +156,26 @@
/> />
<el-table-column label="操作" align="center" min-width="120px"> <el-table-column label="操作" align="center" min-width="120px">
<template #default="scope"> <template #default="scope">
<el-button link type="primary" @click="openForm('update', scope.row.id)">
编辑 <el-button
link
type="primary"
@click="
push({
path: 'update',
query: {
id: scope.row.id
}
})
"
v-hasPermi="['system:task-info:update']"
>
详情
</el-button> </el-button>
<el-button link type="danger" @click="handleDelete(scope.row.id)"> 删除 </el-button> <el-button link type="danger" @click="handleDelete(scope.row.id)"> 删除 </el-button>
<!--
<el-button link type="danger" @click="detailformRef(scope.row.id)"> 详情 </el-button> <el-button link type="danger" @click="detailformRef(scope.row.id)"> 详情 </el-button> -->
<!-- <router-link :to="'/enterprises/detailEnterprises/' + scope.row.type">--> <!-- <router-link :to="'/enterprises/detailEnterprises/' + scope.row.type">-->
<!-- <el-button link type="primary">详情</el-button>--> <!-- <el-button link type="primary">详情</el-button>-->
<!-- </router-link>--> <!-- </router-link>-->
@ -151,7 +192,7 @@
</ContentWrap> </ContentWrap>
<!-- 表单弹窗添加/修改 --> <!-- 表单弹窗添加/修改 -->
<EnterprisesForm ref="formRef" @success="getList" />
</template> </template>
<script setup lang="ts"> <script setup lang="ts">
@ -159,8 +200,7 @@ import { getStrDictOptions, DICT_TYPE } from '@/utils/dict'
import { dateFormatter } from '@/utils/formatTime' import { dateFormatter } from '@/utils/formatTime'
import download from '@/utils/download' import download from '@/utils/download'
import { EnterprisesApi, EnterprisesVO } from '@/api/enterprises' import { EnterprisesApi, EnterprisesVO } from '@/api/enterprises'
import EnterprisesForm from './EnterprisesForm.vue' import update from './update.vue'
/** 企业 列表 */ /** 企业 列表 */
defineOptions({ name: 'Enterprises' }) defineOptions({ name: 'Enterprises' })
@ -179,6 +219,7 @@ const queryParams = reactive({
region: undefined, region: undefined,
enterprisesName: undefined, enterprisesName: undefined,
address: undefined, address: undefined,
enterprisesStatus:undefined,
contactName: undefined, contactName: undefined,
environmentalContactPhone: undefined, environmentalContactPhone: undefined,
registrationNumber: undefined, registrationNumber: undefined,
@ -224,14 +265,17 @@ const openForm = (type: string, id?: number) => {
/*详情*/ /*详情*/
const { push } = useRouter() // const { push } = useRouter() //
const detailformRef = (id?: number) => { // const detailformRef = (id?: number) => {
push({ // push({
path: '/enterprises/detailEnterprises', // path: '/system/enterprise/get',
query: { // query: {
id // id
} // }
}) // })
} // }
/** 删除按钮操作 */ /** 删除按钮操作 */
const handleDelete = async (id: number) => { const handleDelete = async (id: number) => {

211
src/views/enterprises/EnterprisesForm.vue → src/views/enterprises/update.vue

@ -1,13 +1,8 @@
<template> <template>
<Dialog :title="dialogTitle" v-model="dialogVisible"> <ContentWrap title="企业基本信息">
<el-form <section class="taskForm">
ref="formRef" <el-form ref="formRef" :model="formData" :rules="formRules" label-width="auto" v-loading="loading">
:model="formData" <el-form-item label="企业类型" prop="type">
:rules="formRules"
label-width="100px"
v-loading="formLoading"
>
<el-form-item label="企业类型" prop="type">
<el-select v-model="formData.type" placeholder="请选择企业类型"> <el-select v-model="formData.type" placeholder="请选择企业类型">
<el-option <el-option
v-for="dict in getStrDictOptions(DICT_TYPE.ENTERPRISES_TYPE)" v-for="dict in getStrDictOptions(DICT_TYPE.ENTERPRISES_TYPE)"
@ -27,6 +22,25 @@
/> />
</el-select> </el-select>
</el-form-item> </el-form-item>
<el-form-item label="专管员" prop="startUserSelectAssignees">
<section class="selec-wrapper">
<section class="users">
<el-tag
v-for="user in formData.startUserSelectAssignees"
:key="user.id"
closable
@close="removeUser(user.id)"
>
{{ user.nickname }} {{ user.deptName }}
</el-tag>
</section>
<section class="select" @click="handlerClickSelect"> 请选择专管员</section>
</section>
</el-form-item>
<el-form-item label="企业名称" prop="enterprisesName"> <el-form-item label="企业名称" prop="enterprisesName">
<el-input v-model="formData.enterprisesName" placeholder="请输入企业名称" /> <el-input v-model="formData.enterprisesName" placeholder="请输入企业名称" />
</el-form-item> </el-form-item>
@ -61,36 +75,74 @@
placeholder="选择企业成立时间" placeholder="选择企业成立时间"
/> />
</el-form-item> </el-form-item>
<el-form-item label="企业经纬度" prop="gpsLocation"> <el-form-item label="企业经纬度" prop="gpsLocation">
<el-input v-model="formData.gpsLocation" placeholder="请输入企业经纬度" /> <el-input
v-model="formData.gpsLocation"
placeholder="点击按钮选择坐标"
readonly
>
<template #append>
<!-- 选择坐标按钮 -->
<el-button @click="showMap = true">选择坐标</el-button>
</template>
</el-input>
</el-form-item> </el-form-item>
<el-form-item label="管理部门" prop="managerDeptId">
<el-select v-model="formData.managerDeptId" placeholder="请选择管理部门"> <!-- 地图弹窗 -->
<el-option label="请选择字典生成" value="" /> <el-dialog
</el-select> v-model="showMap"
title="选择坐标"
width="80%"
:before-close="handleClose"
>
<div id="map-container" style="width: 100%; height: 400px;"></div>
<template #footer>
<el-button @click="showMap = false">取消</el-button>
<el-button type="primary" @click="confirmCoordinate">确定</el-button>
</template>
</el-dialog>
<el-form-item label="签到半径" prop="gpsLocation" >
<el-input v-model="formData.signRadius" placeholder="请输入签到半径" style="width: 280px;" /><span style="margin-left: 10px">单位</span>
</el-form-item> </el-form-item>
</el-form>
<template #footer>
<el-button @click="submitForm" type="primary" :disabled="formLoading"> </el-button> </el-form>
<el-button @click="dialogVisible = false"> </el-button> </section>
</template>
</Dialog> <el-dialog v-model="dialogVisible" title="选择用户">
</template>s <!-- SelectUser 组件放入弹框中 -->
<template #content>
<SelectUser ref="selectUserRef" @select="handlerSelectUser" />
</template>
<!-- 弹框底部的取消和确定按钮 -->
<template #footer>
<el-button @click="dialogVisible = false">取消</el-button>
<el-button type="primary" @click="dialogVisible = false">确定</el-button>
</template>
</el-dialog>
</ContentWrap>
</template>
<script setup lang="ts"> <script setup lang="ts">
import { getStrDictOptions, DICT_TYPE } from '@/utils/dict' import { getStrDictOptions, DICT_TYPE } from '@/utils/dict'
import { EnterprisesApi, EnterprisesVO } from '@/api/enterprises' import { EnterprisesApi, EnterprisesVO } from '@/api/enterprises'
import { FileInfoApi } from '@/api/enterprises/fileinfo' import { FileInfoApi } from '@/api/enterprises/fileinfo'
import { ElMessage } from 'element-plus' import { ElMessage } from 'element-plus'
import SelectUser from '@/views/enterprises/components/SelectUser.vue'
/** 企业 表单 */ /** 企业 表单 */
defineOptions({ name: 'EnterprisesForm' }) defineOptions({ name: 'UpdateEnterprises' })
const { t } = useI18n() // const { t } = useI18n() //
const message = useMessage() // const message = useMessage() //
const dialogVisible = ref(false) // const dialogVisible = ref(false) //
const dialogTitle = ref('') // const dialogTitle = ref('') //
const formLoading = ref(false) // 12 const formLoading = ref(false) // 12
const formType = ref('') // create - update - const formType = ref('') // create - update -
const selectUserRef = ref()
const loading = ref(false)
const formData = ref({ const formData = ref({
id: undefined, id: undefined,
departmentId: undefined, departmentId: undefined,
@ -106,31 +158,42 @@ const formData = ref({
establishmentDate: undefined, establishmentDate: undefined,
gpsLocation: undefined, gpsLocation: undefined,
managerDeptId: undefined, managerDeptId: undefined,
ides:undefined ides:undefined,
startUserSelectAssignees: []
}) })
const formRules = reactive({ const formRules = reactive({
type: [{ required: true, message: '企业类型不能为空', trigger: 'change' }], type: [{ required: true, message: '企业类型不能为空', trigger: 'change' }],
enterprisesName: [{ required: true, message: '企业名称不能为空', trigger: 'blur' }], enterprisesName: [{ required: true, message: '企业名称不能为空', trigger: 'blur' }],
}) })
const formRef = ref() // Ref const formRef = ref() // Ref
const {query}=useRoute()
/** 打开弹窗 */ function init(){
const open = async (type: string, id?: number) => { if(query.id){
dialogVisible.value = true EnterprisesApi.getEnterprises(query.id).then(res=>{
dialogTitle.value = t('action.' + type) formData.value=res
formType.value = type })
resetForm() }
// }
if (id) {
formLoading.value = true
try {
formData.value = await EnterprisesApi.getEnterprises(id) onMounted(()=>{
} finally { init()
formLoading.value = false })
}
}
function handlerClickSelect() {
dialogVisible.value = true;
// SelectUser open
unref(selectUserRef)?.open();
}
function handlerSelectUser(row) {
if (formData.value.startUserSelectAssignees.findIndex((i) => i.id == row.id) > -1) return
formData.value.startUserSelectAssignees.push(row)
} }
defineExpose({ open }) // open
/** 提交表单 */ /** 提交表单 */
const emit = defineEmits(['success']) // success const emit = defineEmits(['success']) // success
@ -138,7 +201,7 @@ const submitForm = async () => {
// //
await formRef.value.validate() await formRef.value.validate()
// //
formLoading.value = true loading.value = true
try { try {
const data = formData.value as unknown as EnterprisesVO const data = formData.value as unknown as EnterprisesVO
if (formType.value === 'create') { if (formType.value === 'create') {
@ -152,7 +215,7 @@ const submitForm = async () => {
// //
emit('success') emit('success')
} finally { } finally {
formLoading.value = false loading.value = false
} }
} }
@ -173,6 +236,7 @@ const resetForm = () => {
establishmentDate: undefined, establishmentDate: undefined,
gpsLocation: undefined, gpsLocation: undefined,
managerDeptId: undefined, managerDeptId: undefined,
startUserSelectAssignees: []
} }
formRef.value?.resetFields() formRef.value?.resetFields()
} }
@ -200,7 +264,7 @@ async function uploadSuccess(res) {
} }
function getCarImg() { function getCarImg() {
formLoading.value = true loading.value = true
FileInfoApi.getFileInfoPage({ unitId: formData.value.id, type: 4 }).then((res) => { FileInfoApi.getFileInfoPage({ unitId: formData.value.id, type: 4 }).then((res) => {
uploadList.value = res.list.map((item) => { uploadList.value = res.list.map((item) => {
return { return {
@ -209,7 +273,7 @@ function getCarImg() {
name: item.attachmentName name: item.attachmentName
} }
}) })
formLoading.value = false loading.value = false
}) })
} }
@ -218,4 +282,63 @@ function uploadRemove(file) {
ElMessage.success('删除成功') ElMessage.success('删除成功')
}) })
} }
</script> </script>
<style lang="scss" scoped>
.selec-wrapper {
max-width: 400px;
display: flex;
flex-flow: row nowrap;
gap: 5px;
.users {
flex: 1;
display: flex;
flex-flow: row wrap;
gap: 5px;
}
.select {
cursor: pointer;
background-color: #f1faff;
border: 1px dashed #00a3ff;
padding: 0px 15px;
color: #00a3ff;
// color: #00a3ff;
// text-decoration: underline;
border-radius: 6px;
height: fit-content;
&:hover {
opacity: 0.8;
}
}
}
.modal-enter-from {
opacity: 0;
transition: 0.2s all;
}
.modal-leave-to {
opacity: 0;
}
.modal-enter-from .modal-container,
.modal-leave-to .modal-container {
-webkit-transform: scale(1.1);
transform: scale(1.1);
}
#map-container {
width: 100%;
height: 400px;
margin-top: 20px;
}
</style>

139
src/views/task/create.vue

@ -15,16 +15,24 @@
end-placeholder="选择任务计划结束时间" end-placeholder="选择任务计划结束时间"
/> />
</el-form-item> </el-form-item>
<el-form-item label="类型" prop="taskType"> <el-form-item label="类型" prop="taskType">
<el-select v-model="formData.taskType" placeholder="请选择任务类型"> <el-tree-select
<el-option v-model="formData.tags"
v-for="dict in getIntDictOptions(DICT_TYPE.TASK_TYPE)" :data="tagList"
:key="dict.value" check-strictly
:label="dict.label" :render-after-expand="false"
:value="dict.value" placeholder="请选择类型"
/> node-key="id"
</el-select> show-checkbox
multiple
:props="{
label: 'tagName'
}"
/>
</el-form-item> </el-form-item>
<el-form-item label="执行周期" prop="execCycle" v-if="formData.taskType == 2"> <el-form-item label="执行周期" prop="execCycle" v-if="formData.taskType == 2">
<el-select v-model="formData.execCycle" placeholder="请选择执行周期"> <el-select v-model="formData.execCycle" placeholder="请选择执行周期">
<el-option <el-option
@ -45,21 +53,21 @@
/> />
</el-select> </el-select>
</el-form-item> </el-form-item>
<el-form-item label="标签" prop="tags" style="width: 100%"> <!-- <el-form-item label="标签" prop="tags" style="width: 100%">-->
<el-tree-select <!-- <el-tree-select-->
v-model="formData.tags" <!-- v-model="formData.tags"-->
:data="tagList" <!-- :data="tagList"-->
check-strictly <!-- check-strictly-->
:render-after-expand="false" <!-- :render-after-expand="false"-->
placeholder="请选择标签" <!-- placeholder="请选择标签"-->
node-key="id" <!-- node-key="id"-->
show-checkbox <!-- show-checkbox-->
multiple <!-- multiple-->
:props="{ <!-- :props="{-->
label: 'tagName' <!-- label: 'tagName'-->
}" <!-- }"-->
/> <!-- />-->
</el-form-item> <!-- </el-form-item>-->
<el-form-item label="描述" prop="description" style="width: 100%"> <el-form-item label="描述" prop="description" style="width: 100%">
<el-input <el-input
type="textarea" type="textarea"
@ -91,7 +99,7 @@
<el-form-item label="" prop="type"> <el-form-item label="" prop="type">
<el-select <el-select
v-model="enterprise.queryParams.type" v-model="enterprise.queryParams.type"
placeholder="请选择企业类型" placeholder="请选择企业规模"
clearable clearable
@change="handleQuery" @change="handleQuery"
@clear="handleQuery" @clear="handleQuery"
@ -122,6 +130,27 @@
/> />
</el-select> </el-select>
</el-form-item> </el-form-item>
<!-- <el-form-item label="" prop="id">-->
<!-- <el-select-->
<!-- v-model="enterprise.queryParams.id"-->
<!-- placeholder="请选择企业资质"-->
<!-- clearable-->
<!-- @clear="handleQuery"-->
<!-- @change="handleQuery"-->
<!-- class="!w-150px"-->
<!-- >-->
<!-- <el-option-->
<!-- v-for="dict in getStrDictOptions(DICT_TYPE.ENTERPRISES_QUA)"-->
<!-- :key="dict.value"-->
<!-- :label="dict.label"-->
<!-- :value="dict.value"-->
<!-- />-->
<!-- </el-select>-->
<!-- </el-form-item>-->
<el-form-item> <el-form-item>
<el-button @click="handleQuery"> <el-button @click="handleQuery">
<Icon icon="ep:search" class="mr-5px" /> 搜索 <Icon icon="ep:search" class="mr-5px" /> 搜索
@ -183,10 +212,14 @@
</section> </section>
<section> <section>
<section class="check-area"> <section class="check-area">
<section v-for="item in formData.enterprises" :key="item.id" class="isChecked"> <section v-for="item in formData.enterprises" :key="item.id" class="isChecked" >
<el-tooltip :content="item.enterprisesName" placement="top"> <el-tooltip :content="item.enterprisesName" placement="top">
<span> <span >
{{ item.enterprisesName }} 企业名称{{ item.enterprisesName }}
<section class="flex gap-5px">
区域: <DictTag :type="DICT_TYPE.ENTERPRISES_AREA" :value="Number(item.region)" />
规模<DictTag :type="DICT_TYPE.ENTERPRISES_TYPE" :value="Number(item.type)" />
</section>
</span> </span>
</el-tooltip> </el-tooltip>
<el-icon @click="checkEnterprise(item)"><Close /></el-icon> <el-icon @click="checkEnterprise(item)"><Close /></el-icon>
@ -219,9 +252,12 @@ import { TagLibraryApi } from '@/api/system/taglibrary'
import { EnterprisesApi, EnterprisesVO } from '@/api/enterprises' import { EnterprisesApi, EnterprisesVO } from '@/api/enterprises'
import { TaskInfoApi } from '@/api/system/taskinfo' import { TaskInfoApi } from '@/api/system/taskinfo'
import { useTagsViewStore} from '@/store/modules/tagsView' import { useTagsViewStore} from '@/store/modules/tagsView'
import {defaultProps, handleTree} from "@/utils/tree";
defineOptions({ name: 'CreateTask' })
defineOptions({ name: 'CreateTask' })
const typeList = ref<Tree[]>([]) //
const loading = ref(false) const loading = ref(false)
const formData = ref({ const formData = ref({
id: undefined, id: undefined,
@ -270,7 +306,8 @@ const enterprise = ref({
enterprisesName: undefined, enterprisesName: undefined,
type: undefined, type: undefined,
region: undefined, region: undefined,
registrationNumber: undefined registrationNumber: undefined,
id:undefined
}), }),
total: ref(0) total: ref(0)
}) })
@ -290,7 +327,7 @@ const resetQuery = () => {
* 获取标签列表 * 获取标签列表
*/ */
function getTagList() { function getTagList() {
TagLibraryApi.getTagLibraryPage({}).then((res) => { TagLibraryApi.getTagLibraryPage({tagType:'2'}).then((res) => {
tagList.value = res tagList.value = res
}) })
} }
@ -366,30 +403,40 @@ function uniqueFunc(arr, uniId) {
const res = new Map() const res = new Map()
return arr.filter((item) => !res.has(item[uniId]) && res.set(item[uniId], 1)) return arr.filter((item) => !res.has(item[uniId]) && res.set(item[uniId], 1))
} }
// typeList.value = handleTree(await TagLibraryApi.getTagLibraryPage(formData.value.id))
/** /**
* 提交表单 * 提交表单
*/ */
async function submitForm() { async function submitForm() {
const validate = await unref(formRef).validate() const validate = await unref(formRef).validate()
if (validate) { if (validate) {
const data = JSON.parse(JSON.stringify(formData.value)) const data = JSON.parse(JSON.stringify(formData.value))
data.enterpriseIds = formData.value.enterprises.map((i) => i.id) data.enterpriseIds = formData.value.enterprises.map((i) => i.id)
data.startDate = data.planTime[0] if(data.enterpriseIds.length==0){
data.endDate = data.planTime[1] message.success("温馨提示:请您选择执法对象")
if (data.id) { }else{
TaskInfoApi.updateTaskInfo(data).then(() => { if(data.status<2){
message.success('操作成功') data.startDate = data.planTime[0]
tagView.delView(route) data.endDate = data.planTime[1]
router.go(-1) if (data.id) {
}) TaskInfoApi.updateTaskInfo(data).then(() => {
} else { message.success('操作成功')
TaskInfoApi.createTaskInfo(data).then(() => { tagView.delView(route)
message.success('操作成功') router.go(-1)
tagView.delView(route) })
router.go(-1) } else {
}) TaskInfoApi.createTaskInfo(data).then(() => {
message.success('操作成功')
tagView.delView(route)
router.go(-1)
})
}
}else{
message.success('温馨提示:该任务已经执行,无法再进行修改')
}
} }
} }
} }
@ -463,7 +510,7 @@ onMounted(()=>{
} }
.isChecked { .isChecked {
width: calc(100% / 4 - 10px); width: calc(100% / 4 - 10px);
height: 50px; height: 80px;
color: #fff; color: #fff;
background-color: var(--el-color-primary); background-color: var(--el-color-primary);
padding: 5px 10px; padding: 5px 10px;

21
src/views/task/index.vue

@ -90,7 +90,7 @@
<!-- 列表 --> <!-- 列表 -->
<ContentWrap> <ContentWrap>
<el-table v-loading="loading" :data="list" :stripe="true" :show-overflow-tooltip="true"> <el-table v-loading="loading" :data="list" :stripe="true" :show-overflow-tooltip="true">
<el-table-column label="任务编号" align="center" width="150px" prop="taskNumber" /> <el-table-column label="发布时间" align="center" width="180px" prop="createTime" :formatter="dateFormatter"/>
<el-table-column label="任务状态" align="center" prop="status"> <el-table-column label="任务状态" align="center" prop="status">
<template #default="scope"> <template #default="scope">
<dict-tag :type="DICT_TYPE.TASK_STATE" :value="scope.row.status" /> <dict-tag :type="DICT_TYPE.TASK_STATE" :value="scope.row.status" />
@ -107,22 +107,21 @@
<dict-tag :type="DICT_TYPE.TASK_TYPE" :value="scope.row.taskType" /> <dict-tag :type="DICT_TYPE.TASK_TYPE" :value="scope.row.taskType" />
</template> </template>
</el-table-column> </el-table-column>
<el-table-column label="任务优先级" align="center" prop="priority"> <!-- <el-table-column label="任务优先级" align="center" prop="priority">
<template #default="scope"> <template #default="scope">
<dict-tag :type="DICT_TYPE.TASK_PRIORITY" :value="scope.row.priority" /> <dict-tag :type="DICT_TYPE.TASK_PRIORITY" :value="scope.row.priority" />
</template> </template>
</el-table-column> </el-table-column> -->
<el-table-column label="发布部门" align="center" prop="publishDep" /> <el-table-column label="发布部门" align="center" prop="publishDep" />
<el-table-column <el-table-column
label="计划开始时间" label="开始时间"
align="center" align="center"
prop="startDate" prop="startDate"
:formatter="dateFormatter3" :formatter="dateFormatter3"
/> />
<el-table-column <el-table-column
label="计划结束时间" label="结束时间"
align="center" align="center"
prop="endDate" prop="endDate"
:formatter="dateFormatter3" :formatter="dateFormatter3"
@ -143,17 +142,18 @@
</el-table-column> --> </el-table-column> -->
<!-- <el-table-column label="执行到第几" align="center" prop="taskStep" /> --> <!-- <el-table-column label="执行到第几" align="center" prop="taskStep" /> -->
<el-table-column label="执法对象" align="center" min-width="120px"> <el-table-column label="执法对象" align="center" min-width="50px">
<template #default="scope"> <template #default="scope">
<el-button link type="primary" @click="push({ <el-button link type="primary" @click="
push({
path: 'create', path: 'create',
query: { query: {
id: scope.row.id id: scope.row.id
} }
}) })
"> ">
<el-Tag type="success">{{scope.row.enterpriseIdes.length}}</el-Tag>&nbsp; <el-Tag type="success">{{scope.row.enterpriseIdes.length}}</el-Tag>&nbsp;
</el-button>&nbsp; </el-button>&nbsp;
</template> </template>
@ -210,6 +210,8 @@
<script setup lang="ts"> <script setup lang="ts">
import { getIntDictOptions, DICT_TYPE } from '@/utils/dict' import { getIntDictOptions, DICT_TYPE } from '@/utils/dict'
import { dateFormatter3 } from '@/utils/formatTime' import { dateFormatter3 } from '@/utils/formatTime'
import { dateFormatter } from '@/utils/formatTime'
import download from '@/utils/download' import download from '@/utils/download'
import { TaskInfoApi, TaskInfoVO } from '@/api/system/taskinfo' import { TaskInfoApi, TaskInfoVO } from '@/api/system/taskinfo'
import TaskInfoForm from './TaskInfoForm.vue' import TaskInfoForm from './TaskInfoForm.vue'
@ -250,7 +252,6 @@ const getList = async () => {
loading.value = true loading.value = true
try { try {
const data = await TaskInfoApi.getTaskInfoPage(queryParams) const data = await TaskInfoApi.getTaskInfoPage(queryParams)
console.log("data==>", data)
list.value = data.list list.value = data.list
total.value = data.total total.value = data.total
} finally { } finally {

Loading…
Cancel
Save