stimulus-pdf-viewer-rails 0.4.0 → 0.4.1

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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 863e0c885d62300048eda7098bb47e91082b609197aa5712557f9e76c1a33cd2
4
- data.tar.gz: c99cdaa21cd6318fdec59037bd07ec86d1aed8260f45bd17852c90305e903f77
3
+ metadata.gz: 2304be55407cf2f6bda31771ad7dff2bd54499278bb24b24e0429f161c835569
4
+ data.tar.gz: 28149508a79eaabd4b5f65120cb6758082b263e5b66540b693671e3a328d1424
5
5
  SHA512:
6
- metadata.gz: 0a203691d3cc984e25cae915193472832086a52671137d9ccedf12dd8712033a99d3505c4cb664c5f5eb76943591bbb6f868703fbdf7b75ae3de5acd5957244d
7
- data.tar.gz: 0bf609b800a496af6828e6382608214a75d6c7d2c583c3a34773797236fe73a7d66073369f28891908477fd6b02c40a19a7765b22d72f47f0d5baf1106087527
6
+ metadata.gz: 86c15ca518c858a764d8050175314e96244dd6941dd1b9556d58758e33f8e1767968516ca617e8a3dd9d13752caafbd6c2d1fb429658ba8981f7f730a8ec24d8
7
+ data.tar.gz: 757a7972ddabe9b0f12c737dda5336cd1be4f0a319faa73df52887e08bde64de84871cb1d22fce37f8fc571b3a648b1fa229bec9d1c29c3ae6f7f3a0d0a1973d
data/CHANGELOG.md CHANGED
@@ -2,6 +2,18 @@
2
2
 
3
3
  All notable changes to this project will be documented in this file.
4
4
 
5
+ ## [0.4.1] - 2026-08-10
6
+
7
+ ### Fixed
8
+ - Updated stimulus-pdf-viewer to 0.4.1
9
+
10
+ This fixes `initialAnnotation` deep-links, which never scrolled to or selected
11
+ the annotation (a string/number id mismatch in the annotation map lookup), and
12
+ gives deep-linked annotations the same flash/highlight treatment as sidebar
13
+ clicks. See the upstream
14
+ [0.4.1 changelog](https://github.com/jhubert/stimulus-pdf-viewer/blob/main/CHANGELOG.md)
15
+ for full details.
16
+
5
17
  ## [0.4.0] - 2026-06-24
6
18
 
7
19
  ### Added
@@ -1729,7 +1729,7 @@ class AnnotationManager {
1729
1729
  this.annotationsByPage.clear();
1730
1730
 
1731
1731
  for (const annotation of annotationsData) {
1732
- this.annotations.set(annotation.id, annotation);
1732
+ this.annotations.set(this._key(annotation.id), annotation);
1733
1733
 
1734
1734
  if (!this.annotationsByPage.has(annotation.page)) {
1735
1735
  this.annotationsByPage.set(annotation.page, []);
@@ -1738,8 +1738,14 @@ class AnnotationManager {
1738
1738
  }
1739
1739
  }
1740
1740
 
1741
+ // Ids arrive as numbers from JSON payloads but as strings from DOM
1742
+ // datasets and Stimulus values, so the map is keyed by string
1743
+ _key(id) {
1744
+ return String(id)
1745
+ }
1746
+
1741
1747
  getAnnotation(id) {
1742
- return this.annotations.get(id)
1748
+ return this.annotations.get(this._key(id))
1743
1749
  }
1744
1750
 
1745
1751
  getAnnotationsForPage(pageNumber) {
@@ -1785,7 +1791,7 @@ class AnnotationManager {
1785
1791
  }
1786
1792
 
1787
1793
  async deleteAnnotation(id) {
1788
- const existingAnnotation = this.annotations.get(id);
1794
+ const existingAnnotation = this.getAnnotation(id);
1789
1795
  if (!existingAnnotation) return
1790
1796
 
1791
1797
  try {
@@ -1824,7 +1830,7 @@ class AnnotationManager {
1824
1830
  }
1825
1831
 
1826
1832
  _addAnnotation(annotation) {
1827
- this.annotations.set(annotation.id, annotation);
1833
+ this.annotations.set(this._key(annotation.id), annotation);
1828
1834
 
1829
1835
  if (!this.annotationsByPage.has(annotation.page)) {
1830
1836
  this.annotationsByPage.set(annotation.page, []);
@@ -1833,7 +1839,7 @@ class AnnotationManager {
1833
1839
  }
1834
1840
 
1835
1841
  _updateAnnotation(annotation) {
1836
- const oldAnnotation = this.annotations.get(annotation.id);
1842
+ const oldAnnotation = this.getAnnotation(annotation.id);
1837
1843
  if (!oldAnnotation) {
1838
1844
  this._addAnnotation(annotation);
1839
1845
  return
@@ -1850,27 +1856,27 @@ class AnnotationManager {
1850
1856
  } else {
1851
1857
  // Update in place
1852
1858
  const pageAnnotations = this.annotationsByPage.get(annotation.page);
1853
- const index = pageAnnotations.findIndex(a => a.id === annotation.id);
1859
+ const index = pageAnnotations.findIndex(a => this._key(a.id) === this._key(annotation.id));
1854
1860
  if (index !== -1) {
1855
1861
  pageAnnotations[index] = annotation;
1856
1862
  }
1857
1863
  }
1858
1864
 
1859
- this.annotations.set(annotation.id, annotation);
1865
+ this.annotations.set(this._key(annotation.id), annotation);
1860
1866
  }
1861
1867
 
1862
1868
  _removeAnnotation(id) {
1863
- const annotation = this.annotations.get(id);
1869
+ const annotation = this.getAnnotation(id);
1864
1870
  if (!annotation) return
1865
1871
 
1866
1872
  this._removeAnnotationFromPage(id, annotation.page);
1867
- this.annotations.delete(id);
1873
+ this.annotations.delete(this._key(id));
1868
1874
  }
1869
1875
 
1870
1876
  _removeAnnotationFromPage(id, pageNumber) {
1871
1877
  const pageAnnotations = this.annotationsByPage.get(pageNumber);
1872
1878
  if (pageAnnotations) {
1873
- const index = pageAnnotations.findIndex(a => a.id === id);
1879
+ const index = pageAnnotations.findIndex(a => this._key(a.id) === this._key(id));
1874
1880
  if (index !== -1) {
1875
1881
  pageAnnotations.splice(index, 1);
1876
1882
  }
@@ -4363,7 +4369,7 @@ class AnnotationSidebar {
4363
4369
  }
4364
4370
 
4365
4371
  // Selection state
4366
- if (this.selectedAnnotationId === annotation.id) {
4372
+ if (this.selectedAnnotationId === String(annotation.id)) {
4367
4373
  item.classList.add("selected");
4368
4374
  }
4369
4375
 
@@ -4471,6 +4477,9 @@ class AnnotationSidebar {
4471
4477
  }
4472
4478
 
4473
4479
  _selectItem(annotationId) {
4480
+ // Ids arrive as numbers from JSON payloads but as strings from DOM
4481
+ // datasets and deep-links, so selection state is tracked as string
4482
+ annotationId = String(annotationId);
4474
4483
  const previousId = this.selectedAnnotationId;
4475
4484
 
4476
4485
  // Skip if already selected
@@ -4527,7 +4536,7 @@ class AnnotationSidebar {
4527
4536
  onAnnotationDeleted(annotation) {
4528
4537
  if (this.isOpen) {
4529
4538
  // Clear selection if deleted annotation was selected
4530
- if (this.selectedAnnotationId === annotation.id) {
4539
+ if (this.selectedAnnotationId === String(annotation.id)) {
4531
4540
  const previousId = this.selectedAnnotationId;
4532
4541
  this.selectedAnnotationId = null;
4533
4542
  this.element.dispatchEvent(new CustomEvent("pdf-sidebar:annotation-deselected", {
@@ -7527,9 +7536,10 @@ class PdfViewer {
7527
7536
  this.viewer.goToPage(this.initialPage);
7528
7537
  }
7529
7538
 
7530
- // Navigate to initial annotation if specified
7539
+ // Navigate to initial annotation if specified, flashing it so
7540
+ // deep-link visitors can spot it immediately
7531
7541
  if (this.initialAnnotation) {
7532
- this._scrollToAnnotation(this.initialAnnotation);
7542
+ this._scrollToAnnotationWithFlash(this.initialAnnotation);
7533
7543
  }
7534
7544
 
7535
7545
  // Start with select tool
@@ -8428,20 +8438,9 @@ class PdfViewer {
8428
8438
  }
8429
8439
  }
8430
8440
 
8431
- _scrollToAnnotation(annotationId) {
8432
- const annotation = this.annotationManager.getAnnotation(annotationId);
8433
- if (!annotation) return
8434
-
8435
- // Mark this annotation for selection when it's rendered
8436
- this.pendingAnnotationSelection = annotationId;
8437
-
8438
- // Go to the page - the annotation will be selected in _renderAnnotationsForPage
8439
- this.viewer.goToPage(annotation.page);
8440
- }
8441
-
8442
8441
  /**
8443
8442
  * Scroll to annotation and flash/highlight it.
8444
- * Called from the annotation sidebar when clicking an annotation.
8443
+ * Called from the annotation sidebar and for initial deep-links.
8445
8444
  */
8446
8445
  _scrollToAnnotationWithFlash(annotationId) {
8447
8446
  const annotation = this.annotationManager.getAnnotation(annotationId);
@@ -1749,7 +1749,7 @@
1749
1749
  this.annotationsByPage.clear();
1750
1750
 
1751
1751
  for (const annotation of annotationsData) {
1752
- this.annotations.set(annotation.id, annotation);
1752
+ this.annotations.set(this._key(annotation.id), annotation);
1753
1753
 
1754
1754
  if (!this.annotationsByPage.has(annotation.page)) {
1755
1755
  this.annotationsByPage.set(annotation.page, []);
@@ -1758,8 +1758,14 @@
1758
1758
  }
1759
1759
  }
1760
1760
 
1761
+ // Ids arrive as numbers from JSON payloads but as strings from DOM
1762
+ // datasets and Stimulus values, so the map is keyed by string
1763
+ _key(id) {
1764
+ return String(id)
1765
+ }
1766
+
1761
1767
  getAnnotation(id) {
1762
- return this.annotations.get(id)
1768
+ return this.annotations.get(this._key(id))
1763
1769
  }
1764
1770
 
1765
1771
  getAnnotationsForPage(pageNumber) {
@@ -1805,7 +1811,7 @@
1805
1811
  }
1806
1812
 
1807
1813
  async deleteAnnotation(id) {
1808
- const existingAnnotation = this.annotations.get(id);
1814
+ const existingAnnotation = this.getAnnotation(id);
1809
1815
  if (!existingAnnotation) return
1810
1816
 
1811
1817
  try {
@@ -1844,7 +1850,7 @@
1844
1850
  }
1845
1851
 
1846
1852
  _addAnnotation(annotation) {
1847
- this.annotations.set(annotation.id, annotation);
1853
+ this.annotations.set(this._key(annotation.id), annotation);
1848
1854
 
1849
1855
  if (!this.annotationsByPage.has(annotation.page)) {
1850
1856
  this.annotationsByPage.set(annotation.page, []);
@@ -1853,7 +1859,7 @@
1853
1859
  }
1854
1860
 
1855
1861
  _updateAnnotation(annotation) {
1856
- const oldAnnotation = this.annotations.get(annotation.id);
1862
+ const oldAnnotation = this.getAnnotation(annotation.id);
1857
1863
  if (!oldAnnotation) {
1858
1864
  this._addAnnotation(annotation);
1859
1865
  return
@@ -1870,27 +1876,27 @@
1870
1876
  } else {
1871
1877
  // Update in place
1872
1878
  const pageAnnotations = this.annotationsByPage.get(annotation.page);
1873
- const index = pageAnnotations.findIndex(a => a.id === annotation.id);
1879
+ const index = pageAnnotations.findIndex(a => this._key(a.id) === this._key(annotation.id));
1874
1880
  if (index !== -1) {
1875
1881
  pageAnnotations[index] = annotation;
1876
1882
  }
1877
1883
  }
1878
1884
 
1879
- this.annotations.set(annotation.id, annotation);
1885
+ this.annotations.set(this._key(annotation.id), annotation);
1880
1886
  }
1881
1887
 
1882
1888
  _removeAnnotation(id) {
1883
- const annotation = this.annotations.get(id);
1889
+ const annotation = this.getAnnotation(id);
1884
1890
  if (!annotation) return
1885
1891
 
1886
1892
  this._removeAnnotationFromPage(id, annotation.page);
1887
- this.annotations.delete(id);
1893
+ this.annotations.delete(this._key(id));
1888
1894
  }
1889
1895
 
1890
1896
  _removeAnnotationFromPage(id, pageNumber) {
1891
1897
  const pageAnnotations = this.annotationsByPage.get(pageNumber);
1892
1898
  if (pageAnnotations) {
1893
- const index = pageAnnotations.findIndex(a => a.id === id);
1899
+ const index = pageAnnotations.findIndex(a => this._key(a.id) === this._key(id));
1894
1900
  if (index !== -1) {
1895
1901
  pageAnnotations.splice(index, 1);
1896
1902
  }
@@ -4383,7 +4389,7 @@
4383
4389
  }
4384
4390
 
4385
4391
  // Selection state
4386
- if (this.selectedAnnotationId === annotation.id) {
4392
+ if (this.selectedAnnotationId === String(annotation.id)) {
4387
4393
  item.classList.add("selected");
4388
4394
  }
4389
4395
 
@@ -4491,6 +4497,9 @@
4491
4497
  }
4492
4498
 
4493
4499
  _selectItem(annotationId) {
4500
+ // Ids arrive as numbers from JSON payloads but as strings from DOM
4501
+ // datasets and deep-links, so selection state is tracked as string
4502
+ annotationId = String(annotationId);
4494
4503
  const previousId = this.selectedAnnotationId;
4495
4504
 
4496
4505
  // Skip if already selected
@@ -4547,7 +4556,7 @@
4547
4556
  onAnnotationDeleted(annotation) {
4548
4557
  if (this.isOpen) {
4549
4558
  // Clear selection if deleted annotation was selected
4550
- if (this.selectedAnnotationId === annotation.id) {
4559
+ if (this.selectedAnnotationId === String(annotation.id)) {
4551
4560
  const previousId = this.selectedAnnotationId;
4552
4561
  this.selectedAnnotationId = null;
4553
4562
  this.element.dispatchEvent(new CustomEvent("pdf-sidebar:annotation-deselected", {
@@ -7547,9 +7556,10 @@
7547
7556
  this.viewer.goToPage(this.initialPage);
7548
7557
  }
7549
7558
 
7550
- // Navigate to initial annotation if specified
7559
+ // Navigate to initial annotation if specified, flashing it so
7560
+ // deep-link visitors can spot it immediately
7551
7561
  if (this.initialAnnotation) {
7552
- this._scrollToAnnotation(this.initialAnnotation);
7562
+ this._scrollToAnnotationWithFlash(this.initialAnnotation);
7553
7563
  }
7554
7564
 
7555
7565
  // Start with select tool
@@ -8448,20 +8458,9 @@
8448
8458
  }
8449
8459
  }
8450
8460
 
8451
- _scrollToAnnotation(annotationId) {
8452
- const annotation = this.annotationManager.getAnnotation(annotationId);
8453
- if (!annotation) return
8454
-
8455
- // Mark this annotation for selection when it's rendered
8456
- this.pendingAnnotationSelection = annotationId;
8457
-
8458
- // Go to the page - the annotation will be selected in _renderAnnotationsForPage
8459
- this.viewer.goToPage(annotation.page);
8460
- }
8461
-
8462
8461
  /**
8463
8462
  * Scroll to annotation and flash/highlight it.
8464
- * Called from the annotation sidebar when clicking an annotation.
8463
+ * Called from the annotation sidebar and for initial deep-links.
8465
8464
  */
8466
8465
  _scrollToAnnotationWithFlash(annotationId) {
8467
8466
  const annotation = this.annotationManager.getAnnotation(annotationId);
@@ -1,7 +1,7 @@
1
1
  module StimulusPdfViewer
2
2
  module Rails
3
- VERSION = "0.4.0"
3
+ VERSION = '0.4.1'
4
4
  # This should match the npm package version
5
- STIMULUS_PDF_VIEWER_VERSION = "0.4.0"
5
+ STIMULUS_PDF_VIEWER_VERSION = '0.4.1'
6
6
  end
7
7
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: stimulus-pdf-viewer-rails
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.4.0
4
+ version: 0.4.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Jeremy Baker
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2026-06-24 00:00:00.000000000 Z
11
+ date: 2026-08-10 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: railties