import { getBillboardCanvases } from "./utils";

const Cesium = window.Cesium;

// 获取经纬度
export const getPosition = (x, y, z = 0.0) => {
  return Cesium.Cartesian3.fromDegrees(x, y, z);
};

// 创建倾斜摄影
export const createObliquePhotography = (url, viewer) => {
  const tileset = new Cesium.Cesium3DTileset({
    url,
    skipLevelOfDetail: true,
    baseScreenSpaceError: 1024,
    maximumScreenSpaceError: 128, // 数值加大，能让最终成像变模糊
    skipScreenSpaceErrorFactor: 16,
    skipLevels: 1,
    immediatelyLoadDesiredLevelOfDetail: false,
    loadSiblings: true, // 如果为true则不会在已加载完概况房屋后，自动从中心开始超清化房屋
    cullWithChildrenBounds: true,
    cullRequestsWhileMoving: true,
    cullRequestsWhileMovingMultiplier: 10, // 值越小能够更快的剔除
    preloadWhenHidden: true,
    preferLeaves: true,
    maximumMemoryUsage: 128, // 内存分配变小有利于倾斜摄影数据回收，提升性能体验
    progressiveResolutionHeightFraction: 0.5, // 数值偏于0能够让初始加载变得模糊
    dynamicScreenSpaceErrorDensity: 0.5, // 数值加大，能让周边加载变快
    dynamicScreenSpaceErrorFactor: 1, // 不知道起了什么作用没，反正放着吧先
    dynamicScreenSpaceError: true, // 有了这个后，会在真正的全屏加载完之后才清晰化房屋
  });

  tileset.readyPromise.then((tileset) => {
    // 笛卡尔转换为弧度
    const cartographic = Cesium.Cartographic.fromCartesian(
      tileset.boundingSphere.center,
    );
    const lng = Cesium.Math.toDegrees(cartographic.longitude); // 使用经纬度和弧度的转换，将WGS84弧度坐标系转换到目标值，弧度转度
    const lat = Cesium.Math.toDegrees(cartographic.latitude);
    // 计算中心点位置的地表坐标
    const surface = Cesium.Cartesian3.fromDegrees(lng, lat, 0);
    // 偏移后的坐标
    const offset = Cesium.Cartesian3.fromDegrees(lng, lat, 5);
    const translation = Cesium.Cartesian3.subtract(
      offset,
      surface,
      new Cesium.Cartesian3(),
    );
    tileset.modelMatrix = Cesium.Matrix4.fromTranslation(translation);
  });
  viewer.scene.primitives.add(tileset);
};

// 创建唯一Id
export const createId = () => {
  return Cesium.createGuid();
};

// 创建数据源
export const createEntityCollection = (name) => {
  return new Cesium.CustomDataSource(`${name}_${createId()}`);
};

// 创建 billboard
export const getBillboard = async ({ image, name = "" }) => {
  const { base64, width, height } = await getBillboardCanvases(image, name);
  return {
    image: base64,
    width,
    height,
    verticalOrigin: Cesium.VerticalOrigin.BOTTOM,
    horizontalOrigin: Cesium.HorizontalOrigin.CENTER,
    heightReference: Cesium.HeightReference.CLAMP_TO_GROUND,
    disableDepthTestDistance: Number.POSITIVE_INFINITY,
    clampToGround: true,
  };
};

// 移除数据源
export const removeEntityCollection = (viewer, name) => {
  viewer.dataSources._dataSources
    .filter(ds => ds.name.startsWith(`${name}_`))
    .forEach((item) => {
      viewer.dataSources.remove(item);
    });
};

// 合并数据源
export const createMergedEntityCollection = (viewer, name) => {
  const mergedDataSource = createEntityCollection(name);
  viewer.dataSources._dataSources
    .filter(ds =>
      ds.name.startsWith(`${name.substring(0, name.indexOf("Merged"))}_`),
    )
    .forEach((dataSource) => {
      dataSource.entities.values.forEach((entity) => {
        mergedDataSource.entities.add(entity);
      });
    });
  return mergedDataSource;
};

// 添加合并数据源
export const addMergedEntityCollection = async (viewer, firstName, lastName = "") => {
  const mergedDataSource = createMergedEntityCollection(viewer, `${firstName}Merged${lastName ? `_${lastName}` : ""}`);
  await viewer.dataSources.add(mergedDataSource);
  removeEntityCollection(viewer, `${firstName}${lastName ? `_${lastName}` : ""}`);
  return mergedDataSource;
};
