二级页面初步完善

This commit is contained in:
BianLzhaoMin 2025-06-18 18:08:48 +08:00
parent cf35fb0643
commit a40836ea9b
17 changed files with 1291 additions and 237 deletions

Binary file not shown.

After

Width:  |  Height:  |  Size: 947 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 592 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 641 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 25 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 410 B

View File

@ -17,5 +17,8 @@
--bt-box-shadow: 0 1px 2px rgba(0, 0, 0, 0.9), 0 0px 2px rgba(0, 0, 0, 0.9);
--bt-box-shadow-1: 0 1px 2px rgba(0, 0, 0, 0.9), 0 0px 2px rgba(0, 0, 0, 0.9);
--box-shadow-2: 0 1px 0 hsl(0 calc(1 * 0%) 0.8% / 0.2),
0 1.5px 0 hsl(240 calc(1 * 7.7%) 2.5% / 0.05), 0 2px 0 hsl(0 calc(1 * 0%) 0.8% / 0.05);
0 1.5px 0 hsl(240 calc(1 * 7.7%) 2.5% / 0.05), 0 2px 0 hsl(0 calc(1 * 0%) 0.8% / 0.05);
--n-border: 1px solid #7fc0ff;
}

View File

@ -0,0 +1,88 @@
.n-pagination .n-pagination-item,
.n-base-selection-input__content {
color: #fff;
}
.n-pagination .n-pagination-item.n-pagination-item--button {
color: #fff;
}
.n-pagination .n-pagination-item:not(.n-pagination-item--disabled):hover.n-pagination-item--button {
color: #fff;
}
.n-pagination .n-pagination-item.n-pagination-item--disabled.n-pagination-item--active,
.n-pagination .n-pagination-item.n-pagination-item--disabled.n-pagination-item--button {
background-color: #1d3861;
}
.n-base-selection .n-base-selection-label {
background-color: #1d3861;
color: #fff;
}
.n-base-select-menu {
background-color: #1d3861 !important;
}
.n-base-select-option__content {
color: #ffffff !important;
}
.n-base-selection--active {
background-color: #1d3861 !important;
color: #fff !important;
border-color: #7dd3fc !important;
}
.n-input {
background-color: #1d3861;
border: 1px solid #1090f0;
}
.n-input:not(.n-input--disabled).n-input--focus {
background-color: #1d3861;
color: #fff;
}
.n-input .n-input__input-el,
.n-input .n-input__textarea-el {
color: #fff;
}
.n-input:not(.n-input--disabled):hover .n-input__state-border {
// border: 1px solid #7dd3fc;
border: none;
}
.n-input .n-input__border,
.n-input .n-input__state-border {
transition: box-shadow 0.3s var(--n-bezier) !important;
border: none;
}
.n-input:not(.n-input--disabled).n-input--focus .n-input__state-border {
border: 1px solid #7dd3fc;
}
.n-data-table .n-data-table-th {
background-color: #14295c;
color: #fff;
border: none;
}
.n-data-table.n-data-table--bordered .n-data-table-wrapper {
border: none;
}
.n-data-table .n-data-table-tr:not(.n-data-table-tr--summary):hover > .n-data-table-td {
background-color: #2f5789;
}
.n-data-table .n-data-table-td {
background-color: #072148;
color: #fff;
}
.n-form-item .n-form-item-label {
color: #fff;
}

View File

@ -41,30 +41,77 @@
</div>
</div>
<!-- 抽屉内容保持不变 -->
<n-drawer resizable placement="bottom" :default-height="600" v-model:show="morePanelVisible">
现场定点巡检拍照
<!-- 模态框 -->
<n-modal v-model:show="morePanelVisible">
<n-card
:bordered="false"
size="huge"
role="dialog"
aria-modal="true"
class="more-panel-card"
>
<n-flex justify="space-between">
<n-gradient-text
style="font-size: 20px; font-weight: 600; letter-spacing: 2px"
gradient="linear-gradient(90deg, #CDF7FD 0%, #DAFAFE 20%, #CDF7FD 40%, #DAFAFE 60%, #CDF7FD 80%, #DAFAFE 100%)"
>
现场定点巡检拍照
</n-gradient-text>
<n-form ref="formRef" inline :model="searchForm" :rules="rules" label-placement="left">
<n-form-item>
<n-date-picker
clearable
type="daterange"
style="width: 280px"
placeholder="时间范围"
value-format="yyyy-MM-dd"
<img
class="close-icon"
src="@/assets/home-imgs/close.png"
@click="morePanelVisible = false"
/>
</n-form-item>
<n-form-item>
<n-input placeholder="输入途经点" style="width: 280px" />
</n-form-item>
</n-flex>
<n-form-item>
<n-button attr-type="button"> 查询 </n-button>
<n-button attr-type="button" style="margin-left: 10px"> 重置 </n-button>
</n-form-item>
</n-form>
</n-drawer>
<n-form
inline
ref="formRef"
size="small"
label-placement="left"
style="margin-top: 10px"
>
<n-form-item>
<n-date-picker type="daterange" clearable style="width: 240px" />
</n-form-item>
<n-form-item>
<n-input placeholder="输入途经点" clearable style="width: 240px" />
</n-form-item>
<n-button type="info"> 查询</n-button>
<n-button color="#6E90A9" style="margin-left: 8px"> 重置 </n-button>
</n-form>
<!-- 内容区域 -->
<div class="table-container">
<!-- 分页 -->
<div v-for="item in 7" :key="item" class="table-item">
<n-image
width="100%"
object-fit="cover"
class="item-image"
src="https://img1.baidu.com/it/u=3294211986,2810142789&fm=253&fmt=auto&app=138&f=JPEG?w=500&h=500"
/>
<div class="table-item-title">
<span>途经点</span>
<span>2025-06-01 10:00:00</span>
</div>
</div>
</div>
<div style="margin-top: 10px; display: flex; justify-content: flex-end">
<n-pagination
v-model:page="page"
v-model:page-size="pageSize"
:page-count="100"
show-size-picker
:page-sizes="[10, 20, 30, 40]"
/>
</div>
</n-card>
</n-modal>
</template>
<script setup>
@ -77,6 +124,9 @@ const marqueeContainer = ref(null)
const trackWidth = ref('auto')
const imageHeight = ref('0px')
const itemMargin = 10 // 10px
const page = ref(1)
const pageSize = ref(10)
const itemCount = ref(100)
//
const items = ref([
@ -293,4 +343,83 @@ onUnmounted(() => {
}
/* 抽屉样式保持不变 */
.more-panel-card {
width: 80%;
height: 80vh;
background: url('@/assets/home-imgs/modal-bg.png') no-repeat center center;
background-size: 100% 100%;
}
.close-icon {
width: 20px;
height: 20px;
cursor: pointer;
}
.table-container {
height: 75%;
display: flex;
flex-wrap: wrap;
color: #fff;
.table-item {
flex-shrink: 0;
width: calc((100% - 30px) / 4);
height: calc((100% - 20px) / 2);
margin-right: 10px;
margin-bottom: 10px;
border-radius: 5px;
display: flex;
flex-direction: column;
align-items: center;
justify-content: space-between;
overflow: hidden;
.item-image {
// width: 100%;
height: 150px;
flex-shrink: 0;
/* 确保Naive UI的n-image组件完全填充 */
:deep(.n-image) {
// width: 100%;
display: block;
img {
// width: 100%;
// height: v-bind(imageHeight);
object-fit: cover;
}
}
}
.table-item-title {
width: 100%;
height: 42px;
display: flex;
justify-content: space-between;
align-items: center;
font-size: 14px;
background: url('@/assets/home-imgs/center-two-bg.png') no-repeat center center;
background-size: 100% 100%;
& span:nth-child(1) {
margin-left: 6px;
font-size: 16px;
color: #37e7ff;
}
& span:nth-child(2) {
margin-right: 6px;
color: #fff;
font-size: 14px;
}
}
}
.table-item:nth-child(4n) {
margin-right: 0;
}
}
</style>

View File

@ -41,10 +41,26 @@
<n-grid-item :span="4">
<div class="row-3-item-1">
<!-- 上下左右控制按钮 -->
<img class="arrow-top" src="@/assets/home-imgs/control-2-arrow.png" alt="" />
<img class="arrow-right" src="@/assets/home-imgs/control-2-arrow.png" alt="" />
<img class="arrow-bottom" src="@/assets/home-imgs/control-2-arrow.png" alt="" />
<img class="arrow-left" src="@/assets/home-imgs/control-2-arrow.png" alt="" />
<img
class="arrow-top hand-direction"
src="@/assets/home-imgs/control-2-arrow.png"
alt=""
/>
<img
class="arrow-right hand-direction"
src="@/assets/home-imgs/control-2-arrow.png"
alt=""
/>
<img
class="arrow-bottom hand-direction"
src="@/assets/home-imgs/control-2-arrow.png"
alt=""
/>
<img
class="arrow-left hand-direction"
src="@/assets/home-imgs/control-2-arrow.png"
alt=""
/>
<!-- 中间的按钮 -->
<div class="row-3-item-1-center">
@ -102,6 +118,127 @@
</div>
</n-grid-item>
</n-grid>
<!-- 第四行 -->
<n-grid :cols="12" class="row-4">
<n-grid-item :span="3">
<div>警灯</div>
</n-grid-item>
<n-grid-item :span="3">
<div>
<n-radio
:checked="checkedValue === '关'"
value="关"
name="basic-demo"
@change="handleChange1"
>
</n-radio>
</div>
</n-grid-item>
<n-grid-item :span="3">
<div>
<n-radio
:checked="checkedValue === '闪烁'"
value="闪烁"
name="basic-demo"
@change="handleChange2"
>
闪烁
</n-radio>
</div>
</n-grid-item>
<n-grid-item :span="3">
<div class="row-4-item">
<n-radio
:checked="checkedValue === '运动时闪烁'"
value="运动时闪烁"
name="basic-demo"
@change="handleChange3"
>
运动时闪烁
</n-radio>
</div>
</n-grid-item>
</n-grid>
<!-- 第五行 -->
<n-grid :cols="12" class="row-5">
<n-grid-item :span="3">
<div>录音播放</div>
</n-grid-item>
<n-grid-item :span="3">
<div>
<div>
<!-- <n-select
size="tiny"
v-model:value="selectValue"
:options="selectOptions"
/> -->
<!-- <n-select
size="small"
v-model:value="selectValue"
:options="selectOptions"
/> -->
<n-select
:options="selectOptions"
size="small"
:dropdown-style="{
borderRadius: '4px',
boxShadow: '0 4px 6px -1px rgba(0, 0, 0, 0.1)',
color: '#fff',
}"
/>
</div>
<div style="margin-top: 16px">
<n-radio
:checked="checkedValue === '循环播放'"
value="循环播放"
name="basic-demo"
@change="handleChange4"
>
循环播放
</n-radio>
</div>
</div>
</n-grid-item>
<n-grid-item :span="6">
<div class="row-5-item">
<div class="row-5-item-1">
<img src="@/assets/home-imgs/control-3-voice.png" alt="" />
<div style="width: 60%">
<n-slider
:default-value="50"
:step="10"
:format-tooltip="formatTooltip"
/>
</div>
</div>
<div class="row-5-item-1" style="margin-top: 16px">
<img src="@/assets/home-imgs/control-3-video.png" alt="" />
<div style="width: 60%">
<n-slider
:default-value="50"
:step="10"
:format-tooltip="formatTooltip"
/>
</div>
</div>
</div>
</n-grid-item>
</n-grid>
<!-- 第六行 -->
<n-grid :cols="10" class="row-6">
<n-grid-item :span="4">
<div class="row-6-item">回桩充电</div>
</n-grid-item>
<n-grid-item :span="3">
<div class="row-6-item-1">
<img src="@/assets/home-imgs/control-3-mk.png" alt="" />
</div>
</n-grid-item>
</n-grid>
</div>
</template>
@ -115,6 +252,18 @@ const isDragging = ref(false)
const currentTop = ref(0)
const startY = ref(0)
const startTop = ref(0)
const checkedValue = ref('')
const selectValue = ref('')
const selectOptions = ref([
{
label: '录音1',
value: '录音1',
},
{
label: '录音2',
value: '录音2',
},
])
// (0-100)
const currentHeight = computed(() => {
@ -165,8 +314,30 @@ onMounted(() => {
const maxTop = containerHeight - draggableHeight - 20
currentTop.value = maxTop * (1 - upDownHeight.value / 100)
})
const handleChange1 = (e) => {
console.log(e)
checkedValue.value = e.target.value
}
const handleChange2 = (e) => {
console.log(e)
checkedValue.value = e.target.value
}
const handleChange3 = (e) => {
checkedValue.value = e.target.value
}
const handleChange4 = (e) => {
checkedValue.value = e.target.value
}
const formatTooltip = (value) => {
return `${value}%`
}
</script>
<style lang="scss" scoped>
.control-deck {
justify-content: space-between;
}
.row-1-item,
.row-2-item {
width: 100px;
@ -214,6 +385,12 @@ onMounted(() => {
object-fit: contain;
}
// //
// .hand-direction:hover {
// transform: scale(1.1);
// transition: transform 0.3s ease-in-out;
// }
.arrow-top {
position: absolute;
top: 6px;
@ -373,4 +550,79 @@ onMounted(() => {
touch-action: none;
}
}
.row-4 {
margin: 24px 0;
.row-4-item {
text-align: center;
}
}
.row-5-item-1 {
width: 100%;
display: flex;
justify-content: center;
align-items: center;
> img {
width: 20px;
height: 20px;
margin-right: 10px;
object-fit: contain;
}
}
.row-6 {
margin-top: 20px;
display: flex;
align-items: center;
}
.row-6-item {
padding: 4px 12px;
display: inline-block;
background-color: #005db6;
border: 1px solid #7fc0ff;
border-radius: 4px;
cursor: pointer;
}
.row-6-item-1 {
text-align: center;
img {
width: 40px;
height: 60px;
object-fit: contain;
cursor: pointer;
}
}
:deep(.n-radio__label) {
color: #fff !important;
}
:deep(.n-radio__dot) {
background: transparent;
border: 1px solid #7fc0ff;
box-shadow: none;
}
:deep(.n-radio__dot::before) {
background: #7fc0ff;
}
// :deep(.n-base-selection .n-base-selection-label) {
// background-color: #054a92;
// color: #fff;
// }
:deep(.n-slider .n-slider-rail .n-slider-rail__fill) {
background-color: #7fc0ff;
}
:deep(.n-slider .n-slider-handles .n-slider-handle-wrapper .n-slider-handle) {
background-color: #7fc0ff;
}
:deep(.n-slider .n-slider-rail) {
background-color: #2d6098;
}
</style>

View File

@ -57,54 +57,232 @@
</div>
</div>
<!-- drawer内容保持不变 -->
<!-- 弹框内容 更多数据 -->
<n-modal v-model:show="morePanelVisible">
<n-card
:bordered="false"
size="huge"
role="dialog"
aria-modal="true"
class="more-panel-card"
>
<n-flex justify="space-between">
<n-gradient-text
style="font-size: 20px; font-weight: 600; letter-spacing: 2px"
gradient="linear-gradient(90deg, #CDF7FD 0%, #DAFAFE 20%, #CDF7FD 40%, #DAFAFE 60%, #CDF7FD 80%, #DAFAFE 100%)"
>
人员动态
</n-gradient-text>
<n-drawer resizable placement="bottom" :default-height="600" v-model:show="morePanelVisible">
现场定点巡检拍照
<n-form ref="formRef" inline :model="searchForm" :rules="rules" label-placement="left">
<n-form-item>
<n-date-picker
clearable
type="daterange"
style="width: 280px"
placeholder="时间范围"
value-format="yyyy-MM-dd"
<img
class="close-icon"
src="@/assets/home-imgs/close.png"
@click="morePanelVisible = false"
/>
</n-form-item>
<n-form-item>
<n-input placeholder="输入姓名" style="width: 280px" />
</n-form-item>
<n-form-item>
<n-select placeholder="选择类型" style="width: 280px" />
</n-form-item>
</n-flex>
<n-form-item>
<n-button attr-type="button"> 查询 </n-button>
<n-button attr-type="button" style="margin-left: 10px"> 重置 </n-button>
</n-form-item>
</n-form>
<n-form inline ref="formRef" size="small" label-placement="left">
<n-form-item>
<n-date-picker type="daterange" clearable style="width: 240px" />
</n-form-item>
<n-form-item>
<n-input placeholder="输入途经点" clearable style="width: 240px" />
</n-form-item>
<n-form-item>
<n-input placeholder="类型" clearable style="width: 240px" />
</n-form-item>
<n-data-table :columns="columns" :data="data" title-align="center" />
<div class="pagination-container">
<n-pagination
v-model:page="page"
:page-count="100"
size="medium"
show-quick-jumper
show-size-picker
/>
</div>
</n-drawer>
<n-button type="info"> 查询</n-button>
<n-button color="#6E90A9" style="margin-left: 8px"> 重置 </n-button>
<n-button type="info" style="margin-left: 10px" @click="onHandleAddPerson">
新增项目部人员
</n-button>
</n-form>
<!-- 内容区域 -->
<n-data-table :columns="columns" :data="data" />
<div style="margin-top: 10px; display: flex; justify-content: flex-end">
<n-pagination
v-model:page="page"
v-model:page-size="pageSize"
:page-count="100"
show-size-picker
:page-sizes="[10, 20, 30, 40]"
/>
</div>
</n-card>
</n-modal>
<!-- 弹框内容 新增项目部人员 -->
<n-modal v-model:show="addPersonPanelVisible">
<n-card
:bordered="false"
size="huge"
role="dialog"
aria-modal="true"
class="add-person-panel-card"
>
<n-flex justify="space-between">
<n-gradient-text
style="font-size: 20px; font-weight: 600; letter-spacing: 2px"
gradient="linear-gradient(90deg, #CDF7FD 0%, #DAFAFE 20%, #CDF7FD 40%, #DAFAFE 60%, #CDF7FD 80%, #DAFAFE 100%)"
>
新增项目部人员
</n-gradient-text>
<img
class="close-icon"
src="@/assets/home-imgs/close.png"
@click="addPersonPanelVisible = false"
/>
</n-flex>
<n-form
ref="addPersonFormRef"
label-placement="left"
size="small"
label-width="80"
style="margin-top: 10px"
>
<n-form-item label="姓名">
<n-input placeholder="姓名" clearable />
</n-form-item>
<n-form-item label="联系方式">
<n-input placeholder="联系方式" clearable />
</n-form-item>
<div class="name-phone-photo">
<!-- <div class="name">
<n-form-item>
<n-input placeholder="姓名" clearable />
</n-form-item>
</div>
<div class="phone">
<n-form-item>
<n-input placeholder="姓名" clearable />
</n-form-item>
</div>
<div class="photo">
<n-form-item>
<n-input placeholder="姓名" clearable />
</n-form-item>
</div> -->
<!-- <div class="left">
</div>
<div class="right">
</div> -->
</div>
<n-form-item label="岗位工种">
<n-input placeholder="岗位工种" clearable />
</n-form-item>
<n-form-item label="年龄">
<n-input placeholder="年龄" clearable />
</n-form-item>
<n-form-item label="人脸照片">
<!-- <n-upload
action="https://www.mocky.io/v2/5e4bafc63100007100d8b70f"
:headers="{
'naive-info': 'hello!',
}"
:data="{
'naive-data': 'cool! naive!',
}"
>
<img src="@/assets/home-imgs/upload-img.png" alt="" />
</n-upload> -->
<n-upload
action="https://www.mocky.io/v2/5e4bafc63100007100d8b70f"
:default-file-list="previewFileList"
list-type="image-card"
@preview="handlePreview"
/>
<n-modal
preset="card"
v-model:show="showModal"
style="width: 600px"
title="一张很酷的图片"
>
<img :src="previewImageUrl" style="width: 100%" />
</n-modal>
<n-button type="info" style="width: 20%"> 保存 </n-button>
</n-form-item>
</n-form>
</n-card>
</n-modal>
</template>
<script setup>
import { NTag } from 'naive-ui'
import TitleBackground from '@/components/TitleBackground/index.vue'
import { ref, onMounted, onUpdated, nextTick } from 'vue'
import { ref, onMounted, onUpdated, nextTick, h } from 'vue'
const morePanelVisible = ref(false)
const contentContainer = ref(null)
const shouldScroll = ref(false)
const morePanelVisible = ref(false) //
const addPersonPanelVisible = ref(false) //
const addPersonFormRef = ref(null) //
const contentContainer = ref(null) //
const shouldScroll = ref(false) //
const page = ref(1)
const pageSize = ref(10)
const columns = ref([
{
title: '日期时间',
key: 'age',
align: 'center',
},
{
title: '图片',
key: 'tags',
align: 'center',
render(row) {
const tags = row.tags.map((tagKey) => {
return h(
NTag,
{
style: {
marginRight: '6px',
},
type: 'info',
bordered: false,
},
{
default: () => tagKey,
},
)
})
return tags
},
},
{
title: '姓名',
key: 'age',
align: 'center',
},
{
title: '年龄',
key: 'age',
align: 'center',
},
{
title: '工种',
key: 'age',
align: 'center',
},
])
const data = ref([
{
age: '2025-06-01 10:00:00',
tags: ['nice'],
},
])
//
const checkIfShouldScroll = () => {
@ -137,6 +315,12 @@ onUpdated(() => {
const onHandleMore = () => {
morePanelVisible.value = true
}
//
const onHandleAddPerson = () => {
console.log('新增项目部人员')
addPersonPanelVisible.value = true
}
</script>
<style lang="scss" scoped>
@ -225,4 +409,55 @@ const onHandleMore = () => {
transform: translateY(var(--scroll-distance, -100%));
}
}
.more-panel-card {
width: 70%;
height: 75vh;
background: url('@/assets/home-imgs/modal-bg.png') no-repeat center center;
background-size: 100% 100%;
}
.close-icon {
width: 20px;
height: 20px;
cursor: pointer;
}
.add-person-panel-card {
width: 40%;
height: 50vh;
background: url('@/assets/home-imgs/modal-bg.png') no-repeat center center;
background-size: 100% 100%;
}
.name-phone-photo {
display: flex;
justify-content: space-between;
.right {
width: 40%;
height: 97px;
display: flex;
align-items: center;
background-color: #1d3861;
border: 1px solid #1090f0;
}
.left {
width: 58%;
}
}
.n-upload-trigger {
// display: flex;
// flex-direction: column;
// align-items: center;
// justify-content: center;
img {
width: 28px;
height: 28px;
cursor: pointer;
}
}
</style>

View File

@ -1,155 +0,0 @@
<template>
<!-- 右二 ---- 智能对比 -->
<div class="right-two child-container">
<div class="title-container">
<TitleBackground :title="`智能对比`" />
<div class="more-btn">更多</div>
</div>
<!-- 内容区域 -->
<div class="content-container">
<div class="content-item" v-for="item in 4" :key="item" :class="`item-${item}`">
<div>
<span style="padding-left: 10px; font-size: 16px"> 巡检次数 </span>
<span style="padding-left: 10px; font-size: 14px"> 总数 </span>
<span> 100 </span>
</div>
<div>
<span style="padding-left: 10px; font-size: 18px; font-weight: bold"> 26 </span>
<span style="font-size: 14px"> </span>
</div>
</div>
</div>
</div>
<n-drawer resizable placement="bottom" :default-height="600" v-model:show="morePanelVisible">
现场定点巡检拍照
<n-form ref="formRef" inline :model="searchForm" :rules="rules" label-placement="left">
<n-form-item>
<n-date-picker
clearable
type="daterange"
style="width: 280px"
placeholder="时间范围"
value-format="yyyy-MM-dd"
/>
</n-form-item>
<n-form-item>
<n-input placeholder="输入姓名" style="width: 280px" />
</n-form-item>
<n-form-item>
<n-select placeholder="选择类型" style="width: 280px" />
</n-form-item>
<n-form-item>
<n-button attr-type="button"> 查询 </n-button>
<n-button attr-type="button" style="margin-left: 10px"> 重置 </n-button>
</n-form-item>
</n-form>
<n-data-table :columns="columns" :data="data" title-align="center" />
<div class="pagination-container">
<n-pagination
v-model:page="page"
:page-count="100"
size="medium"
show-quick-jumper
show-size-picker
/>
</div>
</n-drawer>
</template>
<script setup>
import { BorderBox8 as DvBorderBox8 } from '@kjgl77/datav-vue3'
const morePanelVisible = ref(false)
const searchForm = ref({})
const page = ref(1)
const data = ref([
{
name: '2025-06-16 10:00:00',
age: '1',
address: '1',
tags: '1',
actions: '1',
},
])
const columns = ref([
{
title: '日期时间',
key: 'name',
},
{
title: '图片',
key: 'age',
},
{
title: '姓名',
key: 'address',
},
{
title: '性别',
key: 'tags',
},
{
title: '工种',
key: 'actions',
},
])
const onHandleMore = () => {
console.log('更多')
morePanelVisible.value = true
}
</script>
<style lang="scss" scoped>
.right-two {
.title-container {
position: relative;
.more-btn {
position: absolute;
right: 0;
top: 0;
}
}
}
.content-container {
flex: 1;
display: grid;
grid-template-columns: repeat(4, 1fr);
grid-template-rows: repeat(4, 1fr);
gap: 10px;
padding: 20px 2px;
.content-item {
display: flex;
flex-direction: column;
justify-content: space-around;
border: 1px solid #00deff;
color: #b9e8fe;
}
.item-1 {
grid-column: 1 / 3;
grid-row: 1 / 3;
}
.item-2 {
grid-column: 3 / 5;
grid-row: 1 / 3;
}
.item-3 {
grid-column: 1 / 3;
grid-row: 3 / 5;
}
.item-4 {
grid-column: 3 / 5;
grid-row: 3 / 5;
}
}
</style>

View File

@ -0,0 +1,243 @@
<template>
<!-- 右二 ---- 智能对比 -->
<div class="right-two child-container">
<div class="title-container">
<TitleBackground :title="`智能对比`" />
<div class="more-btn" @click="onHandleMore">更多</div>
</div>
<!-- 内容区域 -->
<div class="content-container">
<div class="content-item" v-for="item in 4" :key="item" :class="`item-${item}`">
<div>
<span style="padding-left: 10px; font-size: 16px"> 巡检次数 </span>
<span style="padding-left: 10px; font-size: 14px"> 总数 </span>
<span> 100 </span>
</div>
<div>
<span style="padding-left: 10px; font-size: 18px; font-weight: bold"> 26 </span>
<span style="font-size: 14px"> </span>
</div>
</div>
</div>
</div>
<!-- 弹框内容 -->
<n-modal v-model:show="morePanelVisible">
<n-card
:bordered="false"
size="huge"
role="dialog"
aria-modal="true"
class="more-panel-card"
>
<n-flex justify="space-between">
<n-gradient-text
style="font-size: 20px; font-weight: 600; letter-spacing: 2px"
gradient="linear-gradient(90deg, #CDF7FD 0%, #DAFAFE 20%, #CDF7FD 40%, #DAFAFE 60%, #CDF7FD 80%, #DAFAFE 100%)"
>
人员动态
</n-gradient-text>
<img
class="close-icon"
src="@/assets/home-imgs/close.png"
@click="morePanelVisible = false"
/>
</n-flex>
<div class="tabs-btns">
<div
class="tabs-btn"
:key="item.name"
v-for="(item, index) in tapsBtns"
:class="{ active: activeIndex === index }"
@click="onHandleTabs(item.component, index)"
>
{{ item.name }}
</div>
</div>
<component :is="componentMap[currentComponent]" />
</n-card>
</n-modal>
</template>
<script setup>
import { NTag } from 'naive-ui'
import { ref, onMounted, onUpdated, nextTick, h } from 'vue'
import TapsOne from './taps-one.vue'
import TapsTwo from './taps-two.vue'
import TapsThree from './taps-three.vue'
const morePanelVisible = ref(false)
const contentContainer = ref(null)
const shouldScroll = ref(false)
const page = ref(1)
const pageSize = ref(10)
const activeIndex = ref(0)
const currentComponent = ref('comp-a')
const componentMap = {
'comp-a': TapsOne,
'comp-b': TapsTwo,
'comp-c': TapsThree,
}
const tapsBtns = ref([
{
name: '巡检次数',
component: 'comp-a',
},
{
name: '巡检照片',
component: 'comp-b',
},
{
name: '比对结果',
component: 'comp-c',
},
])
const columns = ref([
{
title: '日期时间',
key: 'age',
align: 'center',
},
{
title: '图片',
key: 'tags',
align: 'center',
render(row) {
const tags = row.tags.map((tagKey) => {
return h(
NTag,
{
style: {
marginRight: '6px',
},
type: 'info',
bordered: false,
},
{
default: () => tagKey,
},
)
})
return tags
},
},
{
title: '姓名',
key: 'age',
align: 'center',
},
{
title: '年龄',
key: 'age',
align: 'center',
},
{
title: '工种',
key: 'age',
align: 'center',
},
])
const data = ref([
{
age: '2025-06-01 10:00:00',
tags: ['nice'],
},
])
const onHandleMore = () => {
console.log('更多')
morePanelVisible.value = true
}
const onHandleTabs = (component, index) => {
activeIndex.value = index
currentComponent.value = component
}
</script>
<style lang="scss" scoped>
.right-two {
.title-container {
position: relative;
.more-btn {
position: absolute;
right: 0;
top: 0;
}
}
}
.content-container {
flex: 1;
display: grid;
grid-template-columns: repeat(4, 1fr);
grid-template-rows: repeat(4, 1fr);
gap: 10px;
padding: 20px 2px;
.content-item {
display: flex;
flex-direction: column;
justify-content: space-around;
border: 1px solid #00deff;
color: #b9e8fe;
}
.item-1 {
grid-column: 1 / 3;
grid-row: 1 / 3;
}
.item-2 {
grid-column: 3 / 5;
grid-row: 1 / 3;
}
.item-3 {
grid-column: 1 / 3;
grid-row: 3 / 5;
}
.item-4 {
grid-column: 3 / 5;
grid-row: 3 / 5;
}
}
.more-panel-card {
width: 80%;
height: 80vh;
background: url('@/assets/home-imgs/modal-bg.png') no-repeat center center;
background-size: 100% 100%;
}
.close-icon {
width: 20px;
height: 20px;
cursor: pointer;
}
.tabs-btns {
display: flex;
margin: 20px 0;
.tabs-btn {
width: 100px;
height: 42px;
background-color: #1b4589;
color: #fff;
text-align: center;
line-height: 42px;
cursor: pointer;
}
.active {
background-color: #1090f0;
border-radius: 8px;
}
}
</style>

View File

@ -0,0 +1,65 @@
<template>
<n-form inline ref="formRef" size="small" label-placement="left">
<n-form-item>
<n-date-picker type="daterange" clearable style="width: 240px" />
</n-form-item>
<n-form-item>
<n-button type="info"> 查询 </n-button>
<n-button color="#6E90A9" style="margin-left: 10px"> 重置 </n-button>
</n-form-item>
</n-form>
<!-- 内容区域 -->
<n-data-table :columns="columns" :data="data" />
<div style="margin-top: 10px; display: flex; justify-content: flex-end">
<n-pagination
v-model:page="page"
v-model:page-size="pageSize"
:page-count="100"
show-size-picker
:page-sizes="[10, 20, 30, 40]"
/>
</div>
</template>
<script setup>
import { ref } from 'vue'
const page = ref(1)
const pageSize = ref(10)
const columns = ref([
{
title: '巡检日期',
key: 'age',
align: 'center',
},
{
title: '巡检开始时间',
key: 'tags',
align: 'center',
},
{
title: '巡检结束时间',
key: 'age',
align: 'center',
},
{
title: '巡检照片',
key: 'age',
align: 'center',
},
{
title: '巡检时长',
key: 'age',
align: 'center',
},
])
const data = ref([
{
age: '2025-06-01 10:00:00',
tags: ['nice'],
},
])
</script>

View File

@ -0,0 +1,86 @@
<template>
<n-form inline ref="formRef" size="small" label-placement="left">
<n-form-item>
<n-date-picker type="daterange" clearable style="width: 240px" />
</n-form-item>
<n-form-item>
<n-input placeholder="输入途经点" clearable style="width: 240px" />
</n-form-item>
<n-form-item>
<n-input placeholder="类型" clearable style="width: 240px" />
</n-form-item>
<n-form-item>
<n-button type="info"> 查询 </n-button>
<n-button color="#6E90A9" style="margin-left: 10px"> 重置 </n-button>
</n-form-item>
</n-form>
<!-- 内容区域 -->
<n-data-table :columns="columns" :data="data" />
<div style="margin-top: 10px; display: flex; justify-content: flex-end">
<n-pagination
v-model:page="page"
v-model:page-size="pageSize"
:page-count="100"
show-size-picker
:page-sizes="[10, 20, 30, 40]"
/>
</div>
</template>
<script setup>
import { ref } from 'vue'
const page = ref(1)
const pageSize = ref(10)
const columns = ref([
{
title: '途经点',
key: 'age',
align: 'center',
},
{
title: '比对时间',
key: 'tags',
align: 'center',
},
{
title: '第一张巡检照片',
key: 'age',
align: 'center',
},
{
title: '上一次巡检照片',
key: 'age',
align: 'center',
},
{
title: '比对结果',
key: 'age',
align: 'center',
},
{
title: '第一张巡检照片拍摄时间',
key: 'age',
align: 'center',
},
{
title: '上一次巡检照片拍摄时间',
key: 'age',
align: 'center',
},
{
title: '相似度',
key: 'age',
align: 'center',
},
])
const data = ref([
{
age: '2025-06-01 10:00:00',
tags: ['nice'],
},
])
</script>

View File

@ -0,0 +1,98 @@
<template>
<div class="table-container">
<!-- 分页 -->
<div v-for="item in 7" :key="item" class="table-item">
<n-image
width="100%"
object-fit="cover"
class="item-image"
src="https://img1.baidu.com/it/u=3294211986,2810142789&fm=253&fmt=auto&app=138&f=JPEG?w=500&h=500"
/>
<div class="table-item-title">
<span>途经点</span>
<span>2025-06-01 10:00:00</span>
</div>
</div>
</div>
<div style="margin-top: 10px; display: flex; justify-content: flex-end">
<n-pagination
v-model:page="page"
v-model:page-size="pageSize"
:page-count="100"
show-size-picker
:page-sizes="[10, 20, 30, 40]"
/>
</div>
</template>
<script setup></script>
<style lang="scss" scoped>
.table-container {
height: 75%;
display: flex;
flex-wrap: wrap;
color: #fff;
.table-item {
flex-shrink: 0;
width: calc((100% - 30px) / 4);
height: calc((100% - 20px) / 2);
margin-right: 10px;
margin-bottom: 10px;
border-radius: 5px;
display: flex;
flex-direction: column;
align-items: center;
justify-content: space-between;
overflow: hidden;
.item-image {
// width: 100%;
height: 120px;
flex-shrink: 0;
/* 确保Naive UI的n-image组件完全填充 */
:deep(.n-image) {
// width: 100%;
display: block;
img {
// width: 100%;
// height: v-bind(imageHeight);
object-fit: cover;
}
}
}
.table-item-title {
width: 100%;
height: 42px;
display: flex;
justify-content: space-between;
align-items: center;
font-size: 14px;
background: url('@/assets/home-imgs/center-two-bg.png') no-repeat center center;
background-size: 100% 100%;
& span:nth-child(1) {
margin-left: 6px;
font-size: 16px;
color: #37e7ff;
}
& span:nth-child(2) {
margin-right: 6px;
color: #fff;
font-size: 14px;
}
}
}
.table-item:nth-child(4n) {
margin-right: 0;
}
}
</style>

View File

@ -58,14 +58,12 @@
</div>
<!-- 操作面板 -->
<n-drawer
resizable
placement="right"
:default-width="502"
v-model:show="operationPanelVisible"
class="operation-panel"
>
这里是机器人的操作面板
<n-drawer resizable placement="right" :default-width="502" v-model:show="operationPanelVisible">
<div class="operation-panel-container">
<div class="operation-panel-content">
<ControlDeck />
</div>
</div>
</n-drawer>
</template>
@ -77,11 +75,11 @@ import LeftTwo from './components/left-two.vue'
import CenterOne from './components/center-one.vue'
import CenterTwo from './components/center-two.vue'
import RightOne from './components/right-one.vue'
import RightTwo from './components/right-two.vue'
import RightTwo from './components/right-two/index.vue'
import ControlDeck from './components/control-deck.vue'
const appRef = ref(null) // DOM
const fullScreenVisible = ref(true) //
const fullScreenVisible = ref(false) //
// 使 useScale Hook setup()
const { baseWidth, baseHeight, scale } = useScale(appRef)
@ -146,20 +144,14 @@ const onHandleFullScreenToggle = (visible) => {
}
.full-screen-right1 {
grid-column: 9 / 13;
grid-row: 1 / 7;
grid-row: 1 / 6;
}
.full-screen-right2 {
grid-column: 9 / 13;
grid-row: 7 / 13;
grid-row: 6 / 13;
}
}
.n-drawer.n-drawer--right-placement {
top: 50% !important;
bottom: 10px !important;
right: 10px !important;
}
.pagination-container {
display: flex;
justify-content: flex-end;
@ -186,4 +178,22 @@ const onHandleFullScreenToggle = (visible) => {
line-height: 24px;
cursor: pointer;
}
.n-drawer {
background-color: rgba(0, 0, 0, 0.8);
}
.operation-panel-container {
height: 100%;
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
.operation-panel-content {
width: 90%;
background-color: rgba(0, 112, 190, 0.3);
color: #fff;
border: 1px solid #0070be;
}
}
</style>