<!--
 * @Author: SunTao 328867980@qq.com
 * @Date: 2024-11-15 13:14:03
 * @LastEditors: SunTao 328867980@qq.com
 * @LastEditTime: 2024-12-10 13:22:17
 * @FilePath: \znxjxt-ui\src\views\big-screen\overview-components\components\inspection-follow.vue
 * @Description: 总览大屏-巡检车辆-跟车弹窗
-->

<template>
  <div class="inspection-content">
    <fssm-map ref="carMap" :baseMap="'img_c'"></fssm-map>
  </div>
</template>

<script>
// websocket
import logo from "@/assets/xc.png";
import FssmMap from "@/components/map/fssm-map.vue";
import { Point } from "ol/geom";
import { Feature } from "ol";
import { Style, Icon } from "ol/style";
import VectorSource from "ol/source/Vector";
import VectorLayer from "ol/layer/Vector";

export default {
  name: "InspectionFollow",
  components: {
    FssmMap,
  },
  props: {
    dialogItem: {
      type: Object,
      default: () => {},
    },
  },
  data() {
    return {
      // 小车图层数据源
      carMapPointSource: null,
      // 小车地图点位数组
      carPointList: [],
      // 小车地图点位features数组
      mapPointFeatures: [],
      // 病害图层数据源
      defectLayerSource: null,
    };
  },
  created() {
    this.handleMessage();
  },
  methods: {
    /**
     * @description: 处理websocket消息
     * @return {*}
     */
    handleMessage() {
      this.$ws.on("message", (itemMessage) => {
        if (itemMessage.type === "carPosition") {
          if (this.carPointList.includes(itemMessage.data.entityId)) {
            // 获取当前位置和目标位置
            this.carMapPointSource.getFeatures().forEach((item) => {
              if (item.get("data") === itemMessage.data.entityId) {
                const currentLocation = item.getGeometry().getCoordinates();
                const targetLocation = itemMessage.data.location;
                // 计算两点之间的差值
                const dx =
                  (targetLocation[0] * 1 - currentLocation[0] * 1) / 100;
                const dy =
                  (targetLocation[1] * 1 - currentLocation[1] * 1) / 100;
                // 设置计数器
                let count = 0;
                // 创建定时器,每10ms移动一次,总共移动100次,约1秒完成
                const timer = setInterval(() => {
                  count++;
                  if (count >= 100) {
                    clearInterval(timer);
                    return;
                  }

                  // 计算当前帧的位置
                  const x = currentLocation[0] * 1 + dx * count;
                  const y = currentLocation[1] * 1 + dy * count;

                  // 更新小车位置
                  // const [features] = this.carMapPointSource.getFeatures();
                  item.setGeometry(new Point([x, y]));
                  item.setStyle([
                    new Style({
                      image: new Icon({
                        crossOrigin: "anonymous",
                        src: logo,
                        // 图标缩放比例
                        scale: 0.5,
                        // 将角度转换为弧度,并除以180*π
                        rotation:
                          (itemMessage.data.direction - 90) * (Math.PI / 180),
                      }),
                    }),
                  ]);
                }, 10);
              }
            });
          } else {
            this.carPointList.push(itemMessage.data.entityId);
            this.drawCarMapPoint(itemMessage.data);
            if (this.dialogItem.extId === itemMessage.data.entityId) {
              this.$nextTick(() => {
                const map = this.$refs.carMap.instance.get("map");
                map.getView().setCenter(itemMessage.data.location);
                map.getView().setZoom(17)
              });
            }
          }
        } else if (itemMessage.type === "defect") {
          if (!this.defectLayerSource) {
            this.drawDefectMapPoint(itemMessage.data);
          } else {
            const feature = new Feature({
              geometry: new Point(itemMessage.data.geometry.coordinates),
              data: itemMessage,
              type: "defectPoint",
            });
            // 可以给点位设置样式
            feature.setStyle([
              new Style({
                image: new Icon({
                  crossOrigin: "anonymous",
                  src: require(`@/assets/screen/index/${itemMessage.data.defecttype}.png`),
                  // 图标缩放比例
                  scale: 0.5,
                }),
              }),
            ]);
            this.defectLayerSource.addFeature(feature);
          }
        }
      });
    },

    /**
     * @description: 绘制小车地图点位
     * @param {object} item
     * @return {void}
     */
    drawCarMapPoint(item) {
      const features = [];
      const feature = new Feature({
        geometry: new Point(item.location),
        data: item.entityId,
        type: "carPoint",
      });
      // 可以给点位设置样式
      feature.setStyle([
        new Style({
          image: new Icon({
            crossOrigin: "anonymous",
            src: logo,
            // 图标缩放比例
            scale: 0.03,
            // 将角度转换为弧度,并除以180*π
            rotation: item.direction * (Math.PI / 180),
          }),
        }),
      ]);
      this.mapPointFeatures.push(feature);
      this.carMapPointSource = new VectorSource({
        features: this.mapPointFeatures,
      });
      const carMapPointLayer = new VectorLayer({
        source: this.carMapPointSource,
        properties: {
          type: "carPoint",
        },
      });
      this.$nextTick(() => {
        const map = this.$refs.carMap.instance.get("map");
        map.addLayer(carMapPointLayer);
      });
    },

    /**
     * @description: 绘制病害地图点位
     * @param {object} item
     * @return {void}
     */
    drawDefectMapPoint(item) {
      const features = [];
      const feature = new Feature({
        geometry: new Point(item.geometry.coordinates),
        data: item,
        type: "defectPoint",
      });
      // 可以给点位设置样式
      feature.setStyle([
        new Style({
          image: new Icon({
            crossOrigin: "anonymous",
            src: require(`@/assets/screen/index/${item.defecttype}.png`),
            // 图标缩放比例
            scale: 0.5,
          }),
        }),
      ]);
      features.push(feature);
      this.defectLayerSource = new VectorSource({
        features,
      });
      const carMapPointLayer = new VectorLayer({
        source: this.defectLayerSource,
        properties: {
          type: "defectPoint",
        },
      });
      this.$nextTick(() => {
        const map = this.$refs.carMap.instance.get("map");
        map.addLayer(carMapPointLayer);
      });
    },
  },
  destroyed() {
    this.carPointList = [];
    this.mapPointFeatures = [];
    this.carMapPointSource = null;
    this.defectLayerSource = null;
  },
};
</script>

<style lang="scss" scoped>
.inspection-content {
  width: 100%;
  height: 45rem;

  // 内网不需要
  ::v-deep .baseLayerClass {
    filter: grayscale(200%) invert(200%) sepia(50%) hue-rotate(175deg)
      brightness(80%) saturate(550%);
  }
}
</style>
