<template>
  <div class="md:max-w-[720px] mx-auto">
    <n-card segmented>
      <template #header>
        <n-page-header @back="navigateTo('/')">
          <template #title>Challenge #{{ challenge?.id }}</template>
          <template #subtitle>
            <div class="flex items-center gap-2">
              <n-tag size="small" class="case-capital">{{ challenge?.status?.replaceAll("-", " ") }}</n-tag>
            </div>
          </template>
        </n-page-header>
      </template>

      <div id="answering-content" v-if="challenge?.status === 'in-progress'">
        <problem-solution-program
          v-if="problem.type === 'programming'"
          v-model:answers="answers"
          :challenge="challenge"
          :problem="problem"
        />
      </div>

      <div id="preview-challenge" class="flex flex-col gap-4" v-else>
        <div>
          <div class="font-bold">状态</div>
          <div class="case-capital">{{ challenge?.status?.replaceAll("-", " ") }}</div>
        </div>
        <div>
          <div class="font-bold">问题</div>
          <div>
            <nuxt-link target="_blank" :to="`/problems/${challenge.problem}`">
              #{{ challenge?.problem }} | {{ problem?.title }}
            </nuxt-link>
          </div>
        </div>
        <div>
          <div class="font-bold">答案</div>
          <client-only>
            <div class="mt-2 mx-[-4px]">
              <problem-preview-program
                v-if="problem.type === 'programming'"
                :answers="answers"
                :challenge="challenge"
                :problem="problem"
              />
            </div>
          </client-only>
        </div>
        <div>
          <div class="font-bold">结果</div>
          <n-card embedded class="mt-2 mx-[-4px]">
            <div v-if="challenge?.details?.cases"></div>
            <n-empty v-else description="未进行判题，暂无挑战结果" />
          </n-card>
        </div>
      </div>

      <template #action>
        <div v-if="challenge?.status === 'in-progress'" id="answering-widgets" class="w-full flex justify-between">
          <div class="flex gap-2">
            <n-button secondary circle class="rounded-[4px]" type="warning" :disabled="submitting" @click="save">
              <template #icon>
                <n-icon :component="Save" />
              </template>
            </n-button>
          </div>
          <div class="flex gap-2">
            <n-button secondary type="error" :disabled="submitting" @click="abandon">放弃</n-button>
            <n-button type="primary" :disabled="submitting" @click="submit">提交</n-button>
          </div>
        </div>
      </template>
    </n-card>
  </div>
</template>

<script setup lang="ts">
import { NButton, NCard, NPageHeader, NTag, NIcon, NEmpty, useDialog, useMessage } from "naive-ui";
import { Save } from "@vicons/carbon";

const route = useRoute();
const client = useSupabaseClient();
const message = useMessage();
const dialog = useDialog();

const submitting = ref(false);

const { data: challenge } = await client
  .from("challenges")
  .select<any, any>("*")
  .eq("id", route.params.id)
  .single();

const { data: problem } = await client
  .from("problems")
  .select<any, any>("*")
  .eq("id", challenge?.problem)
  .single();

useHead({
  title: challenge ? `挑战 #${challenge.id}` : "挑战 #404"
});

const answers = ref(challenge?.answers ?? {});

async function save() {
  submitting.value = true;
  const instance = message.loading("正在保存，请稍后……");

  const { error } = await client
    .from("challenges")
    // @ts-ignore
    .update<any>({
      answers: answers.value
    })
    .eq("id", challenge.id);

  if (error != null) {
    message.error(`Something went wrong... ${error.message}`);
  }

  instance.destroy();
  submitting.value = false;
}

onMounted(() => {
  document.addEventListener("keydown", (event) => {
    const prefixKey = navigator.platform.indexOf("Mac") == 0 ? event.metaKey : event.ctrlKey;
    if (prefixKey && event.key == "s") {
      event.preventDefault();
      save();
    }
  });
});

function abandon() {
  const instance = dialog.warning({
    title: "警告",
    content: "你确定要放弃该次挑战？这会让该挑战立刻转化为放弃状态，并且扣除 5 点社会信用点，三思而后行！",
    positiveText: "确定",
    negativeText: "再试试",
    onPositiveClick: async () => {
      await client
        .from("challenges")
        // @ts-ignore
        .update<any>({ status: "abandoned" })
        .eq("id", challenge.id);

      const delay = (ms: number) => new Promise(res => setTimeout(res, ms));

      instance.loading = true;
      message.info("已放弃挑战该题");

      await delay(1850);
      window.close();
    }
  });
}

async function submit() {
  await save();

  const instance = dialog.warning({
    title: "警告",
    content: "你确定要提交吗？确认提交后无法再次修改答案，等待判题可能需要一段时间。",
    positiveText: "确定",
    negativeText: "不确定",
    onPositiveClick: async () => {
      instance.loading = true;

      const inst = message.loading("正在提交中，请稍后……");

      const { error } = await client
        .from("challenges")
        // @ts-ignore
        .update<any>({ status: "submitted" })
        .eq("id", challenge.id);

      if (error != null) {
        message.error(`Something went wrong... ${error.message}`);
      }

      inst.destroy();
      message.success("提交成功！即将跳转结果页面……");

      const delay = (ms: number) => new Promise(res => setTimeout(res, ms));

      await delay(1850);
      reloadNuxtApp();
    }
  });
}
</script>
