<template>
  <div>
    <div class="mask" v-if="actionState"></div>
    <Transition :enter-active-class="proxy?.animate.rankingWindow.enter"
      :leave-active-class="proxy?.animate.rankingWindow.leave">
      <div class="confirmDiaBgBox" v-if="actionState">
        <div class="confirmDiaBg">
          <div class="confirmDiaWindow">
            <div class="prompt"><i></i><span>{{ actionText }}</span></div>
            <div class="confirmDiaWindow-con">


              <div class="gamePic">
                <template v-if="currentGame == 'game_fruit'">
                  <img src="@/assets/images/game/img2.png" width="200" />
                </template>
                <template v-if="currentGame == 'game_basketball'">
                  <img src="@/assets/images/game/img1.png" width="200" />
                </template>
                <template v-if="currentGame == 'game_football'">
                  <img src="@/assets/images/game/img3.png" width="200" />
                </template>
                <div class="time" v-if="timerNum > 0">
                  <div>{{ timerNum }}</div>
                </div>
              </div>
              <div class="gamePlayer">
                <div class="item" v-for="item in areaStateList" :key="item.area">
                  <div class="player">

  
                      <div><img src="@/assets/images/game/fruit1.png" class="fade-image"
                          :class="{ 'fade-image1': !item.state }"></img></div>
                      <div><img v-if="!item.state" src="@/assets/images/game/fruit2.png" class="fade-image"
                          :class="{ 'fade-image2': !item.state }"></img></div>


                    <!-- <template v-if="currentGame == 'bodyposecontroller'">
                      <div><img src="@/assets/images/game/fruit1.png" class="fade-image"
                          :class="{ 'fade-image1': !item.state }"></img></div>
                      <div><img v-if="!item.state" src="@/assets/images/game/fruit2.png" class="fade-image"
                          :class="{ 'fade-image2': !item.state }"></img></div>
                    </template>
                    <template v-if="currentGame == 'game_fruit'">
                      <div><img src="@/assets/images/game/fruit1.png" class="fade-image"
                          :class="{ 'fade-image1': !item.state }"></img></div>
                      <div><img v-if="!item.state" src="@/assets/images/game/fruit2.png" class="fade-image"
                          :class="{ 'fade-image2': !item.state }"></img></div>
                    </template>
                    <template v-if="currentGame == 'game_basketball'">
                      <div><img src="@/assets/images/game/basketball1.png" class="fade-image"
                          :class="{ 'fade-image1': !item.state }"></img></div>
                      <div><img v-if="!item.state" src="@/assets/images/game/basketball2.png" class="fade-image"
                          :class="{ 'fade-image2': !item.state }"></img></div>
                    </template>
                    <template v-if="currentGame == 'game_football'">
                      <div><img src="@/assets/images/game/football1.png" class="fade-image"
                          :class="{ 'fade-image1': !item.state }"></img></div>
                      <div><img v-if="!item.state" src="@/assets/images/game/football2.png" class="fade-image"
                          :class="{ 'fade-image2': !item.state }"></img></div>
                    </template> -->
                    <div v-if="item.state" class="ok"><img src="@/assets/images/game/ok.png"></div>
                  </div>
                </div>
              </div>
              <div class="picBox"></div>


              <div class="name">
                <template v-if="currentGame == 'game_fruit'">玩法：挥动双手切开水果，失败三次结束游戏</template>
                <template v-if="currentGame == 'game_basketball'">玩法：身体左右移动对准篮筐，双手投篮</template>
                <template v-if="currentGame == 'game_football'">玩法：身体左右移动躲避雪糕筒，踢腿射门</template>
              </div>

              <div class="music"> <el-select v-model="music.id" :popper-append-to-body="false" placeholder="请选择"
                  @change="changeMusic" clearable>
                  <el-option v-for="item in music.list" :key="item.id" :label="item.name" :value="item.id" />
                </el-select></div>
            </div>
          </div>
          <div @click="getExit" class="close"></div>
        </div>
      </div>
    </Transition>
  </div>

</template>
<script setup lang="ts">
import { clearInterval, clearTimeout, setInterval, setTimeout } from 'worker-timers';
import useAppStore from '@/store/modules/app';
import { initSpeech, speckText, playMusic, controlMusic, speckCancel, chineseNumber } from '@/utils/speech';
const { proxy } = getCurrentInstance() as any;
const emit = defineEmits(['confirmExit', 'confirmStart', 'setMusic']);
//父值
const props = defineProps({
  musicId: {
    type: String,
    default: ""
  }
});
const data = reactive<any>({
  currentGame: "",
  currentGameArea: [],
  actionState: false,//窗口状态
  areaStateList: [],
  lock: false,
  actionText: "",
  timer: null,
  timerNum: null,
  music: { id: null, list: [] }
});

const { currentGame, currentGameArea, actionState, areaStateList, lock, actionText, timer, timerNum, music } = toRefs(data);



onBeforeMount(() => {
  //初始化语音
  initSpeech();
  //音乐
  getMusic();
})

onMounted(() => {
})

/**
 * 初始化
 */
const getInit = (e: any) => {
  let area = e.ctrl_name.replace('bodyposecontroller_', '');
  let arr = e.data.result.boxes;
  let myArr = e.data.result.keypoints;
  let result = [];
  for (let i = 0; i < myArr.length; i += 3) {
    result.push(myArr.slice(i, i + 2));
  }
  //console.log("result", result)
  //全部用肘过肩
  let leftA = result[6][1];//右肩Y
  let rightA = result[5][1];//左肩Y
  let leftB = result[8][1];//右肘Y
  let rightB = result[7][1];//左肘Y
  let bizi = result[0][1];//鼻子Y
  if (leftB < leftA || rightB < rightA || leftB < bizi || rightB < bizi) {
    let myIndex = areaStateList.value.findIndex((item: any) => {
      return item.area == area;
    })
    let boxes = [{ x: arr[0], y: arr[3] }, { x: arr[0], y: arr[1] }, { x: arr[2], y: arr[1] }, { x: arr[2], y: arr[3] }];
    areaStateList.value[myIndex].state = true;
    areaStateList.value[myIndex].boxes = boxes;
  }
  // if (currentGame.value == 'bodyposecontroller') {
  //   let leftA = result[6][1];//右肩Y
  //   let rightA = result[5][1];//左肩Y
  //   let leftB = result[8][1];//右肘Y
  //   let rightB = result[7][1];//左肘Y
  //   let bizi = result[0][1];//鼻子Y
  //   if (leftB < leftA || rightB < rightA || leftB < bizi || rightB < bizi) {
  //     let myIndex = areaStateList.value.findIndex((item: any) => {
  //       return item.area == area;
  //     })
  //     let boxes = [{ x: arr[0], y: arr[3] }, { x: arr[0], y: arr[1] }, { x: arr[2], y: arr[1] }, { x: arr[2], y: arr[3] }];
  //     areaStateList.value[myIndex].state = true;
  //     areaStateList.value[myIndex].boxes = boxes;
  //   }
  // }
  // if (currentGame.value == 'game_basketball') {
  //   let leftA = result[6][1];//右肩Y
  //   let rightA = result[5][1];//左肩Y
  //     let leftB = result[8][1];//右肘Y
  //     let rightB = result[7][1];//左肘Y
  //   let bizi = result[0][1];//鼻子Y
  //   if (leftB < leftA || rightB < rightA || leftB < bizi || rightB < bizi) {
  //     let myIndex = areaStateList.value.findIndex((item: any) => {
  //       return item.area == area;
  //     })
  //     let boxes = [{ x: arr[0], y: arr[3] }, { x: arr[0], y: arr[1] }, { x: arr[2], y: arr[1] }, { x: arr[2], y: arr[3] }];
  //     areaStateList.value[myIndex].state = true;
  //     areaStateList.value[myIndex].boxes = boxes;
  //   }
  // }
  // if (currentGame.value == 'game_football') {
  //   let leftA = { x: result[12][0], y: result[12][1] };//大腿
  //   let leftB = { x: result[14][0], y: result[14][1] };//膝盖
  //   let leftC = { x: result[16][0], y: result[16][1] };//脚

  //   let rightA = { x: result[11][0], y: result[11][1] };//大腿
  //   let rightB = { x: result[13][0], y: result[13][1] };//膝盖
  //   let rightC = { x: result[15][0], y: result[15][1] };//脚

  //   let jiaodu1 = calculateAngleAtB(leftA, leftB, leftC)
  //   let jiaodu2 = calculateAngleAtB(rightA, rightB, rightC)
  //   // console.log("jiaodu1",jiaodu1)
  //   // console.log("jiaodu2",jiaodu2)
  //   if (jiaodu1 <= 80 && jiaodu2 >= 120 || jiaodu2 <= 80 && jiaodu2 >= 120) {
  //     let myIndex = areaStateList.value.findIndex((item: any) => {
  //       return item.area == area;
  //     })
  //     let boxes = [{ x: arr[0], y: arr[3] }, { x: arr[0], y: arr[1] }, { x: arr[2], y: arr[1] }, { x: arr[2], y: arr[3] }];
  //     areaStateList.value[myIndex].state = true;
  //     areaStateList.value[myIndex].boxes = boxes;
  //   }
  // }
  // if (currentGame.value == 'game_fruit') {
  //   let leftA = result[6][1];//右肩Y
  //   let rightA = result[5][1];//左肩Y
  //   let leftB = result[8][1];//右肘Y
  //   let rightB = result[7][1];//左肘Y
  //   let bizi = result[0][1];//鼻子Y
  //   if (leftB < leftA || rightB < rightA || leftB < bizi || rightB < bizi) {
  //     let myIndex = areaStateList.value.findIndex((item: any) => {
  //       return item.area == area;
  //     })
  //     let boxes = [{ x: arr[0], y: arr[3] }, { x: arr[0], y: arr[1] }, { x: arr[2], y: arr[1] }, { x: arr[2], y: arr[3] }];
  //     areaStateList.value[myIndex].state = true;
  //     areaStateList.value[myIndex].boxes = boxes;
  //   }
  // }
};

/**
 * 计算B点的夹角度数（∠ABC）
 * @param {Object} pointA - A点坐标 {x, y, z可选}
 * @param {Object} pointB - B点坐标 {x, y, z可选}
 * @param {Object} pointC - C点坐标 {x, y, z可选}
 * @returns {number} B点的夹角度数（保留两位小数）
 */
const calculateAngleAtB = (pointA, pointB, pointC) => {
  // 计算向量BA和向量BC
  const vectorBA = {
    x: pointA.x - pointB.x,
    y: pointA.y - pointB.y,
    z: (pointA.z || 0) - (pointB.z || 0)
  };

  const vectorBC = {
    x: pointC.x - pointB.x,
    y: pointC.y - pointB.y,
    z: (pointC.z || 0) - (pointB.z || 0)
  };

  // 计算点积
  const dotProduct =
    vectorBA.x * vectorBC.x +
    vectorBA.y * vectorBC.y +
    vectorBA.z * vectorBC.z;

  // 计算向量BA的模长
  const lengthBA = Math.sqrt(
    vectorBA.x ** 2 +
    vectorBA.y ** 2 +
    vectorBA.z ** 2
  );

  // 计算向量BC的模长
  const lengthBC = Math.sqrt(
    vectorBC.x ** 2 +
    vectorBC.y ** 2 +
    vectorBC.z ** 2
  );

  // 防止除以零的情况
  if (lengthBA === 0 || lengthBC === 0) {
    throw new Error("点A、B、C不能重合");
  }

  // 计算余弦值
  const cosine = dotProduct / (lengthBA * lengthBC);

  // 由于计算误差可能导致cosine略超出[-1, 1]范围，需要修正
  const clampedCosine = Math.max(Math.min(cosine, 1), -1);

  // 计算弧度并转换为角度
  const angleRadians = Math.acos(clampedCosine);
  const angleDegrees = angleRadians * (180 / Math.PI);

  // 保留两位小数并返回
  return parseFloat(angleDegrees.toFixed(2));
}

/**
 * 打开
 */
const getOpen = async (game: any, area: any) => {
  lock.value = false;
  currentGame.value = game;
  currentGameArea.value = area;
  let list = area.map((item: any) => {
    let obj = {
      area: item,
      state: false
    }
    return obj;
  }) || [];
  areaStateList.value = list;
  actionState.value = true;
  let txt = "举手开始游戏"
  // if (currentGame.value == 'bodyposecontroller') {
  //   txt = "举手开始游戏";
  // }
  // if (currentGame.value == 'game_fruit') {
  //   txt = "举手开始游戏";
  // }
  // if (currentGame.value == 'game_basketball') {
  //   txt = "请做投篮动作开始游戏";
  // }
  // if (currentGame.value == 'game_football') {
  //   txt = "请踢腿开始游戏";
  // }
  actionText.value = txt;
  speckText(actionText.value);
};

/**
 * 关闭
*/
const getExit = () => {
  clearInterval(timer.value);
  timer.value = null;
  timerNum.value = 0;
  speckCancel(); //停止播报
  actionState.value = false;
  emit('confirmExit', {});
};

//获取音乐
const getMusic = async () => {
  const list: any = useAppStore().getMusic();
  if (list.length) {
    music.value.list = list;
  } else {
    await proxy?.$http.train.musicList().then((res: any) => {
      if (res.data.length > 0) {
        let myList: any = res.data;
        music.value.list = myList;
        useAppStore().setMusic(myList);
      }
    });
  }
};

/**
 * 选择音乐
 */
const changeMusic = (data: any) => {
  emit('setMusic', data);
};

/**
 * 设置音乐
 */
const setMusic = (data: any) => {
  music.value.id = data;
};

/**
 * 监听全部OK
 */
watch(
  () => areaStateList.value,
  (newData, oldData) => {
    //都准备就绪就开始
    if (lock.value) {
      return false;
    }
    let state = newData.every((item: any) => {
      return item.state;
    })
    if (state) {
      lock.value = true;
      timerNum.value = 3;
      speckText(timerNum.value);
      timer.value = setInterval(() => {
        timerNum.value--;
        speckText(timerNum.value);
        if (timerNum.value == 0) {
          actionState.value = false;
          clearInterval(timer.value);
          timer.value = null;
          emit('confirmStart', areaStateList.value);
        }
      }, 1000)
    }
  },
  { deep: true }
);


//暴露给父组件用
defineExpose({
  getOpen,
  setMusic,
  getInit
})
</script>
<style lang="scss" scoped>
.mask {
  position: fixed;
  height: 100vh;
  width: 100vw;
  top: 0;
  left: 0;
  background: rgba(0, 0, 0, 0.6);
  z-index: 998;
}

.confirmDiaBgBox {
  position: fixed;
  height: 100vh;
  width: 100vw;
  top: 0;
  left: 0;
  z-index: 998;
  display: flex;
  align-items: center;
  justify-content: center;
}

.confirmDiaBg {
  width: 70%;
  display: flex;
  flex-direction: column;

  .confirmDiaWindow {
    border-radius: 15px;
    opacity: 1;
    text-align: center;
    display: flex;
    align-items: center;
    justify-content: center;
    flex-direction: column;
    margin-bottom: 20px;
    background: linear-gradient(59deg, #092941 -85%, #2A484B 96%);
    box-shadow: inset 0px 1px 0px 2px rgba(255, 255, 255, 0.5577);

    .prompt {
      color: #ffffff;
      font-size: 2.5vh;
      display: flex;
      align-items: center;
      padding-top: 2vh;

      i {
        width: 3vh;
        height: 3vh;
        margin-right: 3px;
        display: block;
        background-image: url('@/assets/images/game/prompt.png');
        background-position: bottom;
        background-repeat: no-repeat;
        background-size: 100%;
      }
    }

    .confirmDiaWindow-con {
      width: 85%;
      padding: 25px;
      display: flex;
      flex-direction: column;
      align-items: center;

      .gamePic {
        border: 5px solid #3BDDCE;
        width: calc(30vh * (1920 / 1080));
        height: 30vh;
        position: relative;
        display: flex;

        .time {
          position: absolute;
          left: 0;
          top: 0;
          width: 100%;
          height: 100%;
          background: rgba(0, 0, 0, 0.5);
          color: #ffffff;
          font-size: 10rem;
          display: flex;
          align-items: center;
          justify-content: center;
        }

        img {
          width: 100%;
          height: 100%;
        }
      }

      .gamePlayer {
        display: flex;
        width: calc(30vh * (1920 / 1080));
        position: relative;
        margin-top: calc(22vh * (1000 / 518) / -2);

        .item {
          flex: 1;
          display: flex;
          justify-content: center;

          .player {
            position: relative;
            width: 22vh;
            height: calc(22vh * (1000 / 518));
          }

          .ok {
            width: 8vh;
            height: 8vh;
            position: absolute;
            top: 50%;
            left: 50%;
            margin-top: 1vh;
            margin-left: -4vh;

            img {
              width: 100%;
            }
          }

          .fade-image {
            width: 100%;
            height: 100%;
            position: absolute;
            left: 0;
            top: 0;
          }

          .fade-image1 {
            animation: fadeOpacity1 2s infinite;
          }

          .fade-image2 {
            animation: fadeOpacity2 2s infinite;
          }

          @keyframes fadeOpacity1 {
            0% {
              opacity: 1;
            }

            50% {
              opacity: 0;
            }

            100% {
              opacity: 1;
            }
          }

          @keyframes fadeOpacity2 {
            0% {
              opacity: 0;
            }

            50% {
              opacity: 1;
            }

            100% {
              opacity: 0;
            }
          }
        }
      }

      .picBox {
        width: calc(30vh * (1920 / 1080) * 2);
        height: 25vh;
        max-width: 100%;
        background-image: url('@/assets/images/game/bg.png');
        background-position: bottom;
        background-repeat: no-repeat;
        background-size: 100% 100%;
        display: flex;
        justify-content: center;
        position: relative;
        margin-top: -15vh;

      }


      .name {
        width: 100%;
        color: #ffffff;
        font-size: 2.8vh;
        padding: 20px 0;
      }
    }

    .music {
      width: 120px;
      display: block;
      cursor: pointer;
      background-position: left center;
      background-repeat: no-repeat;
      background-size: 1.1rem 1.1rem;
      background-image: url('@/assets/images/common/music.png');
      padding-left: 1.8rem;

      ::v-deep(.el-select__wrapper) {
        background: none;
        color: #ffffff;
        .el-select__placeholder{
          color: #ffffff;
        }
      }
    }
  }

  .close {
    margin: 0 auto;
  }
}
</style>
