Browse Source

feat: 加上问题详情

master
buaixuexideshitongxue 4 weeks ago
parent
commit
3fb55833c1
  1. 370
      src/components/negativeInfo/police-dialog.vue

370
src/components/negativeInfo/police-dialog.vue

@ -0,0 +1,370 @@
<template>
<el-dialog
title="个人问题详情"
:model-value="modelValue"
@update:model-value="emit('update:modelValue', $event)"
width="85vw"
top="1vh"
style="margin: 1vh auto"
>
<header class="flex center v-center gap">
<label>统计范围</label>
<div style="width: 320px">
<date-time-range-picker-ext
v-model="time"
style="width: 300px"
@change="getProfileData"
/>
</div>
<el-button type="primary" @click="getProfileData">查询</el-button>
</header>
<el-scrollbar
max-height="calc(98vh - 120px)"
v-loading="loading"
element-loading-text="个人问题详情加载中..."
>
<main>
<el-row class="mb-20" :gutter="20">
<el-col :span="8">
<h5>民警基本情况</h5>
<div class="card-item h-220">
<el-row>
<el-col :span="6">
<div class="flex v-center" style="height: 100%">
<img
v-if="policeInfo.avatarUrl"
:src="`${BASE_PATH}/file/stream/${policeInfo.avatarUrl}`"
class="police-avatar"
style="width: 94px"
/>
<icon name="local-icon-police" :size="120" v-else />
</div>
</el-col>
<el-col :span="18">
<div class="row">
<div class="col col-12">
<label>姓名</label>
<span>{{ policeInfo.name }}</span>
</div>
<div class="col col-12">
<label>性别</label>
<span>{{ getGenderFromIdCode(policeInfo.idCode) }}</span>
</div>
<div class="col col-24">
<label>所属单位</label>
<span>
<span
>{{
activeRow.parentDepartName
? activeRow.parentDepartName + "/"
: ""
}}{{ activeRow.departName || "/" }}</span
>
</span>
</div>
<div class="col col-24">
<label>警号</label>
<span>{{ policeInfo.empNo }}</span>
</div>
<div class="col col-24">
<label>身份证号</label>
<span>{{ policeInfo.idCode }}</span>
</div>
<div class="col col-24">
<label>入职时间</label>
<span>{{ policeInfo.employmentDate || "/" }}</span>
</div>
<div class="col col-24">
<label>手机号</label>
<span>{{ policeInfo.mobile || "/" }}</span>
</div>
</div>
</el-col>
</el-row>
</div>
</el-col>
<el-col :span="8">
<h5>问题情况</h5>
<div class="card-item h-220">
<div class="flex v-center h100">
<div style="width: 25%" class="text-center">
<div class="text-primary" style="font-size: 34px">
{{ negativeInfo.size }}
</div>
<div class="mb-10">问题总数</div>
</div>
<div style="width: 75%" class="text-center">
<div
v-if="negativeInfo.jcj110BusinessSize || negativeInfo.jcj110Size"
class="mb-20"
>
<description-pair
label="110接处警"
label1="量"
label2="问题数"
:value1="negativeInfo.jcj110BusinessSize"
:value2="negativeInfo.jcj110Size"
/>
</div>
<div
v-if="negativeInfo.jcj122BusinessSize || negativeInfo.jcj122Size"
class="mb-20"
>
<description-pair
label="122接处警"
label1="量"
label2="问题数"
:value1="negativeInfo.jcj122BusinessSize"
:value2="negativeInfo.jcj122Size"
/>
</div>
<div>
<description-pair
label="执法办案"
label2="问题数"
:value1="negativeInfo.zfbaBusinessSize"
:value2="negativeInfo.zfbaSize"
/>
</div>
</div>
</div>
</div>
</el-col>
<el-col :span="8">
<h5>问题累计分值</h5>
<div class="flex center card-item wrap h-220">
<el-progress
type="dashboard"
:percentage="100"
:stroke-width="16"
:width="200"
color="#5B8FF9"
>
<div class="score-progress-body">
<div>
<div style="font-size: 16px">分数</div>
<div>
<span
class="score-progress_score score-theme text-bold"
style="color: #19257d"
>{{ score }}</span
>
</div>
</div>
</div>
</el-progress>
<div style="width: 100%" class="text-center">累计{{ days }}天分值</div>
</div>
</el-col>
</el-row>
<el-row class="mb-20" :gutter="20">
<el-col :span="8">
<h5>问题来源占比</h5>
<div class="card-item">
<v-charts
style="height: 320px"
:option="problemSourcesPieOptions"
autoresize
/>
</div>
</el-col>
<el-col :span="8">
<h5>问题涉及方面</h5>
<div class="card-item">
<v-charts
style="height: 320px"
:option="problemTypePieOptions"
autoresize
/>
</div>
</el-col>
<el-col :span="8">
<h5>突出问题排名</h5>
<div class="flex center card-item h-320">
<datav-chart-bar1
size="small"
:data="problemTypeBarList"
:color="colors"
labelPosition="top"
/>
<el-empty v-if="problemTypeBarList.length === 0" />
</div>
</el-col>
</el-row>
<h5>问题变化趋势</h5>
<div class="card-item">
<v-charts style="height: 320px" :option="barOption" autoresize />
</div>
<h5>问题清单 {{ negativeList.length }}</h5>
<el-table :data="negativeList" height="500">
<el-table-column label="发现时间" prop="discoveryTime" width="160" />
<el-table-column label="问题来源" prop="problemSources" width="150" />
<el-table-column label="业务类别" prop="businessTypeName" width="150" />
<el-table-column label="问题详情" prop="thingDesc" show-overflow-tooltip />
<el-table-column
label="核查情况"
prop="checkStatusDesc"
show-overflow-tooltip
/>
<el-table-column label="问题类型" prop="problemType" show-overflow-tooltip />
<el-table-column label="分值" width="100" align="center">
<template #default="{ row }">
<span class="text-danger">{{ row.score }}</span>
</template>
</el-table-column>
<el-table-column label="操作" width="160">
<template #default="{ row }">
<el-button type="primary" link @click="handleAction(row)"
>查看详情
</el-button>
</template>
</el-table-column>
</el-table>
</main>
</el-scrollbar>
</el-dialog>
<negative-dialog
v-model="negativeShow"
:id="activeNegativeId"
@close="negativeShow = false"
/>
</template>
<script setup>
import { BASE_PATH } from "@/api/request";
import vCharts from "vue-echarts";
import { getPoliceProfile, listNegativeMonthly } from "@/api/sensitivePerception/profilePolice";
import { getGenderFromIdCode } from "@/utils/util";
import moment from "moment";
const props = defineProps({
modelValue: Boolean,
idCode: String,
activeRow: { type: Object, default: () => ({}) },
initialTime: { type: Array, default: () => [] },
});
const emit = defineEmits(["update:modelValue"]);
const time = ref([]);
const policeInfo = ref({});
const negativeInfo = ref({});
const loading = ref(false);
const negativeList = ref([]);
const problemTypeBarList = ref([]);
const score = ref(0);
const days = ref(0);
const problemSourcesPieOptions = ref({
tooltip: { trigger: "item" },
series: [{ type: "pie", radius: ["40%", "70%"], data: [] }],
});
const problemTypePieOptions = ref({
tooltip: { trigger: "item" },
series: [{ type: "pie", radius: ["40%", "70%"], data: [] }],
});
const barOption = ref({
xAxis: { type: "category", data: [] },
yAxis: { type: "value" },
series: [{ data: [], type: "bar", color: "#5B8FF9 " }],
});
const colors = [
{ color: "var(--success-color)", percentage: 60 },
{ color: "#DC6231", percentage: 80 },
{ color: "var(--danger-color)", percentage: 100 },
];
watch(
() => [props.idCode, props.modelValue],
([idCode, isOpen]) => {
if (!isOpen || !idCode) return;
time.value = props.initialTime.length === 2
? [...props.initialTime]
: [
moment().startOf("year").format("YYYY-MM-DD HH:mm:ss"),
moment().format("YYYY-MM-DD HH:mm:ss"),
];
getProfileData();
listNegativeMonthly(idCode).then((data) => {
barOption.value.xAxis.data = data.months;
barOption.value.series[0].data = data.values;
});
}
);
async function getProfileData() {
if (!props.idCode) return;
loading.value = true;
try {
const data = await getPoliceProfile(props.idCode, {
beginTime: time.value.length ? time.value[0] : "",
endTime: time.value.length ? time.value[1] : "",
});
score.value = Math.round(data.score);
days.value = data.days;
negativeList.value = data.negatives;
policeInfo.value = data.policeInfo;
negativeInfo.value = data.negativeInfo;
problemSourcesPieOptions.value.series[0].data = data.problemSourcesList;
problemTypePieOptions.value.series[0].data = data.problemTypeList;
problemTypeBarList.value = data.problemTypeBarList;
} finally {
loading.value = false;
}
}
const negativeShow = ref(false);
const activeNegativeId = ref("");
function handleAction(row) {
negativeShow.value = true;
activeNegativeId.value = row.id;
}
</script>
<style lang="scss" scoped>
.col {
--label-width: 60px;
}
.score-progress-body {
text-align: center;
font-size: 18px;
.score-progress_score {
font-size: 50px;
line-height: 70px;
}
.score-progress_title {
font-size: 26px;
line-height: 22px;
}
}
.score-theme {
&[type="success"] {
color: var(--success-color);
}
&[type="warning"] {
color: #e87749;
}
&[type="danger"] {
color: var(--danger-color);
}
}
h5 {
margin-bottom: 12px;
}
.card-item {
background: #f9faff;
padding: 16px;
min-height: 200px;
}
.h-220 {
height: 220px;
}
.h-320 {
height: 320px;
}
</style>
Loading…
Cancel
Save