svelte-remote-image 0.1.3 → 0.2.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.
package/README.md CHANGED
@@ -60,24 +60,18 @@ Sample code.
60
60
  The image component renders into:
61
61
 
62
62
  ```
63
- <div class="picture-wrapper s-wHckl4XSACcy" style="background-color: #c5c5c5">
64
- <picture class="s-wHckl4XSACcy">
65
- <source
66
- srcset="https://nostr-image-optimizer.ocknamo.com/image/width=1600,quality=50,format=webp/https://ocknamo.com/static/b84d6366deec053ff3fa77df01a54464/dccd3/cat.webp 1600w, https://nostr-image-optimizer.ocknamo.com/image/width=800,quality=50,format=webp/https://ocknamo.com/static/b84d6366deec053ff3fa77df01a54464/dccd3/cat.webp 800w"
67
- type="image/webp" class="s-wHckl4XSACcy">
68
- <source
69
- srcset="https://nostr-image-optimizer.ocknamo.com/image/width=1600,quality=50,format=jpeg/https://ocknamo.com/static/b84d6366deec053ff3fa77df01a54464/dccd3/cat.webp 1600w, https://nostr-image-optimizer.ocknamo.com/image/width=800,quality=50,format=jpeg/https://ocknamo.com/static/b84d6366deec053ff3fa77df01a54464/dccd3/cat.webp 800w"
70
- type="image/jpeg" class="s-wHckl4XSACcy"> <img width="800" style="" class="image-blur-loading s-wHckl4XSACcy"
71
- src="https://nostr-image-optimizer.ocknamo.com/image/width=1600,quality=70,format=webp/https://ocknamo.com/static/b84d6366deec053ff3fa77df01a54464/dccd3/cat.webp"
72
- alt="blog top" loading="lazy">
73
- </picture>
74
- </div>
75
-
76
- <!-- css -->
77
- .picture-wrapper.s-wHckl4XSACcy {
78
- width: fit-content;
79
- height: fit-content;
80
- }
63
+ <picture>
64
+ <source
65
+ srcset="https://nostr-image-optimizer.ocknamo.com/image/width=1600,quality=50,format=webp/https://ocknamo.com/static/b84d6366deec053ff3fa77df01a54464/dccd3/cat.webp 1600w, https://nostr-image-optimizer.ocknamo.com/image/width=800,quality=50,format=webp/https://ocknamo.com/static/b84d6366deec053ff3fa77df01a54464/dccd3/cat.webp 800w"
66
+ type="image/webp">
67
+ <source
68
+ srcset="https://nostr-image-optimizer.ocknamo.com/image/width=1600,quality=50,format=jpeg/https://ocknamo.com/static/b84d6366deec053ff3fa77df01a54464/dccd3/cat.webp 1600w, https://nostr-image-optimizer.ocknamo.com/image/width=800,quality=50,format=jpeg/https://ocknamo.com/static/b84d6366deec053ff3fa77df01a54464/dccd3/cat.webp 800w"
69
+ type="image/jpeg"> <img width="800"
70
+ style="max-width: 100%; background-color: '#c5c5c5'; display: inline;"
71
+ class="image-blur-loaded"
72
+ src="https://nostr-image-optimizer.ocknamo.com/image/width=1600,quality=70,format=webp/https://ocknamo.com/static/b84d6366deec053ff3fa77df01a54464/dccd3/cat.webp"
73
+ alt="blog top" loading="lazy">
74
+ </picture>
81
75
  ```
82
76
 
83
77
  Inspired by [svelte-img](https://github.com/zerodevx/svelte-img?tab=readme-ov-file#remote-images-from-an-api).
@@ -86,42 +80,54 @@ Inspired by [svelte-img](https://github.com/zerodevx/svelte-img?tab=readme-ov-fi
86
80
 
87
81
  ### ImageSrc
88
82
 
89
- - img: string
90
- - image url.
83
+ #### img: string
91
84
 
92
- - w: number
93
- - image width.
85
+ Image url.
86
+
87
+ #### w: number
88
+
89
+ Image width.
90
+
91
+ #### h?: number
92
+
93
+ Image height.
94
+
95
+ #### webp?: Srcset[]
96
+
97
+ Image sources for webp.
98
+
99
+ #### jpeg?: Srcset[]
100
+
101
+ Image sources for jpeg.
102
+
103
+ #### png?: Srcset[]
94
104
 
95
- - h?: number
96
- - image height.
105
+ Image sources for png.
97
106
 
98
- - webp?: Srcset[]
99
- - image source for webp.
107
+ #### failback: string[]
100
108
 
101
- - jpeg?: Srcset[]
102
- - image source for jpeg.
109
+ Failback image urls.
110
+ The order is important because the images are tested in order from the top of the array.
103
111
 
104
- - png?: Srcset[]
105
- - image source for png.
112
+ #### alt: string
106
113
 
107
- - failback: string
108
- - failback image url.
114
+ Alt text for image.
109
115
 
110
- - alt: string
111
- - alt
116
+ #### placeholder?: { dataUri?: string; color?: string }
112
117
 
113
- - placeholder?: { dataUri?: string; color?: string }
114
- - Image data and background color for fastest display.
118
+ Image data and background color for fastest display.
115
119
 
116
- - blur?: boolean
117
- - Whether to use the blur effect when displaying the image.
120
+ #### blur?: boolean
121
+
122
+ Whether to use the blur effect when displaying the image.
123
+ Default false.
118
124
 
119
- ### Srcset
125
+ #### Srcset
120
126
 
121
127
  - src: string
122
128
  - Image URL.
123
129
  - w: number
124
- - width to display.
130
+ - Width of actual image.
125
131
 
126
132
  ## Developing
127
133
 
@@ -1,36 +1,74 @@
1
- <script>export let src;
1
+ <script>import { browser } from "$app/environment";
2
+ import { afterUpdate, tick } from "svelte";
3
+ export let src;
2
4
  export let style = "";
5
+ const imgId = `svelte-remote-image-${src.alt.replaceAll(" ", "-")}-${Math.round(Math.random() * 1e7)}`;
6
+ const getImgElement = () => browser ? document.getElementById(imgId) : null;
3
7
  let loadStatus = "loading";
4
- if (src.placeholder) {
5
- if (src.placeholder.dataUri) {
6
- style = `${style} background: url(${src.placeholder.dataUri}) no-repeat center/cover;`;
8
+ $: {
9
+ loadStatus = "loading";
10
+ if (src.placeholder) {
11
+ if (src.placeholder.dataUri) {
12
+ style = `${style} background: url(${src.placeholder.dataUri}) no-repeat center/cover;`;
13
+ }
14
+ if (src.placeholder.color) {
15
+ style = `${style} background-color: ${src.placeholder.color};`;
16
+ }
7
17
  }
8
- if (src.placeholder.color) {
9
- style = `${style} background-color: ${src.placeholder.color};`;
18
+ const img = getImgElement();
19
+ if (img) {
20
+ img.style.visibility = "hidden";
10
21
  }
11
22
  }
23
+ afterUpdate(async () => {
24
+ const img = getImgElement();
25
+ if (!img) {
26
+ return;
27
+ }
28
+ await tick();
29
+ if (img.naturalWidth !== 0 && img.naturalHeight !== 0) {
30
+ img.style.visibility = "visible";
31
+ loadStatus = "loaded";
32
+ } else {
33
+ handleImgError();
34
+ }
35
+ });
12
36
  const handleImgError = (e) => {
13
- if (e.type !== "error") {
37
+ if (e && e.type !== "error") {
38
+ return;
39
+ }
40
+ const img = getImgElement();
41
+ if (!img) {
42
+ return;
43
+ }
44
+ img.style.visibility = "hidden";
45
+ let failbackUrl = void 0;
46
+ const index = src.failback.findIndex(
47
+ (url) => new URL(url).toString() === new URL(img.src).toString()
48
+ );
49
+ if (index === -1) {
50
+ failbackUrl = src.failback[0];
51
+ } else {
52
+ failbackUrl = src.failback[index + 1];
53
+ }
54
+ if (!failbackUrl) {
14
55
  return;
15
56
  }
16
- const img = e.currentTarget;
17
- img.style.display = "none";
18
57
  src = {
19
58
  ...src,
20
- img: src.failback,
59
+ img: failbackUrl,
21
60
  webp: [],
22
61
  jpeg: [],
23
62
  png: [],
24
63
  placeholder: {
25
64
  color: src.placeholder?.color,
26
65
  dataUri: src.placeholder?.dataUri
27
- },
28
- blur: src.blur
66
+ }
29
67
  };
30
68
  };
31
69
  const handleLoaded = (e) => {
32
70
  const img = e.currentTarget;
33
- img.style.display = "inline";
71
+ img.style.visibility = "visible";
34
72
  loadStatus = "loaded";
35
73
  };
36
74
  </script>
@@ -46,6 +84,7 @@ const handleLoaded = (e) => {
46
84
  <source srcset={src.png.map((s) => `${s.src} ${s.w}w`).join(', ')} type="image/png" />
47
85
  {/if}
48
86
  <img
87
+ id={imgId}
49
88
  width={src.w}
50
89
  height={src.h}
51
90
  {style}
@@ -9,7 +9,7 @@ export interface ImageSrc {
9
9
  webp?: Srcset[];
10
10
  jpeg?: Srcset[];
11
11
  png?: Srcset[];
12
- failback: string;
12
+ failback: string[];
13
13
  alt: string;
14
14
  placeholder?: {
15
15
  dataUri?: string;
package/package.json CHANGED
@@ -1,7 +1,8 @@
1
1
  {
2
2
  "name": "svelte-remote-image",
3
- "version": "0.1.3",
3
+ "version": "0.2.1",
4
4
  "license": "MIT",
5
+ "homepage": "https://github.com/ocknamo/svelte-remote-image",
5
6
  "scripts": {
6
7
  "dev": "vite dev",
7
8
  "build": "vite build && npm run package",