Files
fengjie-datascreen/src/views/home/components/box-1.vue
2024-12-27 13:51:47 +08:00

441 lines
12 KiB
Vue
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
<template>
<div class="box-2">
<Title1 title="景区信息">
<template #right>
<img class="more" src="@/assets/images/more.png" />
</template>
</Title1>
<div class="flex pt-20">
<div
class="item"
:class="{ core: index == 0, queue: index == 1, congestion: index == 2 }"
v-for="(item, index) in homeData?.scenicSpot"
:key="index"
>
<span class="label">{{ item.name }}</span>
<div class="flex align-end">
<countup :end-val="item.value" /><span class="unit"></span>
</div>
</div>
</div>
<div class="flex pt-20">
<div class="box">
<Title2 title="景区排队人数" />
<div class="statistic">
<div class="statistic-item">
<span class="statistic-title">三峡之巅</span>
<span class="statistic-value">
<span class="prefix">排队</span>
<span class="value">100</span>
<span class="suffix"></span>
</span>
</div>
<div class="statistic-item">
<span class="statistic-title">白帝城</span>
<span class="statistic-value">通畅</span>
</div>
<div class="statistic-item">
<span class="statistic-title">天坑地缝</span>
<span class="statistic-value">通畅</span>
</div>
<div class="statistic-item">
<span class="statistic-title">永安宫</span>
<span class="statistic-value">通畅</span>
</div>
</div>
<div class="flex rela">
<Title3 title="景区排队人数" />
<div class="dropdown">
<Dropdown
label="选择排队景区"
:options="[
{ label: '山峡之巅', value: 100 },
{ label: '白帝城', value: 100 },
{ label: '龙桥河', value: 100 }
]"
/>
</div>
</div>
<div class="pt-20">
<Line
:width="370"
:height="140"
:config="{ legend: false }"
:data="[
{
name: '企业数',
data: [64, 159, 112, 86, 151, 131, 118, 232, 23, 64, 159, 112, 86, 151, 131, 118]
}
]"
:xAxisData="[
'12-16 10:00',
'12-16 14:00',
'12-16 16:00',
'12-16 22:00',
'12-17 02:00',
'12-17 06:00',
'12-17 10:00',
'12-17 14:00',
'12-17 16:00',
'12-16 22:00',
'12-18 02:00',
'12-18 06:00',
'12-8 10:00',
'12-18 14:00',
'12-18 16:00',
'12-18 20:00'
]"
/>
</div>
</div>
<div class="box">
<Title2 title="景区承载量" />
<div class="statistic">
<div class="statistic-item">
<gauge id="gauge1" />
<span class="statistic-title">三峡之巅</span>
</div>
<div class="statistic-item">
<gauge id="gauge2" />
<span class="statistic-title">三峡之巅</span>
</div>
<div class="statistic-item">
<gauge id="gauge3" />
<span class="statistic-title">三峡之巅</span>
</div>
<div class="statistic-item">
<gauge id="gauge4" />
<span class="statistic-title">三峡之巅</span>
</div>
</div>
<Title3 title="今日景区承载量" />
<div class="pt-20">
<Line
:width="370"
:height="140"
:config="{ legend: false }"
:data="[
{
name: '企业数',
data: [64, 159, 112, 86, 151, 131, 118, 232, 23, 64, 159, 112, 86, 151, 131, 118]
}
]"
:xAxisData="[
'12-16 10:00',
'12-16 14:00',
'12-16 16:00',
'12-16 22:00',
'12-17 02:00',
'12-17 06:00',
'12-17 10:00',
'12-17 14:00',
'12-17 16:00',
'12-16 22:00',
'12-18 02:00',
'12-18 06:00',
'12-8 10:00',
'12-18 14:00',
'12-18 16:00',
'12-18 20:00'
]"
/>
</div>
</div>
</div>
<div class="ticket-box">
<Title2 title="景区购票数" />
<div class="ticket-wrap">
<img src="@/assets/images/ticket.png" />
<div v-for="(item, index) in homeData?.admission" :key="index">
<span class="label">{{ item.name }}</span><countup :end-val="item.value" />
</div>
</div>
</div>
<Title1 title="游客画像" />
<div class="flex">
<div class="box-1">
<Title3 title="年龄/性别占比" />
<age />
<div class="count">总人数<countup :end-val="ageRateTotal" /></div>
<div
class="cell pt-20"
v-for="(item, index) in homeData?.userPortrait.genderRate"
:key="index"
>
<img class="icon" src="@/assets/images/man.png" />
<div class="bg">
<span class="text">{{ item.name }}</span>
<div class="progress">
<el-progress
:percentage="Number(item.value)"
:show-text="false"
:color="`linear-gradient( to right, ${
item.name == '男' ? '#074D90' : '#0A4482'
} 0%, ${item.name == '男' ? '#55E0FF' : '#FF7021'} 100%)`"
/>
</div>
<span class="man">{{ item.value }}%</span>
</div>
</div>
</div>
<div class="box-1">
<Title3 title="客源地分析TOP5" />
<top />
</div>
<div class="box-1">
<Title3 title="购票来源" />
<div class="count">总人数<countup :end-val="channelTotal" /></div>
<ticket />
</div>
</div>
</div>
</template>
<script setup>
import countup from 'vue-countup-v3'
import top from './top.vue'
import age from './age.vue'
import gauge from './gauge.vue'
import ticket from './ticket.vue'
const homeData = inject('homeData')
const ageRateTotal = computed(() => {
return homeData.value?.userPortrait.genderRate.reduce(
(total, current) => Number(current.count) + total,
0
)
})
const channelTotal = computed(() => {
return homeData.value?.userPortrait.channel.reduce(
(total, current) => Number(current.count) + total,
0
)
})
</script>
<style lang="scss" scoped>
.box-2 {
margin-top: vh(120);
width: vw(800);
height: vh(950);
padding: vw(8);
box-sizing: border-box;
background-image: url('@/assets/images/bg-2.png');
background-size: 100% 100%;
.more {
position: absolute;
top: vh(0);
right: vw(20);
cursor: pointer;
width: vw(60);
height: auto;
}
.dropdown {
position: absolute;
right: vw(8);
bottom: -30%;
z-index: 990;
}
.item {
position: relative;
flex: 1;
padding-left: vw(70);
height: vh(52);
margin: 0 vh(10);
display: flex;
align-items: center;
background-size: 100% 100%;
.label {
position: absolute;
top: vh(-10);
font-weight: 400;
font-size: vw(14);
color: rgba(255, 255, 255, 0.7);
}
.countup-wrap {
color: #02f9fa;
font-size: vw(28);
font-weight: bold;
}
}
.unit {
color: #02f9fa;
font-size: vw(14);
margin-bottom: vh(4);
}
.core {
background-image: url('@/assets/images/core.png');
}
.queue {
background-image: url('@/assets/images/queue.png');
}
.congestion {
background-image: url('@/assets/images/congestion.png');
}
.box {
width: vw(384);
height: vh(320);
background-image: url('@/assets/images/bg-3.png');
background-size: 100% 100%;
&:nth-child(1) {
margin-right: vw(10);
}
.statistic {
display: flex;
margin-top: vh(12);
width: 100%;
height: vh(88);
background-image: url('@/assets/images/bg-4.png');
background-size: 100% 100%;
&-item {
flex: 1;
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
}
&-title {
font-size: vw(14);
color: rgba(255, 255, 255, 0.9);
}
&-value {
margin-top: vh(10);
font-weight: bold;
font-size: vw(24);
color: #02f9fa;
}
.value {
font-weight: bold;
font-size: vw(28);
color: #ff4400;
}
.prefix,
.suffix {
color: #ff4400;
font-size: vw(12);
}
}
}
.box-1 {
width: vw(253);
height: vh(290);
background-image: url('@/assets/images/bg-3.png');
background-size: 100% 100%;
&:nth-child(1) {
margin-right: vw(10);
}
&:nth-child(2) {
margin-right: vw(10);
}
}
.count {
margin: vw(20) vw(20) 0 vw(20);
height: vh(24);
font-weight: bold;
font-size: vw(14);
color: #ffffff;
display: flex;
align-items: center;
justify-content: center;
box-sizing: border-box;
border-left: vw(4) solid #37d8fc;
border-right: vw(4) solid #37d8fc;
background: rgba(0, 150, 255, 0.19);
}
.cell {
margin-left: vw(10);
display: flex;
align-items: center;
.bg {
display: flex;
align-items: center;
height: vh(20);
padding-right: vw(10);
background: linear-gradient(to right, rgba(0, 150, 255, 0), rgba(0, 150, 255, 0.17) 100%);
}
.icon {
width: vw(26);
height: auto;
margin-right: vw(4);
}
.text {
font-weight: 400;
font-size: vw(14);
color: rgba(255, 255, 255, 0.9);
}
.progress {
width: vw(120);
margin-left: vw(4);
}
.man {
font-weight: bold;
font-size: vw(14);
color: #02f9fa;
margin-left: vw(10);
}
.woman {
font-weight: bold;
font-size: vw(14);
color: #f15a25;
margin-left: vw(10);
}
}
.ticket-box {
margin-top: vh(20);
width: 100%;
height: vh(106);
background: linear-gradient(to right, rgba(0, 77, 136, 0) 0%, rgba(0, 77, 136, 0.6) 100%);
.title {
width: vw(253);
height: vh(28);
display: flex;
align-items: center;
background-image: url('@/assets/images/title-5.png');
background-size: 100% 100%;
& > span {
padding-left: vw(22);
font-weight: bold;
font-size: vw(15);
background-image: linear-gradient(to bottom, #ffffff 0%, #75c1ff 100%);
-webkit-background-clip: text;
background-clip: text;
-webkit-text-fill-color: transparent; /* 兼容WebKit内核浏览器 */
color: transparent; /* 兼容其他浏览器 */
}
}
}
.ticket-wrap {
margin-top: vh(8);
display: flex;
align-items: center;
justify-content: space-between;
& > img {
width: vw(74);
height: auto;
}
& > div {
flex: 1;
height: vh(58);
display: flex;
align-items: center;
background-image: url('@/assets/images/ticket-item-bg.png');
background-size: 100% 100%;
}
.label {
padding-left: vw(10);
font-weight: 400;
font-size: vw(14);
color: rgba(255, 255, 255, 0.9);
}
.countup-wrap {
color: #02f9fa;
font-size: vw(28);
font-weight: bold;
}
}
}
</style>