<template>
  <div id="map-container" class="map-container">
    <slot></slot>
  </div>
</template>

<script setup>
import * as Cesium from 'cesium';

const props = defineProps({
  options: {
    type: Object,
    default: () => {
      return {}
    }
  }
})
let viewer = null;


onMounted(async () => {
  initMap();
})

// 初始化地图
const initMap = async () => {
 let terrainProvider = await Cesium.createWorldTerrainAsync()
  const oldOptions = {
    // 动画仪表盘
    animation: false,
    // 基础图层选择按钮
    baseLayerPicker: false,
    // 全屏按钮
    fullscreenButton: false,
    vrButton: false,
    // 地名地址查询框
    geocoder: false,
    // 返回地球视角按钮
    homeButton: false,
    // 属性框（显示拾取要素的属性）
    infoBox: false,
    // 场景模式切换按钮（三维地球、2.5维场景、二维地图）
    sceneModePicker: false,
    // 拾取要素识别（显示个框，但不明确选中内容）？？？
    selectionIndicator: false,
    // 时间轴
    timeline: false,
    // 操作提示按钮
    navigationHelpButton: false,
    // 超采样开4倍，如果显示困难再降低
    msaaSamples: 2,
    scene3DOnly: true,
    shouldAnimate: true,
    contextOptions: {
      webgl: {
        // 允许截图
        preserveDrawingBuffer: true,
      },
    },
  }
  // 添加cesium的token（目前使用zq发布的）
  Cesium.Ion.defaultAccessToken = 'eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJqdGkiOiJiZjljMTU0MC03OGY5LTRjMzQtYWJkYS02MzI2OTI2OGUyNTgiLCJpZCI6MzE3NTgsImlhdCI6MTc0MTA1MjY3OH0.uvbT5jSUFS-wU41MvzAuY33yfYnUiOWQCWad2KSX28o'
  console.log(props.options.configJson)
  let configJson = props.options.configJson;
  try {
    configJson = JSON.parse(configJson)
  } catch (e) {
    configJson = {}
  }
  if (props.options.isTerrainProvider) {
    oldOptions.terrainProvider = terrainProvider;
  }
  let options = Object.assign(oldOptions, configJson)
  viewer = new Cesium.Viewer('map-container', options)

  // 启用深度测试
  // viewer.scene.globe.depthTestAgainstTerrain = true;
  // 隐藏logo
  viewer.cesiumWidget.creditContainer.style.display = 'none'

  setInitConfig();

  // 取消左键双击
  viewer.cesiumWidget.screenSpaceEventHandler.removeInputAction(Cesium.ScreenSpaceEventType.LEFT_DOUBLE_CLICK);
}

// 设置初始值
const setInitConfig = () => {
  let options = props.options;
  mapSetView(options);
  // 地形夸张
  if (options.terrainExaggeration) {
    viewer.scene.globe.terrainExaggeration = options.terrainExaggeration;
  }

  setMapImg(options);
}

// 设置地图
const setMapImg = (options) => {
  if (!options.ditu) {
    return;
  }

  if (options.ditu === 'amap') {
    const gaodeVector = new Cesium.UrlTemplateImageryProvider({
      url: "https://webrd01.is.autonavi.com/appmaptile?lang=zh_cn&size=1&scale=1&style=8&x={x}&y={y}&z={z}",
      name: "高德矢量地图",
    });
    viewer.imageryLayers.addImageryProvider(gaodeVector);
  } else if (options.ditu === 'tencent') {
    const tencentVector = new Cesium.UrlTemplateImageryProvider({
      url: "https://rt3.map.gtimg.com/tile?z={z}&x={x}&y={reverseY}&styleid=1&version=297",
      customTags: {
        sx: function (imageryProvider, x, y, level) {
          return x >> 4;
        },
        sy: function (imageryProvider, x, y, level) {
          return ((1 << level) - y) >> 4;
        },
      },
      name: "腾讯矢量地图",
    });
    viewer.imageryLayers.addImageryProvider(tencentVector);
  } else if (options.ditu === 'baidu') {
    const baiduVector = new CustomBaiduImageryProvider({
      url: "http://online{s}.map.bdimg.com/onlinelabel/?qt=tile&x={x}&y={y}&z={z}&styles=pl&scaler=1&p=1",
    });
    viewer.imageryLayers.addImageryProvider(baiduVector);
  } else if (options.ditu === 'tianditu') {
    const tiandituImage = new Cesium.WebMapTileServiceImageryProvider({
      url: "http://t0.tianditu.gov.cn/img_w/wmts?tk=25129831bd91c81af49d3ecf578f6b3c",
      layer: "img",
      style: "default",
      format: "tiles",
      tileMatrixSetID: "w",
      maximumLevel: 18,
      credit: new Cesium.Credit("© Tianditu", "http://www.tianditu.gov.cn/"),
      name: "天地图影像地图",
    });
    viewer.imageryLayers.addImageryProvider(tiandituImage);
  }
}

// 地图设置视角
const mapSetView = (options) => {
  let destination = Cesium.Cartesian3.fromDegrees(options.setView.x, options.setView.y, options.setView.z);
  let orientation = {
    heading: Cesium.Math.toRadians(options.setView.heading),
    pitch: Cesium.Math.toRadians(options.setView.pitch),
    roll: Cesium.Math.toRadians(options.setView.roll)
  }

  if (options.setView.duration === '默认') {
    viewer.camera.flyTo({
      destination,
      orientation
    })
  } else {
    viewer.camera.flyTo({
      destination,
      orientation,
      duration: options.setView.duration
    })
  }
}

onUnmounted(() => {
  if (viewer) {
    viewer.entities.removeAll()
    viewer.imageryLayers.removeAll()
    for (let index = 0; index < viewer.dataSources.length; index++) {
      const datasource = viewer.dataSources.get(index);
      datasource.entities.removeAll()
    }
    viewer.dataSources.removeAll(true)
    // viewer.scene.primitives.removeAll();
    viewer.destroy()
  }
})

</script>

<style lang="scss" scoped>
.map-container {
  width: 100%;
  height: 100%;
}
</style>