Repository navigation
Expand file tree
/
Copy pathPtImage.astro
More file actions
67 lines (59 loc) · 1.88 KB
/
Copy pathPtImage.astro
File metadata and controls
67 lines (59 loc) · 1.88 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
---
import { stegaClean } from "@sanity/client/stega";
import type { Props as PtProps } from "astro-portabletext/types";
import type { SanityImageSource } from "@sanity/image-url";
type ImageNode = SanityImageSource & {
_type: "image";
alt?: string;
caption?: string;
};
type Props = PtProps<ImageNode>;
const { node } = Astro.props;
// Parse intrinsic dimensions from Sanity asset _ref ("image-<hash>-<width>x<height>-<ext>")
// so we never pass a forced 16:9 .height(1080) to @sanity/image-url (which causes
// @sanity/image-url to inject ?rect=... and crop tall/square images like memes or diagrams).
const assetRef = stegaClean(
(node as { asset?: { _ref?: string } })?.asset?._ref,
);
const dimMatch = assetRef?.match(/-(\d+)x(\d+)-[a-z0-9]+$/i);
const intrinsicWidth = dimMatch ? Number(dimMatch[1]) : 1200;
const intrinsicHeight = dimMatch ? Number(dimMatch[2]) : 675;
const builder = Astro.locals.sanity.urlForImage(node);
const maxWidth = Math.min(intrinsicWidth, 1600);
const src = builder?.width(maxWidth).quality(82).url();
const responsiveWidths = [480, 640, 800, 960, 1200, 1600].filter(
(w) => w <= maxWidth,
);
if (!responsiveWidths.includes(maxWidth)) {
responsiveWidths.push(maxWidth);
}
const srcset = builder
? responsiveWidths
.map((w) => `${builder.width(w).quality(82).url()} ${w}w`)
.join(", ")
: undefined;
const alt = stegaClean(node.alt) ?? "";
const caption = node.caption;
---
{
src && (
<figure class="not-prose my-8 flex flex-col items-center">
<img
class="h-auto w-auto max-w-full max-h-[80dvh] rounded-md shadow-md"
src={src}
srcset={srcset}
width={intrinsicWidth}
height={intrinsicHeight}
sizes="(max-width: 896px) 100vw, 896px"
alt={alt}
loading="lazy"
decoding="async"
/>
{caption && (
<figcaption class="mt-2 text-center text-sm text-muted-foreground">
{caption}
</figcaption>
)}
</figure>
)
}