<template>
  <com-dialog
    title="场景离线包下载"
    :width="500"
    v-model:show="show"
    :hideFloor="state === State.package"
    enterText="下 载"
    @quit="onSuccess(false)"
    @submit="download"
  >
    <div>
      <div class="title">
        {{ stateTitle[state] }}
      </div>

      <div style="margintop: 20px" v-if="state === State.uncreate">
        当前剩余下载次数：
        <span>{{ count }}</span
        >次
      </div>

      <div v-else-if="state === State.package">
        <div
          class="text"
          style="display: flex; justify-content: space-between; margin-top: 15px"
        >
          <span>{{ filename }}</span>
          <span>{{ percent }}%</span>
        </div>
        <div>
          <el-slider :disabled="true" v-model="percent" :show-tooltip="false" />
        </div>
      </div>
    </div>
  </com-dialog>
</template>

<script setup lang="ts">
import { onMounted, onUnmounted, ref } from "vue";
import saveAs from "@/util/file-serve";
import comDialog from "@/components/dialog/index.vue";
import { checkHasDownload, getDownloadProcess, downloadScene, axios } from "@/request";
import { ElMessage } from "element-plus";
import { SceneDpwnloadProps } from "./";

const props = defineProps<SceneDpwnloadProps & { onSuccess: (down: boolean) => void }>();

enum State {
  uncreate,
  package,
  readDown,
}
const getState = (type: number) => {
  const stateTypes = [
    { codes: [0, 2], state: State.uncreate },
    { codes: [1], state: State.package },
    { codes: [3], state: State.readDown },
  ];
  return stateTypes.find((stateType) => stateType.codes.includes(type))?.state!;
};

const show = ref(false);
const state = ref<State>(State.uncreate);
const count = ref<number>(0);
const filename = ref<string>(props.scene.sceneName + ".zip");
const downloadURL = ref<string>();
const percent = ref(0);

const stateTitle = {
  [State.uncreate]: "下载场景离线数据包，可在本地运行查看。",
  [State.package]: "正在打包场景离线数据",
  [State.readDown]: filename.value,
};

// 初始化
const initial = async () => {
  const res = await axios.get(checkHasDownload + props.scene.num);
  state.value = getState(res.data.downloadStatus);
  count.value = res.data.count;
  downloadURL.value = res.data.downloadUrl;

  if (state.value === State.uncreate) {
    const unCountFlag =
      count.value == 0 ||
      (await axios.get(downloadScene + props.scene.num)).data.downloadStatus !== 1;

    if (unCountFlag) {
      ElMessage.error("暂无剩余下载次数");
      throw "暂无剩余下载次数";
    }
  }
  show.value = true;
  if (state.value === State.package) {
    refreshPercent();
  }
};

// 下载
const download = () => {
  if (!downloadURL.value) {
    ElMessage.error("下载链接未生成，请稍等！");
  } else {
    saveAs(downloadURL.value, filename.value);
  }
  props.onSuccess(true);
};

// 进度请求
let timer: any;
const refreshPercent = async () => {
  const res = await axios.get(getDownloadProcess, {
    params: {
      sceneNum: props.scene.num,
      isTiles: true,
    },
  });

  percent.value = parseInt(res.data.percent);
  downloadURL.value = res.data.url;
  if (downloadURL.value) {
    state.value = State.readDown;
    download();
  } else {
    timer = setTimeout(refreshPercent, 1000);
  }
};

onUnmounted(() => clearTimeout(timer));
onMounted(initial);
</script>
