Album location hovers (#345)
This commit is contained in:
parent
a03b758e3b
commit
c2a0e1585f
1
.vscode/settings.json
vendored
1
.vscode/settings.json
vendored
@ -48,6 +48,7 @@
|
||||
"nowrap",
|
||||
"Oklab",
|
||||
"oklch",
|
||||
"openlayers",
|
||||
"parameterizes",
|
||||
"piexif",
|
||||
"piexifjs",
|
||||
|
||||
@ -40,11 +40,13 @@
|
||||
"next": "15.5.4",
|
||||
"next-auth": "5.0.0-beta.29",
|
||||
"next-themes": "^0.4.6",
|
||||
"ol": "^10.6.1",
|
||||
"pg": "^8.16.3",
|
||||
"piexifjs": "^1.0.6",
|
||||
"react": "19.1.1",
|
||||
"react-dom": "19.1.1",
|
||||
"react-icons": "^5.5.0",
|
||||
"react-openlayers": "^10.5.1",
|
||||
"sanitize-html": "^2.17.0",
|
||||
"sharp": "^0.34.4",
|
||||
"sonner": "^2.0.7",
|
||||
@ -57,7 +59,7 @@
|
||||
"devDependencies": {
|
||||
"@eslint/eslintrc": "^3.3.1",
|
||||
"@next/bundle-analyzer": "15.5.4",
|
||||
"@next/eslint-plugin-next": "^15.5.4",
|
||||
"@next/eslint-plugin-next": "15.5.4",
|
||||
"@stylistic/eslint-plugin": "^5.4.0",
|
||||
"@tailwindcss/postcss": "^4.1.13",
|
||||
"@testing-library/dom": "^10.4.1",
|
||||
|
||||
130
pnpm-lock.yaml
generated
130
pnpm-lock.yaml
generated
@ -98,6 +98,9 @@ importers:
|
||||
next-themes:
|
||||
specifier: ^0.4.6
|
||||
version: 0.4.6(react-dom@19.1.1(react@19.1.1))(react@19.1.1)
|
||||
ol:
|
||||
specifier: ^10.6.1
|
||||
version: 10.6.1
|
||||
pg:
|
||||
specifier: ^8.16.3
|
||||
version: 8.16.3
|
||||
@ -113,6 +116,9 @@ importers:
|
||||
react-icons:
|
||||
specifier: ^5.5.0
|
||||
version: 5.5.0(react@19.1.1)
|
||||
react-openlayers:
|
||||
specifier: ^10.5.1
|
||||
version: 10.5.1(ol@10.6.1)(react-dom@19.1.1(react@19.1.1))(react@19.1.1)
|
||||
sanitize-html:
|
||||
specifier: ^2.17.0
|
||||
version: 2.17.0
|
||||
@ -145,7 +151,7 @@ importers:
|
||||
specifier: 15.5.4
|
||||
version: 15.5.4
|
||||
'@next/eslint-plugin-next':
|
||||
specifier: ^15.5.4
|
||||
specifier: 15.5.4
|
||||
version: 15.5.4
|
||||
'@stylistic/eslint-plugin':
|
||||
specifier: ^5.4.0
|
||||
@ -1066,6 +1072,9 @@ packages:
|
||||
'@panva/hkdf@1.2.1':
|
||||
resolution: {integrity: sha512-6oclG6Y3PiDFcoyk8srjLfVKyMfVCKJ27JwNPViuXziFpmdz+MZnZN/aKY0JGXgYuO/VghU0jcOAZgWXZ1Dmrw==}
|
||||
|
||||
'@petamoriken/float16@3.9.3':
|
||||
resolution: {integrity: sha512-8awtpHXCx/bNpFt4mt2xdkgtgVvKqty8VbjHI/WWWQuEw+KLzFot3f4+LkQY9YmOtq7A5GdOnqoIC8Pdygjk2g==}
|
||||
|
||||
'@pkgjs/parseargs@0.11.0':
|
||||
resolution: {integrity: sha512-+1VkjdD0QBLPodGrJUeqarH8VAIvQODIbwh9XpP5Syisf7YoQgsJKPNFoqqLQlu+VQ/tVSshMR6loPMn8U+dPg==}
|
||||
engines: {node: '>=14'}
|
||||
@ -1805,6 +1814,9 @@ packages:
|
||||
'@types/piexifjs@1.0.0':
|
||||
resolution: {integrity: sha512-PPiGeCkmkZQgYjvqtjD3kp4OkbCox2vEFVuK4DaLVOIazJLAXk+/ujbizkIPH5CN4AnN9Clo5ckzUlaj3+SzCA==}
|
||||
|
||||
'@types/rbush@4.0.0':
|
||||
resolution: {integrity: sha512-+N+2H39P8X+Hy1I5mC6awlTX54k3FhiUmvt7HWzGJZvF+syUAAxP/stwppS8JE84YHqFgRMv6fCy31202CMFxQ==}
|
||||
|
||||
'@types/react-dom@19.1.9':
|
||||
resolution: {integrity: sha512-qXRuZaOsAdXKFyOhRBg6Lqqc0yay13vN7KrIg4L7N4aaHN68ma9OK3NE1BoDFgFOTfM7zg+3/8+2n8rLUH3OKQ==}
|
||||
peerDependencies:
|
||||
@ -2491,6 +2503,9 @@ packages:
|
||||
duplexer@0.1.2:
|
||||
resolution: {integrity: sha512-jtD6YG370ZCIi/9GTaJKQxWTZD045+4R4hTk/x1UyoqadyJ9x9CgSi1RlVDQF8U2sxLLSnFkCaMihqljHIWgMg==}
|
||||
|
||||
earcut@3.0.2:
|
||||
resolution: {integrity: sha512-X7hshQbLyMJ/3RPhyObLARM2sNxxmRALLKx1+NVFFnQ9gKzmCrxm9+uLIAdBcvc8FNLpctqlQ2V6AE92Ol9UDQ==}
|
||||
|
||||
eastasianwidth@0.2.0:
|
||||
resolution: {integrity: sha512-I88TYZWc9XiYHRQ4/3c5rjjfgkjhLyW2luGIheGERbNQ6OY7yTybanSpDXZa8y7VUP9YmDcYa+eyq4ca7iLqWA==}
|
||||
|
||||
@ -2820,6 +2835,10 @@ packages:
|
||||
resolution: {integrity: sha512-3hN7NaskYvMDLQY55gnW3NQ+mesEAepTqlg+VEbj7zzqEMBVNhzcGYYeqFo/TlYz6eQiFcp1HcsCZO+nGgS8zg==}
|
||||
engines: {node: '>=6.9.0'}
|
||||
|
||||
geotiff@2.1.3:
|
||||
resolution: {integrity: sha512-PT6uoF5a1+kbC3tHmZSUsLHBp2QJlHasxxxxPW47QIY1VBKpFB+FcDvX+MxER6UzgLQZ0xDzJ9s48B9JbOCTqA==}
|
||||
engines: {node: '>=10.19'}
|
||||
|
||||
get-caller-file@2.0.5:
|
||||
resolution: {integrity: sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg==}
|
||||
engines: {node: 6.* || 8.* || >= 10.*}
|
||||
@ -3375,6 +3394,9 @@ packages:
|
||||
resolution: {integrity: sha512-MbjN408fEndfiQXbFQ1vnd+1NoLDsnQW41410oQBXiyXDMYH5z505juWa4KUE1LqxRC7DgOgZDbKLxHIwm27hA==}
|
||||
engines: {node: '>=0.10'}
|
||||
|
||||
lerc@3.0.0:
|
||||
resolution: {integrity: sha512-Rm4J/WaHhRa93nCN2mwWDZFoRVF18G1f47C+kvQWyHGEZxFpTUi73p7lMVSAndyxGt6lJ2/CFbOcf9ra5p8aww==}
|
||||
|
||||
leven@3.1.0:
|
||||
resolution: {integrity: sha512-qsda+H8jTaUaN/x5vzW2rzc+8Rw4TAQ/4KjB46IwK5VH+IlVeeeje/EoZRpiXvIqjFgK84QffqPztGI3VBLG1A==}
|
||||
engines: {node: '>=6'}
|
||||
@ -3673,6 +3695,9 @@ packages:
|
||||
resolution: {integrity: sha512-gXah6aZrcUxjWg2zR2MwouP2eHlCBzdV4pygudehaKXSGW4v2AsRQUK+lwwXhii6KFZcunEnmSUoYp5CXibxtA==}
|
||||
engines: {node: '>= 0.4'}
|
||||
|
||||
ol@10.6.1:
|
||||
resolution: {integrity: sha512-xp174YOwPeLj7c7/8TCIEHQ4d41tgTDDhdv6SqNdySsql5/MaFJEJkjlsYcvOPt7xA6vrum/QG4UdJ0iCGT1cg==}
|
||||
|
||||
once@1.4.0:
|
||||
resolution: {integrity: sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==}
|
||||
|
||||
@ -3715,10 +3740,16 @@ packages:
|
||||
package-json-from-dist@1.0.1:
|
||||
resolution: {integrity: sha512-UEZIS3/by4OC8vL3P2dTXRETpebLI2NiI5vIrjaD/5UtrkFX/tNbwjTSRAGC/+7CAo2pIcBaRgWmcBBHcsaCIw==}
|
||||
|
||||
pako@2.1.0:
|
||||
resolution: {integrity: sha512-w+eufiZ1WuJYgPXbV/PO3NCMEc3xqylkKHzp8bxp1uW4qaSNQUkwmLLEc3kKsfz8lpV1F8Ht3U1Cm+9Srog2ug==}
|
||||
|
||||
parent-module@1.0.1:
|
||||
resolution: {integrity: sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==}
|
||||
engines: {node: '>=6'}
|
||||
|
||||
parse-headers@2.0.6:
|
||||
resolution: {integrity: sha512-Tz11t3uKztEW5FEVZnj1ox8GKblWn+PvHY9TmJV5Mll2uHEwRdR/5Li1OlXoECjLYkApdhWy44ocONwXLiKO5A==}
|
||||
|
||||
parse-json@5.2.0:
|
||||
resolution: {integrity: sha512-ayCKvm/phCGxOkYRSCM82iDwct8/EonSEgCSxWxD7ve6jHggsFl4fZVQBPRNgQoKiuV/odhFrGzQXZwbifC8Rg==}
|
||||
engines: {node: '>=8'}
|
||||
@ -3748,6 +3779,10 @@ packages:
|
||||
resolution: {integrity: sha512-Xa4Nw17FS9ApQFJ9umLiJS4orGjm7ZzwUrwamcGQuHSzDyth9boKDaycYdDcZDuqYATXw4HFXgaqWTctW/v1HA==}
|
||||
engines: {node: '>=16 || 14 >=14.18'}
|
||||
|
||||
pbf@4.0.1:
|
||||
resolution: {integrity: sha512-SuLdBvS42z33m8ejRbInMapQe8n0D3vN/Xd5fmWM3tufNgRQFBpaW2YVJxQZV4iPNqb0vEFvssMEo5w9c6BTIA==}
|
||||
hasBin: true
|
||||
|
||||
pg-cloudflare@1.2.7:
|
||||
resolution: {integrity: sha512-YgCtzMH0ptvZJslLM1ffsY4EuGaU0cx4XSdXLRFae8bPP4dS5xL1tNB3k2o/N64cHJpwU7dxKli/nZ2lUa5fLg==}
|
||||
|
||||
@ -3859,6 +3894,9 @@ packages:
|
||||
prop-types@15.8.1:
|
||||
resolution: {integrity: sha512-oj87CgZICdulUohogVAR7AjlC0327U4el4L6eAvOqCeudMDVU0NThNaV+b9Df4dXgSP1gXMTnPdhfe/2qDH5cg==}
|
||||
|
||||
protocol-buffers-schema@3.6.0:
|
||||
resolution: {integrity: sha512-TdDRD+/QNdrCGCE7v8340QyuXd4kIWIgapsE2+n/SaGiSSbomYl4TjHlvIoCWRpE7wFt02EpB35VVA2ImcBVqw==}
|
||||
|
||||
punycode@2.3.1:
|
||||
resolution: {integrity: sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==}
|
||||
engines: {node: '>=6'}
|
||||
@ -3869,10 +3907,20 @@ packages:
|
||||
queue-microtask@1.2.3:
|
||||
resolution: {integrity: sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==}
|
||||
|
||||
quick-lru@6.1.2:
|
||||
resolution: {integrity: sha512-AAFUA5O1d83pIHEhJwWCq/RQcRukCkn/NSm2QsTEMle5f2hP0ChI2+3Xb051PZCkLryI/Ir1MVKviT2FIloaTQ==}
|
||||
engines: {node: '>=12'}
|
||||
|
||||
quick-lru@7.1.0:
|
||||
resolution: {integrity: sha512-Pzd/4IFnTb8E+I1P5rbLQoqpUHcXKg48qTYKi4EANg+sTPwGFEMOcYGiiZz6xuQcOMZP7MPsrdAPx+16Q8qahg==}
|
||||
engines: {node: '>=18'}
|
||||
|
||||
quickselect@3.0.0:
|
||||
resolution: {integrity: sha512-XdjUArbK4Bm5fLLvlm5KpTFOiOThgfWWI4axAZDWg4E/0mKdZyI9tNEfds27qCi1ze/vwTR16kvmmGhRra3c2g==}
|
||||
|
||||
rbush@4.0.1:
|
||||
resolution: {integrity: sha512-IP0UpfeWQujYC8Jg162rMNc01Rf0gWMMAb2Uxus/Q0qOFw4lCcq6ZnQEZwUoJqWyUGJ9th7JjwI4yIWo+uvoAQ==}
|
||||
|
||||
react-dom@19.1.1:
|
||||
resolution: {integrity: sha512-Dlq/5LAZgF0Gaz6yiqZCf6VCcZs1ghAJyrsu84Q/GT0gV+mCxbfmKNoGRKBYMJ8IEdGPqu49YWXD02GCknEDkw==}
|
||||
peerDependencies:
|
||||
@ -3892,6 +3940,13 @@ packages:
|
||||
react-is@18.3.1:
|
||||
resolution: {integrity: sha512-/LLMVyas0ljjAtoYiPqYiL8VWXzUUdThrmU5+n20DZv+a+ClRoevUzw5JxU+Ieh5/c87ytoTBV9G1FiKfNJdmg==}
|
||||
|
||||
react-openlayers@10.5.1:
|
||||
resolution: {integrity: sha512-IWEXerUjn/N6sbUP/FURKvYDtJj/FZVxmK0WBw4kbAVVyQvs/5JTlD/x9+QEPqNzbAITX6lwasdrQ+WW51y/6g==}
|
||||
peerDependencies:
|
||||
ol: ^10.5.0
|
||||
react: ^18 || ^19
|
||||
react-dom: ^18 || ^19
|
||||
|
||||
react-remove-scroll-bar@2.3.8:
|
||||
resolution: {integrity: sha512-9r+yi9+mgU33AKcj6IbT9oRCO78WriSj6t/cF8DWBZJ9aOGPOTEDvdUDz1FwKim7QXWwmHqtdHnRJfhAxEG46Q==}
|
||||
engines: {node: '>=10'}
|
||||
@ -3957,6 +4012,9 @@ packages:
|
||||
resolve-pkg-maps@1.0.0:
|
||||
resolution: {integrity: sha512-seS2Tj26TBVOC2NIc2rOe2y2ZO7efxITtLZcGSOnHHNOQ7CkiUBfw0Iw2ck6xkIhPwLhKNLS8BO+hEpngQlqzw==}
|
||||
|
||||
resolve-protobuf-schema@2.1.0:
|
||||
resolution: {integrity: sha512-kI5ffTiZWmJaS/huM8wZfEMer1eRd7oJQhDuxeCLe3t7N7mX3z94CN0xPxBQxFYQTSNz9T0i+v6inKqSdK8xrQ==}
|
||||
|
||||
resolve@1.22.10:
|
||||
resolution: {integrity: sha512-NPRy+/ncIMeDlTAsuqwKIiferiawhefFJtkNSW0qZJEqMEb+qBt/77B/jGeeek+F0uOeN05CDa6HXbbIgtVX4w==}
|
||||
engines: {node: '>= 0.4'}
|
||||
@ -4402,6 +4460,9 @@ packages:
|
||||
walker@1.0.8:
|
||||
resolution: {integrity: sha512-ts/8E8l5b7kY0vlWLewOkDXMmPdLcVV4GmOQLyxuSswIJsweeFZtAsMF7k1Nszz+TYBQrlYRmzOnr398y1JemQ==}
|
||||
|
||||
web-worker@1.5.0:
|
||||
resolution: {integrity: sha512-RiMReJrTAiA+mBjGONMnjVDP2u3p9R1vkcGz6gDIrOMT3oGuYwX2WRMYI9ipkphSuE5XKEhydbhNEJh4NY9mlw==}
|
||||
|
||||
webidl-conversions@3.0.1:
|
||||
resolution: {integrity: sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==}
|
||||
|
||||
@ -4497,6 +4558,9 @@ packages:
|
||||
resolution: {integrity: sha512-EvGK8EJ3DhaHfbRlETOWAS5pO9MZITeauHKJyb8wyajUfQUenkIg2MvLDTZ4T/TgIcm3HU0TFBgWWboAZ30UHg==}
|
||||
engines: {node: '>=18'}
|
||||
|
||||
xml-utils@1.10.2:
|
||||
resolution: {integrity: sha512-RqM+2o1RYs6T8+3DzDSoTRAUfrvaejbVHcp3+thnAtDKo8LskR+HomLajEy5UjTz24rpka7AxVBRR3g2wTUkJA==}
|
||||
|
||||
xmlchars@2.2.0:
|
||||
resolution: {integrity: sha512-JZnDKK8B0RCDw84FNdDAIpZK+JuJw+s7Lz8nksI7SIuU3UXJJslUthsi+uWBUYOwPFwW7W7PRLRfUKpxjtjFCw==}
|
||||
|
||||
@ -4534,6 +4598,9 @@ packages:
|
||||
zod@4.1.11:
|
||||
resolution: {integrity: sha512-WPsqwxITS2tzx1bzhIKsEs19ABD5vmCVa4xBo2tq/SrV4RNZtfws1EnCWQXM6yh8bD08a1idvkB5MZSBiZsjwg==}
|
||||
|
||||
zstddec@0.1.0:
|
||||
resolution: {integrity: sha512-w2NTI8+3l3eeltKAdK8QpiLo/flRAr2p8AGeakfMZOXBxOg9HIu4LVDxBi81sYgVhFhdJjv1OrB5ssI8uFPoLg==}
|
||||
|
||||
snapshots:
|
||||
|
||||
'@adobe/css-tools@4.4.4': {}
|
||||
@ -5783,6 +5850,8 @@ snapshots:
|
||||
|
||||
'@panva/hkdf@1.2.1': {}
|
||||
|
||||
'@petamoriken/float16@3.9.3': {}
|
||||
|
||||
'@pkgjs/parseargs@0.11.0':
|
||||
optional: true
|
||||
|
||||
@ -6630,6 +6699,8 @@ snapshots:
|
||||
|
||||
'@types/piexifjs@1.0.0': {}
|
||||
|
||||
'@types/rbush@4.0.0': {}
|
||||
|
||||
'@types/react-dom@19.1.9(@types/react@19.1.15)':
|
||||
dependencies:
|
||||
'@types/react': 19.1.15
|
||||
@ -7294,6 +7365,8 @@ snapshots:
|
||||
|
||||
duplexer@0.1.2: {}
|
||||
|
||||
earcut@3.0.2: {}
|
||||
|
||||
eastasianwidth@0.2.0: {}
|
||||
|
||||
electron-to-chromium@1.5.218: {}
|
||||
@ -7764,6 +7837,17 @@ snapshots:
|
||||
|
||||
gensync@1.0.0-beta.2: {}
|
||||
|
||||
geotiff@2.1.3:
|
||||
dependencies:
|
||||
'@petamoriken/float16': 3.9.3
|
||||
lerc: 3.0.0
|
||||
pako: 2.1.0
|
||||
parse-headers: 2.0.6
|
||||
quick-lru: 6.1.2
|
||||
web-worker: 1.5.0
|
||||
xml-utils: 1.10.2
|
||||
zstddec: 0.1.0
|
||||
|
||||
get-caller-file@2.0.5: {}
|
||||
|
||||
get-intrinsic@1.3.0:
|
||||
@ -8554,6 +8638,8 @@ snapshots:
|
||||
dependencies:
|
||||
language-subtag-registry: 0.3.23
|
||||
|
||||
lerc@3.0.0: {}
|
||||
|
||||
leven@3.1.0: {}
|
||||
|
||||
levn@0.4.1:
|
||||
@ -8792,6 +8878,14 @@ snapshots:
|
||||
define-properties: 1.2.1
|
||||
es-object-atoms: 1.1.1
|
||||
|
||||
ol@10.6.1:
|
||||
dependencies:
|
||||
'@types/rbush': 4.0.0
|
||||
earcut: 3.0.2
|
||||
geotiff: 2.1.3
|
||||
pbf: 4.0.1
|
||||
rbush: 4.0.1
|
||||
|
||||
once@1.4.0:
|
||||
dependencies:
|
||||
wrappy: 1.0.2
|
||||
@ -8837,10 +8931,14 @@ snapshots:
|
||||
|
||||
package-json-from-dist@1.0.1: {}
|
||||
|
||||
pako@2.1.0: {}
|
||||
|
||||
parent-module@1.0.1:
|
||||
dependencies:
|
||||
callsites: 3.1.0
|
||||
|
||||
parse-headers@2.0.6: {}
|
||||
|
||||
parse-json@5.2.0:
|
||||
dependencies:
|
||||
'@babel/code-frame': 7.27.1
|
||||
@ -8867,6 +8965,10 @@ snapshots:
|
||||
lru-cache: 10.4.3
|
||||
minipass: 7.1.2
|
||||
|
||||
pbf@4.0.1:
|
||||
dependencies:
|
||||
resolve-protobuf-schema: 2.1.0
|
||||
|
||||
pg-cloudflare@1.2.7:
|
||||
optional: true
|
||||
|
||||
@ -8972,14 +9074,24 @@ snapshots:
|
||||
object-assign: 4.1.1
|
||||
react-is: 16.13.1
|
||||
|
||||
protocol-buffers-schema@3.6.0: {}
|
||||
|
||||
punycode@2.3.1: {}
|
||||
|
||||
pure-rand@7.0.1: {}
|
||||
|
||||
queue-microtask@1.2.3: {}
|
||||
|
||||
quick-lru@6.1.2: {}
|
||||
|
||||
quick-lru@7.1.0: {}
|
||||
|
||||
quickselect@3.0.0: {}
|
||||
|
||||
rbush@4.0.1:
|
||||
dependencies:
|
||||
quickselect: 3.0.0
|
||||
|
||||
react-dom@19.1.1(react@19.1.1):
|
||||
dependencies:
|
||||
react: 19.1.1
|
||||
@ -8995,6 +9107,12 @@ snapshots:
|
||||
|
||||
react-is@18.3.1: {}
|
||||
|
||||
react-openlayers@10.5.1(ol@10.6.1)(react-dom@19.1.1(react@19.1.1))(react@19.1.1):
|
||||
dependencies:
|
||||
ol: 10.6.1
|
||||
react: 19.1.1
|
||||
react-dom: 19.1.1(react@19.1.1)
|
||||
|
||||
react-remove-scroll-bar@2.3.8(@types/react@19.1.15)(react@19.1.1):
|
||||
dependencies:
|
||||
react: 19.1.1
|
||||
@ -9061,6 +9179,10 @@ snapshots:
|
||||
|
||||
resolve-pkg-maps@1.0.0: {}
|
||||
|
||||
resolve-protobuf-schema@2.1.0:
|
||||
dependencies:
|
||||
protocol-buffers-schema: 3.6.0
|
||||
|
||||
resolve@1.22.10:
|
||||
dependencies:
|
||||
is-core-module: 2.16.1
|
||||
@ -9589,6 +9711,8 @@ snapshots:
|
||||
dependencies:
|
||||
makeerror: 1.0.12
|
||||
|
||||
web-worker@1.5.0: {}
|
||||
|
||||
webidl-conversions@3.0.1: {}
|
||||
|
||||
webidl-conversions@7.0.0: {}
|
||||
@ -9700,6 +9824,8 @@ snapshots:
|
||||
|
||||
xml-name-validator@5.0.0: {}
|
||||
|
||||
xml-utils@1.10.2: {}
|
||||
|
||||
xmlchars@2.2.0: {}
|
||||
|
||||
xtend@4.0.2: {}
|
||||
@ -9727,3 +9853,5 @@ snapshots:
|
||||
yocto-queue@0.1.0: {}
|
||||
|
||||
zod@4.1.11: {}
|
||||
|
||||
zstddec@0.1.0: {}
|
||||
|
||||
@ -66,8 +66,8 @@ export default async function AlbumHeader({
|
||||
>
|
||||
{album.location &&
|
||||
<PlaceEntity
|
||||
location={album.location}
|
||||
className="translate-x-[-2px] mr-3!"
|
||||
place={album.location}
|
||||
className="translate-x-[-2px] mr-1.5!"
|
||||
/>}
|
||||
{tags.length > 0 && <>
|
||||
<IconTag
|
||||
|
||||
@ -1,11 +1,15 @@
|
||||
'use client';
|
||||
|
||||
import { ReactNode, useRef, useEffect } from 'react';
|
||||
import { SharedHoverProps, useSharedHoverState } from '../shared-hover/state';
|
||||
import useSupportsHover from '@/utility/useSupportsHover';
|
||||
import clsx from 'clsx/lite';
|
||||
|
||||
export default function SharedHover({
|
||||
hoverKey: key,
|
||||
children,
|
||||
content,
|
||||
className,
|
||||
width,
|
||||
height,
|
||||
offsetAbove = -1,
|
||||
@ -15,6 +19,7 @@ export default function SharedHover({
|
||||
hoverKey: string
|
||||
children :ReactNode
|
||||
content: ReactNode
|
||||
className?: string
|
||||
width: number
|
||||
height: number
|
||||
offsetAbove?: number
|
||||
@ -47,7 +52,7 @@ export default function SharedHover({
|
||||
|
||||
return (
|
||||
<div
|
||||
className="max-w-full"
|
||||
className={clsx('max-w-full', className)}
|
||||
ref={ref}
|
||||
onMouseEnter={() => supportsHover &&
|
||||
showHover?.(ref.current, {
|
||||
|
||||
@ -4,7 +4,7 @@ import MaskedScroll from '@/components/MaskedScroll';
|
||||
import PhotoAlbum from '@/album/PhotoAlbum';
|
||||
import PhotoTag from '@/tag/PhotoTag';
|
||||
import PhotoFavs from '@/tag/PhotoFavs';
|
||||
import clsx from 'clsx';
|
||||
import clsx from 'clsx/lite';
|
||||
import { CATEGORY_VISIBILITY } from '@/app/config';
|
||||
import PhotoRecents from '@/recents/PhotoRecents';
|
||||
import PhotoFilm from '@/film/PhotoFilm';
|
||||
|
||||
@ -3,23 +3,50 @@ import { Place } from '.';
|
||||
import EntityLink, {
|
||||
EntityLinkExternalProps,
|
||||
} from '@/components/entity/EntityLink';
|
||||
import { getDimensionsFromSize } from '@/utility/size';
|
||||
import PlaceMap from './PlaceMap';
|
||||
import SharedHover from '@/components/shared-hover/SharedHover';
|
||||
import clsx from 'clsx/lite';
|
||||
|
||||
const { width, height } = getDimensionsFromSize(300, 16 / 9);
|
||||
|
||||
export default function PlaceEntity({
|
||||
location,
|
||||
place,
|
||||
...props
|
||||
}: {
|
||||
location: Place
|
||||
place: Place
|
||||
} & EntityLinkExternalProps) {
|
||||
return (
|
||||
<SharedHover {...{
|
||||
hoverKey: place.id,
|
||||
content: <div className="relative">
|
||||
<PlaceMap {...{ place, width, height }} />
|
||||
<span
|
||||
className={clsx(
|
||||
'absolute bottom-2.5 left-2.5',
|
||||
'px-1.5 py-0.5 rounded-sm',
|
||||
'text-white/90 bg-black/40 backdrop-blur-lg',
|
||||
'outline-medium shadow-sm',
|
||||
'uppercase text-[0.7rem]',
|
||||
)}
|
||||
>
|
||||
{place.nameFormatted || place.name}
|
||||
</span>
|
||||
</div>,
|
||||
className: 'inline-flex',
|
||||
width,
|
||||
height,
|
||||
}}>
|
||||
<EntityLink
|
||||
{...props}
|
||||
icon={<IconPlace
|
||||
className="text-[13px] translate-x-[2px]"
|
||||
/>}
|
||||
label={location.nameFormatted || location.name}
|
||||
path={location.link}
|
||||
label={place.nameFormatted || place.name}
|
||||
path={place.link}
|
||||
pathTarget="_blank"
|
||||
badged
|
||||
/>
|
||||
</SharedHover>
|
||||
);
|
||||
}
|
||||
73
src/place/PlaceMap.tsx
Normal file
73
src/place/PlaceMap.tsx
Normal file
@ -0,0 +1,73 @@
|
||||
'use client';
|
||||
|
||||
import { OSM } from 'ol/source';
|
||||
import { fromLonLat } from 'ol/proj';
|
||||
import { useMemo, useRef } from 'react';
|
||||
import { Map, View, TileLayer } from 'react-openlayers';
|
||||
import { Place } from '.';
|
||||
import { boundingExtent } from 'ol/extent';
|
||||
|
||||
import 'react-openlayers/dist/index.css'; // for css
|
||||
|
||||
const MULTIPLIER = 2;
|
||||
|
||||
export default function PlaceMap({
|
||||
place,
|
||||
width,
|
||||
height,
|
||||
monochrome,
|
||||
}: {
|
||||
place: Place
|
||||
width: number
|
||||
height: number
|
||||
monochrome?: boolean
|
||||
}) {
|
||||
const osm = useRef(new OSM());
|
||||
|
||||
const centerLon = place.location?.longitude ?? 0;
|
||||
const centerLat = place.location?.latitude ?? 0;
|
||||
const highLon = place.viewport?.high?.longitude ?? 0;
|
||||
const highLat = place.viewport?.high?.latitude ?? 0;
|
||||
const lowLon = place.viewport?.low?.longitude ?? 0;
|
||||
const lowLat = place.viewport?.low?.latitude ?? 0;
|
||||
|
||||
const center = useMemo(() =>
|
||||
fromLonLat([centerLon, centerLat])
|
||||
, [centerLon, centerLat]);
|
||||
|
||||
const extent = useMemo(() =>
|
||||
boundingExtent([
|
||||
fromLonLat([highLon, highLat]),
|
||||
fromLonLat([lowLon, lowLat]),
|
||||
])
|
||||
, [highLon, highLat, lowLon, lowLat]);
|
||||
|
||||
return (
|
||||
<div style={{ width, height }}>
|
||||
<div style={{
|
||||
transform: `scale(${1 / MULTIPLIER})`,
|
||||
transformOrigin: 'top left',
|
||||
}}>
|
||||
<Map
|
||||
controls={[]}
|
||||
interactions={[]}
|
||||
style={{
|
||||
width: width * MULTIPLIER,
|
||||
height: height * MULTIPLIER,
|
||||
...monochrome && {
|
||||
filter: 'saturate(0) contrast(1.05) brightness(1.05)',
|
||||
},
|
||||
}}
|
||||
>
|
||||
<TileLayer source={osm.current} />
|
||||
<View {...{
|
||||
center,
|
||||
extent,
|
||||
// Zoom must be defined despite setting extent
|
||||
zoom: 1,
|
||||
}} />
|
||||
</Map>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
Loading…
Reference in New Issue
Block a user