// Navigator panel - shows full page with draggable viewport box
// Affinity/Photoshop-style mini-map for page navigation
// Feature Registration Pattern implementation

import type { ReaderContext } from "../core/reader-context";

let context: ReaderContext;

export function init(readerContext: ReaderContext): void {
  context = readerContext;
  let state: NavigatorState | null = null;

  context.events.on(
    "navigator:initialize",
    (detail: { containerSelector: string; totalPages: number }) => {
      state = initializeNavigator(detail.containerSelector);
      state.totalPages = detail.totalPages;
    },
  );

  context.events.on(
    "navigator:update",
    (detail: { currentPage: number; contentImage?: HTMLImageElement }) => {
      if (state) {
        state.currentPage = detail.currentPage;
        if (detail.contentImage) {
          state.contentImage = detail.contentImage;
          updateNavigatorViewport(state);
        }
      }
    },
  );

  context.events.on("navigator:pan", (detail: { x: number; y: number }) => {
    if (state) {
      handleNavigatorPan(state, detail.x, detail.y);
    }
  });
}

interface NavigatorState {
  panelId: string;
  container: HTMLElement;
  viewport: HTMLElement;
  currentPage: number;
  totalPages: number;
  scale: number;
  contentImage: HTMLImageElement | null;
  isDragging: boolean;
}

function initializeNavigator(containerSelector: string): NavigatorState {
  const container = document.querySelector(containerSelector) as HTMLElement;
  if (!container) throw new Error("Navigator container not found");

  const viewport = document.createElement("div");
  viewport.className = "navigator-viewport-box";
  viewport.style.cssText = `
    position: absolute;
    border: 2px solid var(--accent-color, #3b82f6);
    background: rgba(59, 130, 246, 0.1);
    cursor: move;
    z-index: 10;
  `;

  container.appendChild(viewport);

  const state: NavigatorState = {
    panelId: "navigator",
    container,
    viewport,
    currentPage: 1,
    totalPages: 1,
    scale: 0.1,
    contentImage: null,
    isDragging: false,
  };

  setupNavigatorDragHandler(state);
  return state;
}

function setupNavigatorDragHandler(state: NavigatorState): void {
  state.viewport.addEventListener("mousedown", (e) => {
    e.preventDefault();
    state.isDragging = true;
    state.viewport.style.cursor = "grabbing";
  });

  document.addEventListener("mousemove", (e) => {
    if (!state.isDragging || !state.contentImage) return;

    const containerRect = state.container.getBoundingClientRect();
    const imgRect = state.contentImage.getBoundingClientRect();

    const relX = (e.clientX - imgRect.left) / imgRect.width;
    const relY = (e.clientY - imgRect.top) / imgRect.height;

    const mainViewer = document.getElementById("reader-content");
    if (mainViewer) {
      mainViewer.dispatchEvent(
        new CustomEvent("navigator-pan", {
          detail: { x: relX, y: relY },
        }),
      );
    }
  });

  document.addEventListener("mouseup", () => {
    if (state.isDragging) {
      state.isDragging = false;
      state.viewport.style.cursor = "move";
    }
  });
}

function updateNavigatorViewport(state: NavigatorState): void {
  if (!state.contentImage) return;

  const containerRect = state.container.getBoundingClientRect();
  const imgRect = state.contentImage.getBoundingClientRect();

  state.scale = containerRect.width / imgRect.width;

  state.viewport.style.width = `${containerRect.width}px`;
  state.viewport.style.height = `${containerRect.height * state.scale}px`;

  state.viewport.style.left = "0";
  state.viewport.style.top = `${(state.currentPage - 1) * imgRect.height * state.scale}px`;
}

function handleNavigatorPan(state: NavigatorState, x: number, y: number): void {
  if (!state.contentImage) return;

  const imgRect = state.contentImage.getBoundingClientRect();

  const viewportX = x * state.container.offsetWidth;
  const viewportY = y * state.container.offsetHeight;

  state.viewport.style.left = `${viewportX}px`;
  state.viewport.style.top = `${viewportY}px`;
}
