8 changed files with 582 additions and 192 deletions
@ -0,0 +1,57 @@
|
||||
<template> |
||||
<div class="text-center description-value" :size="size"> |
||||
<span>{{ value1 }}</span> |
||||
<span class="separator">/</span> |
||||
<span class="value2">{{ value2 }}</span> |
||||
</div> |
||||
<div class="text-center description-label" :size="size"> |
||||
<span>{{ label1 }}</span> |
||||
<span>/</span> |
||||
<span>{{ label2 }}</span> |
||||
</div> |
||||
</template> |
||||
<script setup> |
||||
defineProps({ |
||||
label1: { |
||||
type: String, |
||||
default: "", |
||||
}, |
||||
value1: { |
||||
type: String, |
||||
default: "", |
||||
}, |
||||
label2: { |
||||
type: String, |
||||
default: "", |
||||
}, |
||||
value2: { |
||||
type: String, |
||||
default: "", |
||||
}, |
||||
size: { |
||||
type: String, |
||||
default: "", |
||||
} |
||||
}); |
||||
</script> |
||||
<style lang="scss" scoped> |
||||
.description-value { |
||||
margin-bottom: 16px; |
||||
font-size: 18px; |
||||
color: var(--primary-color); |
||||
&[size=large] { |
||||
font-size: 28px; |
||||
} |
||||
.separator { |
||||
margin: 0 10px; |
||||
color: #666666; |
||||
} |
||||
.value2 { |
||||
color: #FF2B2B; |
||||
} |
||||
} |
||||
.description-label { |
||||
font-size: 16px; |
||||
color: #666666; |
||||
} |
||||
</style> |
||||
@ -0,0 +1,203 @@
|
||||
<template> |
||||
<div class="container"> |
||||
<header> |
||||
<el-form :label-width="114"> |
||||
<el-row> |
||||
<el-col :span="6"> |
||||
<el-form-item label="单位名称"> |
||||
<el-input |
||||
placeholder="请输入" |
||||
v-model="query.name" |
||||
/> |
||||
</el-form-item> |
||||
</el-col> |
||||
<el-col :span="6"> |
||||
<el-form-item label="单位类型"> |
||||
<el-input |
||||
placeholder="请输入" |
||||
v-model="query.six" |
||||
/> |
||||
</el-form-item> |
||||
</el-col> |
||||
<el-col :span="6"> |
||||
<el-form-item label="统计时间"> </el-form-item> |
||||
</el-col> |
||||
</el-row> |
||||
</el-form> |
||||
<div class="mb-25 flex end"> |
||||
<div> |
||||
<el-button type="primary" @click="getList"> |
||||
<template #icon> |
||||
<icon name="el-icon-Search" /> |
||||
</template> |
||||
查询</el-button |
||||
> |
||||
<el-button @click="reset">重置</el-button> |
||||
</div> |
||||
</div> |
||||
</header> |
||||
<div class="table-container"> |
||||
<el-table :data="list"> |
||||
<el-table-column label="单位名称" prop="" /> |
||||
<el-table-column label="主要责任人" prop="" /> |
||||
<el-table-column label="民警人数" prop="" /> |
||||
<el-table-column label="协辅警人数" prop="" /> |
||||
<el-table-column label="查实问题涉及人数" prop="" width="180" /> |
||||
<el-table-column |
||||
label="查实问题数" |
||||
prop="departName" |
||||
width="120" |
||||
/> |
||||
<el-table-column |
||||
label="风险指数" |
||||
prop="fxzs" |
||||
width="120" |
||||
align="center" |
||||
/> |
||||
|
||||
<el-table-column label="操作" width="160"> |
||||
<template #default="{ row }"> |
||||
<el-button type="primary" link @click="show = true" |
||||
>查看详情</el-button |
||||
> |
||||
</template> |
||||
</el-table-column> |
||||
</el-table> |
||||
</div> |
||||
</div> |
||||
|
||||
<el-dialog title="单位问题画像" v-model="show" width="85vw" top="2vh"> |
||||
<header class="flex center v-center gap"> |
||||
<label for="">统计范围</label> |
||||
|
||||
<el-button type="primary">查询</el-button> |
||||
</header> |
||||
<main> |
||||
<el-row> |
||||
<el-col :span="8"> |
||||
<h5>单位情况</h5> |
||||
<div class="row"> |
||||
<div class="col col-24"> |
||||
<label>单位名称</label> |
||||
<span>{{}}</span> |
||||
</div> |
||||
<div class="col col-24"> |
||||
<label>所长</label> |
||||
<span>{{}}</span> |
||||
</div> |
||||
<div class="col col-24"> |
||||
<label>副所长</label> |
||||
<span>{{}}</span> |
||||
</div> |
||||
</div> |
||||
<el-row> |
||||
<el-col :span="12"> |
||||
<description-pair |
||||
label1="民警总人数" |
||||
label2="问题涉及民警数" |
||||
value1="132" |
||||
value2="21" |
||||
size="large" |
||||
/> |
||||
</el-col> |
||||
<el-col :span="12"> |
||||
<description-pair |
||||
label1="协辅警人数" |
||||
label2="问题涉及协辅警数" |
||||
value1="132" |
||||
value2="21" |
||||
size="large" |
||||
/> |
||||
</el-col> |
||||
</el-row> |
||||
</el-col> |
||||
<el-col :span="8"> |
||||
<h5>问题情况</h5> |
||||
<el-row> |
||||
<el-col :span="6" class="text-center"> |
||||
<div class="text-primary" style="font-size: 34px"> |
||||
51 |
||||
</div> |
||||
<div>问题总数</div> |
||||
</el-col> |
||||
<el-col :span="18"> |
||||
<el-row> |
||||
<el-col :span="12"> |
||||
<description-pair |
||||
label1="110接处警量" |
||||
label2="问题数" |
||||
value1="132" |
||||
value2="21" |
||||
/> |
||||
</el-col> |
||||
<el-col :span="12"> |
||||
<description-pair |
||||
label1="执法办案" |
||||
label2="问题数" |
||||
value1="132" |
||||
value2="21" |
||||
/> |
||||
</el-col> |
||||
</el-row> |
||||
</el-col> |
||||
</el-row> |
||||
</el-col> |
||||
<el-col :span="8"> |
||||
<h5>风险指数</h5> |
||||
<div class="flex center"> |
||||
<el-progress |
||||
type="dashboard" |
||||
:percentage="78" |
||||
:stroke-width="16" |
||||
:width="250" |
||||
color="#DC6231" |
||||
> |
||||
<div> |
||||
<span style="">78</span> |
||||
</div> |
||||
<div>分险指标值</div> |
||||
<div>中风险</div> |
||||
</el-progress> |
||||
</div> |
||||
</el-col> |
||||
</el-row> |
||||
<el-row> |
||||
<el-col :span="8"> |
||||
<h5>问题来源占比</h5> |
||||
</el-col> |
||||
<el-col :span="8"> |
||||
<h5>业务类型占比</h5> |
||||
</el-col> |
||||
<el-col :span="8"> |
||||
<h5>风险问题构成</h5> |
||||
</el-col> |
||||
</el-row> |
||||
<el-row> |
||||
<el-col :span="8"> |
||||
<h5>个人问题排名</h5> |
||||
</el-col> |
||||
<el-col :span="8"> |
||||
<h5>突出问题排名</h5> |
||||
</el-col> |
||||
<el-col :span="8"> |
||||
<h5>单位问题标签</h5> |
||||
</el-col> |
||||
</el-row> |
||||
<h5>问题变化趋势</h5> |
||||
<div></div> |
||||
<h5>问题清单</h5> |
||||
<div></div> |
||||
</main> |
||||
</el-dialog> |
||||
</template> |
||||
<script lang="ts" setup> |
||||
const query = ref({ |
||||
current: 1, |
||||
size: 10, |
||||
}); |
||||
const list = ref<any[]>([]); |
||||
|
||||
const show = ref(true); |
||||
</script> |
||||
<style lang="scss" scoped> |
||||
</style> |
||||
@ -0,0 +1,299 @@
|
||||
<template> |
||||
<div class="container"> |
||||
<header class="mb-20"> |
||||
<div class="flex between"> |
||||
<div> |
||||
<el-button type="primary" @click="handleAdd"> |
||||
<template #icon> |
||||
<icon name="el-icon-Plus" /> |
||||
</template> |
||||
新增</el-button |
||||
> |
||||
</div> |
||||
<div style="width: 50%"> |
||||
<el-row> |
||||
<el-col :span="12"> </el-col> |
||||
<el-col :span="12"> |
||||
<div class="flex end"> |
||||
<el-button type="primary" @click="getList"> |
||||
<template #icon> |
||||
<icon name="el-icon-Search" /> |
||||
</template> |
||||
查询</el-button |
||||
> |
||||
<el-button @click="reset">重置</el-button> |
||||
</div> |
||||
</el-col> |
||||
</el-row> |
||||
</div> |
||||
</div> |
||||
<div class="flex between mt-10"> |
||||
<div> |
||||
<div class="text-primary mt-10 mb-10">赋分分公式如下</div> |
||||
<div> |
||||
问题综合得分 = |
||||
基础分值x(1+问题严重等级系数)x(1+问题发生频次系数)x(1+问题发生率系数) |
||||
</div> |
||||
</div> |
||||
<a |
||||
class="flex v-center gap file-link" |
||||
:href="`${BASE_PATH}/templates/长沙公安数字督察灵敏感知体系问题赋分及风险预警机制.pdf`" |
||||
target="__blank" |
||||
> |
||||
<icon name="local-icon-pdf" :size="48" /> |
||||
<span>问题赋分机制.pdf</span> |
||||
</a> |
||||
</div> |
||||
</header> |
||||
<div class="table-container"> |
||||
<el-table :data="dictContents" row-key="id"> |
||||
<el-table-column |
||||
label="问题条目" |
||||
prop="name" |
||||
show-overflow-tooltip="" |
||||
/> |
||||
<el-table-column label="基础分值" prop="score" width="200" align="center"> |
||||
<template #default="{ row }"> |
||||
<span v-if="row.level === 1">{{ |
||||
getScoreRange(row) |
||||
}}</span> |
||||
<span v-else>{{ row.score }}</span> |
||||
</template> |
||||
</el-table-column> |
||||
<el-table-column |
||||
label="问题严重等级" |
||||
prop="isActiveLevel" |
||||
align="center" |
||||
> |
||||
<template #default="{ row }"> |
||||
<el-tag type="success" v-if="row.isActiveLevel === true" |
||||
>开启</el-tag |
||||
> |
||||
<el-tag type="danger" v-if="row.isActiveLevel === false" |
||||
>关闭</el-tag |
||||
> |
||||
</template> |
||||
</el-table-column> |
||||
<el-table-column |
||||
label="序号" |
||||
prop="sort" |
||||
width="100" |
||||
align="center" |
||||
/> |
||||
<el-table-column label="最后更新时间" prop="updTime" /> |
||||
<el-table-column label="操作"> |
||||
<template #default="{ row }"> |
||||
<el-button type="primary" link @click="handleEdit(row)" |
||||
>编辑</el-button |
||||
> |
||||
<el-button type="danger" link @click="handleDelete(row)" |
||||
>删除</el-button |
||||
> |
||||
</template> |
||||
</el-table-column> |
||||
</el-table> |
||||
</div> |
||||
<div class="mt-40"> |
||||
<div>基础分值设定规则:</div> |
||||
<p> |
||||
1、二级问题条目设定的基础分值,作为其下属三级问题条目的默认基础分值。 |
||||
</p> |
||||
<p> |
||||
2、若三级问题条目已单独设置基础分值,则赋分时以该三级条目的基础分值为准。 |
||||
</p> |
||||
<p> |
||||
3、如三级问题条目未设置基础分值,则采用其所属二级问题条目的基础分值进行赋分。 |
||||
</p> |
||||
</div> |
||||
</div> |
||||
|
||||
<el-dialog |
||||
v-model="show" |
||||
:title="mode === 'add' ? '新增问题类型' : '编辑问题类型'" |
||||
width="600" |
||||
> |
||||
<el-form label-width="120" ref="formRef" :model="formData"> |
||||
<el-form-item |
||||
label="父级节点" |
||||
:rules="{ |
||||
required: true, |
||||
message: '请选择父级节点', |
||||
}" |
||||
prop="parentCode" |
||||
> |
||||
<el-tree-select |
||||
class="flex-1" |
||||
v-model="formData.parentCode" |
||||
:data="dictContentOptions" |
||||
clearable |
||||
node-key="id" |
||||
:props="{ |
||||
label: 'name', |
||||
}" |
||||
:default-expanded-keys="[DICT_CONTENT_ROOT_ID]" |
||||
placeholder="请选择父级节点" |
||||
check-strictly |
||||
filterable |
||||
/> |
||||
</el-form-item> |
||||
<el-form-item |
||||
label="问题条目" |
||||
prop="name" |
||||
:rules="{ |
||||
required: true, |
||||
message: '请输入问题条目', |
||||
}" |
||||
> |
||||
<el-input |
||||
v-model="formData.name" |
||||
placeholder="请输入问题条目" |
||||
clearable |
||||
/> |
||||
</el-form-item> |
||||
<el-form-item label="基础分值" prop="score" v-if="formData.parentCode != DICT_CONTENT_ROOT_ID"> |
||||
<el-input |
||||
v-model="formData.score" |
||||
placeholder="请输入序号" |
||||
type="number" |
||||
clearable |
||||
/> |
||||
</el-form-item> |
||||
<el-form-item label="序号" prop="sort"> |
||||
<el-input |
||||
v-model="formData.sort" |
||||
placeholder="请输入序号" |
||||
type="number" |
||||
clearable |
||||
/> |
||||
</el-form-item> |
||||
<el-form-item |
||||
label="问题严重等级" |
||||
prop="isActiveLevel" |
||||
:rules="{ |
||||
required: true, |
||||
message: '请选择问题严重等级', |
||||
trigger: ['blur'], |
||||
}" |
||||
> |
||||
<el-switch |
||||
v-model="formData.isActiveLevel" |
||||
inline-prompt |
||||
active-text="开启" |
||||
inactive-text="关闭" |
||||
:active-value="true" |
||||
:inactive-value="false" |
||||
/> |
||||
</el-form-item> |
||||
</el-form> |
||||
<footer class="flex end"> |
||||
<el-button @click="show = false">取消</el-button> |
||||
<el-button type="primary" @click="submit">确定</el-button> |
||||
</footer> |
||||
</el-dialog> |
||||
</template> |
||||
<script lang="ts" setup> |
||||
import { BASE_PATH } from "@/api/request"; |
||||
import { DICT_CONTENT_ROOT_ID } from "@/enums/appEnums"; |
||||
import { |
||||
listDictContentTree, |
||||
addDictContent, |
||||
updateDictContent, |
||||
delDictContent, |
||||
} from "@/api/system/dictContent"; |
||||
import feedback from "@/utils/feedback"; |
||||
|
||||
const dictContents = ref([]); |
||||
const dictContentOptions = ref([ |
||||
{ |
||||
id: DICT_CONTENT_ROOT_ID, |
||||
name: "顶级", |
||||
children: [], |
||||
}, |
||||
]); |
||||
|
||||
function getList() { |
||||
listDictContentTree().then((data) => { |
||||
dictContents.value = data; |
||||
dictContentOptions.value[0].children = data; |
||||
}); |
||||
} |
||||
getList(); |
||||
|
||||
const show = ref(false); |
||||
const formData = ref({}); |
||||
const formRef = ref(); |
||||
|
||||
const mode = ref<string>("add"); |
||||
watch(mode, (val) => { |
||||
if (val === "add") { |
||||
formData.value = {}; |
||||
formRef.value.resetFields(); |
||||
} |
||||
}); |
||||
async function submit() { |
||||
await formRef.value.validate(); |
||||
if (mode.value === "add") { |
||||
await addDictContent(formData.value); |
||||
const parentCode = formData.value.parentCode; |
||||
formData.value = {}; |
||||
formRef.value.resetFields(); |
||||
formData.value.parentCode = parentCode; |
||||
} else { |
||||
await updateDictContent(formData.value); |
||||
} |
||||
show.value = false; |
||||
getList(); |
||||
} |
||||
|
||||
function handleAdd() { |
||||
show.value = true; |
||||
mode.value = "add"; |
||||
} |
||||
|
||||
function handleEdit(row) { |
||||
show.value = true; |
||||
mode.value = "edit"; |
||||
formData.value = {...row}; |
||||
} |
||||
|
||||
const handleDelete = async (row) => { |
||||
await feedback.confirm(`确定要删除 "${row.name}"?`); |
||||
await delDictContent(row.id); |
||||
getList(); |
||||
feedback.msgSuccess("删除成功"); |
||||
}; |
||||
|
||||
function getScoreRange(row) { |
||||
const sorceSet = new Set(); |
||||
row.children.forEach((item) => { |
||||
if (item.score) { |
||||
sorceSet.add(item.score); |
||||
} |
||||
item.children.forEach((j) => { |
||||
if (j.score) { |
||||
sorceSet.add(j.score); |
||||
} |
||||
}); |
||||
}); |
||||
if (sorceSet.size === 0) { |
||||
return '' |
||||
} |
||||
if (sorceSet.size === 1) { |
||||
return sorceSet.values().next().value |
||||
} |
||||
const min = Math.min(...sorceSet); |
||||
const max = Math.max(...sorceSet); |
||||
return `${min}-${max}` |
||||
} |
||||
</script> |
||||
<style lang="scss" scoped> |
||||
.file-link { |
||||
font-size: 18px; |
||||
text-decoration: none; |
||||
color: #19257d; |
||||
padding: 0 8px; |
||||
&:hover { |
||||
background-color: #eee; |
||||
} |
||||
} |
||||
</style> |
||||
@ -1,179 +0,0 @@
|
||||
<template> |
||||
<div class="container"> |
||||
<header class="flex between mb-20"> |
||||
<div> |
||||
<el-button type="primary" @click="handleAdd"> |
||||
<template #icon> |
||||
<icon name="el-icon-Plus" /> |
||||
</template> |
||||
新增</el-button |
||||
> |
||||
</div> |
||||
<div></div> |
||||
</header> |
||||
<div class="table-container"> |
||||
<el-table :data="dictContents" row-key="id"> |
||||
<el-table-column label="类型名称" prop="name" show-overflow-tooltip="" /> |
||||
<el-table-column label="序号" prop="sort" width="200" /> |
||||
<el-table-column label="最后更新时间" prop="updTime" /> |
||||
<el-table-column label="操作"> |
||||
<template #default="{ row }"> |
||||
<el-button type="primary" link @click="handleEdit(row)" |
||||
>编辑</el-button |
||||
> |
||||
<el-button |
||||
type="danger" |
||||
link |
||||
@click="handleDelete(row)" |
||||
>删除</el-button |
||||
> |
||||
</template> |
||||
</el-table-column> |
||||
</el-table> |
||||
</div> |
||||
</div> |
||||
|
||||
<el-dialog |
||||
v-model="show" |
||||
:title="mode === 'add' ? '新增问题类型' : '编辑问题类型'" |
||||
width="600" |
||||
> |
||||
<el-form label-width="120" ref="formRef" :model="formData"> |
||||
<el-form-item |
||||
label="父级节点" |
||||
:rules="{ |
||||
required: true, |
||||
message: '请选择父级节点', |
||||
}" |
||||
prop="parentCode" |
||||
> |
||||
<el-tree-select |
||||
class="flex-1" |
||||
v-model="formData.parentCode" |
||||
:data="dictContentOptions" |
||||
clearable |
||||
node-key="id" |
||||
:props="{ |
||||
label: 'name', |
||||
}" |
||||
:default-expanded-keys="[DICT_CONTENT_ROOT_ID]" |
||||
placeholder="请选择父级节点" |
||||
check-strictly |
||||
filterable |
||||
/> |
||||
</el-form-item> |
||||
<el-form-item |
||||
label="类型名称" |
||||
prop="name" |
||||
:rules="{ |
||||
required: true, |
||||
message: '请输入类型名称', |
||||
}" |
||||
> |
||||
<el-input |
||||
v-model="formData.name" |
||||
placeholder="请输入类型名称" |
||||
clearable |
||||
/> |
||||
</el-form-item> |
||||
<el-form-item label="序号" prop="sort" > |
||||
<el-input |
||||
v-model="formData.sort" |
||||
placeholder="请输入序号" |
||||
type="number" |
||||
clearable |
||||
/> |
||||
</el-form-item> |
||||
<el-form-item label="备注"> |
||||
<el-input |
||||
v-model="formData.remark" |
||||
placeholder="请输入备注" |
||||
type="textarea" |
||||
clearable |
||||
/> |
||||
</el-form-item> |
||||
</el-form> |
||||
<footer class="flex end"> |
||||
<el-button @click="show = false">取消</el-button> |
||||
<el-button type="primary" @click="submit">确定</el-button> |
||||
</footer> |
||||
</el-dialog> |
||||
</template> |
||||
<script lang="ts" setup> |
||||
import { DICT_CONTENT_ROOT_ID } from "@/enums/appEnums"; |
||||
import { |
||||
listDictContentTree, |
||||
addDictContent, |
||||
updateDictContent, |
||||
delDictContent |
||||
} from "@/api/system/dictContent"; |
||||
import feedback from "@/utils/feedback"; |
||||
|
||||
const dictContents = ref([]); |
||||
const dictContentOptions = ref([ |
||||
{ |
||||
id: DICT_CONTENT_ROOT_ID, |
||||
name: "顶级", |
||||
children: [], |
||||
}, |
||||
]); |
||||
|
||||
function getList() { |
||||
listDictContentTree().then((data) => { |
||||
dictContents.value = data; |
||||
dictContentOptions.value[0].children = data; |
||||
}); |
||||
} |
||||
getList(); |
||||
|
||||
const show = ref(false); |
||||
const formData = ref({}); |
||||
const formRef = ref(); |
||||
|
||||
const mode = ref<string>("add"); |
||||
watch(mode, (val) => { |
||||
if (val === 'add') { |
||||
formData.value = {} |
||||
formRef.value.resetFields() |
||||
} |
||||
}) |
||||
async function submit() { |
||||
await formRef.value.validate(); |
||||
if (mode.value === "add") { |
||||
await addDictContent(formData.value); |
||||
const parentCode = formData.value.parentCode |
||||
formData.value = {} |
||||
formRef.value.resetFields() |
||||
formData.value.parentCode = parentCode |
||||
} else { |
||||
await updateDictContent(formData.value); |
||||
} |
||||
show.value = false |
||||
getList() |
||||
} |
||||
|
||||
function handleAdd() { |
||||
show.value = true; |
||||
mode.value = "add"; |
||||
} |
||||
|
||||
function handleEdit(row) { |
||||
show.value = true; |
||||
mode.value = "edit"; |
||||
formData.value = row; |
||||
} |
||||
|
||||
const handleDelete = async (row) => { |
||||
await feedback.confirm(`确定要删除 "${row.name}"?`); |
||||
await delDictContent(row.id) |
||||
getList() |
||||
feedback.msgSuccess('删除成功') |
||||
}; |
||||
</script> |
||||
<style lang="scss" scoped> |
||||
.form-tips { |
||||
font-size: 12px; |
||||
line-height: 1.2; |
||||
color: #666; |
||||
} |
||||
</style> |
||||
Loading…
Reference in new issue