pdfjs-reader-core 0.2.7 → 0.2.9

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.cjs CHANGED
@@ -4777,7 +4777,7 @@ var init_ThumbnailPanel = __esm({
4777
4777
  className,
4778
4778
  thumbnailScale = 0.2
4779
4779
  }) {
4780
- const { document: document2, currentPage, numPages, goToPage, isLoading } = usePDFViewer();
4780
+ const { document: document2, currentPage, numPages, goToPage } = usePDFViewer();
4781
4781
  const containerRef = (0, import_react18.useRef)(null);
4782
4782
  (0, import_react18.useEffect)(() => {
4783
4783
  const container = containerRef.current;
@@ -4794,10 +4794,7 @@ var init_ThumbnailPanel = __esm({
4794
4794
  [goToPage]
4795
4795
  );
4796
4796
  if (!document2) {
4797
- if (isLoading) {
4798
- return null;
4799
- }
4800
- return /* @__PURE__ */ (0, import_jsx_runtime4.jsx)("div", { className: cn("thumbnail-panel p-4", className), children: /* @__PURE__ */ (0, import_jsx_runtime4.jsx)("div", { className: "text-sm text-gray-500", children: "No document loaded" }) });
4797
+ return null;
4801
4798
  }
4802
4799
  return /* @__PURE__ */ (0, import_jsx_runtime4.jsx)(
4803
4800
  "div",
@@ -5128,7 +5125,7 @@ var init_OutlinePanel = __esm({
5128
5125
  OutlinePanel = (0, import_react20.memo)(function OutlinePanel2({
5129
5126
  className
5130
5127
  }) {
5131
- const { document: document2, goToPage, isLoading: isDocumentLoading } = usePDFViewer();
5128
+ const { document: document2, goToPage } = usePDFViewer();
5132
5129
  const [outline, setOutline] = (0, import_react20.useState)(null);
5133
5130
  const [isLoading, setIsLoading] = (0, import_react20.useState)(false);
5134
5131
  const [error, setError] = (0, import_react20.useState)(null);
@@ -5207,10 +5204,7 @@ var init_OutlinePanel = __esm({
5207
5204
  [goToPage]
5208
5205
  );
5209
5206
  if (!document2) {
5210
- if (isDocumentLoading) {
5211
- return null;
5212
- }
5213
- return /* @__PURE__ */ (0, import_jsx_runtime6.jsx)("div", { className: cn("flex items-center justify-center p-4", className), children: /* @__PURE__ */ (0, import_jsx_runtime6.jsx)("p", { className: "text-sm text-gray-500 dark:text-gray-400", children: "No document loaded" }) });
5207
+ return null;
5214
5208
  }
5215
5209
  if (isLoading) {
5216
5210
  return /* @__PURE__ */ (0, import_jsx_runtime6.jsx)("div", { className: cn("flex items-center justify-center p-4", className), children: /* @__PURE__ */ (0, import_jsx_runtime6.jsxs)("div", { className: "flex items-center gap-2", children: [
@@ -7730,6 +7724,138 @@ var init_PDFPage2 = __esm({
7730
7724
  }
7731
7725
  });
7732
7726
 
7727
+ // src/components/PDFLoadingScreen/PDFLoadingScreen.tsx
7728
+ function formatBytes(bytes) {
7729
+ if (bytes < 1024) return `${bytes} B`;
7730
+ if (bytes < 1024 * 1024) return `${(bytes / 1024).toFixed(1)} KB`;
7731
+ return `${(bytes / (1024 * 1024)).toFixed(1)} MB`;
7732
+ }
7733
+ var import_react33, import_jsx_runtime19, phaseMessages, PDFLoadingScreen;
7734
+ var init_PDFLoadingScreen = __esm({
7735
+ "src/components/PDFLoadingScreen/PDFLoadingScreen.tsx"() {
7736
+ "use strict";
7737
+ import_react33 = require("react");
7738
+ init_utils();
7739
+ import_jsx_runtime19 = require("react/jsx-runtime");
7740
+ phaseMessages = {
7741
+ initializing: "Initializing...",
7742
+ fetching: "Loading document...",
7743
+ parsing: "Processing pages...",
7744
+ rendering: "Preparing view..."
7745
+ };
7746
+ PDFLoadingScreen = (0, import_react33.memo)(function PDFLoadingScreen2({
7747
+ progress,
7748
+ bytesLoaded,
7749
+ totalBytes,
7750
+ phase = "fetching",
7751
+ documentName,
7752
+ className
7753
+ }) {
7754
+ const hasProgress = progress !== void 0 && progress >= 0;
7755
+ const hasBytes = bytesLoaded !== void 0 && totalBytes !== void 0 && totalBytes > 0;
7756
+ return /* @__PURE__ */ (0, import_jsx_runtime19.jsxs)(
7757
+ "div",
7758
+ {
7759
+ className: cn(
7760
+ "pdf-loading-screen",
7761
+ "flex flex-col items-center justify-center",
7762
+ "w-full h-full min-h-[400px]",
7763
+ "bg-slate-50 dark:bg-slate-800",
7764
+ className
7765
+ ),
7766
+ role: "status",
7767
+ "aria-live": "polite",
7768
+ "aria-label": phaseMessages[phase],
7769
+ children: [
7770
+ /* @__PURE__ */ (0, import_jsx_runtime19.jsxs)("div", { className: "pdf-loading-skeleton", children: [
7771
+ /* @__PURE__ */ (0, import_jsx_runtime19.jsx)("div", { className: "pdf-loading-icon", children: /* @__PURE__ */ (0, import_jsx_runtime19.jsxs)(
7772
+ "svg",
7773
+ {
7774
+ width: "48",
7775
+ height: "56",
7776
+ viewBox: "0 0 48 56",
7777
+ fill: "none",
7778
+ xmlns: "http://www.w3.org/2000/svg",
7779
+ className: "pdf-document-icon",
7780
+ children: [
7781
+ /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
7782
+ "path",
7783
+ {
7784
+ d: "M4 4C4 1.79086 5.79086 0 8 0H30L44 14V52C44 54.2091 42.2091 56 40 56H8C5.79086 56 4 54.2091 4 52V4Z",
7785
+ className: "fill-white dark:fill-slate-700"
7786
+ }
7787
+ ),
7788
+ /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
7789
+ "path",
7790
+ {
7791
+ d: "M30 0L44 14H34C31.7909 14 30 12.2091 30 10V0Z",
7792
+ className: "fill-slate-200 dark:fill-slate-600"
7793
+ }
7794
+ ),
7795
+ /* @__PURE__ */ (0, import_jsx_runtime19.jsx)("rect", { x: "10", y: "22", width: "24", height: "3", rx: "1.5", className: "fill-slate-200 dark:fill-slate-600" }),
7796
+ /* @__PURE__ */ (0, import_jsx_runtime19.jsx)("rect", { x: "10", y: "28", width: "20", height: "3", rx: "1.5", className: "fill-slate-200 dark:fill-slate-600" }),
7797
+ /* @__PURE__ */ (0, import_jsx_runtime19.jsx)("rect", { x: "10", y: "34", width: "22", height: "3", rx: "1.5", className: "fill-slate-200 dark:fill-slate-600" }),
7798
+ /* @__PURE__ */ (0, import_jsx_runtime19.jsx)("rect", { x: "10", y: "40", width: "16", height: "3", rx: "1.5", className: "fill-slate-200 dark:fill-slate-600" }),
7799
+ /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
7800
+ "path",
7801
+ {
7802
+ d: "M4 4C4 1.79086 5.79086 0 8 0H30L44 14V52C44 54.2091 42.2091 56 40 56H8C5.79086 56 4 54.2091 4 52V4Z",
7803
+ className: "stroke-slate-300 dark:stroke-slate-500",
7804
+ strokeWidth: "1",
7805
+ fill: "none"
7806
+ }
7807
+ )
7808
+ ]
7809
+ }
7810
+ ) }),
7811
+ /* @__PURE__ */ (0, import_jsx_runtime19.jsxs)("div", { className: "pdf-skeleton-lines", children: [
7812
+ /* @__PURE__ */ (0, import_jsx_runtime19.jsx)("div", { className: "pdf-skeleton-line pdf-skeleton-line-1" }),
7813
+ /* @__PURE__ */ (0, import_jsx_runtime19.jsx)("div", { className: "pdf-skeleton-line pdf-skeleton-line-2" }),
7814
+ /* @__PURE__ */ (0, import_jsx_runtime19.jsx)("div", { className: "pdf-skeleton-line pdf-skeleton-line-3" })
7815
+ ] })
7816
+ ] }),
7817
+ /* @__PURE__ */ (0, import_jsx_runtime19.jsxs)("div", { className: "pdf-loading-info", children: [
7818
+ documentName && /* @__PURE__ */ (0, import_jsx_runtime19.jsx)("p", { className: "pdf-loading-document-name", children: documentName }),
7819
+ /* @__PURE__ */ (0, import_jsx_runtime19.jsx)("p", { className: "pdf-loading-message", children: phaseMessages[phase] }),
7820
+ /* @__PURE__ */ (0, import_jsx_runtime19.jsxs)("div", { className: "pdf-loading-progress-container", children: [
7821
+ /* @__PURE__ */ (0, import_jsx_runtime19.jsx)("div", { className: "pdf-loading-progress-track", children: /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
7822
+ "div",
7823
+ {
7824
+ className: cn(
7825
+ "pdf-loading-progress-fill",
7826
+ !hasProgress && "pdf-loading-progress-indeterminate"
7827
+ ),
7828
+ style: hasProgress ? { width: `${Math.min(100, progress)}%` } : void 0
7829
+ }
7830
+ ) }),
7831
+ /* @__PURE__ */ (0, import_jsx_runtime19.jsxs)("div", { className: "pdf-loading-progress-details", children: [
7832
+ hasProgress && /* @__PURE__ */ (0, import_jsx_runtime19.jsxs)("span", { className: "pdf-loading-progress-percent", children: [
7833
+ Math.round(progress),
7834
+ "%"
7835
+ ] }),
7836
+ hasBytes && /* @__PURE__ */ (0, import_jsx_runtime19.jsxs)("span", { className: "pdf-loading-progress-bytes", children: [
7837
+ formatBytes(bytesLoaded),
7838
+ " / ",
7839
+ formatBytes(totalBytes)
7840
+ ] })
7841
+ ] })
7842
+ ] })
7843
+ ] })
7844
+ ]
7845
+ }
7846
+ );
7847
+ });
7848
+ }
7849
+ });
7850
+
7851
+ // src/components/PDFLoadingScreen/index.ts
7852
+ var init_PDFLoadingScreen2 = __esm({
7853
+ "src/components/PDFLoadingScreen/index.ts"() {
7854
+ "use strict";
7855
+ init_PDFLoadingScreen();
7856
+ }
7857
+ });
7858
+
7733
7859
  // src/components/SelectionToolbar/SelectionToolbar.tsx
7734
7860
  function calculatePosition(selection) {
7735
7861
  if (!selection || selection.rects.length === 0) {
@@ -7745,13 +7871,13 @@ function calculatePosition(selection) {
7745
7871
  const left = firstRect.left + firstRect.width / 2;
7746
7872
  return { top, left, visible: true };
7747
7873
  }
7748
- var import_react33, import_jsx_runtime19, HIGHLIGHT_COLOR_BUTTONS, SelectionToolbar;
7874
+ var import_react34, import_jsx_runtime20, HIGHLIGHT_COLOR_BUTTONS, SelectionToolbar;
7749
7875
  var init_SelectionToolbar = __esm({
7750
7876
  "src/components/SelectionToolbar/SelectionToolbar.tsx"() {
7751
7877
  "use strict";
7752
- import_react33 = require("react");
7878
+ import_react34 = require("react");
7753
7879
  init_utils();
7754
- import_jsx_runtime19 = require("react/jsx-runtime");
7880
+ import_jsx_runtime20 = require("react/jsx-runtime");
7755
7881
  HIGHLIGHT_COLOR_BUTTONS = [
7756
7882
  { color: "yellow", bg: "bg-yellow-300", hoverBg: "hover:bg-yellow-400", ringColor: "ring-yellow-400" },
7757
7883
  { color: "green", bg: "bg-green-300", hoverBg: "hover:bg-green-400", ringColor: "ring-green-400" },
@@ -7759,16 +7885,16 @@ var init_SelectionToolbar = __esm({
7759
7885
  { color: "pink", bg: "bg-pink-300", hoverBg: "hover:bg-pink-400", ringColor: "ring-pink-400" },
7760
7886
  { color: "orange", bg: "bg-orange-300", hoverBg: "hover:bg-orange-400", ringColor: "ring-orange-400" }
7761
7887
  ];
7762
- SelectionToolbar = (0, import_react33.memo)(function SelectionToolbar2({
7888
+ SelectionToolbar = (0, import_react34.memo)(function SelectionToolbar2({
7763
7889
  selection,
7764
7890
  onCreateHighlight,
7765
7891
  onCopy,
7766
7892
  activeColor = "yellow",
7767
7893
  className
7768
7894
  }) {
7769
- const [position, setPosition] = (0, import_react33.useState)({ top: 0, left: 0, visible: false });
7770
- const toolbarRef = (0, import_react33.useRef)(null);
7771
- (0, import_react33.useEffect)(() => {
7895
+ const [position, setPosition] = (0, import_react34.useState)({ top: 0, left: 0, visible: false });
7896
+ const toolbarRef = (0, import_react34.useRef)(null);
7897
+ (0, import_react34.useEffect)(() => {
7772
7898
  if (selection && selection.text && selection.rects.length > 0) {
7773
7899
  const newPosition = calculatePosition(selection);
7774
7900
  if (toolbarRef.current && newPosition.visible) {
@@ -7796,19 +7922,19 @@ var init_SelectionToolbar = __esm({
7796
7922
  setPosition({ top: 0, left: 0, visible: false });
7797
7923
  }
7798
7924
  }, [selection]);
7799
- const handleColorClick = (0, import_react33.useCallback)(
7925
+ const handleColorClick = (0, import_react34.useCallback)(
7800
7926
  (color) => {
7801
7927
  onCreateHighlight(color);
7802
7928
  },
7803
7929
  [onCreateHighlight]
7804
7930
  );
7805
- const handleCopy = (0, import_react33.useCallback)(() => {
7931
+ const handleCopy = (0, import_react34.useCallback)(() => {
7806
7932
  onCopy?.();
7807
7933
  }, [onCopy]);
7808
7934
  if (!position.visible || !selection?.text) {
7809
7935
  return null;
7810
7936
  }
7811
- return /* @__PURE__ */ (0, import_jsx_runtime19.jsxs)(
7937
+ return /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)(
7812
7938
  "div",
7813
7939
  {
7814
7940
  ref: toolbarRef,
@@ -7832,7 +7958,7 @@ var init_SelectionToolbar = __esm({
7832
7958
  e.stopPropagation();
7833
7959
  },
7834
7960
  children: [
7835
- HIGHLIGHT_COLOR_BUTTONS.map((btn) => /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
7961
+ HIGHLIGHT_COLOR_BUTTONS.map((btn) => /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
7836
7962
  "button",
7837
7963
  {
7838
7964
  onClick: () => handleColorClick(btn.color),
@@ -7849,7 +7975,7 @@ var init_SelectionToolbar = __esm({
7849
7975
  ),
7850
7976
  title: `Highlight ${btn.color}`,
7851
7977
  "aria-label": `Highlight with ${btn.color}`,
7852
- children: /* @__PURE__ */ (0, import_jsx_runtime19.jsx)("svg", { className: "w-4 h-4 text-gray-700", fill: "none", viewBox: "0 0 24 24", stroke: "currentColor", children: /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
7978
+ children: /* @__PURE__ */ (0, import_jsx_runtime20.jsx)("svg", { className: "w-4 h-4 text-gray-700", fill: "none", viewBox: "0 0 24 24", stroke: "currentColor", children: /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
7853
7979
  "path",
7854
7980
  {
7855
7981
  strokeLinecap: "round",
@@ -7861,8 +7987,8 @@ var init_SelectionToolbar = __esm({
7861
7987
  },
7862
7988
  btn.color
7863
7989
  )),
7864
- /* @__PURE__ */ (0, import_jsx_runtime19.jsx)("div", { className: "w-px h-6 bg-gray-300 dark:bg-gray-600 mx-1" }),
7865
- /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
7990
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsx)("div", { className: "w-px h-6 bg-gray-300 dark:bg-gray-600 mx-1" }),
7991
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
7866
7992
  "button",
7867
7993
  {
7868
7994
  onClick: handleCopy,
@@ -7874,7 +8000,7 @@ var init_SelectionToolbar = __esm({
7874
8000
  ),
7875
8001
  title: "Copy text",
7876
8002
  "aria-label": "Copy selected text",
7877
- children: /* @__PURE__ */ (0, import_jsx_runtime19.jsx)("svg", { className: "w-5 h-5", fill: "none", viewBox: "0 0 24 24", stroke: "currentColor", children: /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
8003
+ children: /* @__PURE__ */ (0, import_jsx_runtime20.jsx)("svg", { className: "w-5 h-5", fill: "none", viewBox: "0 0 24 24", stroke: "currentColor", children: /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
7878
8004
  "path",
7879
8005
  {
7880
8006
  strokeLinecap: "round",
@@ -7914,13 +8040,13 @@ function calculatePopoverPosition(highlight, scale, pageElement) {
7914
8040
  const left = scaledLeft + scaledWidth / 2;
7915
8041
  return { top, left, visible: true };
7916
8042
  }
7917
- var import_react34, import_jsx_runtime20, HIGHLIGHT_COLOR_OPTIONS, HighlightPopover;
8043
+ var import_react35, import_jsx_runtime21, HIGHLIGHT_COLOR_OPTIONS, HighlightPopover;
7918
8044
  var init_HighlightPopover = __esm({
7919
8045
  "src/components/HighlightPopover/HighlightPopover.tsx"() {
7920
8046
  "use strict";
7921
- import_react34 = require("react");
8047
+ import_react35 = require("react");
7922
8048
  init_utils();
7923
- import_jsx_runtime20 = require("react/jsx-runtime");
8049
+ import_jsx_runtime21 = require("react/jsx-runtime");
7924
8050
  HIGHLIGHT_COLOR_OPTIONS = [
7925
8051
  { color: "yellow", bg: "bg-yellow-300", hoverBg: "hover:bg-yellow-400", borderColor: "border-yellow-400" },
7926
8052
  { color: "green", bg: "bg-green-300", hoverBg: "hover:bg-green-400", borderColor: "border-green-400" },
@@ -7928,7 +8054,7 @@ var init_HighlightPopover = __esm({
7928
8054
  { color: "pink", bg: "bg-pink-300", hoverBg: "hover:bg-pink-400", borderColor: "border-pink-400" },
7929
8055
  { color: "orange", bg: "bg-orange-300", hoverBg: "hover:bg-orange-400", borderColor: "border-orange-400" }
7930
8056
  ];
7931
- HighlightPopover = (0, import_react34.memo)(function HighlightPopover2({
8057
+ HighlightPopover = (0, import_react35.memo)(function HighlightPopover2({
7932
8058
  highlight,
7933
8059
  scale,
7934
8060
  pageElement,
@@ -7939,16 +8065,16 @@ var init_HighlightPopover = __esm({
7939
8065
  onClose,
7940
8066
  className
7941
8067
  }) {
7942
- const [isEditingComment, setIsEditingComment] = (0, import_react34.useState)(false);
7943
- const [comment, setComment] = (0, import_react34.useState)(highlight?.comment ?? "");
7944
- const [position, setPosition] = (0, import_react34.useState)({ top: 0, left: 0, visible: false });
7945
- const popoverRef = (0, import_react34.useRef)(null);
7946
- const textareaRef = (0, import_react34.useRef)(null);
7947
- (0, import_react34.useEffect)(() => {
8068
+ const [isEditingComment, setIsEditingComment] = (0, import_react35.useState)(false);
8069
+ const [comment, setComment] = (0, import_react35.useState)(highlight?.comment ?? "");
8070
+ const [position, setPosition] = (0, import_react35.useState)({ top: 0, left: 0, visible: false });
8071
+ const popoverRef = (0, import_react35.useRef)(null);
8072
+ const textareaRef = (0, import_react35.useRef)(null);
8073
+ (0, import_react35.useEffect)(() => {
7948
8074
  setComment(highlight?.comment ?? "");
7949
8075
  setIsEditingComment(false);
7950
8076
  }, [highlight?.id, highlight?.comment]);
7951
- (0, import_react34.useEffect)(() => {
8077
+ (0, import_react35.useEffect)(() => {
7952
8078
  if (highlight && pageElement) {
7953
8079
  const newPosition = calculatePopoverPosition(highlight, scale, pageElement);
7954
8080
  if (newPosition.visible && popoverRef.current) {
@@ -7978,12 +8104,12 @@ var init_HighlightPopover = __esm({
7978
8104
  setPosition({ top: 0, left: 0, visible: false });
7979
8105
  }
7980
8106
  }, [highlight, pageElement, scale, isEditingComment]);
7981
- (0, import_react34.useEffect)(() => {
8107
+ (0, import_react35.useEffect)(() => {
7982
8108
  if (isEditingComment && textareaRef.current) {
7983
8109
  textareaRef.current.focus();
7984
8110
  }
7985
8111
  }, [isEditingComment]);
7986
- (0, import_react34.useEffect)(() => {
8112
+ (0, import_react35.useEffect)(() => {
7987
8113
  function handleClickOutside(event) {
7988
8114
  if (popoverRef.current && !popoverRef.current.contains(event.target)) {
7989
8115
  onClose();
@@ -7994,7 +8120,7 @@ var init_HighlightPopover = __esm({
7994
8120
  return () => document.removeEventListener("mousedown", handleClickOutside);
7995
8121
  }
7996
8122
  }, [position.visible, onClose]);
7997
- (0, import_react34.useEffect)(() => {
8123
+ (0, import_react35.useEffect)(() => {
7998
8124
  function handleKeyDown(event) {
7999
8125
  if (event.key === "Escape") {
8000
8126
  if (isEditingComment) {
@@ -8010,7 +8136,7 @@ var init_HighlightPopover = __esm({
8010
8136
  return () => document.removeEventListener("keydown", handleKeyDown);
8011
8137
  }
8012
8138
  }, [position.visible, isEditingComment, highlight?.comment, onClose]);
8013
- const handleColorClick = (0, import_react34.useCallback)(
8139
+ const handleColorClick = (0, import_react35.useCallback)(
8014
8140
  (color) => {
8015
8141
  if (highlight) {
8016
8142
  onColorChange(highlight.id, color);
@@ -8018,19 +8144,19 @@ var init_HighlightPopover = __esm({
8018
8144
  },
8019
8145
  [highlight, onColorChange]
8020
8146
  );
8021
- const handleSaveComment = (0, import_react34.useCallback)(() => {
8147
+ const handleSaveComment = (0, import_react35.useCallback)(() => {
8022
8148
  if (highlight) {
8023
8149
  onCommentChange(highlight.id, comment.trim());
8024
8150
  setIsEditingComment(false);
8025
8151
  }
8026
8152
  }, [highlight, comment, onCommentChange]);
8027
- const handleDeleteClick = (0, import_react34.useCallback)(() => {
8153
+ const handleDeleteClick = (0, import_react35.useCallback)(() => {
8028
8154
  if (highlight) {
8029
8155
  onDelete(highlight.id);
8030
8156
  onClose();
8031
8157
  }
8032
8158
  }, [highlight, onDelete, onClose]);
8033
- const handleCopyClick = (0, import_react34.useCallback)(() => {
8159
+ const handleCopyClick = (0, import_react35.useCallback)(() => {
8034
8160
  if (highlight?.text) {
8035
8161
  navigator.clipboard.writeText(highlight.text);
8036
8162
  onCopy?.(highlight.text);
@@ -8039,7 +8165,7 @@ var init_HighlightPopover = __esm({
8039
8165
  if (!highlight || !position.visible) {
8040
8166
  return null;
8041
8167
  }
8042
- return /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)(
8168
+ return /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)(
8043
8169
  "div",
8044
8170
  {
8045
8171
  ref: popoverRef,
@@ -8059,8 +8185,8 @@ var init_HighlightPopover = __esm({
8059
8185
  width: 280
8060
8186
  },
8061
8187
  children: [
8062
- /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)("div", { className: "flex items-center justify-between p-2 border-b border-gray-200 dark:border-gray-700", children: [
8063
- /* @__PURE__ */ (0, import_jsx_runtime20.jsx)("div", { className: "flex items-center gap-1", children: HIGHLIGHT_COLOR_OPTIONS.map((opt) => /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
8188
+ /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)("div", { className: "flex items-center justify-between p-2 border-b border-gray-200 dark:border-gray-700", children: [
8189
+ /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("div", { className: "flex items-center gap-1", children: HIGHLIGHT_COLOR_OPTIONS.map((opt) => /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
8064
8190
  "button",
8065
8191
  {
8066
8192
  onClick: () => handleColorClick(opt.color),
@@ -8078,7 +8204,7 @@ var init_HighlightPopover = __esm({
8078
8204
  },
8079
8205
  opt.color
8080
8206
  )) }),
8081
- /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
8207
+ /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
8082
8208
  "button",
8083
8209
  {
8084
8210
  onClick: handleDeleteClick,
@@ -8090,7 +8216,7 @@ var init_HighlightPopover = __esm({
8090
8216
  ),
8091
8217
  title: "Delete highlight",
8092
8218
  "aria-label": "Delete highlight",
8093
- children: /* @__PURE__ */ (0, import_jsx_runtime20.jsx)("svg", { className: "w-4 h-4", fill: "none", viewBox: "0 0 24 24", stroke: "currentColor", children: /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
8219
+ children: /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("svg", { className: "w-4 h-4", fill: "none", viewBox: "0 0 24 24", stroke: "currentColor", children: /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
8094
8220
  "path",
8095
8221
  {
8096
8222
  strokeLinecap: "round",
@@ -8102,8 +8228,8 @@ var init_HighlightPopover = __esm({
8102
8228
  }
8103
8229
  )
8104
8230
  ] }),
8105
- /* @__PURE__ */ (0, import_jsx_runtime20.jsx)("div", { className: "p-2", children: isEditingComment ? /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)("div", { className: "space-y-2", children: [
8106
- /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
8231
+ /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("div", { className: "p-2", children: isEditingComment ? /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)("div", { className: "space-y-2", children: [
8232
+ /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
8107
8233
  "textarea",
8108
8234
  {
8109
8235
  ref: textareaRef,
@@ -8122,8 +8248,8 @@ var init_HighlightPopover = __esm({
8122
8248
  rows: 3
8123
8249
  }
8124
8250
  ),
8125
- /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)("div", { className: "flex justify-end gap-2", children: [
8126
- /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
8251
+ /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)("div", { className: "flex justify-end gap-2", children: [
8252
+ /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
8127
8253
  "button",
8128
8254
  {
8129
8255
  onClick: () => {
@@ -8139,7 +8265,7 @@ var init_HighlightPopover = __esm({
8139
8265
  children: "Cancel"
8140
8266
  }
8141
8267
  ),
8142
- /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
8268
+ /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
8143
8269
  "button",
8144
8270
  {
8145
8271
  onClick: handleSaveComment,
@@ -8153,14 +8279,14 @@ var init_HighlightPopover = __esm({
8153
8279
  }
8154
8280
  )
8155
8281
  ] })
8156
- ] }) : /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)("div", { className: "space-y-2", children: [
8157
- /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)("p", { className: "text-xs text-gray-500 dark:text-gray-400 line-clamp-2", children: [
8282
+ ] }) : /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)("div", { className: "space-y-2", children: [
8283
+ /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)("p", { className: "text-xs text-gray-500 dark:text-gray-400 line-clamp-2", children: [
8158
8284
  "\u201C",
8159
8285
  highlight.text.slice(0, 100),
8160
8286
  highlight.text.length > 100 ? "..." : "",
8161
8287
  "\u201D"
8162
8288
  ] }),
8163
- highlight.comment ? /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
8289
+ highlight.comment ? /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
8164
8290
  "button",
8165
8291
  {
8166
8292
  onClick: () => setIsEditingComment(true),
@@ -8173,7 +8299,7 @@ var init_HighlightPopover = __esm({
8173
8299
  ),
8174
8300
  children: highlight.comment
8175
8301
  }
8176
- ) : /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
8302
+ ) : /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
8177
8303
  "button",
8178
8304
  {
8179
8305
  onClick: () => setIsEditingComment(true),
@@ -8186,7 +8312,7 @@ var init_HighlightPopover = __esm({
8186
8312
  children: "+ Add a note..."
8187
8313
  }
8188
8314
  ),
8189
- /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)(
8315
+ /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)(
8190
8316
  "button",
8191
8317
  {
8192
8318
  onClick: handleCopyClick,
@@ -8197,7 +8323,7 @@ var init_HighlightPopover = __esm({
8197
8323
  "focus:outline-none focus:ring-2 focus:ring-blue-500"
8198
8324
  ),
8199
8325
  children: [
8200
- /* @__PURE__ */ (0, import_jsx_runtime20.jsx)("svg", { className: "w-4 h-4", fill: "none", viewBox: "0 0 24 24", stroke: "currentColor", children: /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
8326
+ /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("svg", { className: "w-4 h-4", fill: "none", viewBox: "0 0 24 24", stroke: "currentColor", children: /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
8201
8327
  "path",
8202
8328
  {
8203
8329
  strokeLinecap: "round",
@@ -8227,19 +8353,20 @@ var init_HighlightPopover2 = __esm({
8227
8353
  });
8228
8354
 
8229
8355
  // src/components/PDFViewer/DocumentContainer.tsx
8230
- var import_react35, import_jsx_runtime21, DocumentContainer;
8356
+ var import_react36, import_jsx_runtime22, DocumentContainer;
8231
8357
  var init_DocumentContainer = __esm({
8232
8358
  "src/components/PDFViewer/DocumentContainer.tsx"() {
8233
8359
  "use strict";
8234
- import_react35 = require("react");
8360
+ import_react36 = require("react");
8235
8361
  init_PDFPage2();
8362
+ init_PDFLoadingScreen2();
8236
8363
  init_hooks();
8237
8364
  init_useHighlights();
8238
8365
  init_SelectionToolbar2();
8239
8366
  init_HighlightPopover2();
8240
8367
  init_utils();
8241
- import_jsx_runtime21 = require("react/jsx-runtime");
8242
- DocumentContainer = (0, import_react35.memo)(function DocumentContainer2({
8368
+ import_jsx_runtime22 = require("react/jsx-runtime");
8369
+ DocumentContainer = (0, import_react36.memo)(function DocumentContainer2({
8243
8370
  className,
8244
8371
  enableTouchGestures = true
8245
8372
  }) {
@@ -8256,34 +8383,34 @@ var init_DocumentContainer = __esm({
8256
8383
  } = usePDFViewer();
8257
8384
  const scrollToPageRequest = useViewerStore((s) => s.scrollToPageRequest);
8258
8385
  const { viewerStore } = usePDFViewerStores();
8259
- const [currentPageObj, setCurrentPageObj] = (0, import_react35.useState)(null);
8260
- const [isLoadingPage, setIsLoadingPage] = (0, import_react35.useState)(false);
8261
- const containerRef = (0, import_react35.useRef)(null);
8262
- const documentRef = (0, import_react35.useRef)(null);
8263
- const baseScaleRef = (0, import_react35.useRef)(scale);
8386
+ const [currentPageObj, setCurrentPageObj] = (0, import_react36.useState)(null);
8387
+ const [isLoadingPage, setIsLoadingPage] = (0, import_react36.useState)(false);
8388
+ const containerRef = (0, import_react36.useRef)(null);
8389
+ const documentRef = (0, import_react36.useRef)(null);
8390
+ const baseScaleRef = (0, import_react36.useRef)(scale);
8264
8391
  const isTouchDevice = useIsTouchDevice();
8265
8392
  const { selection, clearSelection, copySelection } = useTextSelection();
8266
- const handlePinchZoom = (0, import_react35.useCallback)(
8393
+ const handlePinchZoom = (0, import_react36.useCallback)(
8267
8394
  (pinchScale) => {
8268
8395
  const newScale = Math.max(0.25, Math.min(4, baseScaleRef.current * pinchScale));
8269
8396
  setScale(newScale);
8270
8397
  },
8271
8398
  [setScale]
8272
8399
  );
8273
- const handleSwipeLeft = (0, import_react35.useCallback)(() => {
8400
+ const handleSwipeLeft = (0, import_react36.useCallback)(() => {
8274
8401
  nextPage();
8275
8402
  }, [nextPage]);
8276
- const handleSwipeRight = (0, import_react35.useCallback)(() => {
8403
+ const handleSwipeRight = (0, import_react36.useCallback)(() => {
8277
8404
  previousPage();
8278
8405
  }, [previousPage]);
8279
- const handleDoubleTap = (0, import_react35.useCallback)(
8406
+ const handleDoubleTap = (0, import_react36.useCallback)(
8280
8407
  (_position) => {
8281
8408
  const newScale = scale < 1.5 ? 2 : 1;
8282
8409
  setScale(newScale);
8283
8410
  },
8284
8411
  [scale, setScale]
8285
8412
  );
8286
- (0, import_react35.useEffect)(() => {
8413
+ (0, import_react36.useEffect)(() => {
8287
8414
  baseScaleRef.current = scale;
8288
8415
  }, [scale]);
8289
8416
  const { ref: touchRef } = useTouchGestures({
@@ -8303,13 +8430,13 @@ var init_DocumentContainer = __esm({
8303
8430
  selectHighlight,
8304
8431
  activeColor
8305
8432
  } = useHighlights();
8306
- (0, import_react35.useEffect)(() => {
8433
+ (0, import_react36.useEffect)(() => {
8307
8434
  if (document2 !== documentRef.current) {
8308
8435
  documentRef.current = document2;
8309
8436
  setCurrentPageObj(null);
8310
8437
  }
8311
8438
  }, [document2]);
8312
- (0, import_react35.useEffect)(() => {
8439
+ (0, import_react36.useEffect)(() => {
8313
8440
  if (!document2) {
8314
8441
  setCurrentPageObj(null);
8315
8442
  return;
@@ -8345,10 +8472,10 @@ var init_DocumentContainer = __esm({
8345
8472
  cancelled = true;
8346
8473
  };
8347
8474
  }, [document2, currentPage, scrollToPageRequest, viewerStore]);
8348
- const getPageElement = (0, import_react35.useCallback)(() => {
8475
+ const getPageElement = (0, import_react36.useCallback)(() => {
8349
8476
  return containerRef.current?.querySelector(`[data-page-number="${currentPage}"]`);
8350
8477
  }, [currentPage]);
8351
- const handleCreateHighlight = (0, import_react35.useCallback)(
8478
+ const handleCreateHighlight = (0, import_react36.useCallback)(
8352
8479
  (color) => {
8353
8480
  if (!selection) return;
8354
8481
  const pageElement = getPageElement();
@@ -8358,25 +8485,25 @@ var init_DocumentContainer = __esm({
8358
8485
  },
8359
8486
  [selection, getPageElement, createHighlightFromSelection, scale, clearSelection]
8360
8487
  );
8361
- const handleCopySelection = (0, import_react35.useCallback)(() => {
8488
+ const handleCopySelection = (0, import_react36.useCallback)(() => {
8362
8489
  copySelection();
8363
8490
  }, [copySelection]);
8364
- const handleColorChange = (0, import_react35.useCallback)(
8491
+ const handleColorChange = (0, import_react36.useCallback)(
8365
8492
  (id, color) => {
8366
8493
  updateHighlight(id, { color });
8367
8494
  },
8368
8495
  [updateHighlight]
8369
8496
  );
8370
- const handleCommentChange = (0, import_react35.useCallback)(
8497
+ const handleCommentChange = (0, import_react36.useCallback)(
8371
8498
  (id, comment) => {
8372
8499
  updateHighlight(id, { comment: comment || void 0 });
8373
8500
  },
8374
8501
  [updateHighlight]
8375
8502
  );
8376
- const handleClosePopover = (0, import_react35.useCallback)(() => {
8503
+ const handleClosePopover = (0, import_react36.useCallback)(() => {
8377
8504
  selectHighlight(null);
8378
8505
  }, [selectHighlight]);
8379
- const setContainerRef = (0, import_react35.useCallback)(
8506
+ const setContainerRef = (0, import_react36.useCallback)(
8380
8507
  (element) => {
8381
8508
  containerRef.current = element;
8382
8509
  touchRef(element);
@@ -8389,23 +8516,20 @@ var init_DocumentContainer = __esm({
8389
8516
  sepia: "bg-amber-50"
8390
8517
  };
8391
8518
  if (!document2) {
8392
- if (isLoading) {
8393
- return null;
8394
- }
8395
- return /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
8519
+ return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
8396
8520
  "div",
8397
8521
  {
8398
8522
  className: cn(
8399
8523
  "document-container",
8400
- "flex-1 flex items-center justify-center",
8524
+ "flex-1",
8401
8525
  themeStyles[theme],
8402
8526
  className
8403
8527
  ),
8404
- children: /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("div", { className: "text-gray-500 dark:text-gray-400", children: "No document loaded" })
8528
+ children: /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(PDFLoadingScreen, { phase: isLoading ? "fetching" : "initializing" })
8405
8529
  }
8406
8530
  );
8407
8531
  }
8408
- return /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)(
8532
+ return /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)(
8409
8533
  "div",
8410
8534
  {
8411
8535
  ref: setContainerRef,
@@ -8418,7 +8542,7 @@ var init_DocumentContainer = __esm({
8418
8542
  className
8419
8543
  ),
8420
8544
  children: [
8421
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
8545
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
8422
8546
  PDFPage,
8423
8547
  {
8424
8548
  pageNumber: currentPage,
@@ -8427,7 +8551,7 @@ var init_DocumentContainer = __esm({
8427
8551
  rotation
8428
8552
  }
8429
8553
  ),
8430
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
8554
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
8431
8555
  SelectionToolbar,
8432
8556
  {
8433
8557
  selection,
@@ -8436,7 +8560,7 @@ var init_DocumentContainer = __esm({
8436
8560
  activeColor
8437
8561
  }
8438
8562
  ),
8439
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
8563
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
8440
8564
  HighlightPopover,
8441
8565
  {
8442
8566
  highlight: selectedHighlight,
@@ -8448,7 +8572,7 @@ var init_DocumentContainer = __esm({
8448
8572
  onClose: handleClosePopover
8449
8573
  }
8450
8574
  ),
8451
- isLoadingPage && !currentPageObj && /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("div", { className: "fixed bottom-4 right-4 px-3 py-2 bg-black/75 text-white text-sm rounded-lg", children: "Loading..." })
8575
+ isLoadingPage && !currentPageObj && /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("div", { className: "fixed bottom-4 right-4 px-3 py-2 bg-black/75 text-white text-sm rounded-lg", children: "Loading..." })
8452
8576
  ]
8453
8577
  }
8454
8578
  );
@@ -8457,21 +8581,22 @@ var init_DocumentContainer = __esm({
8457
8581
  });
8458
8582
 
8459
8583
  // src/components/PDFViewer/VirtualizedDocumentContainer.tsx
8460
- var import_react36, import_jsx_runtime22, DEFAULT_PAGE_WIDTH, DEFAULT_PAGE_HEIGHT, VirtualizedDocumentContainer;
8584
+ var import_react37, import_jsx_runtime23, DEFAULT_PAGE_WIDTH, DEFAULT_PAGE_HEIGHT, VirtualizedDocumentContainer;
8461
8585
  var init_VirtualizedDocumentContainer = __esm({
8462
8586
  "src/components/PDFViewer/VirtualizedDocumentContainer.tsx"() {
8463
8587
  "use strict";
8464
- import_react36 = require("react");
8588
+ import_react37 = require("react");
8465
8589
  init_PDFPage2();
8590
+ init_PDFLoadingScreen2();
8466
8591
  init_hooks();
8467
8592
  init_useHighlights();
8468
8593
  init_SelectionToolbar2();
8469
8594
  init_HighlightPopover2();
8470
8595
  init_utils();
8471
- import_jsx_runtime22 = require("react/jsx-runtime");
8596
+ import_jsx_runtime23 = require("react/jsx-runtime");
8472
8597
  DEFAULT_PAGE_WIDTH = 612;
8473
8598
  DEFAULT_PAGE_HEIGHT = 792;
8474
- VirtualizedDocumentContainer = (0, import_react36.memo)(function VirtualizedDocumentContainer2({
8599
+ VirtualizedDocumentContainer = (0, import_react37.memo)(function VirtualizedDocumentContainer2({
8475
8600
  overscan = 2,
8476
8601
  pageGap = 16,
8477
8602
  enableTouchGestures = true,
@@ -8492,17 +8617,17 @@ var init_VirtualizedDocumentContainer = __esm({
8492
8617
  } = usePDFViewer();
8493
8618
  const scrollToPageRequest = useViewerStore((s) => s.scrollToPageRequest);
8494
8619
  const { viewerStore } = usePDFViewerStores();
8495
- const containerRef = (0, import_react36.useRef)(null);
8496
- const scrollContainerRef = (0, import_react36.useRef)(null);
8497
- const documentRef = (0, import_react36.useRef)(null);
8498
- const pageCache = (0, import_react36.useRef)(/* @__PURE__ */ new Map());
8499
- const pageDimensionsCache = (0, import_react36.useRef)(/* @__PURE__ */ new Map());
8500
- const baseScaleRef = (0, import_react36.useRef)(scale);
8620
+ const containerRef = (0, import_react37.useRef)(null);
8621
+ const scrollContainerRef = (0, import_react37.useRef)(null);
8622
+ const documentRef = (0, import_react37.useRef)(null);
8623
+ const pageCache = (0, import_react37.useRef)(/* @__PURE__ */ new Map());
8624
+ const pageDimensionsCache = (0, import_react37.useRef)(/* @__PURE__ */ new Map());
8625
+ const baseScaleRef = (0, import_react37.useRef)(scale);
8501
8626
  const isTouchDevice = useIsTouchDevice();
8502
- const [visiblePages, setVisiblePages] = (0, import_react36.useState)([1]);
8503
- const [pageObjects, setPageObjects] = (0, import_react36.useState)(/* @__PURE__ */ new Map());
8504
- const [totalHeight, setTotalHeight] = (0, import_react36.useState)(0);
8505
- const [pageInfos, setPageInfos] = (0, import_react36.useState)([]);
8627
+ const [visiblePages, setVisiblePages] = (0, import_react37.useState)([1]);
8628
+ const [pageObjects, setPageObjects] = (0, import_react37.useState)(/* @__PURE__ */ new Map());
8629
+ const [totalHeight, setTotalHeight] = (0, import_react37.useState)(0);
8630
+ const [pageInfos, setPageInfos] = (0, import_react37.useState)([]);
8506
8631
  const { selection, clearSelection, copySelection } = useTextSelection();
8507
8632
  const {
8508
8633
  createHighlightFromSelection,
@@ -8512,7 +8637,7 @@ var init_VirtualizedDocumentContainer = __esm({
8512
8637
  selectHighlight,
8513
8638
  activeColor
8514
8639
  } = useHighlights();
8515
- (0, import_react36.useEffect)(() => {
8640
+ (0, import_react37.useEffect)(() => {
8516
8641
  if (document2 !== documentRef.current) {
8517
8642
  documentRef.current = document2;
8518
8643
  pageCache.current.clear();
@@ -8520,7 +8645,7 @@ var init_VirtualizedDocumentContainer = __esm({
8520
8645
  setPageObjects(/* @__PURE__ */ new Map());
8521
8646
  }
8522
8647
  }, [document2]);
8523
- (0, import_react36.useEffect)(() => {
8648
+ (0, import_react37.useEffect)(() => {
8524
8649
  if (!document2 || numPages === 0) return;
8525
8650
  const calculatePageInfos = async () => {
8526
8651
  const infos = [];
@@ -8553,7 +8678,7 @@ var init_VirtualizedDocumentContainer = __esm({
8553
8678
  };
8554
8679
  calculatePageInfos();
8555
8680
  }, [document2, numPages, scale, rotation, pageGap]);
8556
- const updateVisiblePages = (0, import_react36.useCallback)(() => {
8681
+ const updateVisiblePages = (0, import_react37.useCallback)(() => {
8557
8682
  if (!scrollContainerRef.current || pageInfos.length === 0) return;
8558
8683
  const container = scrollContainerRef.current;
8559
8684
  const scrollTop = container.scrollTop;
@@ -8585,7 +8710,7 @@ var init_VirtualizedDocumentContainer = __esm({
8585
8710
  goToPage(firstVisiblePage);
8586
8711
  }
8587
8712
  }, [pageInfos, overscan, currentPage, goToPage]);
8588
- (0, import_react36.useEffect)(() => {
8713
+ (0, import_react37.useEffect)(() => {
8589
8714
  const container = scrollContainerRef.current;
8590
8715
  if (!container) return;
8591
8716
  const handleScroll = () => {
@@ -8595,7 +8720,7 @@ var init_VirtualizedDocumentContainer = __esm({
8595
8720
  updateVisiblePages();
8596
8721
  return () => container.removeEventListener("scroll", handleScroll);
8597
8722
  }, [updateVisiblePages]);
8598
- (0, import_react36.useEffect)(() => {
8723
+ (0, import_react37.useEffect)(() => {
8599
8724
  if (!document2) return;
8600
8725
  const loadPages = async () => {
8601
8726
  const newPageObjects = new Map(pageObjects);
@@ -8628,7 +8753,7 @@ var init_VirtualizedDocumentContainer = __esm({
8628
8753
  };
8629
8754
  loadPages();
8630
8755
  }, [document2, visiblePages, pageObjects]);
8631
- (0, import_react36.useEffect)(() => {
8756
+ (0, import_react37.useEffect)(() => {
8632
8757
  if (!scrollToPageRequest || !scrollContainerRef.current || pageInfos.length === 0) return;
8633
8758
  const { page, requestId, behavior } = scrollToPageRequest;
8634
8759
  const pageInfo = pageInfos.find((p) => p.pageNumber === page);
@@ -8666,7 +8791,7 @@ var init_VirtualizedDocumentContainer = __esm({
8666
8791
  handleScrollEnd();
8667
8792
  }
8668
8793
  }, [scrollToPageRequest, pageInfos, pageGap, viewerStore]);
8669
- (0, import_react36.useEffect)(() => {
8794
+ (0, import_react37.useEffect)(() => {
8670
8795
  if (scrollToPageRequest) return;
8671
8796
  if (!scrollContainerRef.current || pageInfos.length === 0) return;
8672
8797
  const pageInfo = pageInfos.find((p) => p.pageNumber === currentPage);
@@ -8683,14 +8808,14 @@ var init_VirtualizedDocumentContainer = __esm({
8683
8808
  }
8684
8809
  }
8685
8810
  }, [currentPage, pageInfos, pageGap, scrollToPageRequest]);
8686
- const handlePinchZoom = (0, import_react36.useCallback)(
8811
+ const handlePinchZoom = (0, import_react37.useCallback)(
8687
8812
  (pinchScale) => {
8688
8813
  const newScale = Math.max(0.25, Math.min(4, baseScaleRef.current * pinchScale));
8689
8814
  setScale(newScale);
8690
8815
  },
8691
8816
  [setScale]
8692
8817
  );
8693
- (0, import_react36.useEffect)(() => {
8818
+ (0, import_react37.useEffect)(() => {
8694
8819
  baseScaleRef.current = scale;
8695
8820
  }, [scale]);
8696
8821
  const { ref: touchRef } = useTouchGestures({
@@ -8699,20 +8824,20 @@ var init_VirtualizedDocumentContainer = __esm({
8699
8824
  onSwipeRight: previousPage,
8700
8825
  enabled: enableTouchGestures && isTouchDevice
8701
8826
  });
8702
- const setContainerRef = (0, import_react36.useCallback)(
8827
+ const setContainerRef = (0, import_react37.useCallback)(
8703
8828
  (element) => {
8704
8829
  scrollContainerRef.current = element;
8705
8830
  touchRef(element);
8706
8831
  },
8707
8832
  [touchRef]
8708
8833
  );
8709
- const getPageElement = (0, import_react36.useCallback)(
8834
+ const getPageElement = (0, import_react37.useCallback)(
8710
8835
  (pageNumber) => {
8711
8836
  return containerRef.current?.querySelector(`[data-page-number="${pageNumber}"]`);
8712
8837
  },
8713
8838
  []
8714
8839
  );
8715
- const handleCreateHighlight = (0, import_react36.useCallback)(
8840
+ const handleCreateHighlight = (0, import_react37.useCallback)(
8716
8841
  (color) => {
8717
8842
  if (!selection) return;
8718
8843
  const pageElement = getPageElement(selection.pageNumber);
@@ -8722,13 +8847,13 @@ var init_VirtualizedDocumentContainer = __esm({
8722
8847
  },
8723
8848
  [selection, getPageElement, createHighlightFromSelection, scale, clearSelection]
8724
8849
  );
8725
- const handleColorChange = (0, import_react36.useCallback)(
8850
+ const handleColorChange = (0, import_react37.useCallback)(
8726
8851
  (id, color) => {
8727
8852
  updateHighlight(id, { color });
8728
8853
  },
8729
8854
  [updateHighlight]
8730
8855
  );
8731
- const handleCommentChange = (0, import_react36.useCallback)(
8856
+ const handleCommentChange = (0, import_react37.useCallback)(
8732
8857
  (id, comment) => {
8733
8858
  updateHighlight(id, { comment: comment || void 0 });
8734
8859
  },
@@ -8740,23 +8865,20 @@ var init_VirtualizedDocumentContainer = __esm({
8740
8865
  sepia: "bg-amber-50"
8741
8866
  };
8742
8867
  if (!document2) {
8743
- if (isLoading) {
8744
- return null;
8745
- }
8746
- return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
8868
+ return /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(
8747
8869
  "div",
8748
8870
  {
8749
8871
  className: cn(
8750
8872
  "virtualized-document-container",
8751
- "flex-1 flex items-center justify-center",
8873
+ "flex-1",
8752
8874
  themeStyles[theme],
8753
8875
  className
8754
8876
  ),
8755
- children: /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("div", { className: "text-gray-500 dark:text-gray-400", children: "No document loaded" })
8877
+ children: /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(PDFLoadingScreen, { phase: isLoading ? "fetching" : "initializing" })
8756
8878
  }
8757
8879
  );
8758
8880
  }
8759
- return /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)(
8881
+ return /* @__PURE__ */ (0, import_jsx_runtime23.jsxs)(
8760
8882
  "div",
8761
8883
  {
8762
8884
  ref: containerRef,
@@ -8767,7 +8889,7 @@ var init_VirtualizedDocumentContainer = __esm({
8767
8889
  className
8768
8890
  ),
8769
8891
  children: [
8770
- /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
8892
+ /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(
8771
8893
  "div",
8772
8894
  {
8773
8895
  ref: setContainerRef,
@@ -8776,7 +8898,7 @@ var init_VirtualizedDocumentContainer = __esm({
8776
8898
  // Smooth scrolling on iOS
8777
8899
  WebkitOverflowScrolling: "touch"
8778
8900
  },
8779
- children: /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
8901
+ children: /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(
8780
8902
  "div",
8781
8903
  {
8782
8904
  className: "relative mx-auto",
@@ -8788,7 +8910,7 @@ var init_VirtualizedDocumentContainer = __esm({
8788
8910
  const page = pageObjects.get(info.pageNumber);
8789
8911
  const dimensions = pageDimensionsCache.current.get(info.pageNumber);
8790
8912
  const scaledWidth = dimensions ? Math.floor(dimensions.width * scale) : Math.floor(DEFAULT_PAGE_WIDTH * scale);
8791
- return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
8913
+ return /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(
8792
8914
  "div",
8793
8915
  {
8794
8916
  className: "absolute left-1/2 -translate-x-1/2",
@@ -8796,7 +8918,7 @@ var init_VirtualizedDocumentContainer = __esm({
8796
8918
  top: info.top,
8797
8919
  width: scaledWidth
8798
8920
  },
8799
- children: /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
8921
+ children: /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(
8800
8922
  PDFPage,
8801
8923
  {
8802
8924
  pageNumber: info.pageNumber,
@@ -8813,7 +8935,7 @@ var init_VirtualizedDocumentContainer = __esm({
8813
8935
  )
8814
8936
  }
8815
8937
  ),
8816
- /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
8938
+ /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(
8817
8939
  SelectionToolbar,
8818
8940
  {
8819
8941
  selection,
@@ -8822,7 +8944,7 @@ var init_VirtualizedDocumentContainer = __esm({
8822
8944
  activeColor
8823
8945
  }
8824
8946
  ),
8825
- /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
8947
+ /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(
8826
8948
  HighlightPopover,
8827
8949
  {
8828
8950
  highlight: selectedHighlight,
@@ -8842,15 +8964,15 @@ var init_VirtualizedDocumentContainer = __esm({
8842
8964
  });
8843
8965
 
8844
8966
  // src/components/PDFViewer/ContinuousScrollContainer.tsx
8845
- var import_react37, import_jsx_runtime23, ContinuousScrollContainer;
8967
+ var import_react38, import_jsx_runtime24, ContinuousScrollContainer;
8846
8968
  var init_ContinuousScrollContainer = __esm({
8847
8969
  "src/components/PDFViewer/ContinuousScrollContainer.tsx"() {
8848
8970
  "use strict";
8849
- import_react37 = require("react");
8971
+ import_react38 = require("react");
8850
8972
  init_VirtualizedDocumentContainer();
8851
- import_jsx_runtime23 = require("react/jsx-runtime");
8852
- ContinuousScrollContainer = (0, import_react37.memo)(function ContinuousScrollContainer2(props) {
8853
- return /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(
8973
+ import_jsx_runtime24 = require("react/jsx-runtime");
8974
+ ContinuousScrollContainer = (0, import_react38.memo)(function ContinuousScrollContainer2(props) {
8975
+ return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
8854
8976
  VirtualizedDocumentContainer,
8855
8977
  {
8856
8978
  overscan: 3,
@@ -8863,19 +8985,20 @@ var init_ContinuousScrollContainer = __esm({
8863
8985
  });
8864
8986
 
8865
8987
  // src/components/PDFViewer/DualPageContainer.tsx
8866
- var import_react38, import_jsx_runtime24, DualPageContainer;
8988
+ var import_react39, import_jsx_runtime25, DualPageContainer;
8867
8989
  var init_DualPageContainer = __esm({
8868
8990
  "src/components/PDFViewer/DualPageContainer.tsx"() {
8869
8991
  "use strict";
8870
- import_react38 = require("react");
8992
+ import_react39 = require("react");
8871
8993
  init_PDFPage2();
8994
+ init_PDFLoadingScreen2();
8872
8995
  init_hooks();
8873
8996
  init_useHighlights();
8874
8997
  init_SelectionToolbar2();
8875
8998
  init_HighlightPopover2();
8876
8999
  init_utils();
8877
- import_jsx_runtime24 = require("react/jsx-runtime");
8878
- DualPageContainer = (0, import_react38.memo)(function DualPageContainer2({
9000
+ import_jsx_runtime25 = require("react/jsx-runtime");
9001
+ DualPageContainer = (0, import_react39.memo)(function DualPageContainer2({
8879
9002
  showCover = true,
8880
9003
  bookSpread = true,
8881
9004
  pageGap = 4,
@@ -8895,13 +9018,13 @@ var init_DualPageContainer = __esm({
8895
9018
  } = usePDFViewer();
8896
9019
  const scrollToPageRequest = useViewerStore((s) => s.scrollToPageRequest);
8897
9020
  const { viewerStore } = usePDFViewerStores();
8898
- const containerRef = (0, import_react38.useRef)(null);
8899
- const documentRef = (0, import_react38.useRef)(null);
8900
- const baseScaleRef = (0, import_react38.useRef)(scale);
9021
+ const containerRef = (0, import_react39.useRef)(null);
9022
+ const documentRef = (0, import_react39.useRef)(null);
9023
+ const baseScaleRef = (0, import_react39.useRef)(scale);
8901
9024
  const isTouchDevice = useIsTouchDevice();
8902
- const [leftPage, setLeftPage] = (0, import_react38.useState)(null);
8903
- const [rightPage, setRightPage] = (0, import_react38.useState)(null);
8904
- const [isLoading, setIsLoading] = (0, import_react38.useState)(false);
9025
+ const [leftPage, setLeftPage] = (0, import_react39.useState)(null);
9026
+ const [rightPage, setRightPage] = (0, import_react39.useState)(null);
9027
+ const [isLoading, setIsLoading] = (0, import_react39.useState)(false);
8905
9028
  const { selection, clearSelection, copySelection } = useTextSelection();
8906
9029
  const {
8907
9030
  createHighlightFromSelection,
@@ -8911,7 +9034,7 @@ var init_DualPageContainer = __esm({
8911
9034
  selectHighlight,
8912
9035
  activeColor
8913
9036
  } = useHighlights();
8914
- const getSpreadPages = (0, import_react38.useCallback)(
9037
+ const getSpreadPages = (0, import_react39.useCallback)(
8915
9038
  (page) => {
8916
9039
  if (showCover && page === 1) {
8917
9040
  return { left: null, right: 1 };
@@ -8955,14 +9078,14 @@ var init_DualPageContainer = __esm({
8955
9078
  },
8956
9079
  [showCover, bookSpread, numPages]
8957
9080
  );
8958
- (0, import_react38.useEffect)(() => {
9081
+ (0, import_react39.useEffect)(() => {
8959
9082
  if (document2 !== documentRef.current) {
8960
9083
  documentRef.current = document2;
8961
9084
  setLeftPage(null);
8962
9085
  setRightPage(null);
8963
9086
  }
8964
9087
  }, [document2]);
8965
- (0, import_react38.useEffect)(() => {
9088
+ (0, import_react39.useEffect)(() => {
8966
9089
  if (!document2) {
8967
9090
  setLeftPage(null);
8968
9091
  setRightPage(null);
@@ -9004,7 +9127,7 @@ var init_DualPageContainer = __esm({
9004
9127
  cancelled = true;
9005
9128
  };
9006
9129
  }, [document2, currentPage, getSpreadPages, scrollToPageRequest, viewerStore]);
9007
- const goToPreviousSpread = (0, import_react38.useCallback)(() => {
9130
+ const goToPreviousSpread = (0, import_react39.useCallback)(() => {
9008
9131
  const spread2 = getSpreadPages(currentPage);
9009
9132
  const leftmostPage = spread2.left || spread2.right || currentPage;
9010
9133
  if (showCover && leftmostPage === 2) {
@@ -9016,21 +9139,21 @@ var init_DualPageContainer = __esm({
9016
9139
  goToPage(newPage);
9017
9140
  }
9018
9141
  }, [currentPage, showCover, getSpreadPages, goToPage]);
9019
- const goToNextSpread = (0, import_react38.useCallback)(() => {
9142
+ const goToNextSpread = (0, import_react39.useCallback)(() => {
9020
9143
  const spread2 = getSpreadPages(currentPage);
9021
9144
  const rightmostPage = spread2.right || spread2.left || currentPage;
9022
9145
  if (rightmostPage < numPages) {
9023
9146
  goToPage(Math.min(numPages, rightmostPage + 1));
9024
9147
  }
9025
9148
  }, [currentPage, numPages, getSpreadPages, goToPage]);
9026
- const handlePinchZoom = (0, import_react38.useCallback)(
9149
+ const handlePinchZoom = (0, import_react39.useCallback)(
9027
9150
  (pinchScale) => {
9028
9151
  const newScale = Math.max(0.25, Math.min(4, baseScaleRef.current * pinchScale));
9029
9152
  setScale(newScale);
9030
9153
  },
9031
9154
  [setScale]
9032
9155
  );
9033
- (0, import_react38.useEffect)(() => {
9156
+ (0, import_react39.useEffect)(() => {
9034
9157
  baseScaleRef.current = scale;
9035
9158
  }, [scale]);
9036
9159
  const { ref: touchRef } = useTouchGestures({
@@ -9039,20 +9162,20 @@ var init_DualPageContainer = __esm({
9039
9162
  onSwipeRight: goToPreviousSpread,
9040
9163
  enabled: enableTouchGestures && isTouchDevice
9041
9164
  });
9042
- const setContainerRef = (0, import_react38.useCallback)(
9165
+ const setContainerRef = (0, import_react39.useCallback)(
9043
9166
  (element) => {
9044
9167
  containerRef.current = element;
9045
9168
  touchRef(element);
9046
9169
  },
9047
9170
  [touchRef]
9048
9171
  );
9049
- const getPageElement = (0, import_react38.useCallback)(
9172
+ const getPageElement = (0, import_react39.useCallback)(
9050
9173
  (pageNumber) => {
9051
9174
  return containerRef.current?.querySelector(`[data-page-number="${pageNumber}"]`);
9052
9175
  },
9053
9176
  []
9054
9177
  );
9055
- const handleCreateHighlight = (0, import_react38.useCallback)(
9178
+ const handleCreateHighlight = (0, import_react39.useCallback)(
9056
9179
  (color) => {
9057
9180
  if (!selection) return;
9058
9181
  const pageElement = getPageElement(selection.pageNumber);
@@ -9062,13 +9185,13 @@ var init_DualPageContainer = __esm({
9062
9185
  },
9063
9186
  [selection, getPageElement, createHighlightFromSelection, scale, clearSelection]
9064
9187
  );
9065
- const handleColorChange = (0, import_react38.useCallback)(
9188
+ const handleColorChange = (0, import_react39.useCallback)(
9066
9189
  (id, color) => {
9067
9190
  updateHighlight(id, { color });
9068
9191
  },
9069
9192
  [updateHighlight]
9070
9193
  );
9071
- const handleCommentChange = (0, import_react38.useCallback)(
9194
+ const handleCommentChange = (0, import_react39.useCallback)(
9072
9195
  (id, comment) => {
9073
9196
  updateHighlight(id, { comment: comment || void 0 });
9074
9197
  },
@@ -9081,23 +9204,20 @@ var init_DualPageContainer = __esm({
9081
9204
  };
9082
9205
  const spread = getSpreadPages(currentPage);
9083
9206
  if (!document2) {
9084
- if (isDocumentLoading) {
9085
- return null;
9086
- }
9087
- return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
9207
+ return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
9088
9208
  "div",
9089
9209
  {
9090
9210
  className: cn(
9091
9211
  "dual-page-container",
9092
- "flex-1 flex items-center justify-center",
9212
+ "flex-1",
9093
9213
  themeStyles[theme],
9094
9214
  className
9095
9215
  ),
9096
- children: /* @__PURE__ */ (0, import_jsx_runtime24.jsx)("div", { className: "text-gray-500 dark:text-gray-400", children: "No document loaded" })
9216
+ children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(PDFLoadingScreen, { phase: isDocumentLoading ? "fetching" : "initializing" })
9097
9217
  }
9098
9218
  );
9099
9219
  }
9100
- return /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)(
9220
+ return /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(
9101
9221
  "div",
9102
9222
  {
9103
9223
  ref: setContainerRef,
@@ -9110,13 +9230,13 @@ var init_DualPageContainer = __esm({
9110
9230
  className
9111
9231
  ),
9112
9232
  children: [
9113
- /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)(
9233
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(
9114
9234
  "div",
9115
9235
  {
9116
9236
  className: "flex items-center",
9117
9237
  style: { gap: pageGap },
9118
9238
  children: [
9119
- spread.left && /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
9239
+ spread.left && /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
9120
9240
  PDFPage,
9121
9241
  {
9122
9242
  pageNumber: spread.left,
@@ -9125,14 +9245,14 @@ var init_DualPageContainer = __esm({
9125
9245
  rotation
9126
9246
  }
9127
9247
  ),
9128
- spread.left && spread.right && /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
9248
+ spread.left && spread.right && /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
9129
9249
  "div",
9130
9250
  {
9131
9251
  className: "w-px h-full bg-gray-300 dark:bg-gray-600 opacity-50",
9132
9252
  style: { minHeight: "100%" }
9133
9253
  }
9134
9254
  ),
9135
- spread.right && /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
9255
+ spread.right && /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
9136
9256
  PDFPage,
9137
9257
  {
9138
9258
  pageNumber: spread.right,
@@ -9141,7 +9261,7 @@ var init_DualPageContainer = __esm({
9141
9261
  rotation
9142
9262
  }
9143
9263
  ),
9144
- (!spread.left || !spread.right) && /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
9264
+ (!spread.left || !spread.right) && /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
9145
9265
  "div",
9146
9266
  {
9147
9267
  className: "flex items-center justify-center",
@@ -9154,7 +9274,7 @@ var init_DualPageContainer = __esm({
9154
9274
  ]
9155
9275
  }
9156
9276
  ),
9157
- /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
9277
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
9158
9278
  SelectionToolbar,
9159
9279
  {
9160
9280
  selection,
@@ -9163,7 +9283,7 @@ var init_DualPageContainer = __esm({
9163
9283
  activeColor
9164
9284
  }
9165
9285
  ),
9166
- /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
9286
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
9167
9287
  HighlightPopover,
9168
9288
  {
9169
9289
  highlight: selectedHighlight,
@@ -9175,7 +9295,7 @@ var init_DualPageContainer = __esm({
9175
9295
  onClose: () => selectHighlight(null)
9176
9296
  }
9177
9297
  ),
9178
- isLoading && /* @__PURE__ */ (0, import_jsx_runtime24.jsx)("div", { className: "fixed bottom-4 right-4 px-3 py-2 bg-black/75 text-white text-sm rounded-lg", children: "Loading..." })
9298
+ isLoading && /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { className: "fixed bottom-4 right-4 px-3 py-2 bg-black/75 text-white text-sm rounded-lg", children: "Loading..." })
9179
9299
  ]
9180
9300
  }
9181
9301
  );
@@ -9184,15 +9304,15 @@ var init_DualPageContainer = __esm({
9184
9304
  });
9185
9305
 
9186
9306
  // src/components/FloatingZoomControls/FloatingZoomControls.tsx
9187
- var import_react39, import_jsx_runtime25, FloatingZoomControls;
9307
+ var import_react40, import_jsx_runtime26, FloatingZoomControls;
9188
9308
  var init_FloatingZoomControls = __esm({
9189
9309
  "src/components/FloatingZoomControls/FloatingZoomControls.tsx"() {
9190
9310
  "use strict";
9191
- import_react39 = require("react");
9311
+ import_react40 = require("react");
9192
9312
  init_hooks();
9193
9313
  init_utils();
9194
- import_jsx_runtime25 = require("react/jsx-runtime");
9195
- FloatingZoomControls = (0, import_react39.memo)(function FloatingZoomControls2({
9314
+ import_jsx_runtime26 = require("react/jsx-runtime");
9315
+ FloatingZoomControls = (0, import_react40.memo)(function FloatingZoomControls2({
9196
9316
  position = "bottom-right",
9197
9317
  className,
9198
9318
  showFitToWidth = true,
@@ -9202,20 +9322,20 @@ var init_FloatingZoomControls = __esm({
9202
9322
  const { viewerStore } = usePDFViewerStores();
9203
9323
  const scale = useViewerStore((s) => s.scale);
9204
9324
  const document2 = useViewerStore((s) => s.document);
9205
- const handleZoomIn = (0, import_react39.useCallback)(() => {
9325
+ const handleZoomIn = (0, import_react40.useCallback)(() => {
9206
9326
  const currentScale = viewerStore.getState().scale;
9207
9327
  const newScale = Math.min(4, currentScale + 0.05);
9208
9328
  viewerStore.getState().setScale(newScale);
9209
9329
  }, [viewerStore]);
9210
- const handleZoomOut = (0, import_react39.useCallback)(() => {
9330
+ const handleZoomOut = (0, import_react40.useCallback)(() => {
9211
9331
  const currentScale = viewerStore.getState().scale;
9212
9332
  const newScale = Math.max(0.1, currentScale - 0.05);
9213
9333
  viewerStore.getState().setScale(newScale);
9214
9334
  }, [viewerStore]);
9215
- const handleFitToWidth = (0, import_react39.useCallback)(() => {
9335
+ const handleFitToWidth = (0, import_react40.useCallback)(() => {
9216
9336
  viewerStore.getState().setScale(1);
9217
9337
  }, [viewerStore]);
9218
- const handleFitToPage = (0, import_react39.useCallback)(() => {
9338
+ const handleFitToPage = (0, import_react40.useCallback)(() => {
9219
9339
  viewerStore.getState().setScale(0.75);
9220
9340
  }, [viewerStore]);
9221
9341
  if (!document2) return null;
@@ -9226,7 +9346,7 @@ var init_FloatingZoomControls = __esm({
9226
9346
  "top-left": "top-4 left-4"
9227
9347
  };
9228
9348
  const zoomPercentage = Math.round(scale * 100);
9229
- return /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(
9349
+ return /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)(
9230
9350
  "div",
9231
9351
  {
9232
9352
  className: cn(
@@ -9238,7 +9358,7 @@ var init_FloatingZoomControls = __esm({
9238
9358
  className
9239
9359
  ),
9240
9360
  children: [
9241
- /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
9361
+ /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
9242
9362
  "button",
9243
9363
  {
9244
9364
  onClick: handleZoomOut,
@@ -9252,14 +9372,14 @@ var init_FloatingZoomControls = __esm({
9252
9372
  disabled: scale <= 0.25,
9253
9373
  title: "Zoom Out",
9254
9374
  "aria-label": "Zoom Out",
9255
- children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("svg", { className: "w-4 h-4", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M20 12H4" }) })
9375
+ children: /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("svg", { className: "w-4 h-4", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M20 12H4" }) })
9256
9376
  }
9257
9377
  ),
9258
- showZoomLevel && /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)("span", { className: "min-w-[48px] text-center text-sm font-medium text-gray-700 dark:text-gray-300", children: [
9378
+ showZoomLevel && /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)("span", { className: "min-w-[48px] text-center text-sm font-medium text-gray-700 dark:text-gray-300", children: [
9259
9379
  zoomPercentage,
9260
9380
  "%"
9261
9381
  ] }),
9262
- /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
9382
+ /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
9263
9383
  "button",
9264
9384
  {
9265
9385
  onClick: handleZoomIn,
@@ -9273,11 +9393,11 @@ var init_FloatingZoomControls = __esm({
9273
9393
  disabled: scale >= 4,
9274
9394
  title: "Zoom In",
9275
9395
  "aria-label": "Zoom In",
9276
- children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("svg", { className: "w-4 h-4", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M12 4v16m8-8H4" }) })
9396
+ children: /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("svg", { className: "w-4 h-4", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M12 4v16m8-8H4" }) })
9277
9397
  }
9278
9398
  ),
9279
- (showFitToWidth || showFitToPage) && /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { className: "w-px h-6 bg-gray-200 dark:bg-gray-700 mx-1" }),
9280
- showFitToWidth && /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
9399
+ (showFitToWidth || showFitToPage) && /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("div", { className: "w-px h-6 bg-gray-200 dark:bg-gray-700 mx-1" }),
9400
+ showFitToWidth && /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
9281
9401
  "button",
9282
9402
  {
9283
9403
  onClick: handleFitToWidth,
@@ -9289,10 +9409,10 @@ var init_FloatingZoomControls = __esm({
9289
9409
  ),
9290
9410
  title: "Fit to Width",
9291
9411
  "aria-label": "Fit to Width",
9292
- children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("svg", { className: "w-4 h-4", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M4 8V4m0 0h4M4 4l5 5m11-1V4m0 0h-4m4 0l-5 5M4 16v4m0 0h4m-4 0l5-5m11 5l-5-5m5 5v-4m0 4h-4" }) })
9412
+ children: /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("svg", { className: "w-4 h-4", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M4 8V4m0 0h4M4 4l5 5m11-1V4m0 0h-4m4 0l-5 5M4 16v4m0 0h4m-4 0l5-5m11 5l-5-5m5 5v-4m0 4h-4" }) })
9293
9413
  }
9294
9414
  ),
9295
- showFitToPage && /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
9415
+ showFitToPage && /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
9296
9416
  "button",
9297
9417
  {
9298
9418
  onClick: handleFitToPage,
@@ -9304,7 +9424,7 @@ var init_FloatingZoomControls = __esm({
9304
9424
  ),
9305
9425
  title: "Fit to Page",
9306
9426
  "aria-label": "Fit to Page",
9307
- children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("svg", { className: "w-4 h-4", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M9 12h6m-6 4h6m2 5H7a2 2 0 01-2-2V5a2 2 0 012-2h5.586a1 1 0 01.707.293l5.414 5.414a1 1 0 01.293.707V19a2 2 0 01-2 2z" }) })
9427
+ children: /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("svg", { className: "w-4 h-4", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M9 12h6m-6 4h6m2 5H7a2 2 0 01-2-2V5a2 2 0 012-2h5.586a1 1 0 01.707.293l5.414 5.414a1 1 0 01.293.707V19a2 2 0 01-2 2z" }) })
9308
9428
  }
9309
9429
  )
9310
9430
  ]
@@ -9322,138 +9442,6 @@ var init_FloatingZoomControls2 = __esm({
9322
9442
  }
9323
9443
  });
9324
9444
 
9325
- // src/components/PDFLoadingScreen/PDFLoadingScreen.tsx
9326
- function formatBytes(bytes) {
9327
- if (bytes < 1024) return `${bytes} B`;
9328
- if (bytes < 1024 * 1024) return `${(bytes / 1024).toFixed(1)} KB`;
9329
- return `${(bytes / (1024 * 1024)).toFixed(1)} MB`;
9330
- }
9331
- var import_react40, import_jsx_runtime26, phaseMessages, PDFLoadingScreen;
9332
- var init_PDFLoadingScreen = __esm({
9333
- "src/components/PDFLoadingScreen/PDFLoadingScreen.tsx"() {
9334
- "use strict";
9335
- import_react40 = require("react");
9336
- init_utils();
9337
- import_jsx_runtime26 = require("react/jsx-runtime");
9338
- phaseMessages = {
9339
- initializing: "Initializing...",
9340
- fetching: "Loading document...",
9341
- parsing: "Processing pages...",
9342
- rendering: "Preparing view..."
9343
- };
9344
- PDFLoadingScreen = (0, import_react40.memo)(function PDFLoadingScreen2({
9345
- progress,
9346
- bytesLoaded,
9347
- totalBytes,
9348
- phase = "fetching",
9349
- documentName,
9350
- className
9351
- }) {
9352
- const hasProgress = progress !== void 0 && progress >= 0;
9353
- const hasBytes = bytesLoaded !== void 0 && totalBytes !== void 0 && totalBytes > 0;
9354
- return /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)(
9355
- "div",
9356
- {
9357
- className: cn(
9358
- "pdf-loading-screen",
9359
- "flex flex-col items-center justify-center",
9360
- "w-full h-full min-h-[400px]",
9361
- "bg-slate-50 dark:bg-slate-800",
9362
- className
9363
- ),
9364
- role: "status",
9365
- "aria-live": "polite",
9366
- "aria-label": phaseMessages[phase],
9367
- children: [
9368
- /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)("div", { className: "pdf-loading-skeleton", children: [
9369
- /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("div", { className: "pdf-loading-icon", children: /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)(
9370
- "svg",
9371
- {
9372
- width: "48",
9373
- height: "56",
9374
- viewBox: "0 0 48 56",
9375
- fill: "none",
9376
- xmlns: "http://www.w3.org/2000/svg",
9377
- className: "pdf-document-icon",
9378
- children: [
9379
- /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
9380
- "path",
9381
- {
9382
- d: "M4 4C4 1.79086 5.79086 0 8 0H30L44 14V52C44 54.2091 42.2091 56 40 56H8C5.79086 56 4 54.2091 4 52V4Z",
9383
- className: "fill-white dark:fill-slate-700"
9384
- }
9385
- ),
9386
- /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
9387
- "path",
9388
- {
9389
- d: "M30 0L44 14H34C31.7909 14 30 12.2091 30 10V0Z",
9390
- className: "fill-slate-200 dark:fill-slate-600"
9391
- }
9392
- ),
9393
- /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("rect", { x: "10", y: "22", width: "24", height: "3", rx: "1.5", className: "fill-slate-200 dark:fill-slate-600" }),
9394
- /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("rect", { x: "10", y: "28", width: "20", height: "3", rx: "1.5", className: "fill-slate-200 dark:fill-slate-600" }),
9395
- /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("rect", { x: "10", y: "34", width: "22", height: "3", rx: "1.5", className: "fill-slate-200 dark:fill-slate-600" }),
9396
- /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("rect", { x: "10", y: "40", width: "16", height: "3", rx: "1.5", className: "fill-slate-200 dark:fill-slate-600" }),
9397
- /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
9398
- "path",
9399
- {
9400
- d: "M4 4C4 1.79086 5.79086 0 8 0H30L44 14V52C44 54.2091 42.2091 56 40 56H8C5.79086 56 4 54.2091 4 52V4Z",
9401
- className: "stroke-slate-300 dark:stroke-slate-500",
9402
- strokeWidth: "1",
9403
- fill: "none"
9404
- }
9405
- )
9406
- ]
9407
- }
9408
- ) }),
9409
- /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)("div", { className: "pdf-skeleton-lines", children: [
9410
- /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("div", { className: "pdf-skeleton-line pdf-skeleton-line-1" }),
9411
- /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("div", { className: "pdf-skeleton-line pdf-skeleton-line-2" }),
9412
- /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("div", { className: "pdf-skeleton-line pdf-skeleton-line-3" })
9413
- ] })
9414
- ] }),
9415
- /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)("div", { className: "pdf-loading-info", children: [
9416
- documentName && /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("p", { className: "pdf-loading-document-name", children: documentName }),
9417
- /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("p", { className: "pdf-loading-message", children: phaseMessages[phase] }),
9418
- /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)("div", { className: "pdf-loading-progress-container", children: [
9419
- /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("div", { className: "pdf-loading-progress-track", children: /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
9420
- "div",
9421
- {
9422
- className: cn(
9423
- "pdf-loading-progress-fill",
9424
- !hasProgress && "pdf-loading-progress-indeterminate"
9425
- ),
9426
- style: hasProgress ? { width: `${Math.min(100, progress)}%` } : void 0
9427
- }
9428
- ) }),
9429
- /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)("div", { className: "pdf-loading-progress-details", children: [
9430
- hasProgress && /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)("span", { className: "pdf-loading-progress-percent", children: [
9431
- Math.round(progress),
9432
- "%"
9433
- ] }),
9434
- hasBytes && /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)("span", { className: "pdf-loading-progress-bytes", children: [
9435
- formatBytes(bytesLoaded),
9436
- " / ",
9437
- formatBytes(totalBytes)
9438
- ] })
9439
- ] })
9440
- ] })
9441
- ] })
9442
- ]
9443
- }
9444
- );
9445
- });
9446
- }
9447
- });
9448
-
9449
- // src/components/PDFLoadingScreen/index.ts
9450
- var init_PDFLoadingScreen2 = __esm({
9451
- "src/components/PDFLoadingScreen/index.ts"() {
9452
- "use strict";
9453
- init_PDFLoadingScreen();
9454
- }
9455
- });
9456
-
9457
9445
  // src/components/PDFViewer/PDFViewerClient.tsx
9458
9446
  var PDFViewerClient_exports = {};
9459
9447
  __export(PDFViewerClient_exports, {
@@ -10018,12 +10006,13 @@ var init_PDFViewerClient = __esm({
10018
10006
  currentDoc.destroy();
10019
10007
  viewerStore.getState().setDocument(null);
10020
10008
  }
10009
+ viewerStore.getState().setLoading(true, { phase: "initializing" });
10010
+ viewerStore.getState().setError(null);
10011
+ setLoadState("loading");
10021
10012
  const loadDoc = async () => {
10022
10013
  if (!mountedRef.current) return;
10023
10014
  try {
10024
- viewerStore.getState().setLoading(true, { phase: "fetching" });
10025
- viewerStore.getState().setError(null);
10026
- setLoadState("loading");
10015
+ viewerStore.getState().setLoadingProgress({ phase: "fetching" });
10027
10016
  const { document: document2, numPages } = await loadDocument({
10028
10017
  src,
10029
10018
  workerSrc,