环境监测页初步完善

This commit is contained in:
BianLzhaoMin 2025-04-10 14:45:33 +08:00
parent 208dca08a9
commit d6079942bd
34 changed files with 1743 additions and 40 deletions

View File

@ -11,7 +11,7 @@
"@jiaminghi/data-view": "^2.7.3",
"@types/echarts": "^4.4.3",
"core-js": "^3.6.4",
"echarts": "^4.6.0",
"echarts": "^5.4.0",
"element-ui": "2.15.13",
"js-cookie": "3.0.1",
"vue": "^2.6.11",

View File

@ -15,8 +15,8 @@ dependencies:
specifier: ^3.6.4
version: 3.6.4
echarts:
specifier: ^4.6.0
version: 4.6.0
specifier: ^5.4.0
version: 5.4.0
element-ui:
specifier: 2.15.13
version: 2.15.13(vue@2.6.11)
@ -4401,10 +4401,11 @@ packages:
safer-buffer: 2.1.2
dev: true
/echarts@4.6.0:
resolution: {integrity: sha512-xKkcr6v9UVOSF+PMuj7Ngt3bnzLwN1sSXWCvpvX+jYb3mePYsZnABq7wGkPac/m0nV653uGHXoHK8DCKCprdNg==}
/echarts@5.4.0:
resolution: {integrity: sha512-uPsO9VRUIKAdFOoH3B0aNg7NRVdN7aM39/OjovjO9MwmWsAkfGyeXJhK+dbRi51iDrQWliXV60/XwLA7kg3z0w==}
dependencies:
zrender: 4.2.0
tslib: 2.3.0
zrender: 5.4.0
dev: false
/ee-first@1.1.1:
@ -8824,6 +8825,10 @@ packages:
resolution: {integrity: sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==}
dev: true
/tslib@2.3.0:
resolution: {integrity: sha512-N82ooyxVNm6h1riLCoyS9e3fuJ3AMG2zIZs2Gd1ATcSFjSA23Q0fzjjZeh0jbJvWVDZ0cJT8yaNNaaXHzueNjg==}
dev: false
/tslib@2.6.3:
resolution: {integrity: sha512-xNvxJEOUiWPGhUuUdQgAJPKOOJfGnIyKySOc09XkKsgdUV/3E2zvwZYdejjmRgPCgcym1juLH3226yA7sEFJKQ==}
dev: true
@ -9633,6 +9638,8 @@ packages:
strip-indent: 2.0.0
dev: true
/zrender@4.2.0:
resolution: {integrity: sha512-YJ9hxt5uFincYYU3KK31+Ce+B6PJmYYK0Q9fQ6jOUAoC/VHbe4kCKAPkxKeT7jGTxrK5wYu18R0TLGqj2zbEOA==}
/zrender@5.4.0:
resolution: {integrity: sha512-rOS09Z2HSVGFs2dn/TuYk5BlCaZcVe8UDLLjj1ySYF828LATKKdxuakSZMvrDz54yiKPDYVfjdKqcX8Jky3BIA==}
dependencies:
tslib: 2.3.0
dev: false

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.4 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.4 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.9 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.9 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 7.2 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.7 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.4 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.8 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.4 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 489 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 772 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 469 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 752 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 491 B

View File

@ -28,18 +28,19 @@ export default {
height: 100%;
.title_bg {
width: 100%;
height: 38px;
height: 32px;
background: url('@/assets/image/common/box_title_bg.png') no-repeat;
background-size: 100% 100%;
color: #fff;
line-height: 38px;
line-height: 32px;
padding-left: 40px;
letter-spacing: 2px;
font-size: 16px;
}
.charts-content {
width: 100%;
height: calc(100% - 38px);
height: calc(100% - 32px);
}
}
</style>

View File

@ -0,0 +1,224 @@
<template>
<!-- 24小时空气质量数据分析 -->
<div style="height: 100%">
<ChartsBox :boxTitle="`24小时空气质量数据分析`">
<div ref="chartContainer" class="container"> </div>
</ChartsBox>
</div>
</template>
<script>
import ChartsBox from '@/components/ChartsBox/index'
import * as echarts from 'echarts'
require('echarts/theme/macarons')
export default {
components: { ChartsBox },
data() {
return {
chart: null,
}
},
mounted() {
this.$nextTick(() => {
this.initChart()
})
},
beforeDestroy() {
if (!this.chart) {
return
}
this.chart.dispose()
this.chart = null
window.removeEventListener('resize', this.handleResize)
if (this.chart) {
this.chart.dispose()
this.chart = null
}
},
methods: {
initChart() {
// 使 ref container
const container = this.$refs.chartContainer
this.chart = echarts.init(container, 'macarons')
this.chart.setOption({
xAxis: {
type: 'category',
data: [
'00:00',
'03:00',
'06:00',
'09:00',
'12:00',
'15:00',
'18:00',
'21:00',
'24:00',
],
boundaryGap: false,
axisTick: { show: true },
axisLabel: { color: '#4494db' },
axisLine: { lineStyle: { color: '#4494db' } },
splitLine: {
// x线线
show: false,
},
},
yAxis: {
axisTick: { show: false },
axisLine: { lineStyle: { color: '#4494db' } },
splitLine: {
lineStyle: {
type: 'dashed',
color: 'rgba(68, 148, 219, 0.3)',
width: 1,
},
},
},
grid: {
left: 10,
right: 15,
bottom: 5, //
top: 10, //
containLabel: true,
},
legend: {
//
right: 20,
top: 10,
icon: 'circle',
itemWidth: 10,
itemHeight: 10,
textStyle: {
color: '#fff',
fontSize: 12,
},
data: ['PM2.5', 'PM10'],
},
tooltip: {
trigger: 'axis',
axisPointer: {
type: 'cross',
label: {
//
backgroundColor: '#6a7985',
},
},
padding: [5, 10],
formatter: function (params) {
let res = params[0].name + '<br>'
params.forEach((item) => {
res += `${item.marker} ${item.seriesName}: <strong>${item.value}</strong><br>`
})
return res
},
},
series: [
{
name: 'PM2.5',
type: 'line',
smooth: true,
data: [30, 40, 35, 45, 50, 32, 36, 43, 49],
itemStyle: { color: '#306FFF' },
lineStyle: { color: '#306FFF', width: 2 },
areaStyle: {
color: new echarts.graphic.LinearGradient(
0,
0,
0,
1,
[
{
offset: 0,
color: 'rgba(48, 111, 255, 0.5)',
},
{
offset: 1,
color: 'rgba(48, 111, 255, 0.1)',
},
],
),
},
animationDuration: 3000,
symbol: 'circle',
symbolSize: 6,
showSymbol: false,
emphasis: {
itemStyle: {
color: '#ffeb3b',
borderColor: '#fff',
borderWidth: 2,
},
},
},
{
name: 'PM10',
type: 'line',
smooth: true,
data: [27, 36, 31, 48, 42, 36, 22, 39, 52],
itemStyle: { color: '#15a0c6' },
lineStyle: { color: '#15a0c6', width: 2 },
areaStyle: {
color: new echarts.graphic.LinearGradient(
0,
0,
0,
1,
[
{
offset: 0,
color: 'rgba(21, 160, 198, 0.5)',
},
{
offset: 1,
color: 'rgba(21, 160, 198, 0.1)',
},
],
),
},
animationDuration: 3000,
symbol: 'circle',
symbolSize: 6,
showSymbol: false,
emphasis: {
itemStyle: {
color: '#ffeb3b',
borderColor: '#fff',
borderWidth: 2,
},
},
},
],
})
//
window.addEventListener('resize', this.handleResize)
setTimeout(() => {
this.chart.dispatchAction({
type: 'highlight',
seriesIndex: 0,
})
}, 500)
},
handleResize() {
if (this.chart) {
this.chart.resize()
}
},
},
}
</script>
<style lang="scss" scoped>
.container {
height: 103%;
width: 100%;
display: flex;
justify-content: space-around;
align-items: center;
color: #fff;
z-index: 9;
}
</style>

View File

@ -0,0 +1,90 @@
<template>
<!-- 环境监测设备列表 -->
<div style="height: 100%">
<ChartsBox :boxTitle="`实时环境信息`">
<div class="container">
<div
v-for="(item, index) in envInfoList"
:key="index"
class="env-item"
>
<img :src="item.imgPath" alt="" />
<div class="info">
<div>
<span style="font-size: 20px; font-weight: bold">
{{ item.count }}
</span>
<span> {{ item.code }}</span>
</div>
<div style="margin-top: 6px; font-size: 14px">
{{ item.name }}
</div>
</div>
</div>
</div>
</ChartsBox>
</div>
</template>
<script>
import ChartsBox from '@/components/ChartsBox/index'
export default {
components: { ChartsBox },
data() {
return {
envInfoList: [
{
name: '风速',
imgPath: require('@/assets/image/env-img/env-1.png'),
count: 30,
code: 'M/s',
},
{
name: '温度',
imgPath: require('@/assets/image/env-img/env-2.png'),
count: 30,
code: '℃',
},
{
name: '湿速',
imgPath: require('@/assets/image/env-img/env-3.png'),
count: 30,
code: '%',
},
{
name: '噪音',
imgPath: require('@/assets/image/env-img/env-4.png'),
count: 30,
code: '分贝',
},
],
}
},
}
</script>
<style lang="scss" scoped>
.container {
height: 100%;
display: flex;
justify-content: space-around;
align-items: center;
color: #fff;
color: #b5d3f4;
font-size: 16px;
transform: translateY(10px);
.env-item {
display: flex;
align-items: center;
img {
width: 66px;
height: 54px;
}
.info {
margin-left: 6px;
}
}
}
</style>

View File

@ -0,0 +1,402 @@
<template>
<!-- 环境监测设备列表 -->
<div style="height: 100%">
<ChartsBox :boxTitle="`实时空气质量`">
<div class="container">
<div class="pie-container">
<div class="air-qu-item">
<div class="chart" ref="chart1"> </div>
<div class="dz-sm"> PM2.5 </div>
</div>
<div class="air-qu-item">
<div class="chart chart2" ref="chart2"></div>
<div class="dz-bg"> 空气质量 </div>
</div>
<div class="air-qu-item">
<div class="chart" ref="chart3"></div>
<div class="dz-sm"> PM2.5 </div>
</div>
</div>
<div class="scale-box">
<div class="icon-box">
<img
v-for="(item, index) in iconList"
:key="index"
:src="item"
alt=""
/>
</div>
<div class="line"></div>
<div class="num-box">
<span v-for="item in numList" :key="item">
{{ item }}
</span>
</div>
</div>
</div>
</ChartsBox>
</div>
</template>
<script>
import ChartsBox from '@/components/ChartsBox/index'
import * as echarts from 'echarts'
require('echarts/theme/macarons')
export default {
components: { ChartsBox },
data() {
return {
chart1: null,
chart2: null,
chart3: null,
iconList: [
require('@/assets/image/env-img/levelA.png'),
require('@/assets/image/env-img/levelB.png'),
require('@/assets/image/env-img/levelC.png'),
require('@/assets/image/env-img/levelD.png'),
require('@/assets/image/env-img/levelE.png'),
require('@/assets/image/env-img/levelF.png'),
],
numList: [0, 50, 100, 150, 200, 300, 500],
}
},
mounted() {
this.$nextTick(() => {
this.initChart()
})
},
beforeDestroy() {
if (!this.chart) {
return
}
this.chart.dispose()
this.chart = null
window.removeEventListener('resize', this.handleResize)
if (this.chart) {
this.chart.dispose()
this.chart = null
}
},
methods: {
initChart() {
// 使 ref container
const container1 = this.$refs.chart1
const container2 = this.$refs.chart2
const container3 = this.$refs.chart3
this.chart1 = echarts.init(container1, 'macarons')
this.chart1.setOption({
series: [
{
type: 'pie',
radius: ['70%', '90%'],
center: ['50%', '50%'],
startAngle: 225,
label: {
show: true,
position: 'center',
formatter: '{c}',
color: '#FFFFFF',
fontSize: 18,
fontWeight: 'bold',
},
color: [
new echarts.graphic.LinearGradient(0, 0, 0, 1, [
{
offset: 0,
color: '#08dad1',
},
{
offset: 1,
color: '#0b7ddb',
},
]),
'transparent',
],
labelLine: {
normal: {
show: false,
},
},
data: [
{
value: 50,
label: { show: true },
},
{
value: 50,
label: { show: false },
itemStyle: { color: 'rgba(52, 68, 93,0.5)' }, //
},
{
value: 30,
label: { show: false },
itemStyle: { color: 'rgba(255,255,255,0.0)' }, //
},
],
//
graphic: [
{
type: 'text',
left: 'center',
top: 'center',
style: {
text: '50', //
fill: '#FFFFFF', //
fontSize: 28,
fontWeight: 'bold',
textAlign: 'center',
},
},
],
},
],
})
this.chart2 = echarts.init(container2, 'macarons')
this.chart2.setOption({
series: [
{
type: 'pie',
radius: ['80%', '100%'],
center: ['50%', '50%'],
startAngle: 225,
label: {
show: true,
position: 'center',
formatter: '{c}',
color: '#FFFFFF',
fontSize: 18,
fontWeight: 'bold',
},
color: [
new echarts.graphic.LinearGradient(0, 0, 0, 1, [
{
offset: 0,
color: '#08dad1',
},
{
offset: 1,
color: '#0b7ddb',
},
]),
'transparent',
],
labelLine: {
normal: {
show: false,
},
},
data: [
{
value: 40,
label: { show: true },
},
{
value: 60,
label: { show: false },
itemStyle: { color: 'rgba(52, 68, 93,0.5)' }, //
},
{
value: 30,
label: { show: false },
itemStyle: { color: 'rgba(255,255,255,0.0)' }, //
},
],
//
graphic: [
{
type: 'text',
left: 'center',
top: 'center',
style: {
text: '50', //
fill: '#FFFFFF', //
fontSize: 28,
fontWeight: 'bold',
textAlign: 'center',
},
},
],
},
],
})
this.chart3 = echarts.init(container3, 'macarons')
this.chart3.setOption({
series: [
{
type: 'pie',
radius: ['70%', '90%'],
center: ['50%', '50%'],
startAngle: 225,
label: {
show: true,
position: 'center',
formatter: '{c}',
color: '#FFFFFF',
fontSize: 18,
fontWeight: 'bold',
},
color: [
new echarts.graphic.LinearGradient(0, 0, 0, 1, [
{
offset: 0,
color: '#08dad1',
},
{
offset: 1,
color: '#0b7ddb',
},
]),
'transparent',
],
labelLine: {
normal: {
show: false,
},
},
data: [
{
value: 60,
label: { show: true },
},
{
value: 50,
label: { show: false },
itemStyle: { color: 'rgba(52, 68, 93,0.5)' }, //
},
{
value: 30,
label: { show: false },
itemStyle: { color: 'rgba(255,255,255,0.0)' }, //
},
],
//
graphic: [
{
type: 'text',
left: 'center',
top: 'center',
style: {
text: '50', //
fill: '#FFFFFF', //
fontSize: 28,
fontWeight: 'bold',
textAlign: 'center',
},
},
],
},
],
})
//
window.addEventListener('resize', this.handleResize)
},
handleResize() {
if (this.chart1) {
this.chart1.resize()
}
if (this.chart2) {
this.chart2.resize()
}
if (this.chart3) {
this.chart2.resize()
}
},
},
}
</script>
<style lang="scss" scoped>
.container {
height: 100%;
width: 100%;
display: flex;
flex-direction: column;
justify-content: space-around;
align-items: center;
color: #fff;
z-index: 9999;
.pie-container {
width: 100%;
display: flex;
justify-content: space-around;
align-items: center;
.air-qu-item {
display: flex;
flex-direction: column;
align-items: center;
}
.chart {
width: 110px;
height: 80px;
}
.chart2 {
width: 130px;
}
.dz-sm {
width: 110px;
height: 29px;
background: url('@/assets/image/env-img/dz_sm.png') no-repeat;
background-size: 100% 100%;
font-size: 14px;
line-height: 20px;
text-align: center;
}
.dz-bg {
width: 128px;
height: 35px;
background: url('@/assets/image/env-img/dz_sm.png') no-repeat;
background-size: 100% 100%;
font-size: 14px;
line-height: 28px;
text-align: center;
}
}
.scale-box {
width: 100%;
.icon-box {
width: 100%;
display: flex;
align-content: center;
justify-content: space-around;
img {
width: 46px;
height: 46px;
object-fit: contain;
}
}
.num-box {
width: 100%;
display: flex;
align-content: center;
justify-content: space-between;
span {
font-size: 16px;
}
}
.line {
border-top: 1px dashed #0a77dd;
}
}
}
</style>

View File

@ -0,0 +1,207 @@
<template>
<!-- 环境监测设备列表 -->
<div style="height: 100%">
<ChartsBox :boxTitle="`24小时数据分析`">
<div ref="chartContainer" class="container"> </div>
</ChartsBox>
</div>
</template>
<script>
import ChartsBox from '@/components/ChartsBox/index'
import * as echarts from 'echarts'
require('echarts/theme/macarons')
export default {
components: { ChartsBox },
data() {
return {
chart: null,
}
},
mounted() {
this.$nextTick(() => {
this.initChart()
})
},
beforeDestroy() {
if (!this.chart) {
return
}
this.chart.dispose()
this.chart = null
window.removeEventListener('resize', this.handleResize)
if (this.chart) {
this.chart.dispose()
this.chart = null
}
},
methods: {
initChart() {
// 使 ref container
const container = this.$refs.chartContainer
this.chart = echarts.init(container, 'macarons')
this.chart.setOption({
xAxis: {
type: 'category',
data: [
'00:00',
'03:00',
'06:00',
'09:00',
'12:00',
'15:00',
'18:00',
'21:00',
'24:00',
],
boundaryGap: false,
axisTick: { show: true },
axisLabel: { color: '#4494db' },
axisLine: {
lineStyle: { color: '#4494db' },
},
// x线线
},
yAxis: {
axisTick: { show: false },
axisLine: {
lineStyle: { color: '#4494db' },
},
// y线线
splitLine: {
lineStyle: {
type: 'dashed',
color: 'rgba(68, 148, 219, 0.3)',
width: 1,
},
},
},
grid: {
left: 10,
right: 15,
bottom: 0,
top: 12,
containLabel: true,
},
tooltip: {
trigger: 'axis',
axisPointer: { type: 'cross' },
padding: [5, 10],
},
series: [
{
name: '数量',
type: 'line',
smooth: true, // 线
data: [
{ value: 320, name: '00:00' },
{ value: 523, name: '03:00' },
{ value: 320, name: '06:00' },
{ value: 100, name: '09:00' },
{ value: 320, name: '12:00' },
{ value: 300, name: '15:00' },
{ value: 320, name: '18:00' },
{ value: 23, name: '21:00' },
{ value: 66, name: '24:00' },
],
itemStyle: {
color: '#15a0c6',
},
lineStyle: {
color: '#15a0c6',
width: 2,
},
areaStyle: {
color: new echarts.graphic.LinearGradient(
0,
0,
0,
1,
[
{
offset: 0,
color: 'rgba(21, 160, 198, 0.5)',
},
{
offset: 1,
color: 'rgba(21, 160, 198, 0.1)',
},
],
),
},
// 线
animationDuration: 3000,
animationEasing: 'cubicInOut',
symbol: 'circle',
symbolSize: 6,
showSymbol: false, //
//
emphasis: {
scale: true,
itemStyle: {
color: '#ffeb3b',
borderColor: '#fff',
borderWidth: 2,
},
},
// 线
lineAnimation: {
duration: 3000,
easing: 'cubicInOut',
delay: function (idx) {
return idx * 100
},
},
effect: {
show: true,
period: 4,
trailLength: 0.2,
symbol: 'circle',
symbolSize: 6,
loop: true,
},
},
],
//
animation: {
duration: 3000,
easing: 'cubicInOut',
seriesKey: 'line',
animationDelay: function (idx) {
return idx * 100
},
},
})
//
window.addEventListener('resize', this.handleResize)
setTimeout(() => {
this.chart.dispatchAction({
type: 'highlight',
seriesIndex: 0,
})
}, 500)
},
handleResize() {
if (this.chart) {
this.chart.resize()
}
},
},
}
</script>
<style lang="scss" scoped>
.container {
height: 100%;
width: 100%;
display: flex;
justify-content: space-around;
align-items: center;
color: #fff;
z-index: 9999;
}
</style>

View File

@ -0,0 +1,90 @@
<template>
<!-- 环境监测设备列表 -->
<div style="height: 100%; position: relative">
<ChartsBox :boxTitle="`环境监测设备列表`">
<div class="container">
<div
class="device-item"
v-for="(item, index) in deviceList"
:key="index"
>
<img
:src="
item.onLine
? `${require('@/assets/image/env-img/line_big.png')}`
: `${require('@/assets/image/env-img/offline_big.png')}`
"
alt=""
/>
<span :style="item.onLine ? 'color:#71C4FF' : ''">
{{ item.name }}
</span>
<span :style="item.onLine ? 'color:#71C4FF' : ''">
{{ item.code }}
</span>
</div>
</div>
</ChartsBox>
<div class="case">
<img src="@/assets/image/env-img/line.png" alt="" />
<span>在线</span>
<img src="@/assets/image/env-img/offline.png" alt="" />
<span>离线</span>
</div>
</div>
</template>
<script>
import ChartsBox from '@/components/ChartsBox/index'
export default {
components: { ChartsBox },
data() {
return {
deviceList: [
{ name: '1号设备', code: 'YKD-231', onLine: true },
{ name: '2号设备', code: 'YKD-233', onLine: true },
{ name: '3号设备', code: 'YKD-232', onLine: false },
{ name: '4号设备', code: 'YKD-236', onLine: true },
],
}
},
}
</script>
<style lang="scss" scoped>
.container {
height: 100%;
display: flex;
justify-content: space-around;
align-items: center;
color: #fff;
font-size: 12px;
transform: translateY(10px);
.device-item {
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
img {
width: 30px;
height: 30px;
}
}
}
.case {
font-size: 12px;
position: absolute;
top: 10px;
right: 10px;
display: flex;
align-items: center;
span {
padding: 0 12px 0 6px;
}
}
</style>

View File

@ -0,0 +1,291 @@
<template>
<!-- 24小时数据分析 -->
<div style="height: 100%">
<ChartsBox :boxTitle="`24小时数据分析`">
<div ref="chartContainer" class="container"></div>
</ChartsBox>
</div>
</template>
<script>
import ChartsBox from '@/components/ChartsBox/index'
import * as echarts from 'echarts'
require('echarts/theme/macarons')
export default {
components: { ChartsBox },
data() {
return {
chart: null,
}
},
mounted() {
this.$nextTick(() => {
this.initChart()
})
},
beforeDestroy() {
if (!this.chart) {
return
}
this.chart.dispose()
this.chart = null
window.removeEventListener('resize', this.handleResize)
if (this.chart) {
this.chart.dispose()
this.chart = null
}
},
methods: {
initChart() {
// 使 ref container
const container = this.$refs.chartContainer
this.chart = echarts.init(container, 'macarons')
this.chart.setOption({
tooltip: {
trigger: 'item',
formatter: '{b}: {c} ({d}%)',
},
legend: {
data: [
'优',
'良',
'轻度污染',
'中度污染',
'重度污染',
'严重污染',
],
right: '4%',
top: 'middle',
orient: 'vertical',
itemGap: 20,
textStyle: {
color: '#fff', //
fontSize: 13, //
padding: [0, 0, 0, 5], // [,,,]
},
itemStyle: {
//
borderWidth: 0, //
borderRadius: 0, //
},
itemWidth: 14, //
itemHeight: 14,
formatter: (name) => {
// value
const data = this.chart.getOption().series[0].data
const item = data.find((item) => item.name === name)
if (item) {
const total = data.reduce(
(sum, item) => sum + item.value,
0,
)
const percent = (
(item.value / total) *
100
).toFixed(1)
if (
(name === '优' || name === '良') &&
percent.length > 3
) {
return `${name} ${percent}% ${item.value}`
}
if (
(name === '优' || name === '良') &&
percent.length < 4
) {
return `${name} ${percent}% ${item.value}`
}
if (
(name !== '优' || name !== '良') &&
percent > 10
) {
return `${name} ${percent}% ${item.value}`
}
if (
(name !== '优' || name !== '良') &&
percent < 10
) {
return `${name} ${percent}% ${item.value}`
}
}
return name
},
},
series: [
{
name: '空气质量分布',
type: 'pie',
radius: ['45%', '59%'], //
center: ['25%', '50%'], //
avoidLabelOverlap: false,
label: {
show: false, //
},
labelLine: {
show: false, // 线
},
data: [
{
value: 320,
name: '优',
itemStyle: { color: '#0ffd94' },
},
{
value: 240,
name: '良',
itemStyle: { color: '#17f2ff' },
},
{
value: 149,
name: '轻度污染',
itemStyle: { color: '#f6cf1a' },
},
{
value: 100,
name: '中度污染',
itemStyle: { color: '#ee860e' },
},
{
value: 59,
name: '重度污染',
itemStyle: { color: '#e3021a' },
},
{
value: 59,
name: '严重污染',
itemStyle: { color: '#97642e' },
},
],
// animationType: 'scale',
animationEasing: 'cubicInOut',
animationDuration: 1000,
emphasis: {
//
itemStyle: {
shadowBlur: 10,
shadowOffsetX: 0,
shadowColor: 'rgba(0, 0, 0, 0.5)',
},
},
itemStyle: {
borderRadius: 20, //
borderWidth: 4,
borderColor: '#01284d',
},
},
// 1
{
type: 'pie',
radius: ['65%', '68%'],
center: ['25%', '50%'],
silent: true, //
label: { show: false },
data: [
{
value: 10,
itemStyle: { color: '#04356c' },
},
{
value: 10,
itemStyle: { color: '#04356c' },
},
{
value: 10,
itemStyle: { color: '#04356c' },
},
{
value: 10,
itemStyle: { color: '#04356c' },
},
{
value: 10,
itemStyle: { color: '#04356c' },
},
{
value: 10,
itemStyle: { color: '#04356c' },
},
{
value: 10,
itemStyle: { color: '#04356c' },
},
{
value: 10,
itemStyle: { color: '#04356c' },
},
{
value: 10,
itemStyle: { color: '#04356c' },
},
{
value: 10,
itemStyle: { color: '#04356c' },
},
],
},
// 2线
{
type: 'pie',
radius: ['63%', '65%'],
center: ['25%', '50%'],
silent: true,
label: { show: false },
data: [
{
value: 1,
itemStyle: {
color: 'transparent',
borderColor: 'rgba(1,40,77,0.5)',
borderWidth: 1,
borderType: 'dashed', // 线
},
},
],
},
// 3
{
type: 'pie',
radius: ['70%', '76%'],
center: ['25%', '50%'],
silent: true,
label: { show: false },
data: [
{
value: 1,
itemStyle: {
color: 'transparent',
borderColor: '#01284d',
borderWidth: 2,
},
},
],
},
],
})
//
window.addEventListener('resize', this.handleResize)
},
handleResize() {
if (this.chart) {
this.chart.resize()
}
},
},
}
</script>
<style lang="scss" scoped>
.container {
height: 100%;
width: 100%;
z-index: 2;
}
</style>

View File

@ -0,0 +1,177 @@
<template>
<!-- 近七日空气质量详情 -->
<div style="height: 100%">
<ChartsBox :boxTitle="`近七日空气质量详情`">
<div class="container">
<!-- <div class="feel-box"></div> -->
<dv-scroll-board class="dv-scr-board" :config="config" />
</div>
</ChartsBox>
</div>
</template>
<script>
import ChartsBox from '@/components/ChartsBox/index'
export default {
components: { ChartsBox },
data() {
return {
config: {
data: [
[
"<img src='" +
require('@/assets/image/env-img/round.png') +
"' class='table-img'>",
'2025-03-29',
"<div class='air-quality'>空气质量 <img src='" +
require('@/assets/image/env-img/air-A.png') +
"' class='table-img'></div>",
],
[
"<img src='" +
require('@/assets/image/env-img/round.png') +
"' class='table-img'>",
'2025-03-29',
"<div class='air-quality'>空气质量 <img src='" +
require('@/assets/image/env-img/air-A.png') +
"' class='table-img'></div>",
],
[
"<img src='" +
require('@/assets/image/env-img/round.png') +
"' class='table-img'>",
'2025-03-29',
"<div class='air-quality'>空气质量 <img src='" +
require('@/assets/image/env-img/air-B.png') +
"' class='table-img'></div>",
],
[
"<img src='" +
require('@/assets/image/env-img/round.png') +
"' class='table-img'>",
'2025-03-29',
"<div class='air-quality'>空气质量 <img src='" +
require('@/assets/image/env-img/air-B.png') +
"' class='table-img'></div>",
],
[
"<img src='" +
require('@/assets/image/env-img/round.png') +
"' class='table-img'>",
'2025-03-29',
"<div class='air-quality'>空气质量 <img src='" +
require('@/assets/image/env-img/air-C.png') +
"' class='table-img'></div>",
],
[
"<img src='" +
require('@/assets/image/env-img/round.png') +
"' class='table-img'>",
'2025-03-29',
"<div class='air-quality'>空气质量 <img src='" +
require('@/assets/image/env-img/air-C.png') +
"' class='table-img'></div>",
],
[
"<img src='" +
require('@/assets/image/env-img/round.png') +
"' class='table-img'>",
'2025-03-29',
"<div class='air-quality'>空气质量 <img src='" +
require('@/assets/image/env-img/air-C.png') +
"' class='table-img'></div>",
],
[
"<img src='" +
require('@/assets/image/env-img/round.png') +
"' class='table-img'>",
'2025-03-29',
"<div class='air-quality'>空气质量 <img src='" +
require('@/assets/image/env-img/air-A.png') +
"' class='table-img'></div>",
],
[
"<img src='" +
require('@/assets/image/env-img/round.png') +
"' class='table-img'>",
'2025-03-29',
"<div class='air-quality'>空气质量 <img src='" +
require('@/assets/image/env-img/air-C.png') +
"' class='table-img'></div>",
],
],
rowNum: 6, //
// headerHeight: 35,
headerBGC: 'rgba(21, 53, 81, 0.2)', //
oddRowBGC: '', //
evenRowBGC: '', //
columnWidth: [40],
align: ['center'],
hoverPause: true,
waitTime: 5000,
},
}
},
}
</script>
<style lang="scss" scoped>
.container {
height: 100%;
.dv-scr-board {
width: 100%;
height: 100%;
background: linear-gradient(
to bottom right,
rgba(21, 53, 81, 0.2),
rgba(6, 30, 66, 0.7)
);
}
}
::v-deep .img-box {
display: flex;
align-items: center;
.three-img {
transform: translateX(10px);
}
.red-img {
transform: translateX(3px);
}
}
::v-deep .dv-scroll-board .rows .ceil {
display: flex;
align-items: center;
justify-content: center;
}
::v-deep .air-quality {
height: 100%;
display: flex;
align-items: center;
img {
margin-left: 4px;
}
}
// ::v-deep .row-item ::after {
// content: '';
// position: absolute;
// bottom: 0;
// left: 0;
// width: 100%;
// height: 1px; /* */
// background: linear-gradient(
// to right,
// transparent 10%,
// /* / */ #4facfe 40%,
// /* */ #4facfe 70%,
// /* */ transparent 70% /* / */
// );
// }
</style>

View File

@ -0,0 +1,28 @@
<template>
<!-- 天气预报 -->
<div style="height: 100%">
<ChartsBox :boxTitle="`天气预报`">
<div class="container"> </div>
</ChartsBox>
</div>
</template>
<script>
import ChartsBox from '@/components/ChartsBox/index'
export default {
components: { ChartsBox },
data() {
return {}
},
}
</script>
<style lang="scss" scoped>
.container {
height: 100%;
display: flex;
justify-content: space-around;
align-items: center;
color: #fff;
}
</style>

View File

@ -0,0 +1,119 @@
<template>
<div style="height: 100%">
<ChartsBox :boxTitle="`报警信息`">
<div class="container">
<!-- <div class="feel-box"></div> -->
<dv-scroll-board class="dv-scr-board" :config="config" />
</div>
</ChartsBox>
</div>
</template>
<script>
import ChartsBox from '@/components/ChartsBox/index'
export default {
components: { ChartsBox },
data() {
return {
config: {
data: [
[
"<img src='" +
require('@/assets/image/pro-view/blue.png') +
"' class='table-img'>",
'组件1',
'dev-1',
"<span class='colorGrass'>↑75%</span>",
],
[
"<img src='" +
require('@/assets/image/pro-view/blue.png') +
"' class='table-img'>",
'组件2',
'dev-2',
"<span class='colorRed'>↓33%</span>",
],
[
"<div class='img-box'><img src='" +
require('@/assets/image/pro-view/red.png') +
"' class='table-img red-img'><img src='" +
require('@/assets/image/pro-view/three.png') +
"' class='three-img'></div>",
'组件3',
'dev-3',
"<span class='colorGrass'>↑100%</span>",
],
[
"<img src='" +
require('@/assets/image/pro-view/blue.png') +
"' class='table-img'>",
'组件4',
'rea-1',
"<span class='colorGrass'>↑94%</span>",
],
[
"<img src='" +
require('@/assets/image/pro-view/blue.png') +
"' class='table-img'>",
'组件5',
'rea-2',
"<span class='colorGrass'>↑95%</span>",
],
[
"<img src='" +
require('@/assets/image/pro-view/blue.png') +
"' class='table-img'>",
'组件6',
'fix-2',
"<span class='colorGrass'>↑63%</span>",
],
],
rowNum: 5, //
headerHeight: 35,
headerBGC: 'rgba(21, 53, 81, 0.2)', //
oddRowBGC: '', //
evenRowBGC: '', //
columnWidth: [80],
align: ['center'],
hoverPause: true,
waitTime: 5000,
},
}
},
}
</script>
<style lang="scss" scoped>
.container {
height: 100%;
.dv-scr-board {
width: 100%;
height: 100%;
background: linear-gradient(
to bottom right,
rgba(21, 53, 81, 0.2),
rgba(6, 30, 66, 0.7)
);
}
}
::v-deep .img-box {
display: flex;
align-items: center;
.three-img {
transform: translateX(10px);
}
.red-img {
transform: translateX(3px);
}
}
::v-deep .dv-scroll-board .rows .ceil {
display: flex;
align-items: center;
justify-content: center;
}
</style>

View File

@ -1,20 +1,59 @@
<template>
<!-- 环境监测 -->
<div class="home-env-monitor">
<div class="env-1">1</div>
<div class="env-2">2</div>
<div class="env-3">3</div>
<div class="env-4">4</div>
<div class="env-5">5</div>
<div class="env-6">6</div>
<div class="env-7">7</div>
<div class="env-8">8</div>
<div class="env-9">9</div>
<div class="env-1">
<LeftOneModel />
</div>
<div class="env-2">
<CenterOneModel />
</div>
<div class="env-3">
<RightOneModel />
</div>
<div class="env-4">
<LeftTwoModel />
</div>
<div class="env-5">
<CenterTwoModel />
</div>
<div class="env-6">
<RightTwoModel />
</div>
<div class="env-7">
<LeftThreeModel />
</div>
<div class="env-8">
<CenterThreeModel />
</div>
<div class="env-9">
<CenterFourModel />
</div>
</div>
</template>
<script>
export default {}
import LeftOneModel from './components/left-one-model.vue' // 1
import LeftTwoModel from './components/left-two-model.vue' // 2
import LeftThreeModel from './components/left-three-model.vue' // 3
import CenterOneModel from './components/center-one-model.vue' // 1
import CenterTwoModel from './components/center-two-model.vue' // 2
import CenterThreeModel from './components/center-three-model.vue' // 3
import CenterFourModel from './components/center-four-model.vue' // 4
import RightOneModel from './components/right-one-model.vue' // 1
import RightTwoModel from './components/right-two-model.vue' // 2
export default {
components: {
LeftOneModel,
LeftTwoModel,
LeftThreeModel,
CenterOneModel,
CenterTwoModel,
CenterThreeModel,
CenterFourModel,
RightOneModel,
RightTwoModel,
},
}
</script>
<style lang="scss" scoped>
@ -24,44 +63,45 @@ export default {}
font-size: 30px;
color: #fff;
display: grid;
grid-template-rows: repeat(9, 1fr);
grid-template-columns: repeat(9, 1fr);
grid-template-rows: repeat(12, 1fr);
grid-template-columns: repeat(14, 1fr);
gap: 10px;
.env-1 {
grid-column: 1 / 3;
grid-row: 1 / 2;
grid-column: 1 / 5;
grid-row: 1 / 3;
}
.env-2 {
grid-column: 4 / 7;
grid-column: 5 / 11;
grid-row: 1 / 3;
}
.env-3 {
grid-column: 7 / 9;
grid-row: 1 / 3;
grid-column: 11 / 15;
grid-row: 1 / 8;
}
.env-4 {
grid-column: 1 / 3;
grid-row: 3 / 6;
grid-column: 1 / 5;
grid-row: 3 / 8;
}
.env-5 {
grid-column: 2 / 3;
grid-row: 2/ 3;
grid-column: 5 / 11;
grid-row: 3/ 6;
}
.env-6 {
grid-column: 3 / 3;
grid-row: 2/ 3;
grid-column: 11 / 15;
grid-row: 8/ 13;
}
.env-7 {
grid-column: 1 / 3;
grid-row: 7 / 9;
grid-column: 1 / 5;
grid-row: 8 / 13;
}
.env-8 {
grid-column: 2 / 3;
grid-row: 3/ 3;
grid-column: 5 / 11;
grid-row: 6/ 10;
}
.env-9 {
grid-column: 3 / 3;
grid-row: 3 / 3;
grid-column: 5 / 11;
grid-row: 10 / 13;
}
}
</style>

View File

@ -377,6 +377,8 @@ export default {
center center;
background-size: cover;
position: relative;
z-index: 99;
// background-position: center;
.nav-box {
@ -389,6 +391,15 @@ export default {
display: flex;
align-items: center;
cursor: pointer;
transition: transform 0.5s ease-in-out !important; /* 柔和缓慢的过渡效果 */
transform-origin: center !important; /* 从中心点开始缩放 */
}
.nav-item:hover {
transform: scale(
1.05
) !important; /* 放大5%,可以根据需要调整 */
box-shadow: 0 4px 12px rgba(0, 0, 0, 0.1) !important; /* 可选:添加阴影增强立体感 */
}
.nav-icon {
@ -430,6 +441,22 @@ export default {
}
}
.left-nav::before {
content: '';
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
background-color: rgba(0, 0, 0, 0.5);
transition: background-color 0.3s ease; /* 悬停动画 */
}
/* 鼠标悬停时加深遮罩 */
.left-nav:hover::before {
background-color: rgba(0, 0, 0, 0.5);
}
.floating-box {
position: absolute;
top: 50%;