|
|
@@ -137,16 +137,46 @@
|
|
|
<div class="right-panel">
|
|
|
<div class="panel-section">
|
|
|
<div class="section-header">
|
|
|
- <span class="section-title">建议整改清单</span>
|
|
|
+ <span class="section-title">检测要素</span>
|
|
|
+ <span class="section-count">5</span>
|
|
|
</div>
|
|
|
<div class="checklist">
|
|
|
<div
|
|
|
- v-for="(item, index) in currentTask.checklist"
|
|
|
- :key="index"
|
|
|
- :class="['checklist-item', { checked: item.checked }]"
|
|
|
+ v-for="group in detectionGroups"
|
|
|
+ :key="group.id"
|
|
|
+ :class="['check-group', { expanded: expandedGroupId === group.id }]"
|
|
|
>
|
|
|
- <input type="checkbox" :checked="item.checked" @change="toggleCheck(index)" />
|
|
|
- <span>{{ item.text }}</span>
|
|
|
+ <button class="check-group-header" type="button" @click="toggleGroup(group.id)">
|
|
|
+ <div class="check-group-title">
|
|
|
+ <span class="group-index">{{ group.id }}</span>
|
|
|
+ <span>{{ group.title }}</span>
|
|
|
+ </div>
|
|
|
+ <div class="group-meta">
|
|
|
+ <span>{{ group.items.length }} 项</span>
|
|
|
+ <span class="group-caret">▶</span>
|
|
|
+ </div>
|
|
|
+ </button>
|
|
|
+ <div
|
|
|
+ v-for="(item, index) in group.items"
|
|
|
+ v-show="expandedGroupId === group.id"
|
|
|
+ :key="`${group.id}-${index}`"
|
|
|
+ class="checklist-row"
|
|
|
+ >
|
|
|
+ <div class="checklist-item">
|
|
|
+ <span class="item-index">{{ index + 1 }}</span>
|
|
|
+ <span class="item-text">{{ item.text }}</span>
|
|
|
+ </div>
|
|
|
+ <div class="case-examples">
|
|
|
+ <div class="case-card positive">
|
|
|
+ <div class="case-title">正确示例</div>
|
|
|
+ <img src="/case-positive.png" alt="正确示例" />
|
|
|
+ </div>
|
|
|
+ <div class="case-card negative">
|
|
|
+ <div class="case-title">错误示例</div>
|
|
|
+ <img src="/case-negative.png" alt="错误示例" />
|
|
|
+ </div>
|
|
|
+ </div>
|
|
|
+ </div>
|
|
|
</div>
|
|
|
</div>
|
|
|
</div>
|
|
|
@@ -178,11 +208,26 @@ const taskList = ref([
|
|
|
{ label: '配电箱', top: '45%', left: '18%' },
|
|
|
],
|
|
|
checklist: [
|
|
|
- { text: '请检查外观是否整洁,是否存在油污堆积;检查外观是否整洁,是否存在油污堆积;检查外观是否整洁,是否存在油污堆积', checked: false },
|
|
|
- { text: '请确认加油机输油管及阀门连接是否牢固,定期进行紧固检查,以防泄漏或松动;检查外观是否整洁,是否存在油污堆积', checked: false },
|
|
|
- { text: '请检查灭火器是否在有效期内,压力是否正常,放置位置是否便于取用;检查外观是否整洁,是否存在油污堆积', checked: false },
|
|
|
- { text: '请检查配电箱及线路是否规范,是否存在私拉乱接;检查外观是否整洁,是否存在油污堆积', checked: false },
|
|
|
- { text: '请检查防撞柱是否完好,高度是否符合要求,表面反光标识是否清晰;检查外观是否整洁,是否存在油污堆积', checked: false },
|
|
|
+ { text: '加油机外观不整洁,有明显油污' },
|
|
|
+ { text: '机座地脚螺栓明显松动' },
|
|
|
+ { text: '加油机紧固件连接明显松动' },
|
|
|
+ { text: '加油机底部填沙潮湿' },
|
|
|
+ { text: '加油机底部填沙有明显油迹' },
|
|
|
+ { text: '进油管与紧急截断阀连接处未露出沙外' },
|
|
|
+ { text: '油品管线连接处有明显渗漏' },
|
|
|
+ { text: '过滤器有明显油污和渗漏' },
|
|
|
+ { text: '加油机底部未设置截断阀' },
|
|
|
+ { text: '加油软管上未设置安全拉断阀' },
|
|
|
+ { text: '加油枪密封不良,工作时出现明显渗漏' },
|
|
|
+ { text: '汽油加油枪无集气罩' },
|
|
|
+ { text: '加油枪集气罩破损' },
|
|
|
+ { text: '油气回收检测口的丝堵松动' },
|
|
|
+ { text: '油气回收管路渗油' },
|
|
|
+ { text: '加油机静电接地失效' },
|
|
|
+ { text: '加油机铭牌不清晰' },
|
|
|
+ { text: '加油机工艺仓与电气仓之间隔板上的孔洞未密封' },
|
|
|
+ { text: '加油机内防爆挠性管连接明显松动' },
|
|
|
+ { text: '防爆接线盒未在专用接地端子处进行静电接地连接' },
|
|
|
]
|
|
|
},
|
|
|
{
|
|
|
@@ -248,8 +293,106 @@ const currentTask = computed(() => {
|
|
|
return taskList.value.find(t => t.id === currentTaskId.value) || taskList.value[0]
|
|
|
})
|
|
|
|
|
|
+const detectionGroups = computed(() => [
|
|
|
+ {
|
|
|
+ id: 1,
|
|
|
+ title: '加油机',
|
|
|
+ items: currentTask.value.checklist
|
|
|
+ },
|
|
|
+ {
|
|
|
+ id: 2,
|
|
|
+ title: '加油机输油软管',
|
|
|
+ items: [
|
|
|
+ { text: '输油软管外观存在老化、开裂或磨损' },
|
|
|
+ { text: '软管连接接头有明显松动' },
|
|
|
+ { text: '软管与加油枪连接处存在渗漏' },
|
|
|
+ { text: '软管与加油机连接处存在渗漏' },
|
|
|
+ { text: '软管未设置安全拉断阀' },
|
|
|
+ { text: '安全拉断阀安装方向不符合要求' },
|
|
|
+ { text: '安全拉断阀外观破损或锈蚀' },
|
|
|
+ { text: '软管拖地或受车辆碾压风险明显' },
|
|
|
+ { text: '软管长度不符合现场使用要求' },
|
|
|
+ { text: '软管表面有明显油污' },
|
|
|
+ { text: '软管弯折半径过小' },
|
|
|
+ { text: '软管固定支架缺失或损坏' },
|
|
|
+ { text: '软管回位装置失效' },
|
|
|
+ { text: '软管标识不清晰' },
|
|
|
+ { text: '软管未按要求定期检查' },
|
|
|
+ { text: '软管耐压等级标识缺失' },
|
|
|
+ { text: '软管附近存在明火或高温风险' },
|
|
|
+ { text: '软管连接密封件老化' },
|
|
|
+ { text: '软管防静电连接失效' },
|
|
|
+ { text: '软管收纳区域通行受阻' },
|
|
|
+ ]
|
|
|
+ },
|
|
|
+ {
|
|
|
+ id: 3,
|
|
|
+ title: '防撞栏',
|
|
|
+ items: [
|
|
|
+ { text: '防撞栏缺失或设置位置不合理' },
|
|
|
+ { text: '防撞栏固定螺栓松动' },
|
|
|
+ { text: '防撞栏立柱变形或倾斜' },
|
|
|
+ { text: '防撞栏表面反光标识不清晰' },
|
|
|
+ { text: '防撞栏警示颜色脱落' },
|
|
|
+ { text: '防撞栏高度不符合要求' },
|
|
|
+ { text: '防撞栏基础破损' },
|
|
|
+ { text: '防撞栏与设备间距不足' },
|
|
|
+ { text: '车辆通行区域防护不足' },
|
|
|
+ { text: '防撞设施周边存在杂物堆放' },
|
|
|
+ { text: '防撞栏夜间可视性不足' },
|
|
|
+ { text: '防撞栏维修记录缺失' },
|
|
|
+ { text: '防撞栏端部未做安全处理' },
|
|
|
+ ]
|
|
|
+ },
|
|
|
+ {
|
|
|
+ id: 4,
|
|
|
+ title: '支撑柱/立柱',
|
|
|
+ items: [
|
|
|
+ { text: '支撑柱外观存在明显裂缝' },
|
|
|
+ { text: '支撑柱表面防腐层脱落' },
|
|
|
+ { text: '立柱底座固定件松动' },
|
|
|
+ { text: '立柱根部存在积水或锈蚀' },
|
|
|
+ { text: '立柱附近防撞措施不足' },
|
|
|
+ { text: '立柱警示标识不清晰' },
|
|
|
+ { text: '立柱垂直度异常' },
|
|
|
+ { text: '立柱与棚体连接处异常' },
|
|
|
+ { text: '支撑结构存在明显变形' },
|
|
|
+ { text: '立柱周边通行空间不足' },
|
|
|
+ { text: '立柱维护检查记录缺失' },
|
|
|
+ ]
|
|
|
+ },
|
|
|
+ {
|
|
|
+ id: 5,
|
|
|
+ title: '加油枪',
|
|
|
+ items: [
|
|
|
+ { text: '加油枪外观破损或变形' },
|
|
|
+ { text: '加油枪密封不良' },
|
|
|
+ { text: '加油枪工作时出现明显渗漏' },
|
|
|
+ { text: '汽油加油枪无集气罩' },
|
|
|
+ { text: '加油枪集气罩破损' },
|
|
|
+ { text: '枪嘴磨损或变形' },
|
|
|
+ { text: '加油枪开关回位不灵活' },
|
|
|
+ { text: '加油枪自封功能异常' },
|
|
|
+ { text: '加油枪挂枪座损坏' },
|
|
|
+ { text: '加油枪与软管连接处松动' },
|
|
|
+ { text: '加油枪标识不清晰' },
|
|
|
+ { text: '加油枪存在油污堆积' },
|
|
|
+ { text: '油气回收接口松动' },
|
|
|
+ { text: '油气回收通道堵塞' },
|
|
|
+ { text: '加油枪防静电连接异常' },
|
|
|
+ { text: '加油枪使用区域照明不足' },
|
|
|
+ { text: '加油枪放置位置不规范' },
|
|
|
+ { text: '加油枪附近存在杂物' },
|
|
|
+ { text: '加油枪未按要求定期维护' },
|
|
|
+ { text: '加油枪维修更换记录缺失' },
|
|
|
+ ]
|
|
|
+ },
|
|
|
+])
|
|
|
+
|
|
|
+const expandedGroupId = ref(null)
|
|
|
const selectTask = (task) => {
|
|
|
currentTaskId.value = task.id
|
|
|
+ expandedGroupId.value = null
|
|
|
}
|
|
|
|
|
|
const selectTag = (tag) => {
|
|
|
@@ -261,6 +404,10 @@ const toggleCheck = (index) => {
|
|
|
currentTask.value.checklist[index].checked = !currentTask.value.checklist[index].checked
|
|
|
}
|
|
|
}
|
|
|
+
|
|
|
+const toggleGroup = (groupId) => {
|
|
|
+ expandedGroupId.value = expandedGroupId.value === groupId ? null : groupId
|
|
|
+}
|
|
|
</script>
|
|
|
|
|
|
<style scoped lang="scss">
|
|
|
@@ -423,22 +570,21 @@ const toggleCheck = (index) => {
|
|
|
}
|
|
|
|
|
|
.content-body {
|
|
|
- display: flex;
|
|
|
+ display: grid;
|
|
|
+ grid-template-columns: minmax(0, 1fr) 360px;
|
|
|
+ grid-template-rows: auto minmax(0, 1fr);
|
|
|
gap: 20px;
|
|
|
flex: 1;
|
|
|
overflow: hidden;
|
|
|
}
|
|
|
|
|
|
.center-panel {
|
|
|
- flex: 1;
|
|
|
- display: flex;
|
|
|
- flex-direction: column;
|
|
|
- gap: 20px;
|
|
|
- overflow-y: auto;
|
|
|
- padding-right: 8px;
|
|
|
+ display: contents;
|
|
|
}
|
|
|
|
|
|
.image-section {
|
|
|
+ grid-column: 1;
|
|
|
+ grid-row: 1;
|
|
|
position: relative;
|
|
|
background: #fff;
|
|
|
border-radius: 12px;
|
|
|
@@ -488,11 +634,18 @@ const toggleCheck = (index) => {
|
|
|
}
|
|
|
|
|
|
.ai-section {
|
|
|
+ grid-column: 2;
|
|
|
+ grid-row: 1 / 3;
|
|
|
+ align-self: stretch;
|
|
|
background: #fff;
|
|
|
border-radius: 12px;
|
|
|
padding: 16px;
|
|
|
box-shadow: 0 1px 4px rgba(0,0,0,0.05);
|
|
|
- flex-shrink: 0;
|
|
|
+ min-height: 0;
|
|
|
+ height: auto;
|
|
|
+ overflow: hidden;
|
|
|
+ display: flex;
|
|
|
+ flex-direction: column;
|
|
|
|
|
|
.section-header {
|
|
|
display: flex;
|
|
|
@@ -509,6 +662,9 @@ const toggleCheck = (index) => {
|
|
|
}
|
|
|
|
|
|
.ai-content {
|
|
|
+ flex: 1;
|
|
|
+ overflow-y: auto;
|
|
|
+
|
|
|
h4 {
|
|
|
font-size: 14px;
|
|
|
font-weight: 600;
|
|
|
@@ -652,8 +808,11 @@ const toggleCheck = (index) => {
|
|
|
}
|
|
|
|
|
|
.right-panel {
|
|
|
- width: 360px;
|
|
|
- flex-shrink: 0;
|
|
|
+ grid-column: 1;
|
|
|
+ grid-row: 2;
|
|
|
+ min-width: 0;
|
|
|
+ min-height: 0;
|
|
|
+ overflow: hidden;
|
|
|
}
|
|
|
|
|
|
.panel-section {
|
|
|
@@ -662,6 +821,7 @@ const toggleCheck = (index) => {
|
|
|
padding: 16px;
|
|
|
box-shadow: 0 1px 4px rgba(0,0,0,0.05);
|
|
|
height: 100%;
|
|
|
+ min-height: 0;
|
|
|
display: flex;
|
|
|
flex-direction: column;
|
|
|
overflow: hidden;
|
|
|
@@ -670,46 +830,185 @@ const toggleCheck = (index) => {
|
|
|
display: flex;
|
|
|
justify-content: space-between;
|
|
|
align-items: center;
|
|
|
- margin-bottom: 12px;
|
|
|
+ margin-bottom: 16px;
|
|
|
flex-shrink: 0;
|
|
|
|
|
|
.section-title {
|
|
|
- font-size: 16px;
|
|
|
- font-weight: 500;
|
|
|
+ font-size: 18px;
|
|
|
+ font-weight: 700;
|
|
|
color: #333;
|
|
|
}
|
|
|
+
|
|
|
+ .section-count {
|
|
|
+ width: 28px;
|
|
|
+ height: 28px;
|
|
|
+ border-radius: 50%;
|
|
|
+ background: #3f7cff;
|
|
|
+ color: #fff;
|
|
|
+ display: inline-flex;
|
|
|
+ align-items: center;
|
|
|
+ justify-content: center;
|
|
|
+ font-size: 15px;
|
|
|
+ font-weight: 700;
|
|
|
+ }
|
|
|
}
|
|
|
|
|
|
.checklist {
|
|
|
flex: 1;
|
|
|
overflow-y: auto;
|
|
|
+ padding-right: 4px;
|
|
|
|
|
|
- .checklist-item {
|
|
|
+ .check-group {
|
|
|
+ border: 1px solid #d9dee8;
|
|
|
+ border-radius: 8px;
|
|
|
+ overflow: hidden;
|
|
|
+ background: #f8fafc;
|
|
|
+ margin-bottom: 10px;
|
|
|
+
|
|
|
+ &.expanded {
|
|
|
+ border-color: #6c79ff;
|
|
|
+ background: #fff;
|
|
|
+
|
|
|
+ .check-group-header {
|
|
|
+ background: #efedff;
|
|
|
+ }
|
|
|
+
|
|
|
+ .group-caret {
|
|
|
+ transform: rotate(90deg);
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ .check-group-header {
|
|
|
display: flex;
|
|
|
- align-items: flex-start;
|
|
|
- padding: 10px 0;
|
|
|
- border-bottom: 1px solid #f5f5f5;
|
|
|
+ justify-content: space-between;
|
|
|
+ align-items: center;
|
|
|
+ width: 100%;
|
|
|
+ min-height: 48px;
|
|
|
+ padding: 0 14px;
|
|
|
+ border: 0;
|
|
|
+ background: #f8fafc;
|
|
|
+ color: #26324d;
|
|
|
+ font-size: 16px;
|
|
|
+ font-weight: 700;
|
|
|
+ cursor: pointer;
|
|
|
+ }
|
|
|
+
|
|
|
+ .check-group-title,
|
|
|
+ .group-meta {
|
|
|
+ display: flex;
|
|
|
+ align-items: center;
|
|
|
+ gap: 10px;
|
|
|
+ }
|
|
|
+
|
|
|
+ .group-index {
|
|
|
+ width: 22px;
|
|
|
+ height: 22px;
|
|
|
+ border-radius: 50%;
|
|
|
+ background: #2d5ac5;
|
|
|
+ color: #fff;
|
|
|
+ display: inline-flex;
|
|
|
+ align-items: center;
|
|
|
+ justify-content: center;
|
|
|
+ font-size: 13px;
|
|
|
+ font-weight: 700;
|
|
|
+ }
|
|
|
+
|
|
|
+ .group-meta {
|
|
|
+ color: #7a8494;
|
|
|
+ font-size: 14px;
|
|
|
+ font-weight: 500;
|
|
|
+ }
|
|
|
|
|
|
- &:last-child {
|
|
|
- border-bottom: none;
|
|
|
+ .group-caret {
|
|
|
+ font-size: 12px;
|
|
|
+ color: #a6afbd;
|
|
|
+ transition: transform 0.2s ease;
|
|
|
+ }
|
|
|
+
|
|
|
+ .checklist-row {
|
|
|
+ &:first-of-type {
|
|
|
+ .checklist-item {
|
|
|
+ margin-top: 10px;
|
|
|
+ }
|
|
|
}
|
|
|
+ }
|
|
|
|
|
|
- input {
|
|
|
- margin-right: 12px;
|
|
|
- margin-top: 2px;
|
|
|
- cursor: pointer;
|
|
|
- flex-shrink: 0;
|
|
|
+ .checklist-item {
|
|
|
+ display: grid;
|
|
|
+ grid-template-columns: 22px minmax(0, 1fr);
|
|
|
+ gap: 10px;
|
|
|
+ align-items: flex-start;
|
|
|
+ width: calc(100% - 28px);
|
|
|
+ margin: 0 14px;
|
|
|
+ padding: 9px 14px;
|
|
|
+ border-radius: 7px;
|
|
|
+ background: #fff;
|
|
|
+
|
|
|
+ .item-index {
|
|
|
+ width: 22px;
|
|
|
+ height: 22px;
|
|
|
+ border-radius: 50%;
|
|
|
+ background: #e2e7ef;
|
|
|
+ color: #7f8da3;
|
|
|
+ display: inline-flex;
|
|
|
+ align-items: center;
|
|
|
+ justify-content: center;
|
|
|
+ font-size: 12px;
|
|
|
+ font-weight: 700;
|
|
|
+ line-height: 1;
|
|
|
+ margin-top: 1px;
|
|
|
+ }
|
|
|
+
|
|
|
+ .item-text {
|
|
|
+ font-size: 14px;
|
|
|
+ color: #4b5568;
|
|
|
+ line-height: 1.55;
|
|
|
}
|
|
|
+ }
|
|
|
|
|
|
- span {
|
|
|
+ .case-examples {
|
|
|
+ display: grid;
|
|
|
+ grid-template-columns: repeat(2, minmax(0, 1fr));
|
|
|
+ gap: 12px;
|
|
|
+ margin: 4px 14px 12px 46px;
|
|
|
+ padding: 12px;
|
|
|
+ border-radius: 8px;
|
|
|
+ background: #f8fafc;
|
|
|
+ border: 1px solid #e7ecf3;
|
|
|
+ }
|
|
|
+
|
|
|
+ .case-card {
|
|
|
+ min-width: 0;
|
|
|
+
|
|
|
+ .case-title {
|
|
|
font-size: 13px;
|
|
|
- color: #666;
|
|
|
- line-height: 1.5;
|
|
|
+ font-weight: 700;
|
|
|
+ margin-bottom: 8px;
|
|
|
+ }
|
|
|
+
|
|
|
+ img {
|
|
|
+ width: 100%;
|
|
|
+ height: 220px;
|
|
|
+ display: block;
|
|
|
+ object-fit: contain;
|
|
|
+ border-radius: 6px;
|
|
|
+ border: 1px solid #e5eaf0;
|
|
|
+ background: #f6f8fb;
|
|
|
+ }
|
|
|
+
|
|
|
+ &.positive .case-title {
|
|
|
+ color: #16a34a;
|
|
|
}
|
|
|
|
|
|
- &.checked span {
|
|
|
- text-decoration: line-through;
|
|
|
- color: #999;
|
|
|
+ &.negative .case-title {
|
|
|
+ color: #dc2626;
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ @media (max-width: 1200px) {
|
|
|
+ .case-examples {
|
|
|
+ grid-template-columns: 1fr;
|
|
|
}
|
|
|
}
|
|
|
}
|