Newer
Older
cockpit_hxrq_front / src / views / maps / weatherTopic.vue
StephanieGitHub on 22 Apr 2021 10 KB MOD:对接实际数据
<!--
 * @Description: 天气专题
 * @Author: 王晓颖
 * @Date: 2021-04-11
 -->
<template>
  <div id="centerDiv" class="mapcontainer">
    <!--时钟-->
    <clock/>
    <!--天气-->
    <weather/>

    <!--地图-->
    <Map :url="configUrl" @onload="onMapload" />
    <!--按钮-->
    <div class="map-btn-group">
      <select-button :select="weatherShow" name="天气预报" icon="icon-weather" @click="showWeather(weatherShow)"/>
      <select-button :select="disasterShow" name="气象预警" icon="icon-disaster" @click="showDisaster(disasterShow)"/>
      <!--<select-button :select="weatherHeatShow" name="气温热力图" icon="icon-heat" @click="showWeatherHeat(weatherHeatShow)"/>-->
    </div>
    <!--logo-->
    <brand/>

  </div>
</template>

<script>
import 'mars3d-heatmap'
import Map from '@/components/Map/MarsMap.vue'
import Weather from '@/components/weather/weather'
import Clock from '@/components/clock/Clock'
import Brand from '@/components/Brand/brand'
import SelectButton from '@/components/SelectTool/components/selectButton'
import { getWeatherList, getDisasterList } from '@/api/weather'
import { getToday } from '@/utils/dateutils'
import axios from 'axios'
export default {
  name: 'Vip',
  components: {
    Weather,
    Clock,
    Map,
    Brand,
    SelectButton
  },
  data() {
    return {
      map: null, // 地图
      configUrl: 'static/config/config.json',
      alpha: 100, // 透明度
      underground: null, // ?
      weatherShow: true, // 显示气温点位图
      disasterShow: false, // 显示气象灾害图层
      weatherHeatShow: false, // 气温热力图
      disaster: {
        '台风': '01',
        '暴雨': '02',
        '暴雪': '03',
        '寒潮': '04',
        '大风': '05',
        '沙尘暴': '06',
        '高温': '07',
        '干旱': '08',
        '雷电': '09',
        '冰雹': '10',
        '霜冻': '11',
        '大雾': '12',
        '霾': '13',
        '道路结冰': '14'
      }, // 灾害与数字对应表
      disasterLevel: {
        '蓝色': '01',
        '黄色': '02',
        '橙色': '03',
        '红色': '04'
      }, // 灾害等级与数字对应表
      weathers: {
        '晴': 'static/images/map/weather/weather-qing.png',
        '多云': 'static/images/map/weather/weather-duoyun.png',
        '阴': 'static/images/map/weather/weather-yin.png',
        '小雨': 'static/images/map/weather/weather-xiaoyu.png',
        '雨': 'static/images/map/weather/weather-dayu.png',
        '小雪': 'static/images/map/weather/weather-xiaoxue.png',
        '雨夹雪': 'static/images/map/weather/weather-yujiaxue.png'
      }, // 天气与图片地址
      weatherLayer: null, // 天气图层
      disasterLayer: null, // 气象灾害图层
      weatherHeatLayer: null, // 气温热力图
      timer: null, // 定时器
      clock: 7200 //
    }
  },
  methods: {
    // 地图构造完成回调
    onMapload(map) {
      // 以下为演示代码
      this.map = map
      // 背景透明
      this.map._viewer.scene.backgroundColor = new this.Cesium.Color(0.0, 0.0, 0.0, 0.0)
      this.map._viewer.scene.globe.baseColor.alpha = 0
      // 气温图层
      this.addTemperature()
      // this.addDisaster()
      // this.addWeatherHeat()
      this.refreshData()
    },
    // 显示天气分布
    addTemperature() {
      const { mars3d, Cesium } = this
      if (this.weatherLayer) {
        this.map.removeLayer(this.weatherLayer)
      }
      const graphicLayer = new mars3d.layer.GraphicLayer()
      this.weatherLayer = graphicLayer
      this.map.addLayer(graphicLayer)
      const date = getToday()
      getWeatherList(date).then((res) => {
        const data = res.data.map(item => {
          return {
            name: item['WD51_20'],
            lng: parseFloat(item['WD51_21']),
            lat: parseFloat(item['WD51_22']),
            wd: item['WD51_15'].trim(),
            wg: item['WD51_14'].trim(),
            tqxx12: item['WD51_10'],
            tqxx24: item['WD51_12']
          }
        })
        for (const item of data) {
          const graphic = new mars3d.graphic.BillboardEntity({
            name: '天气',
            position: [item.lng, item.lat, 5000],
            style: {
              image: this.weathers[item.tqxx12],
              pixelOffsetX: -15,
              pixelOffsetY: -15,
              scale: 1,
              horizontalOrigin: Cesium.HorizontalOrigin.CENTER,
              verticalOrigin: Cesium.VerticalOrigin.BOTTOM
              // label: {
              //   text: `${item.tqxx12}  ${item.wd}~${item.wg}℃`,
              //   font_size: 16,
              //   color: '#ffffff',
              //   pixelOffsetY: 20,
              //   background: true,
              //   backgroundColor: '#000000',
              //   backgroundOpacity: 0.1,
              //   distanceDisplayCondition: true,
              //   distanceDisplayCondition_far: 2000000,
              //   distanceDisplayCondition_near: 0
              // }
            }
          })
          var html = ` <div class="popup-win"><span class="title">${item.name}</span><br/>
                        <div style="color:#FFB861">天气:${item.tqxx12}</div>
                        <div style="color:#63AEFF">温度:${item.wd}~${item.wg}℃</div>
                        </div>`
          graphic.bindTooltip(html, { anchor: [0, -20] }).openTooltip()
          graphicLayer.addGraphic(graphic)
        }
      })
    },
    // 显示气象灾害分布
    addDisaster() {
      const { mars3d, Cesium } = this
      if (this.disasterLayer) {
        this.map.removeLayer(this.disasterLayer)
      }
      const graphicLayer = new mars3d.layer.GraphicLayer()
      this.disasterLayer = graphicLayer
      this.map.addLayer(graphicLayer)
      const date = getToday()
      getDisasterList(date).then((res) => {
        if (res.data.length === 0) {
          this.$message.info('今日无预警')
        } else {
          let data = res.data.map(item => {
            return {
              name: item['WD52_03'].trim(),
              lng: parseFloat(item['WD52_06'].trim()),
              lat: parseFloat(item['WD52_05'].trim()),
              value: item['WD52_08'].trim(),
              zhlx: item['WD52_12'].trim(),
              zhdj: item['WD52_13'].trim()
            }
          })
          data = data.filter(item => item.lng != null)
          for (const item of data) {
            const img = 'static/images/weather_disaster/' + this.disaster[item.zhlx] + this.disasterLevel[item.zhdj] + '.png'
            const graphic = new mars3d.graphic.BillboardEntity({
              name: '气象灾害',
              position: [item.lng, item.lat, 100],
              style: {
                image: img,
                pixelOffsetX: 0,
                pixelOffsetY: -20,
                scale: 0.5,
                horizontalOrigin: Cesium.HorizontalOrigin.CENTER,
                verticalOrigin: Cesium.VerticalOrigin.BOTTOM
              }
            })
            var html = ` <div class="popup-win"><span class="title">${item.name}</span><br/>
                        <div style="color:#FFB861">预警:${item.zhlx}${item.zhdj}</div>
                        <div style="color:#63AEFF">时间:${item.value}</div>
                        </div>`
            graphic.bindTooltip(html, { anchor: [0, -20] }).openTooltip()
            graphicLayer.addGraphic(graphic)
          }
        }
      })
    },
    // 添加地震分布
    addWeatherHeat() {
      const { mars3d } = this
      axios.get('static/config/weather.json').then((res) => {
        const data = res.data.data
        if (res.data.code === 200) {
          // 过滤掉经度为null的
          const heatLayer = new mars3d.layer.HeatLayer({
            positions: data.map(item => {
              return { lng: item.lng, lat: item.lat, value: item.wd }
            }),
            heatStyle: {
              radius: 30, // 半径
              blur: 1 // 模糊因子
            },
            // 以下为矩形矢量对象的样式参数
            style: {
              opacity: 0.8,
              clampToGround: false,
              height: 10000
            },
            redrawZoom: true,
            flyTo: false
          })
          this.weatherHeatLayer = heatLayer
          this.map.addLayer(heatLayer)
        }
      })
    },
    showWeather(show) {
      if (show) { // 移除
        this.weatherShow = false
        this.map.removeLayer(this.weatherLayer, true)
        this.weatherLayer = null
      } else {
        this.weatherShow = true
        this.addTemperature()
      }
    },
    showDisaster(show) {
      if (show) { // 移除
        this.disasterShow = false
        this.map.removeLayer(this.disasterLayer, true)
        this.disasterLayer = null
      } else {
        this.disasterShow = true
        this.addDisaster()
      }
    },
    showWeatherHeat(show) {
      if (show) { // 移除
        this.weatherHeatShow = false
        this.map.removeLayer(this.weatherHeatLayer, true)
      } else {
        this.weatherHeatShow = true
        this.addWeatherHeat()
      }
    },
    refreshData() {
      this.timer = setInterval(() => {
        console.log('refreshData')
        if (this.weatherLayer) { // 如果供需图层不为空,刷新工薪数据
          this.addTemperature()
        }
        if (this.disasterLayer) {
          this.addDisaster()
        }
      }, this.clock * 1000)
    }
  }
}
</script>

<style rel="stylesheet/scss" lang="scss" scoped>
  .label-div{
    position: absolute;
    top: 140px;
    left:31rem;
    z-index:100;
    color: white;
    padding:2rem 3rem 1.5rem 3rem;
    background-image: url("../../assets/button_images/board-box1.png");
    background-size: 100% 100%;
    .label{
      margin-bottom: 1rem;
      font-size:1.2rem;
    }
    .value{
      font-family: DS-DigitalBold;
      font-size:2.5rem;
    }
  }
  .map-btn-group{
    position: absolute;
    bottom:3rem;
    left:50%;
    transform: translateX(-50%);
    display: flex;
    justify-content: center;
  }
</style>

<style rel="stylesheet/scss" lang="scss">
  /*整个容器*/
  .mapcontainer {
    position: relative;
    height: 100%;
    width: 100%;
    background-color: transparent;
    /*background-color: #051151;*/
  }

</style>