reviw 0.10.4 → 0.10.6

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.
Files changed (2) hide show
  1. package/cli.cjs +120 -2
  2. package/package.json +1 -1
package/cli.cjs CHANGED
@@ -21,7 +21,7 @@ const marked = require("marked");
21
21
  const yaml = require("js-yaml");
22
22
 
23
23
  // --- CLI arguments ---------------------------------------------------------
24
- const VERSION = "0.10.3";
24
+ const VERSION = require("./package.json").version;
25
25
  const args = process.argv.slice(2);
26
26
 
27
27
  const filePaths = [];
@@ -2305,6 +2305,39 @@ function htmlTemplate(dataRows, cols, title, mode, previewHtml) {
2305
2305
  .fullscreen-content .mermaid svg {
2306
2306
  display: block;
2307
2307
  }
2308
+ /* Minimap */
2309
+ .minimap {
2310
+ position: absolute;
2311
+ top: 70px;
2312
+ right: 20px;
2313
+ width: 200px;
2314
+ height: 150px;
2315
+ background: var(--panel-alpha);
2316
+ border: 1px solid var(--border);
2317
+ border-radius: 8px;
2318
+ overflow: hidden;
2319
+ box-shadow: 0 4px 12px rgba(0,0,0,0.15);
2320
+ }
2321
+ .minimap-content {
2322
+ width: 100%;
2323
+ height: 100%;
2324
+ display: flex;
2325
+ align-items: center;
2326
+ justify-content: center;
2327
+ padding: 8px;
2328
+ }
2329
+ .minimap-content svg {
2330
+ max-width: 100%;
2331
+ max-height: 100%;
2332
+ opacity: 0.6;
2333
+ }
2334
+ .minimap-viewport {
2335
+ position: absolute;
2336
+ border: 2px solid var(--accent);
2337
+ background: rgba(102, 126, 234, 0.2);
2338
+ pointer-events: none;
2339
+ border-radius: 2px;
2340
+ }
2308
2341
  /* Error toast */
2309
2342
  .mermaid-error-toast {
2310
2343
  position: fixed;
@@ -2470,6 +2503,10 @@ function htmlTemplate(dataRows, cols, title, mode, previewHtml) {
2470
2503
  <div class="fullscreen-content" id="fs-content">
2471
2504
  <div class="mermaid-wrapper" id="fs-wrapper"></div>
2472
2505
  </div>
2506
+ <div class="minimap" id="fs-minimap">
2507
+ <div class="minimap-content" id="fs-minimap-content"></div>
2508
+ <div class="minimap-viewport" id="fs-minimap-viewport"></div>
2509
+ </div>
2473
2510
  </div>
2474
2511
  <div class="mermaid-error-toast" id="mermaid-error-toast"></div>
2475
2512
  <div class="copy-toast" id="copy-toast">Copied to clipboard!</div>
@@ -3578,12 +3615,15 @@ function htmlTemplate(dataRows, cols, title, mode, previewHtml) {
3578
3615
  const fsWrapper = document.getElementById('fs-wrapper');
3579
3616
  const fsContent = document.getElementById('fs-content');
3580
3617
  const fsZoomInfo = document.getElementById('fs-zoom-info');
3618
+ const minimapContent = document.getElementById('fs-minimap-content');
3619
+ const minimapViewport = document.getElementById('fs-minimap-viewport');
3581
3620
  let currentZoom = 1;
3582
3621
  let initialZoom = 1;
3583
3622
  let panX = 0, panY = 0;
3584
3623
  let isPanning = false;
3585
3624
  let startX, startY;
3586
3625
  let svgNaturalWidth = 0, svgNaturalHeight = 0;
3626
+ let minimapScale = 1;
3587
3627
 
3588
3628
  function openFullscreen(mermaidEl) {
3589
3629
  const svg = mermaidEl.querySelector('svg');
@@ -3592,6 +3632,11 @@ function htmlTemplate(dataRows, cols, title, mode, previewHtml) {
3592
3632
  const clonedSvg = svg.cloneNode(true);
3593
3633
  fsWrapper.appendChild(clonedSvg);
3594
3634
 
3635
+ // Setup minimap
3636
+ minimapContent.innerHTML = '';
3637
+ const minimapSvg = svg.cloneNode(true);
3638
+ minimapContent.appendChild(minimapSvg);
3639
+
3595
3640
  // Get SVG's intrinsic/natural size from viewBox or attributes
3596
3641
  const viewBox = svg.getAttribute('viewBox');
3597
3642
  let naturalWidth, naturalHeight;
@@ -3608,6 +3653,11 @@ function htmlTemplate(dataRows, cols, title, mode, previewHtml) {
3608
3653
  svgNaturalWidth = naturalWidth;
3609
3654
  svgNaturalHeight = naturalHeight;
3610
3655
 
3656
+ // Calculate minimap scale
3657
+ const minimapMaxWidth = 184; // 200 - 16 padding
3658
+ const minimapMaxHeight = 134; // 150 - 16 padding
3659
+ minimapScale = Math.min(minimapMaxWidth / naturalWidth, minimapMaxHeight / naturalHeight);
3660
+
3611
3661
  clonedSvg.style.width = naturalWidth + 'px';
3612
3662
  clonedSvg.style.height = naturalHeight + 'px';
3613
3663
 
@@ -3628,8 +3678,11 @@ function htmlTemplate(dataRows, cols, title, mode, previewHtml) {
3628
3678
  panX = (viewportWidth - scaledWidth) / 2 + 20;
3629
3679
  panY = (viewportHeight - scaledHeight) / 2 + 60;
3630
3680
 
3631
- updateTransform();
3632
3681
  fsOverlay.classList.add('visible');
3682
+ // Wait for DOM to render before calculating minimap position
3683
+ requestAnimationFrame(() => {
3684
+ updateTransform();
3685
+ });
3633
3686
  }
3634
3687
 
3635
3688
  function closeFullscreen() {
@@ -3639,6 +3692,71 @@ function htmlTemplate(dataRows, cols, title, mode, previewHtml) {
3639
3692
  function updateTransform() {
3640
3693
  fsWrapper.style.transform = 'translate(' + panX + 'px, ' + panY + 'px) scale(' + currentZoom + ')';
3641
3694
  fsZoomInfo.textContent = Math.round(currentZoom * 100) + '%';
3695
+ updateMinimap();
3696
+ }
3697
+
3698
+ function updateMinimap() {
3699
+ if (!svgNaturalWidth || !svgNaturalHeight) return;
3700
+
3701
+ const viewportWidth = fsContent.clientWidth;
3702
+ const viewportHeight = fsContent.clientHeight;
3703
+
3704
+ // Minimap container dimensions (inner area)
3705
+ const mmWidth = 184; // 200 - 16 padding
3706
+ const mmHeight = 134; // 150 - 16 padding
3707
+ const mmPadding = 8;
3708
+
3709
+ // SVG thumbnail size in minimap (scaled to fit)
3710
+ const mmSvgWidth = svgNaturalWidth * minimapScale;
3711
+ const mmSvgHeight = svgNaturalHeight * minimapScale;
3712
+ // SVG thumbnail position (centered in minimap)
3713
+ const mmSvgLeft = (mmWidth - mmSvgWidth) / 2 + mmPadding;
3714
+ const mmSvgTop = (mmHeight - mmSvgHeight) / 2 + mmPadding;
3715
+
3716
+ // Calculate which part of the SVG is visible in the viewport
3717
+ // transform: translate(panX, panY) scale(currentZoom)
3718
+ // The viewport shows SVG region starting at (-panX/zoom, -panY/zoom)
3719
+ const svgVisibleLeft = -panX / currentZoom;
3720
+ const svgVisibleTop = -panY / currentZoom;
3721
+ const svgVisibleWidth = viewportWidth / currentZoom;
3722
+ const svgVisibleHeight = viewportHeight / currentZoom;
3723
+
3724
+ // Convert to minimap coordinates
3725
+ let vpLeft = mmSvgLeft + svgVisibleLeft * minimapScale;
3726
+ let vpTop = mmSvgTop + svgVisibleTop * minimapScale;
3727
+ let vpWidth = svgVisibleWidth * minimapScale;
3728
+ let vpHeight = svgVisibleHeight * minimapScale;
3729
+
3730
+ // Clamp to minimap bounds (the viewport rect should stay within minimap)
3731
+ const mmLeft = mmPadding;
3732
+ const mmTop = mmPadding;
3733
+ const mmRight = mmWidth + mmPadding;
3734
+ const mmBottom = mmHeight + mmPadding;
3735
+
3736
+ // Adjust if viewport extends beyond minimap bounds
3737
+ if (vpLeft < mmLeft) {
3738
+ vpWidth -= (mmLeft - vpLeft);
3739
+ vpLeft = mmLeft;
3740
+ }
3741
+ if (vpTop < mmTop) {
3742
+ vpHeight -= (mmTop - vpTop);
3743
+ vpTop = mmTop;
3744
+ }
3745
+ if (vpLeft + vpWidth > mmRight) {
3746
+ vpWidth = mmRight - vpLeft;
3747
+ }
3748
+ if (vpTop + vpHeight > mmBottom) {
3749
+ vpHeight = mmBottom - vpTop;
3750
+ }
3751
+
3752
+ // Ensure minimum size and positive dimensions
3753
+ vpWidth = Math.max(20, vpWidth);
3754
+ vpHeight = Math.max(15, vpHeight);
3755
+
3756
+ minimapViewport.style.left = vpLeft + 'px';
3757
+ minimapViewport.style.top = vpTop + 'px';
3758
+ minimapViewport.style.width = vpWidth + 'px';
3759
+ minimapViewport.style.height = vpHeight + 'px';
3642
3760
  }
3643
3761
 
3644
3762
  // Use multiplicative zoom for consistent behavior
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "reviw",
3
- "version": "0.10.4",
3
+ "version": "0.10.6",
4
4
  "description": "Lightweight file reviewer with in-browser comments for CSV, TSV, Markdown, and Git diffs.",
5
5
  "type": "module",
6
6
  "bin": {