<script setup lang="ts">
import { ref, onMounted, onUnmounted } from 'vue';
import { useRoute, useRouter } from 'vue-router';
import axios, { AxiosError } from 'axios';
import type { Player } from '../models/public';
import TagSelector from './TagSelector.vue';

const route = useRoute();
const router = useRouter();
const backendUrl = import.meta.env.VITE_BACKEND_URL;
const eventSource = ref<EventSource | null>(null);

// lobby state
const players = ref<Player[]>([]);
const creatorName = ref<string>('Unknown');
const creatorId = ref<string>('');
const isCreator = ref(false);
const errorMessage = ref<string>('');
const isLoading = ref(true);
const lobbyCode = ref(route.params.code as string);
const playerId = ref(localStorage.getItem('playerId') || '');

// settings section
const numberOfQuestions = ref(5);
const secondsPerRound = ref(30);
const pointsToWin = ref(10);
const tags = ref<string[]>([]);

async function fetchLobby(): Promise<void> {
  try {
    const result = await axios.get(`${backendUrl}/lobbies/${lobbyCode.value}/lobby`);
    const data = result.data;

    numberOfQuestions.value = data.numberofquestions;
    secondsPerRound.value = data.secondsperround;
    pointsToWin.value = data.pointstowin;
    tags.value = data.tags || [];
  } catch (error) {
    console.error('Error fetching lobby:', error);
    errorMessage.value = 'Failed to fetch lobby data.';
  }
}

async function saveSettings(): Promise<void> {
  try {
    await axios.put(`${backendUrl}/lobbies/${lobbyCode.value}/settings`, {
      numberOfQuestions: numberOfQuestions.value,
      secondsPerRound: secondsPerRound.value,
      pointsToWin: pointsToWin.value,
      tags: tags.value,
    });
  } catch (error) {
    console.error('Error saving settings:', error);
    errorMessage.value = 'Failed to save lobby settings.';
  }
}

async function fetchPlayers(): Promise<void> {
  try {
    const response = await axios.get(`${backendUrl}/lobbies/${lobbyCode.value}/players`);
    players.value = response.data;
  } catch (error) {
    console.error('Error fetching players:', error);
    errorMessage.value = 'Failed to load players. Please try refreshing.';
  }
}

async function addPlayer(): Promise<void> {
  try {
    await axios.post(`${backendUrl}/lobbies/${lobbyCode.value}/players/${playerId.value}`);
  } catch (error) {
    console.error('Error adding player:', error);
    errorMessage.value = 'Failed to join lobby. The name might already be taken.';
  }
}

async function checkIfCreator(): Promise<void> {
  isLoading.value = true;
  try {
    const response = await axios.get(`${backendUrl}/lobbies/${lobbyCode.value}/creator`);
    if (response.data?.id) {
      creatorName.value = response.data.name || 'Unknown';
      creatorId.value = response.data.id.toString();
      isCreator.value = creatorId.value === playerId.value;
    } else {
      errorMessage.value = 'Could not determine lobby creator.';
    }
  } catch (e: unknown) {
    const error = e as AxiosError;
    console.error('Error checking if creator:', error);
    errorMessage.value = error.response
      ? `API Error: ${error.response.status} - ${JSON.stringify(error.response.data) || 'Unknown error'}`
      : 'Failed to check creator status. Network error.';
  } finally {
    isLoading.value = false;
  }
}

async function startGame(): Promise<void> {
  try {
    await axios.post(`${backendUrl}/lobbies/${lobbyCode.value}/start`);
  } catch (error) {
    console.error('Error starting game:', JSON.stringify(error));
    errorMessage.value = 'Failed to start game. Please try again.';
  }
}

async function leaveLobby(): Promise<void> {
  if (playerId.value && lobbyCode.value) {
    try {
      await axios.delete(`${backendUrl}/lobbies/${lobbyCode.value}/players/${playerId.value}`);
      await router.push('/lobbies');
    } catch (error) {
      console.error('Error leaving lobby:', error);
    }
  }
}

function setupEventSource(): void {
  const evtSource = new EventSource(`${backendUrl}/lobbies/${lobbyCode.value}/events`);
  evtSource.onmessage = async (event) => {
    console.log('handle event', event);

    try {
      const data = JSON.parse(event.data);
      if (data.type === 'new_player' || data.type === 'player_left') {
        await fetchPlayers();
      } else if (data.type === 'game_started') {
        router.push(`/lobby/${lobbyCode.value}/game`);
      } else if (data.type === 'lobby_updated') {
        await fetchLobby();
      } else {
        console.log('unhandeld state', event.data);
      }
    } catch (err) {
      console.error('Error parsing event data:', err, event.data);
    }
  };

  evtSource.onerror = () => {
    errorMessage.value = 'Live updates disconnected. Please refresh the page.';
  };

  eventSource.value = evtSource;
}

let saveTimeout: number | null = null;

const debouncedSave = () => {
  // Clear any existing timeout
  if (saveTimeout !== null) {
    clearTimeout(saveTimeout);
  }
  
  // Set a new timeout to save after 300ms
  saveTimeout = setTimeout(async () => {
    try {
      await saveSettings();
    } finally {
      // Reset saving state after a short delay to show feedback
      setTimeout(() => {
      }, 500);
    }
  }, 300) as unknown as number;
};

const handleSave = () => {
  if (isCreator.value) {
    debouncedSave();
  }
};

// Watch for changes in all settings
// watch(numberOfQuestions, debouncedSave);
// watch(secondsPerRound, debouncedSave);
// watch(pointsToWin, debouncedSave);
// watch(tags, debouncedSave, { deep: true });

async function setupLobby(): Promise<void> {
  await fetchLobby();
  await addPlayer();
  await fetchPlayers();
  await checkIfCreator();
  setupEventSource();
}

onMounted(async () => {
  try {
    await setupLobby();
  } catch (error) {
    console.error('Error during component initialization:', error);
    errorMessage.value = 'Error loading lobby. Please try again.';
  } finally {
    isLoading.value = false;
  }
});

onUnmounted(() => {
  if (eventSource.value) {
    eventSource.value.close();
  }
});
</script>

<template>
  <div class="lobby bg-gradient-to-br from-gray-900 via-gray-900 to-gray-900 min-h-screen text-white px-4 py-10">
    <div class="flex justify-between max-w-7xl mx-auto">
      <div class="w-1/3 bg-gray-800 p-6 rounded-lg shadow-lg">
        <div>
          <h1 class="text-2xl font-extrabold mb-2">
            Lobby Code: <span class="text-blue-400">{{ lobbyCode }}</span>
          </h1>
          <div class="mt-3 mb-4">
            <div class="flex items-center mb-2">
              <span class="text-gray-300">Created by:</span>
              <span class="ml-2 font-semibold text-white bg-gray-700 px-3 py-1 rounded-md">
                {{ creatorName || 'Unknown' }}
                <span
                  v-if="isCreator"
                  class="ml-1 text-blue-300"
                >
                  (You)
                </span>
              </span>
            </div>
          </div>
        </div>

        <div class="flex items-center mt-6 mb-4">
          <svg
            xmlns="http://www.w3.org/2000/svg"
            class="h-6 w-6 text-white-400 mr-2"
            fill="none"
            viewBox="0 0 24 24"
            stroke="currentColor"
          >
            <path
              stroke-linecap="round"
              stroke-linejoin="round"
              stroke-width="2"
              d="M10.325 4.317c.426-1.756 2.924-1.756 3.35 0a1.724 1.724 0 002.573 1.066c1.543-.94 3.31.826 2.37 2.37a1.724 1.724 0 001.065 2.572c1.756.426 1.756 2.924 0 3.35a1.724 1.724 0 00-1.066 2.573c.94 1.543-.826 3.31-2.37 2.37a1.724 1.724 0 00-2.572 1.065c-.426 1.756-2.924 1.756-3.35 0a1.724 1.724 0 00-2.573-1.066c-1.543.94-3.31-.826-2.37-2.37a1.724 1.724 0 00-1.065-2.572c-1.756-.426-1.756-2.924 0-3.35a1.724 1.724 0 001.066-2.573c-.94-1.543.826-3.31 2.37-2.37.996.608 2.296.07 2.572-1.065z"
            />
            <path
              stroke-linecap="round"
              stroke-linejoin="round"
              stroke-width="2"
              d="M15 12a3 3 0 11-6 0 3 3 0 016 0z"
            />
          </svg>
          <h2 class="text-2xl text-white font-bold bg-clip-text">
            Game Settings
          </h2>
        </div>
        <div class="w-full h-0.5 bg-blue-400 mb-6 rounded-full" />

        <div class="space-y-4">
          <div>
            <div class="mb-5 relative">
              <label
                for="numQuestions"
                class="flex items-center text-sm font-medium text-blue-300 mb-2"
              >
                <svg
                  xmlns="http://www.w3.org/2000/svg"
                  class="h-4 w-4 mr-2"
                  fill="none"
                  viewBox="0 0 24 24"
                  stroke="currentColor"
                >
                  <path
                    stroke-linecap="round"
                    stroke-linejoin="round"
                    stroke-width="2"
                    d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2"
                  />
                </svg>
                Number of Questions
              </label>
  
              <div class="relative">
                <input
                  id="numQuestions"
                  v-model.number="numberOfQuestions"
                  type="number"
                  min="1"
                  :disabled="!isCreator"
                  class="w-full px-4 py-2 pl-5 rounded-lg bg-gray-700 border border-gray-600 text-white text-lg focus:outline-none focus:ring-2 focus:ring-blue-500 focus:border-blue-500 transition-all duration-200 disabled:opacity-60 disabled:cursor-not-allowed"
                  @blur="handleSave"
                >
              </div>
            </div>          
          </div>

          <div>
            <div class="mb-5 relative">
              <label
                for="secondsPerRound"
                class="flex items-center text-sm font-medium text-blue-300 mb-2"
              >
                <svg
                  xmlns="http://www.w3.org/2000/svg"
                  class="h-4 w-4 mr-2"
                  fill="none"
                  viewBox="0 0 24 24"
                  stroke="currentColor"
                >
                  <path
                    stroke-linecap="round"
                    stroke-linejoin="round"
                    stroke-width="2" 
                    d="M12 8v4l3 3m6-3a9 9 0 11-18 0 9 9 0 0118 0z"
                  />
                </svg>
                Seconds Per Round
              </label>
  
              <div class="relative">
                <input
                  id="secondsPerRound"
                  v-model.number="secondsPerRound"
                  type="number"
                  min="5"
                  :disabled="!isCreator"
                  class="w-full px-4 py-2 pl-5 rounded-lg bg-gray-700 border border-gray-600 text-white text-lg focus:outline-none focus:ring-2 focus:ring-blue-500 focus:border-blue-500 transition-all duration-200 disabled:opacity-60 disabled:cursor-not-allowed"
                  @blur="handleSave"
                >
              </div>
            </div>
          </div>

          <div>
            <div class="mb-5 relative">
              <label
                for="pointsToWin"
                class="flex items-center text-sm font-medium text-blue-300 mb-2"
              >
                <svg
                  xmlns="http://www.w3.org/2000/svg"
                  class="h-4 w-4 mr-2"
                  fill="none"
                  viewBox="0 0 24 24"
                  stroke="currentColor"
                >
                  <path
                    stroke-linecap="round"
                    stroke-linejoin="round"
                    stroke-width="2" 
                    d="M5 3v4M3 5h4M6 17v4m-2-2h4m5-16l2.286 6.857L21 12l-5.714 2.143L13 21l-2.286-6.857L5 12l5.714-2.143L13 3z"
                  />
                </svg>
                Points to Win
              </label>
  
              <div class="relative">
                <input
                  id="pointsToWin"
                  v-model.number="pointsToWin"
                  type="number"
                  min="1"
                  :disabled="!isCreator"
                  class="w-full px-4 py-2 pl-5 rounded-lg bg-gray-700 border border-gray-600 text-white text-lg focus:outline-none focus:ring-2 focus:ring-blue-500 focus:border-blue-500 transition-all duration-200 disabled:opacity-60 disabled:cursor-not-allowed"
                  @blur="handleSave"
                >
              </div>
            </div>
          </div>

          <div>
            <label
              for="questionTags"
              class="flex items-center text-sm font-medium text-blue-300 mb-2"
            >
              <svg
                xmlns="http://www.w3.org/2000/svg"
                class="h-4 w-4 mr-2"
                fill="none"
                viewBox="0 0 24 24"
                stroke="currentColor"
              >
                <path
                  stroke-linecap="round"
                  stroke-linejoin="round"
                  stroke-width="2"
                  d="M7 7h.01M7 3h5c.512 0 1.024.195 1.414.586l7 7a2 2 0 010 2.828l-7 7a2 2 0 01-2.828 0l-7-7A1.994 1.994 0 013 12V7a4 4 0 014-4z"
                />
              </svg>
              Question Tags
            </label>
            <TagSelector 
              v-model="tags" 
              :readonly="!isCreator"
              @update:model-value="handleSave"
            />
          </div>
        </div>
      </div>

      <div class="w-2/3 pl-8">
        <div class="w-full mx-auto">
          <div class="bg-gray-800 border-gray-700 rounded-xl p-6 shadow-lg">
            <div class="flex flex-row justify-between gap-4">
              <button
                class="w-1/4 flex items-center justify-center gap-2 bg-red-600 font-bold hover:bg-red-700 text-white py-2.5 px-5 rounded-lg shadow transition-all duration-200 focus:outline-none focus:ring-2 focus:ring-red-700 focus:ring-opacity-50"
                @click="leaveLobby"
              >
                <svg
                  xmlns="http://www.w3.org/2000/svg"
                  class="h-5 w-5"
                  fill="none"
                  viewBox="0 0 24 24"
                  stroke="currentColor"
                >
                  <path
                    stroke-linecap="round"
                    stroke-linejoin="round"
                    stroke-width="2"
                    d="M17 16l4-4m0 0l-4-4m4 4H7m6 4v1a3 3 0 01-3 3H6a3 3 0 01-3-3V7a3 3 0 013-3h4a3 3 0 013 3v1"
                  />
                </svg>
                Leave Lobby
              </button>
              <div class="flex-1 flex justify-end">
                <button
                  v-if="isCreator"
                  class="flex items-center justify-center font-bold gap-2 bg-blue-700 hover:bg-blue-600 text-white py-2.5 px-5 rounded-lg shadow transition-all duration-200 focus:outline-none focus:ring-2 focus:ring-blue-400 focus:ring-opacity-50 w-1/3"
                  @click="startGame"
                >
                  <svg
                    xmlns="http://www.w3.org/2000/svg"
                    class="h-5 w-5"
                    fill="none"
                    viewBox="0 0 24 24"
                    stroke="currentColor"
                  >
                    <path
                      stroke-linecap="round"
                      stroke-linejoin="round"
                      stroke-width="2"
                      d="M14.752 11.168l-3.197-2.132A1 1 0 0010 9.87v4.263a1 1 0 001.555.832l3.197-2.132a1 1 0 000-1.664z"
                    />
                    <path
                      stroke-linecap="round"
                      stroke-linejoin="round"
                      stroke-width="2"
                      d="M21 12a9 9 0 11-18 0 9 9 0 0118 0z"
                    />
                  </svg>
                  Start Game
                </button>
                <div
                  v-if="!isCreator"
                  class="inline-flex items-center bg-gray-700/50 border border-gray-600 rounded-full px-5 py-2 w-2/3 justify-center"
                >
                  <svg
                    class="animate-spin -ml-1 mr-3 h-5 w-5 text-blue-400"
                    xmlns="http://www.w3.org/2000/svg"
                    fill="none"
                    viewBox="0 0 24 24"
                  >
                    <circle
                      class="opacity-25"
                      cx="12"
                      cy="12"
                      r="10"
                      stroke="currentColor"
                      stroke-width="4"
                    />
                    <path
                      class="opacity-75"
                      fill="currentColor"
                      d="M4 12a8 8 0 018-8V0C5.373 0 0 5.373 0 12h4zm2 5.291A7.962 7.962 0 014 12H0c0 3.042 1.135 5.824 3 7.938l3-2.647z"
                    />
                  </svg>
                  <span class="text-base text-blue-300 font-medium">Waiting for start...</span>
                </div>
              </div>
            </div>
          </div>
        </div>
        <div
          v-if="errorMessage"
          class="bg-red-600 text-white p-4 rounded-lg mb-6 mt-8"
        >
          <p>{{ errorMessage }}</p>
          <button
            class="mt-4 bg-blue-600 hover:bg-blue-700 text-white font-semibold py-2 px-4 rounded-lg"
            @click="setupLobby"
          >
            Retry
          </button>
        </div>

        <div
          v-if="isLoading"
          class="bg-gray-800 p-4 rounded-lg text-center text-xl"
        >
          Loading lobby information...
        </div>

        <div v-else>
          <div class="bg-gray-800 p-6 rounded-lg shadow-lg mt-8">
            <h2 class="text-2xl font-semibold mb-4">
              {{ players.length }} Players 
            </h2>
            <ul class="space-y-3">
              <li
                v-for="player in players"
                :key="player.id"
                class="p-4 rounded-lg bg-gray-700 hover:bg-gray-600 flex justify-between items-center transition-all duration-300"
                :class="{ 'bg-blue-500': player.id.toString() === creatorId }"
              >
                <div class="flex items-center">
                  <span class="font-semibold text-lg">{{ player.name }}</span>
                  <span
                    v-if="player.id.toString() === playerId"
                    class="ml-4 text-blue-300"
                  >
                    (You)
                  </span>
                </div>
                <span
                  v-if="player.id.toString() === creatorId"
                  class="text-sm text-blue-300"
                >
                  Creator
                </span>
              </li>
            </ul>
          </div>
        </div>
      </div>
    </div>
  </div>
</template>
