/*
 * Copyright 2025 Palantir Technologies, Inc. All rights reserved.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

import { useCallback, useEffect, useMemo, useRef, useState } from "react";
import { MAX_SCALE, MIN_SCALE, PAGE_WIDTH_SCALE_VALUE, SCALE_STEP } from "../constants.js";
import { usePdfOutline } from "./usePdfOutline.js";
import { usePdfViewerCore } from "./usePdfViewerCore.js";
import { usePdfViewerSearch } from "./usePdfViewerSearch.js";
export function usePdfViewerState({
  src,
  initialPage,
  initialScale,
  initialAutoSize,
  initialSidebarOpen = false,
  sidebarMode: sidebarModeProp = "thumbnails",
  onDownload
}) {
  const core = usePdfViewerCore({
    src,
    initialPage,
    initialScale,
    initialAutoSize
  });
  const [rotation, setRotation] = useState(0);
  const [sidebarOpen, setSidebarOpen] = useState(initialSidebarOpen);
  const [sidebarMode, setSidebarMode] = useState(sidebarModeProp);
  const search = usePdfViewerSearch(core.eventBusRef, core.findControllerRef, core.document);
  const outlineItems = usePdfOutline(core.document);

  // Sync sidebarMode prop changes to state
  useEffect(function () {
    setSidebarMode(sidebarModeProp);
  }, [sidebarModeProp]);

  // Sync rotation → PDFViewer
  useEffect(function () {
    const pdfViewer = core.pdfViewerRef.current;
    if (pdfViewer != null) {
      pdfViewer.pagesRotation = rotation;
    }
  }, [core.pdfViewerRef, rotation]);

  // Re-apply page-width after rotation changes while auto-size is active.
  // Rotation changes the effective page width, so auto-size must re-fit.
  const prevRotationRef = useRef(rotation);
  useEffect(function () {
    if (prevRotationRef.current === rotation) {
      return;
    }
    prevRotationRef.current = rotation;
    const pdfViewer = core.pdfViewerRef.current;
    if (pdfViewer == null || !core.autoSize) {
      return;
    }
    pdfViewer.currentScaleValue = PAGE_WIDTH_SCALE_VALUE;
  }, [core.pdfViewerRef, core.autoSize, rotation]);

  // Ctrl+F keyboard shortcut
  useEffect(function () {
    const handleKeyDown = e => {
      if ((e.ctrlKey || e.metaKey) && e.key === "f") {
        e.preventDefault();
        search.openSearch();
      }
    };
    window.addEventListener("keydown", handleKeyDown);
    return () => {
      window.removeEventListener("keydown", handleKeyDown);
    };
  }, [search.openSearch]);
  const zoomIn = useCallback(() => {
    core.setAutoSize(false);
    core.setScale(Math.min(core.scale + SCALE_STEP, MAX_SCALE));
  }, [core.scale, core.setScale, core.setAutoSize]);
  const zoomOut = useCallback(() => {
    core.setAutoSize(false);
    core.setScale(Math.max(core.scale - SCALE_STEP, MIN_SCALE));
  }, [core.scale, core.setScale, core.setAutoSize]);
  const toggleAutoSize = useCallback(() => {
    core.setAutoSize(!core.autoSize);
  }, [core.autoSize, core.setAutoSize]);
  const rotateLeft = useCallback(() => {
    setRotation(prev => (prev - 90 + 360) % 360);
  }, []);
  const rotateRight = useCallback(() => {
    setRotation(prev => (prev + 90) % 360);
  }, []);
  const toggleSidebar = useCallback(() => {
    setSidebarOpen(prev => !prev);
  }, []);
  const download = useCallback(filename => {
    if (core.document == null) {
      return;
    }
    void core.document.getData().then(data => {
      const blob = new Blob([data.buffer], {
        type: "application/pdf"
      });
      const url = URL.createObjectURL(blob);
      const resolvedFilename = resolveDownloadFilename(src, filename);
      const a = globalThis.document.createElement("a");
      a.href = url;
      a.download = resolvedFilename;
      a.click();
      URL.revokeObjectURL(url);
      onDownload?.({
        success: true,
        filename: resolvedFilename
      });
    }).catch(err => {
      onDownload?.({
        success: false,
        error: err instanceof Error ? err : new Error("Failed to download PDF")
      });
    });
  }, [core.document, src, onDownload]);
  return useMemo(() => ({
    ...core,
    zoomIn,
    zoomOut,
    toggleAutoSize,
    rotation,
    rotateLeft,
    rotateRight,
    sidebarOpen,
    sidebarMode,
    setSidebarMode,
    toggleSidebar,
    search,
    outlineItems,
    download
  }), [core, zoomIn, zoomOut, toggleAutoSize, rotation, rotateLeft, rotateRight, sidebarOpen, sidebarMode, setSidebarMode, toggleSidebar, search, outlineItems, download]);
}

/** Derive a download filename from an explicit name, the src URL, or a fallback. */
function resolveDownloadFilename(src, filename) {
  if (filename != null) {
    return filename;
  }
  if (typeof src === "string") {
    return src.split("/").pop()?.split("?")[0] || "document.pdf";
  }
  return "document.pdf";
}
//# sourceMappingURL=usePdfViewerState.js.map