<template>

  <div
    class="map-container"
    :="getMapOptions"
  />

  <div

    id="airOverlay"
    class="airport-overlay"
  >
    <span
      id="closeAir"
      class="close-overlay"
      @click="hideAirInfo"
    >x</span>
    <air-info :data="airDetail" />
  </div>
  <div

    v-show="problemPopupShow"
    id="problemOverlay"
    class="problem-overlay"
  >
    <span
      class="close-overlay"
      @click="hideProblemInfo"
    >x</span>
    <problem-info :detail="problemDetail" />
  </div>

  <div
    v-show="listChecked"
    class="menu"
  >
    <div class="tabBar">
      <span
        :class="[tabIndex==1?'checkedColor':'uncheckedColor']"
        style="margin-right:97px"
        @click="showTask"
      >任务</span>
      <span
        :class="[tabIndex==1?'uncheckedColor':'checkedColor']"
        @click="showProblem"
      >问题</span>
    </div>
    <div
      v-if="tabIndex==1"
      class="listDetail"
    >
      <ul>
        <li
          v-for="(item,index) in taskList"
          :key="index"
          style="display:flex;font-size:14px"
        >
          <div style="width:145px;white-space:nowrap;overflow:hidden;text-overflow:ellipsis">{{ item.date }}&nbsp;&nbsp;{{ item.taskName }}</div>
          <div style="width:42px">{{ item.statusInfo }}</div>

          <n-popconfirm
            v-if="item.status==1"
            @positive-click="handlePositiveClick(item)"
            @negative-click="handleNegativeClick"
          >
            <template #trigger>
              <span style="color:#22D33D">立即执行</span>
            </template>
            是否立即开始执行任务?
          </n-popconfirm>
          <div
            v-else
            style="color:#1890FF"
            @click="liveShow(item)"
          >直播</div>
        </li>

      </ul>
      <n-pagination
        v-model:page="page"
        :page-count="pageCount"
        :page-slot="7"
        style="color:#FFFFFF;position:absolute;bottom:10px;left:10px"
      />
    </div>
    <div
      v-else
      class="listDetail"
    >
      <n-date-picker
        :on-update:formatted-value="abc"
        :default-formatted-value="efg"
        type="daterange"
        :default-value="[Date.now() - 6.048e8, Date.now()]"
        :is-date-disabled="disablePreviousDate"
        style="margin-bottom:15px"
      />
      <!-- 多选框 -->
      <n-checkbox-group
        v-model:value="problemTypeSelected"
        @update:value="handleProblemTypeValue"
      >
        <div
          v-for="(item,index) in problemTypeList"
          :key="index"
        >
          <n-checkbox
            :value="item.content"
            :label="item.content"
            style="color:#FFFFFF"
          />
        </div>

      </n-checkbox-group>

    </div>
  </div>
  <div class="menuControl">
    <div
      style="border-bottom:1px solid rgba(1122,112,112,0.65)"
      class="item"
    >
      <div @click="showList">
        <img
          v-if="listChecked==true"
          src="../../../assets/images/listChecked.png"
        >
        <img
          v-else
          src="../../../assets/images/listUnchecked.png"
        >
      </div>

      <span :style="{'color':listChecked?'#1890FF':'#666666'}">列表</span>
    </div>
    <div class="item">
      <div @click="showAirportList">
        <img
          v-if="airportSelected==true"
          src="../../../assets/images/airportChecked.png"
        >
        <img
          v-else
          src="../../../assets/images/airportUnchecked.png"
        >
      </div>

      <span :style="{'color':airportSelected?'#1890FF':'#666666'}">机场</span>
    </div>
  </div>

</template>

<script>
import { Map, View, Feature, Overlay } from 'ol'
import { useRouter } from 'vue-router'
import { XYZ, Vector as VectorSource } from 'ol/source'
import TileLayer from 'ol/layer/Tile.js'
import WMTS from 'ol/source/WMTS.js'
import TileWMS from 'ol/source/TileWMS.js'
import WMTSTileGrid from 'ol/tilegrid/WMTS.js'
import { Tile, Vector as VectorLayer } from 'ol/layer'
import { transform, fromLonLat } from 'ol/proj'
import { Style, Icon, Text, Fill } from 'ol/style'
import * as control from 'ol/control'
import uav_icon from '@/assets/images/airport.png'
import personnel_icon from '@/assets/images/personnelActivities.png'
import problemSpot_icon from '@/assets/images/problemSpot.png'
import deadTree_icon from '@/assets/images/deadTree.png'
import fireHazard_icon from '@/assets/images/fireHazard.png'
import { reactive, toRefs, onMounted, computed, ref, watch } from 'vue'
import { Point } from 'ol/geom'
import { airportList, getMissionList, getQuestionType, getQuestionList } from '@/api/dashboard/index.js'
import { getQuestions } from '@/api/task/index.js'
import { gcj02towgs84 } from '@/utils/coordinate-util.js'
import AirInfo from './AirInfo.vue'
import ProblemInfo from './ProblemInfo.vue'
import { startOfDay } from 'date-fns/esm'
import { useMessage, useDialog } from 'naive-ui'
import { implement } from '@/api/task/index.js'
import { get as getProjection } from 'ol/proj.js'
import { getTopLeft, getWidth } from 'ol/extent.js'
const projection = getProjection('EPSG:4326')
const projectionExtent = projection.getExtent()
const size = getWidth(projectionExtent) / 256
const resolutions = new Array(19)
const matrixIds = new Array(19)
for (let z = 0; z < 19; ++z) {
  // generate resolutions and matrixIds arrays for this WMTS
  resolutions[z] = size / Math.pow(2, z)
  matrixIds[z] = z
}
var message = useMessage()
export default {
  name: 'OneMap',
  components: { AirInfo, ProblemInfo },
  props: {
    id: {
      type: String,
      default: 'map'
    }
  },
  setup(props) {
    const router = useRouter()
    const dialog = useDialog()
    const data = reactive({
      map: null,
      // 机场数组
      airportsAll: [],
      // 机场显隐
      airShow: true,
      // 机场要素集
      airFeatures: [],
      // 机场图层
      airLayer: null,
      // 机场信息容器
      airOverlay: null,
      // 问题信息容器
      problemOverlay: null,
      // 机场细节信息
      airDetail: {},
      // 问题细节信息
      problemDetail: {},
      listShow: false,
      // 时间范围是一周前至今天
      efg: '',
      listIcon: new URL('../../../assets/images/listChecked.png', import.meta.url).href,

      airportIcon: new URL('../../../assets/images/airportChecked.png', import.meta.url).href,
      listFontStyle: {
        'color': '#666666'
      },
      airportFontStyle: {
        'color': '#1890FF'
      },
      problemPopupShow: false,
      tabIndex: 1,
      page: ref(1),
      pageCount: 1,
      taskList: [],
      range: (['2012-09-10', '2022-09-10']),
      problemTypeSelected: null,
      problemTypeList: [],
      listChecked: false,
      airportSelected: true,
      problemLayerList: [],
      airportPopupShow: false
    })
    watch(() => data.page, (newValue, oldValue) => {
      if (newValue !== oldValue) {
        initTaskList()
      }
    })
    const getMapOptions = computed(() => {
      return {
        id: props.id
      }
    })

    const initMap = () => {
      // 天地图影像图
      const tdtImgMap =
        new Tile({
          visible: true,
          source: new XYZ({
            url: 'https://t0.tianditu.gov.cn/DataServer?T=img_w&x={x}&y={y}&l={z}&tk=f634525a82da65f715d168d7ba1899c0'
          })
        })
      var wmsSource = new Tile({
        source: new TileWMS({
          url: 'https://geoserver.t-aaron.com:4080/geoserver/jiangning/wms',
          params: { 'LAYERS': 'jiangning:town' }
        })
      })
      data.map = new Map({
        // 地图容器
        target: props.id,
        view: new View({
          center: transform([118.773136, 31.828065], 'EPSG:4326', 'EPSG:3857'),
          zoom: 11,
          maxZoom: 17
        }),
        layers: [
          tdtImgMap

        ],
        controls: control.defaults({
          attribution: false,
          rotate: false,
          zoom: false
        })

      })
      data.map.addLayer(wmsSource)
      wmsSource.setOpacity(0.3)
    }

    /**
     * @description: 获取机场数据
     * @param {*} res
     * @return {*}
     */
    const loadAirport = (async function() {
      const res = await airportList({ page: 1, limit: 100 })
      if (res.code === 0) {
        data.airportsAll = res.data
        showAirport()
      }
    })()
    /**
     * @description:分页器改变时改变任务列表信息
     */
    const changePage = (v) => {

    }
    /**
     *  展示机场
     */
    const showAirport = () => {
      if (data.airportsAll.length > 0) {
        for (let i = 0; i < data.airportsAll.length; i++) {
          const airport = data.airportsAll[i]
          const lngLat = gcj02towgs84(parseFloat(airport.longitude), parseFloat(airport.latitude))
          const feature = new Feature({
            geometry: new Point(fromLonLat(lngLat))
          })
          // 要素设置样式
          feature.setStyle(
            new Style({
              image: new Icon({
                src: uav_icon
              }),
              text: new Text({
                // 文字内容
                text: airport.name,
                // 位置
                textAlign: 'center',
                // 基准线
                textBaseline: 'top',
                offsetY: 30,
                // 文字样式
                font: 'normal 20px Microsoft YaHei',
                backgroundFill: new Fill({
                  color: '#1890FF'
                }),
                padding: [3, 6, 3, 6],
                // 文字颜色
                fill: new Fill({
                  color: '#fff'
                })
              })
            })
          )
          // 要素设置id
          feature.setId(airport.id)
          // 要素设置属性
          feature.setProperties({
            id: airport.id,
            code: airport.code,
            name: airport.name,
            // 设置类别
            type: 'airport',
            coordinate: fromLonLat(lngLat),
            // 机场外部监控地址
            externalMonitorUrl: airport.externalMonitorUrl,
            // 机场内部监控地址
            internalMonitorUrl: airport.internalMonitorUrl
          })

          data.airFeatures.push(feature)
        }
      }

      data.airLayer = new VectorLayer({
        source: new VectorSource({
          features: data.airFeatures
        }),
        visible: data.airShow
      })
      data.map.addLayer(data.airLayer)

      // 机场信息覆盖物
      data.airOverlay = new Overlay({
        id: 'air_overlay',
        element: document.getElementById('airOverlay'),
        autoPan: true,
        offset: [10, 10]
      })
      data.airportPopupShow = true
      // 点击事件
      data.map.on('click', (evt) => {
        showAirInfo(evt)
      })

      // console.log(new Date().getFullYear())
    }
    /**
     * 展示机场信息
     * @param {} e
     */
    const showAirInfo = (e) => {
      // 防止冒泡
      e.stopPropagation()
      // 点击位置的经纬度
      var feature = data.map.forEachFeatureAtPixel(e.pixel, (feature) => {
        return feature
      })
      if (feature) {
        // 要素类别为机场
        if (feature.getProperties().type === 'airport') {
          data.airDetail = feature.getProperties()

          // 为了overlay位置更加精确
          const coord = feature.getProperties().coordinate
          data.airOverlay.setPosition(coord)

          data.map.addOverlay(data.airOverlay)
        }
        if (feature.getProperties().typeName) {
          data.problemDetail = feature.getProperties()
          // console.log(data.problemDetail, '详情')
          const coord = feature.getProperties().coordinate
          data.problemPopupShow = true
          data.problemOverlay.setPosition(coord)

          data.map.addOverlay(data.problemOverlay)

          // data.problemOverlay.setPosition(coord)
          // data.map.addOverlay(data.problemOverlay)
        }
      }
    }

    /**
     *  关闭展示机场信息
     */
    const hideAirInfo = () => {
      if (data.map.getOverlayById('air_overlay')) {
        data.airDetail = {}
        data.map.removeOverlay(data.airOverlay)
        data.airportPopupShow = false
      }
    }
    /**
     * 关闭显示问题图层信息
     */
    const hideProblemInfo = () => {
      if (data.map.getOverlayById('problem_overlay')) {
        data.problemDetail = {}

        data.map.removeOverlay(data.problemOverlay)
      }
    }
    /**
     * 显示问题信息
     */
    const showProblem = () => {
      data.tabIndex = 0
    }
    /**
     * 显示任务列表信息
     */
    const showTask = () => {
      data.tabIndex = 1
    }
    /**
     * 机场图层控制显隐
     * @param { } value
     */
    const airShowHide = (isShow) => {
      data.airLayer.setVisible(isShow)
      if (!isShow) {
        hideAirInfo()
      }
    }
    /**
     * @description:执行任务
     */
    const performTask = (item) => {
      // console.log(router, '路径')

      router.push({ path: '/taskManage/all', query: { rowInfo: JSON.stringify(item) }})
    }
    const abc = (value) => {
      getQuestionList({
        startTime: value[0],
        endTime: value[1]
      }).then(res => {
        if (res.code === 0) {
          const arr = res.data

          var resArr = []
          var narr = []
          for (var i = 0; i < arr.length; i++) {
            var n = resArr.indexOf(arr[i].typeName)
            if (n == -1) {
              resArr.push(arr[i].typeName)
              narr.push({ 'name': arr[i].typeName, fraction: [arr[i]] })
            } else {
              narr[n].fraction.push(arr[i])
            }
          }

          // 添加问题图层
          addproblemLayer(narr)
        }
      })
    }
    // 添加问题图层
    const addproblemLayer = (narr) => {
      data.problemOverlay = new Overlay({
        id: 'problem_overlay',
        element: document.getElementById('problemOverlay'),
        autoPan: true,
        offset: [10, 10]

      })
      narr.map((item) => {
        const Features = []
        if (item.fraction.length > 0) {
          item.fraction.map((iitem) => {
            const problem = iitem
            const lngLat = gcj02towgs84(parseFloat(problem.lng), parseFloat(problem.lat))
            const feature = new Feature({
              geometry: new Point(fromLonLat(lngLat))
            })

            let icon
            switch (iitem.typeName) {
              case '林场问题图斑':
                icon = problemSpot_icon
                break
              case '病死树':
                icon = deadTree_icon
                break
              case '人员活动':
                icon = personnel_icon
                break
              case '火灾隐患':
                icon = fireHazard_icon
            }
            // 要素设置样式
            feature.setStyle(
              new Style({
                image: new Icon({
                  src: icon
                })
              })
            )
            // 要素设置id
            feature.setId(problem.questionId)
            // 要素设置属性
            problem.coordinate = fromLonLat(lngLat)
            feature.setProperties(problem)
            Features.push(feature)
          })
          // 添加图层
          const layer = new VectorLayer({
            source: new VectorSource({
              features: Features
            }),
            visible: true
          })

          const obj = { type: item.name, layer: layer }
          data.problemLayerList.push(obj)
          data.map.addLayer(layer)
        }
      })
    }
    /**
     * 初始化任务列表信息
     *
     */
    const initTaskList = () => {
      getMissionList({
        page: data.page,
        limit: 8
      }).then(res => {
        if (res.code === 0) {
          data.taskList = res.data.records
          data.pageCount = res.data.pages
          // console.log(data.pageCount, '页数')
          data.taskList.map((item, index) => {
            const arr = item.executionStartTime.split(/[ ]+/)// 以空格分开
            item.date = arr[0]
            item.taskName = item.name

            switch (item.status) {
              case 1:
                item.statusInfo = '待执行'
                break
              case 2:
                item.statusInfo = '执行中'
                break
            }
          })
        }
      })
    }
    /**
     * 获取问题多选类型
     */
    const initProblemType = () => {
      getQuestionType().then(res => {
        if (res.code === 0) {
          data.problemTypeList = res.data
          data.problemTypeSelected = []
          data.problemTypeList.map((item) => {
            data.problemTypeSelected.push(item.content)
          })
        }
      })
    }
    /**
     * @description:是否展示列表
     */
    const showList = () => {
      data.listChecked = !data.listChecked
    }
    /**
     *
     */
    const handleProblemTypeValue = (value) => {
      // console.log(value, '选中的值')
      data.problemLayerList.map((item) => {
        const a = value.indexOf(item.type)

        if (a == -1) {
          item.layer.setVisible(false)
        } else {
          item.layer.setVisible(true)
        }
      })
    }
    /**
     * @description:是否显示机场
     */
    const showAirportList = () => {
      data.airportSelected = !data.airportSelected
      data.airLayer.setVisible(data.airportSelected)
      if (!data.airportSelected) {
        hideAirInfo()
      }
    }
    /**
     * 展示直播视频
     */
    const liveShow = (rowInfo) => {
      router.push({ path: '/taskManage/all', query: { rowInfo: JSON.stringify(rowInfo) }})
    }
    onMounted(() => {
      initMap()
      initTaskList()
      initProblemType()
    })

    return {
      ...toRefs(data),
      getMapOptions,
      loadAirport,
      showProblem,
      showTask,
      airShowHide,
      hideAirInfo,
      changePage,
      showList,
      disablePreviousDate(ts, type, range) {
        const d = 864e5
        // return ts > Date.now()
        if (type === 'start' && range !== null) {
          return startOfDay(range[1]).valueOf() - startOfDay(ts).valueOf() >= d * 8
        }
        if (type === 'end' && range !== null) {
          return startOfDay(ts).valueOf() - startOfDay(range[0]).valueOf() >= d * 8
        }
        return ts > Date.now()
      },
      abc,
      showAirportList,
      handleProblemTypeValue,
      hideProblemInfo,
      performTask,
      handleConfirm() {
        dialog.warning({
          title: '警告',
          content: '你确定？',
          positiveText: '确定',
          negativeText: '不确定',
          onPositiveClick: () => {
            message.success('确定')
          },
          onNegativeClick: () => {
            message.error('不确定')
          }
        })
      },
      handlePositiveClick(row) {
        $message.info('机场设备开始自检，请稍等')
        implement(row.id)
          .then(res => {
            if (res.code === 0) {
              $message.info('操作成功')
            }
          })
      },
      handleNegativeClick() {

      },
      liveShow

    }
  }
}
</script>

<style lang="scss" scoped>
.container{
  width:100vw;
  height:100vh;

   position:relative;
  overflow:hidden;
}
.map-container {
 position:absolute;
 top:0px;
 left:0px;
 right:0px;
 bottom:0px;

}

.layer-management {
  height: calc(100vh - 84%);
  position: absolute;
  width: 100px;
  /* margin-right: 10px; */
  left: 100px;
  top: 100px;
  background-color: rgba(0, 0, 0, 0.6);
}

.layer-management p {
  color: #fff;
}

.airport-overlay {
  width: 530px;
  height: 430px;
  background-color: rgba(0, 0, 0, 0.5);
}
.problem-overlay {
  width: 530px;

  background-color: rgba(0, 0, 0, 0.5);
}
.close-overlay {
  width: 28px;
  height: 28px;
  position: relative;
  color: #fff;
  font-size: 20px;
  cursor: pointer;
  float: right;
  text-align: center;
  line-height: 28px;
}

/* 任务-问题面板 */
.task-question {
  width: 500px;
  height: 800px;
  position: absolute;
  top: 100px;
  right: 140px;
}
.menu {
  position: absolute;
  top: 64px;
  right: 90px;
  width: 355px;
  height: 428px;
  background: #000000;
  box-sizing: border-box;
  padding: 5px;
  .tabBar {
    height: 35px;
    width: 100%;
    font-size: 15px;
    font-family: Noto Sans SC-Regular, Noto Sans SC;
    font-weight: 400;
    display: flex;
    justify-content: center;
    .checkedColor {
      color: #1890ff;
    }
    .uncheckedColor {
      color: #ffffff;
    }
  }
  .listDetail {
    width: 345px;
    height: 383px;
    background: #2c2c2c;
    font-size: 14px;
    font-family: Noto Sans SC-Regular, Noto Sans SC;
    font-weight: 400;
    color: #ffffff;
    position: relative;
    box-sizing: border-box;
    padding: 10px 19px;
    ul {
      li {
        display: flex;
        justify-content: space-between;
        padding: 5px 2px;
        margin-bottom: 3px;
      }
    }
  }
}
// 列表机场控制显隐菜单
.menuControl {
  position: absolute;
  top: 200px;
  right: 40px;
  background: #ffffff;
  box-shadow: 2px 2px 2px 1px rgba(31, 31, 31, 0.38);
  border-radius: 2px;
  width: 40px;
  .item {
    width: 100%;
    height: 60px;
    font-size: 14px;
    font-family: Noto Sans SC-Regular, Noto Sans SC;
    font-weight: 400;
    display: flex;
    flex-direction: column;
    justify-content: center;
    align-items: center;
  }
}
:deep(.n-pagination-item) {
  color: #ffffff !important;
}
:deep(.n-checkbox__label) {
  color: #ffffff !important;
}
:deep(.n-pagination
    .n-pagination-item.n-pagination-item--disabled.n-pagination-item--button) {
  background-color: rgba(0, 0, 0, 0) !important;
}
</style>
