<script lang="ts" setup>
import { Check, Picture as IconPicture, Refresh } from '@element-plus/icons-vue';
import { useCountdown } from '@vueuse/core';
import { onBeforeUnmount, onMounted, ref, shallowRef } from 'vue';
import { useRouter } from 'vue-router';
import { getQrCode, getQrCodeResult, getUserInfo } from '@/api';
import { useUserStore } from '@/stores';
import { useSessionStore } from '@/stores/modules/session.ts';
import { WECHAT_QRCODE_TYPE } from '@/utils/user.ts';
import { useGuideTour } from '@/hooks/useGuideTour';

const props = defineProps({
  type: {
    type: String,
    default: WECHAT_QRCODE_TYPE.LoginOrRegister,
  },
});
const emit = defineEmits(['bind-wechat']);
const QrCodeType = props.type || WECHAT_QRCODE_TYPE.LoginOrRegister;
// 响应式状态
// const urlText = shallowRef('');
const qrCodeUrl = ref('');
const isExpired = ref(false);
const isScanned = ref(false);
const isConfirming = ref(false);
const isAuthorization = ref(false);
const confirmCountdownSeconds = shallowRef(180);
const sceneStr = ref(''); // 场景值，用于标识二维码
const userStore = useUserStore();
const router = useRouter();
const sessionStore = useSessionStore();
const isQrCodeError = ref(false);
const { startFullTour } = useGuideTour();
// 二维码倒计时实例
const { start: qrStart, stop: qrStop } = useCountdown(shallowRef(600), {
  interval: 1000,
  onComplete: () => {
    isExpired.value = true;
    stopPolling();
  },
});
// 计算
const isLoading = computed(() => {
  return qrCodeUrl.value ? false : !isQrCodeError.value;
});
// 确认登录倒计时实例
const { start: confirmStart, stop: confirmStop } = useCountdown(confirmCountdownSeconds, {
  interval: 1000,
  onComplete: () => {
    isExpired.value = true;
    isConfirming.value = false;
    stopPolling();
  },
});

// 轮询相关
let statusPolling: number | null = null;

// 获取登录二维码图片和二维码标识
async function fetchQRCodeInfo() {
  try {
    isQrCodeError.value = false;
    const param = {
      sceneType: QrCodeType,
    };
    const response = await getQrCode(param);
    const urlObj = new URL(response.data.qrCodeUrl);
    const params = new URLSearchParams(urlObj.search);
    const ticketValue = params.get('ticket');
    if (response && response.data.qrCodeUrl && response.data.scene && ticketValue) {
      qrCodeUrl.value = response.data.qrCodeUrl;
      sceneStr.value = response.data.scene;
      return true;
    }
    return false;
  }
  catch (err: any) {
    return false;
  }
}

// 轮询二维码状态
async function checkQRCodeStatus() {
  if (!sceneStr.value)
    return;
  try {
    const param = {
      scene: sceneStr.value,
    };
    const response = await getQrCodeResult(param);

    switch (response.data.sceneResult) {
      case 'Wait': // Wait
        // 继续等待
        break;
      case 'Login': // Login
        // 登录成功
        await handleLoginSuccess(response.data.token, response.data.refreshToken);
        break;
      case 'Register': // Register
        // 需要注册
        handleRegister();
        break;
      case 'Bind': // Bind
        // 绑定成功
        handleBind();
        break;
      case 'Expired': // Expired
        // 二维码过期
        isExpired.value = true;
        stopPolling();
        break;
      default:
        console.warn('未知状态:', response.data.sceneResult);
    }

    // 更新UI状态
    updateUIStatus(response.data.sceneResult);
  }
  catch (error) {
    console.error('检查二维码状态失败:', error);
  }
}

// 处理登录成功
async function handleLoginSuccess(token: string, refreshToken: string) {
  // 停止轮询
  stopPolling();
  userStore.setToken(token, refreshToken);
  const resUserInfo = await getUserInfo();

  // 判断是否为新用户（注册时间小于1小时）
  const creationTime = resUserInfo.data.user.creationTime; // 格式: "2024-11-01 12:01:34"
  const isNewUser = checkIsNewUser(creationTime);

  userStore.setUserInfo(resUserInfo.data);
  // 提示用户
  ElMessage.success('登录成功');

  await router.replace('/');
  await sessionStore.requestSessionList(1, true);
  userStore.closeLoginDialog();

  // 如果是新用户，延迟500ms后自动触发新手引导
  if (isNewUser) {
    setTimeout(() => {
      startFullTour();
    }, 500);
  }
}

// 判断是否为新用户（注册时间距离当前时间小于1小时）
function checkIsNewUser(creationTimeStr: string): boolean {
  try {
    // 解析注册时间字符串 "2024-11-01 12:01:34"
    const creationTime = new Date(creationTimeStr.replace(' ', 'T'));
    const currentTime = new Date();

    // 计算时间差（毫秒）
    const timeDiff = currentTime.getTime() - creationTime.getTime();

    // 1小时 = 60分钟 * 60秒 * 1000毫秒 = 3600000毫秒
    const oneHourInMs = 60 * 60 * 1000;

    return timeDiff < oneHourInMs;
  }
  catch (error) {
    console.error('解析注册时间失败:', error);
    return false;
  }
}

// 处理注册授权
function handleRegister() {
  ElMessage.info('请在微信授权');
}

// 处理绑定
async function handleBind() {
  // 停止轮询
  stopPolling();
  // 处理账号绑定逻辑
  ElMessage.success('微信绑定成功');
  const resUserInfo = await getUserInfo();
  userStore.setUserInfo(resUserInfo.data);
  // 调用父组件方法
  emit('bind-wechat');
}

// 更新UI状态
function updateUIStatus(status: string) {
  switch (status) {
    case 'Wait': // Wait
      isScanned.value = false;
      isConfirming.value = false;
      break;
    case 'Login': // Login - 已扫码并确认
    case 'Bind': // Bind - 已扫码并确认
      isScanned.value = true;
      isConfirming.value = false;
      break;
    case 'Register': // Register - 已扫码并确认
      isScanned.value = true;
      isAuthorization.value = true;
      break;
    case 'Expired': // Expired
      isExpired.value = true;
      isScanned.value = false;
      isConfirming.value = false;
      break;
    default:
      // 其他状态认为是已扫码但未确认
      isScanned.value = true;
      isConfirming.value = true;
  }
}

/** 停止所有轮询 */
function stopPolling() {
  if (statusPolling) {
    clearInterval(statusPolling);
    statusPolling = null;
  }
}

/** 刷新二维码 */
// async function handleRefresh() {
//   isExpired.value = false;
//   isQrCodeError.value = false;
//   isScanned.value = false;
//   isConfirming.value = false;
//   stopPolling();
//
//   const success = await fetchQRCodeInfo();
//   if (success) {
//     qrStart(shallowRef(600));
//     startStatusPolling();
//   }
//   else {
//     isQrCodeError.value = true;
//     stopPolling();
//     ElMessage.error('刷新二维码失败');
//   }
// }

/** 刷新二维码按钮 */
async function handleRefresh() {
  await initQRCode();
}

/** 启动状态轮询 */
function startStatusPolling() {
  stopPolling(); // 先停止之前的轮询

  statusPolling = setInterval(async () => {
    if (!isExpired.value) {
      await checkQRCodeStatus();
    }
  }, 2000); // 每2秒轮询一次
}

/** 组件初始化 */
onMounted(async () => {
  await initQRCode();
  // const success = await fetchQRCodeInfo();
  // if (success) {
  //   qrStart();
  //   startStatusPolling();
  // }
  // else {
  //   isQrCodeError.value = true;
  //   stopPolling();
  //   ElMessage.error('初始化二维码失败');
  // }
});

/** 初始化或刷新二维码 */
async function initQRCode() {
  // 清理旧的定时器和轮询
  qrStop();
  confirmStop();
  stopPolling();

  const success = await fetchQRCodeInfo();
  if (success) {
    isExpired.value = false;
    isQrCodeError.value = false;
    isScanned.value = false;
    isConfirming.value = false;

    qrStart(); // 重新开始倒计时
    startStatusPolling(); // 开始轮询
  }
  else {
    isQrCodeError.value = true;
    ElMessage.error('获取二维码失败');
  }
}

/** 组件卸载清理 */
onBeforeUnmount(() => {
  qrStop();
  confirmStop();
  stopPolling();
});

onMounted(() => {

});
</script>

<template>
  <div class="qr-wrapper">
    <div class="tip">
      {{ QrCodeType === WECHAT_QRCODE_TYPE.Bind ? '请使用手机微信扫码绑定' : '请使用手机微信扫码登录/注册' }}
    </div>

    <div class="qr-img-wrapper">
      <el-image v-loading="isLoading" :src="qrCodeUrl" alt="登录二维码" class="qr-img">
        <template #error>
          <el-icon><IconPicture /></el-icon>
        </template>
      </el-image>

      <!-- 失败覆盖层 -->
      <div v-if="isQrCodeError" class="expired-overlay" @click.stop="handleRefresh">
        <div class="expired-content">
          <p class="expired-text">
            二维码获取失败
          </p>
          <el-button class="refresh-btn" link>
            <el-icon><Refresh /></el-icon>
            点击刷新
          </el-button>
        </div>
      </div>

      <!-- 过期覆盖层 -->
      <div v-if="isExpired" class="expired-overlay" @click.stop="handleRefresh">
        <div class="expired-content">
          <p class="expired-text">
            二维码失效
          </p>
          <el-button class="refresh-btn" link>
            <el-icon><Refresh /></el-icon>
            点击刷新
          </el-button>
        </div>
      </div>

      <!-- 扫码成功覆盖层 -->
      <div v-if="isScanned && !isExpired" class="scanned-overlay">
        <div class="scanned-content">
          <p class="scanned-text">
            <el-icon class="success-icon">
              <Check />
            </el-icon>
            已扫码
          </p>

          <p v-if="isConfirming" class="scanned-text">
            请在手机端确认登录
          </p>
          <p v-if="isAuthorization" class="scanned-text">
            请在手机端微信继续操作<br>
            请关注微信服务号并授权
          </p>

          <p v-else class="scanned-text">
            处理中...
          </p>
        </div>
      </div>
    </div>

    <div class="help-text">
      {{ QrCodeType === WECHAT_QRCODE_TYPE.Bind ? '扫码后请在微信服务号中授权' : '扫码后请在微信服务号中授权' }}
    </div>

    <div v-if="QrCodeType === WECHAT_QRCODE_TYPE.LoginOrRegister" class="tip-old-user">
      <p>提示：</p>
      <p>意社区老用户可用原方式登录</p>
      <p>登录后前往个人中心绑定微信</p>
    </div>
    <div v-if="QrCodeType === WECHAT_QRCODE_TYPE.Bind" class="tip-old-user-bind">
      提示：<br>
      若扫码的微信已注册过意社区账号<br>
      将直接解绑到当前登录账号
    </div>
  </div>
</template>

<style scoped lang="scss">
.tip-old-user{
  line-height: 1.5;
  margin: 5px 0;
  color: #FF4D4F;
  display: flex;
  flex-direction: column;
    text-align: center;
}
.tip-old-user-bind{
  line-height: 1.5;
  margin: 5px 0;
  color: #FF4D4F;
  display: flex;
  align-items: center;
}
.qr-wrapper {
  display: flex;
  flex-direction: column;
  gap: 8px;
  align-items: center;
  .tip {
    font-size: 16px;
    font-weight: 500;
    color: #303133;
    margin-bottom: 10px;
  }
  .qr-img-wrapper {
    position: relative;
    width: 180px;
    height: 180px;
    padding: 12px;
    overflow: hidden;
    border: 1px solid #f0f2f5;
    border-radius: 16px;
    box-shadow: 0 2px 12px 0 rgb(0 0 0 / 8%);
    .qr-img {
      display: flex;
      align-items: center;
      justify-content: center;
      width: 100%;
      height: 100%;
      .el-icon {
        font-size: 18px;
        color: #909399;
      }
    }
    .expired-overlay,
    .scanned-overlay {
      position: absolute;
      top: 0;
      left: 0;
      display: flex;
      align-items: center;
      justify-content: center;
      width: 100%;
      height: 100%;
      border-radius: 16px;
    }
    .expired-overlay {
      cursor: pointer;
      background: hsl(0deg 0% 100% / 95%);
      .expired-content {
        display: flex;
        flex-direction: column;
        gap: 8px;
        text-align: center;
        .expired-text {
          font-size: 14px;
          color: #909399;
        }
      }
    }
    .scanned-overlay {
      cursor: default;
      background: hsl(120deg 60% 97% / 95%);
      .scanned-content {
        display: flex;
        flex-direction: column;
        gap: 8px;
        align-items: center;
        .success-icon {
          font-size: 18px;
          color: #67c23a;
        }
        .scanned-text {
          display: flex;
          gap: 8px;
          align-items: center;
          font-size: 14px;
          color: #606266;
        }
        .countdown-text {
          font-size: 12px;
          color: #909399;
        }
      }
    }
  }
  .help-text {
    font-size: 12px;
    color: #909399;
  }
}
</style>
