your personal website on atproto - mirror blento.app

update link card

+351 -190
+198 -111
src/lib/cards/core/LinkCard/EditingLinkCard.svelte
··· 113 113 onchange={handleImageChange} 114 114 /> 115 115 116 - <div class="relative flex h-full flex-col justify-between p-4"> 117 - <div 118 - class={[ 119 - 'accent:bg-accent-500/50 absolute inset-0 z-20 bg-white/50 dark:bg-black/50', 120 - !hasFetched ? 'animate-pulse' : 'hidden' 121 - ]} 122 - ></div> 123 - 124 - <div class={isFetchingMetadata ? 'pointer-events-none' : ''}> 125 - <button 126 - type="button" 127 - class="bg-base-100 border-base-300 accent:bg-accent-100/50 accent:border-accent-200 dark:border-base-800 dark:bg-base-900 hover:ring-accent-500 relative mb-2 inline-flex size-8 cursor-pointer items-center justify-center rounded-xl border transition-all duration-200 hover:ring-2" 128 - onclick={() => faviconInputRef?.click()} 129 - onmouseenter={() => (isHoveringFavicon = true)} 130 - onmouseleave={() => (isHoveringFavicon = false)} 131 - > 132 - {#if hasFetched && item.cardData.favicon && !faviconHasError} 133 - <img 134 - class="size-6 rounded-lg object-cover" 135 - onerror={() => (faviconHasError = true)} 136 - src={getImage(item.cardData, did, 'favicon')} 137 - alt="" 138 - /> 139 - {:else} 140 - <svg 141 - xmlns="http://www.w3.org/2000/svg" 142 - fill="none" 143 - viewBox="0 0 24 24" 144 - stroke-width="1.5" 145 - stroke="currentColor" 146 - class="size-4" 147 - > 148 - <path 149 - stroke-linecap="round" 150 - stroke-linejoin="round" 151 - d="M13.19 8.688a4.5 4.5 0 0 1 1.242 7.244l-4.5 4.5a4.5 4.5 0 0 1-6.364-6.364l1.757-1.757m13.35-.622 1.757-1.757a4.5 4.5 0 0 0-6.364-6.364l-4.5 4.5a4.5 4.5 0 0 1 1.242 7.244" 152 - /> 153 - </svg> 154 - {/if} 155 - <!-- Hover overlay --> 156 - <div 157 - class={[ 158 - 'absolute inset-0 flex items-center justify-center rounded-xl bg-black/50 transition-opacity duration-200', 159 - isHoveringFavicon ? 'opacity-100' : 'opacity-0' 160 - ]} 161 - > 162 - <svg 163 - xmlns="http://www.w3.org/2000/svg" 164 - fill="none" 165 - viewBox="0 0 24 24" 166 - stroke-width="2" 167 - stroke="currentColor" 168 - class="size-4 text-white" 169 - > 170 - <path 171 - stroke-linecap="round" 172 - stroke-linejoin="round" 173 - d="m16.862 4.487 1.687-1.688a1.875 1.875 0 1 1 2.652 2.652L10.582 16.07a4.5 4.5 0 0 1-1.897 1.13L6 18l.8-2.685a4.5 4.5 0 0 1 1.13-1.897l8.932-8.931Z" 174 - /> 175 - </svg> 176 - </div> 177 - </button> 178 - 116 + {#if item.cardData.showBackgroundImage} 117 + <div class="relative flex h-full flex-col justify-end p-4"> 179 118 <div 180 119 class={[ 181 - '-m-1 rounded-md p-1 transition-colors duration-200', 182 - hasFetched 183 - ? 'hover:bg-base-200/70 dark:hover:bg-base-800/70 accent:hover:bg-accent-200/30' 184 - : '' 120 + 'accent:bg-accent-500/50 absolute inset-0 z-30 bg-white/50 dark:bg-black/50', 121 + !hasFetched ? 'animate-pulse' : 'hidden' 185 122 ]} 186 - > 187 - {#if hasFetched} 188 - <PlainTextEditor 189 - class="text-base-900 dark:text-base-50 line-clamp-2 text-lg font-bold" 190 - key="title" 191 - bind:contentDict={item.cardData} 192 - placeholder="Title here" 193 - /> 194 - {:else} 195 - <span class="text-base-900 dark:text-base-50 line-clamp-2 text-lg font-bold"> 196 - Loading data... 197 - </span> 198 - {/if} 199 - </div> 200 - <!-- <div class="text-base-800 dark:text-base-100 mt-2 text-xs">{item.cardData.description}</div> --> 123 + ></div> 124 + 125 + {#if item.cardData.image} 126 + <img 127 + class="absolute inset-0 -z-10 size-full object-cover" 128 + src={getImage(item.cardData, did)} 129 + alt="" 130 + /> 131 + {/if} 201 132 <div 202 - class="text-accent-600 accent:text-accent-950 dark:text-accent-400 mt-2 text-xs font-semibold" 203 - > 204 - {item.cardData.domain} 205 - </div> 206 - </div> 133 + class="from-base-50/90 via-base-50/40 dark:from-base-950/90 dark:via-base-950/40 absolute inset-0 -z-10 bg-linear-to-t to-transparent" 134 + ></div> 207 135 208 - {#if hasFetched && browser && ((isMobile() && item.mobileH >= 8) || (!isMobile() && item.h >= 4))} 136 + <!-- Full card click to change image --> 209 137 <button 210 138 type="button" 211 - class="hover:ring-accent-500 relative mb-2 aspect-2/1 w-full cursor-pointer overflow-hidden rounded-xl transition-all duration-200 hover:ring-2" 139 + class="absolute inset-0 z-10 cursor-pointer" 212 140 onclick={() => imageInputRef?.click()} 213 141 onmouseenter={() => (isHoveringImage = true)} 214 142 onmouseleave={() => (isHoveringImage = false)} 215 143 > 216 - {#if item.cardData.image} 217 - <img 218 - class="h-full w-full object-cover opacity-100 transition-opacity duration-100 starting:opacity-0" 219 - src={getImage(item.cardData, did)} 220 - alt="" 221 - /> 222 - {:else} 223 - <div class="bg-base-200 dark:bg-base-800 flex h-full w-full items-center justify-center"> 144 + <div 145 + class={[ 146 + 'absolute inset-0 flex items-center justify-center bg-black/50 transition-opacity duration-200', 147 + isHoveringImage ? 'opacity-100' : 'opacity-0' 148 + ]} 149 + > 150 + <div class="text-center text-sm text-white"> 224 151 <svg 225 152 xmlns="http://www.w3.org/2000/svg" 226 153 fill="none" 227 154 viewBox="0 0 24 24" 228 155 stroke-width="1.5" 229 156 stroke="currentColor" 230 - class="text-base-400 dark:text-base-600 size-8" 157 + class="mx-auto mb-1 size-6" 231 158 > 232 159 <path 233 160 stroke-linecap="round" 234 161 stroke-linejoin="round" 235 - d="m2.25 15.75 5.159-5.159a2.25 2.25 0 0 1 3.182 0l5.159 5.159m-1.5-1.5 1.409-1.409a2.25 2.25 0 0 1 3.182 0l2.909 2.909m-18 3.75h16.5a1.5 1.5 0 0 0 1.5-1.5V6a1.5 1.5 0 0 0-1.5-1.5H3.75A1.5 1.5 0 0 0 2.25 6v12a1.5 1.5 0 0 0 1.5 1.5Zm10.5-11.25h.008v.008h-.008V8.25Zm.375 0a.375.375 0 1 1-.75 0 .375.375 0 0 1 .75 0Z" 162 + d="M6.827 6.175A2.31 2.31 0 0 1 5.186 7.23c-.38.054-.757.112-1.134.175C2.999 7.58 2.25 8.507 2.25 9.574V18a2.25 2.25 0 0 0 2.25 2.25h15A2.25 2.25 0 0 0 21.75 18V9.574c0-1.067-.75-1.994-1.802-2.169a47.865 47.865 0 0 0-1.134-.175 2.31 2.31 0 0 1-1.64-1.055l-.822-1.316a2.192 2.192 0 0 0-1.736-1.039 48.774 48.774 0 0 0-5.232 0 2.192 2.192 0 0 0-1.736 1.039l-.821 1.316Z" 163 + /> 164 + <path 165 + stroke-linecap="round" 166 + stroke-linejoin="round" 167 + d="M16.5 12.75a4.5 4.5 0 1 1-9 0 4.5 4.5 0 0 1 9 0ZM18.75 10.5h.008v.008h-.008V10.5Z" 236 168 /> 237 169 </svg> 170 + <span class="font-medium">{item.cardData.image ? 'Change image' : 'Add image'}</span> 238 171 </div> 239 - {/if} 240 - <!-- Hover overlay --> 172 + </div> 173 + </button> 174 + 175 + <!-- Domain and title at the bottom, above the image button --> 176 + <div class="relative z-20"> 177 + <div class="text-accent-600 dark:text-accent-400 text-xs font-semibold"> 178 + {item.cardData.domain} 179 + </div> 241 180 <div 242 181 class={[ 243 - 'absolute inset-0 flex items-center justify-center rounded-xl bg-black/50 transition-opacity duration-200', 244 - isHoveringImage ? 'opacity-100' : 'opacity-0' 182 + '-m-1 rounded-md p-1 transition-colors duration-200', 183 + hasFetched ? 'hover:bg-base-200/70 dark:hover:bg-base-800/70' : '' 245 184 ]} 246 185 > 247 - <div class="text-center text-sm text-white"> 186 + {#if hasFetched} 187 + <PlainTextEditor 188 + class="text-base-900 dark:text-base-50 line-clamp-2 text-lg font-bold" 189 + key="title" 190 + bind:contentDict={item.cardData} 191 + placeholder="Title here" 192 + /> 193 + {:else} 194 + <span class="text-base-900 dark:text-base-50 line-clamp-2 text-lg font-bold"> 195 + Loading data... 196 + </span> 197 + {/if} 198 + </div> 199 + </div> 200 + </div> 201 + {:else} 202 + <div class="relative flex h-full flex-col justify-between p-4"> 203 + <div 204 + class={[ 205 + 'accent:bg-accent-500/50 absolute inset-0 z-20 bg-white/50 dark:bg-black/50', 206 + !hasFetched ? 'animate-pulse' : 'hidden' 207 + ]} 208 + ></div> 209 + 210 + <div class={isFetchingMetadata ? 'pointer-events-none' : ''}> 211 + <button 212 + type="button" 213 + class="bg-base-100 border-base-300 accent:bg-accent-100/50 accent:border-accent-200 dark:border-base-800 dark:bg-base-900 hover:ring-accent-500 relative mb-2 inline-flex size-8 cursor-pointer items-center justify-center rounded-xl border transition-all duration-200 hover:ring-2" 214 + onclick={() => faviconInputRef?.click()} 215 + onmouseenter={() => (isHoveringFavicon = true)} 216 + onmouseleave={() => (isHoveringFavicon = false)} 217 + > 218 + {#if hasFetched && item.cardData.favicon && !faviconHasError} 219 + <img 220 + class="size-6 rounded-lg object-cover" 221 + onerror={() => (faviconHasError = true)} 222 + src={getImage(item.cardData, did, 'favicon')} 223 + alt="" 224 + /> 225 + {:else} 248 226 <svg 249 227 xmlns="http://www.w3.org/2000/svg" 250 228 fill="none" 251 229 viewBox="0 0 24 24" 252 230 stroke-width="1.5" 253 231 stroke="currentColor" 254 - class="mx-auto mb-1 size-6" 232 + class="size-4" 255 233 > 256 234 <path 257 235 stroke-linecap="round" 258 236 stroke-linejoin="round" 259 - d="M6.827 6.175A2.31 2.31 0 0 1 5.186 7.23c-.38.054-.757.112-1.134.175C2.999 7.58 2.25 8.507 2.25 9.574V18a2.25 2.25 0 0 0 2.25 2.25h15A2.25 2.25 0 0 0 21.75 18V9.574c0-1.067-.75-1.994-1.802-2.169a47.865 47.865 0 0 0-1.134-.175 2.31 2.31 0 0 1-1.64-1.055l-.822-1.316a2.192 2.192 0 0 0-1.736-1.039 48.774 48.774 0 0 0-5.232 0 2.192 2.192 0 0 0-1.736 1.039l-.821 1.316Z" 237 + d="M13.19 8.688a4.5 4.5 0 0 1 1.242 7.244l-4.5 4.5a4.5 4.5 0 0 1-6.364-6.364l1.757-1.757m13.35-.622 1.757-1.757a4.5 4.5 0 0 0-6.364-6.364l-4.5 4.5a4.5 4.5 0 0 1 1.242 7.244" 260 238 /> 239 + </svg> 240 + {/if} 241 + <!-- Hover overlay --> 242 + <div 243 + class={[ 244 + 'absolute inset-0 flex items-center justify-center rounded-xl bg-black/50 transition-opacity duration-200', 245 + isHoveringFavicon ? 'opacity-100' : 'opacity-0' 246 + ]} 247 + > 248 + <svg 249 + xmlns="http://www.w3.org/2000/svg" 250 + fill="none" 251 + viewBox="0 0 24 24" 252 + stroke-width="2" 253 + stroke="currentColor" 254 + class="size-4 text-white" 255 + > 261 256 <path 262 257 stroke-linecap="round" 263 258 stroke-linejoin="round" 264 - d="M16.5 12.75a4.5 4.5 0 1 1-9 0 4.5 4.5 0 0 1 9 0ZM18.75 10.5h.008v.008h-.008V10.5Z" 259 + d="m16.862 4.487 1.687-1.688a1.875 1.875 0 1 1 2.652 2.652L10.582 16.07a4.5 4.5 0 0 1-1.897 1.13L6 18l.8-2.685a4.5 4.5 0 0 1 1.13-1.897l8.932-8.931Z" 265 260 /> 266 261 </svg> 267 - <span class="font-medium">{item.cardData.image ? 'Change' : 'Add image'}</span> 268 262 </div> 263 + </button> 264 + 265 + <div 266 + class={[ 267 + '-m-1 rounded-md p-1 transition-colors duration-200', 268 + hasFetched 269 + ? 'hover:bg-base-200/70 dark:hover:bg-base-800/70 accent:hover:bg-accent-200/30' 270 + : '' 271 + ]} 272 + > 273 + {#if hasFetched} 274 + <PlainTextEditor 275 + class="text-base-900 dark:text-base-50 line-clamp-2 text-lg font-bold" 276 + key="title" 277 + bind:contentDict={item.cardData} 278 + placeholder="Title here" 279 + /> 280 + {:else} 281 + <span class="text-base-900 dark:text-base-50 line-clamp-2 text-lg font-bold"> 282 + Loading data... 283 + </span> 284 + {/if} 269 285 </div> 270 - </button> 271 - {/if} 272 - </div> 286 + <!-- <div class="text-base-800 dark:text-base-100 mt-2 text-xs">{item.cardData.description}</div> --> 287 + <div 288 + class="text-accent-600 accent:text-accent-950 dark:text-accent-400 mt-2 text-xs font-semibold" 289 + > 290 + {item.cardData.domain} 291 + </div> 292 + </div> 293 + 294 + {#if hasFetched && browser && ((isMobile() && item.mobileH >= 8) || (!isMobile() && item.h >= 4))} 295 + <button 296 + type="button" 297 + class="hover:ring-accent-500 relative mb-2 aspect-2/1 w-full cursor-pointer overflow-hidden rounded-xl transition-all duration-200 hover:ring-2" 298 + onclick={() => imageInputRef?.click()} 299 + onmouseenter={() => (isHoveringImage = true)} 300 + onmouseleave={() => (isHoveringImage = false)} 301 + > 302 + {#if item.cardData.image} 303 + <img 304 + class="h-full w-full object-cover opacity-100 transition-opacity duration-100 starting:opacity-0" 305 + src={getImage(item.cardData, did)} 306 + alt="" 307 + /> 308 + {:else} 309 + <div class="bg-base-200 dark:bg-base-800 flex h-full w-full items-center justify-center"> 310 + <svg 311 + xmlns="http://www.w3.org/2000/svg" 312 + fill="none" 313 + viewBox="0 0 24 24" 314 + stroke-width="1.5" 315 + stroke="currentColor" 316 + class="text-base-400 dark:text-base-600 size-8" 317 + > 318 + <path 319 + stroke-linecap="round" 320 + stroke-linejoin="round" 321 + d="m2.25 15.75 5.159-5.159a2.25 2.25 0 0 1 3.182 0l5.159 5.159m-1.5-1.5 1.409-1.409a2.25 2.25 0 0 1 3.182 0l2.909 2.909m-18 3.75h16.5a1.5 1.5 0 0 0 1.5-1.5V6a1.5 1.5 0 0 0-1.5-1.5H3.75A1.5 1.5 0 0 0 2.25 6v12a1.5 1.5 0 0 0 1.5 1.5Zm10.5-11.25h.008v.008h-.008V8.25Zm.375 0a.375.375 0 1 1-.75 0 .375.375 0 0 1 .75 0Z" 322 + /> 323 + </svg> 324 + </div> 325 + {/if} 326 + <!-- Hover overlay --> 327 + <div 328 + class={[ 329 + 'absolute inset-0 flex items-center justify-center rounded-xl bg-black/50 transition-opacity duration-200', 330 + isHoveringImage ? 'opacity-100' : 'opacity-0' 331 + ]} 332 + > 333 + <div class="text-center text-sm text-white"> 334 + <svg 335 + xmlns="http://www.w3.org/2000/svg" 336 + fill="none" 337 + viewBox="0 0 24 24" 338 + stroke-width="1.5" 339 + stroke="currentColor" 340 + class="mx-auto mb-1 size-6" 341 + > 342 + <path 343 + stroke-linecap="round" 344 + stroke-linejoin="round" 345 + d="M6.827 6.175A2.31 2.31 0 0 1 5.186 7.23c-.38.054-.757.112-1.134.175C2.999 7.58 2.25 8.507 2.25 9.574V18a2.25 2.25 0 0 0 2.25 2.25h15A2.25 2.25 0 0 0 21.75 18V9.574c0-1.067-.75-1.994-1.802-2.169a47.865 47.865 0 0 0-1.134-.175 2.31 2.31 0 0 1-1.64-1.055l-.822-1.316a2.192 2.192 0 0 0-1.736-1.039 48.774 48.774 0 0 0-5.232 0 2.192 2.192 0 0 0-1.736 1.039l-.821 1.316Z" 346 + /> 347 + <path 348 + stroke-linecap="round" 349 + stroke-linejoin="round" 350 + d="M16.5 12.75a4.5 4.5 0 1 1-9 0 4.5 4.5 0 0 1 9 0ZM18.75 10.5h.008v.008h-.008V10.5Z" 351 + /> 352 + </svg> 353 + <span class="font-medium">{item.cardData.image ? 'Change' : 'Add image'}</span> 354 + </div> 355 + </div> 356 + </button> 357 + {/if} 358 + </div> 359 + {/if}
+134 -74
src/lib/cards/core/LinkCard/LinkCard.svelte
··· 14 14 let did = getDidContext(); 15 15 </script> 16 16 17 - <div class="flex h-full flex-col justify-between p-4"> 18 - <div> 17 + {#if item.cardData.showBackgroundImage && item.cardData.image} 18 + <div class="relative flex h-full flex-col justify-end p-4"> 19 + <img 20 + class="absolute inset-0 -z-10 size-full object-cover" 21 + src={getImage(item.cardData, did)} 22 + alt="" 23 + /> 19 24 <div 20 - class="bg-base-100 border-base-300 accent:bg-accent-100/50 accent:border-accent-200 dark:border-base-800 dark:bg-base-900 mb-2 inline-flex size-8 items-center justify-center rounded-xl border" 21 - > 22 - {#if item.cardData.favicon && !faviconHasError} 23 - <img 24 - class="size-6 rounded-lg object-cover" 25 - onerror={() => (faviconHasError = true)} 26 - src={getImage(item.cardData, did, 'favicon')} 27 - alt="" 28 - /> 29 - {:else} 30 - <svg 31 - xmlns="http://www.w3.org/2000/svg" 32 - fill="none" 33 - viewBox="0 0 24 24" 34 - stroke-width="1.5" 35 - stroke="currentColor" 36 - class="size-4" 37 - > 38 - <path 39 - stroke-linecap="round" 40 - stroke-linejoin="round" 41 - d="M13.19 8.688a4.5 4.5 0 0 1 1.242 7.244l-4.5 4.5a4.5 4.5 0 0 1-6.364-6.364l1.757-1.757m13.35-.622 1.757-1.757a4.5 4.5 0 0 0-6.364-6.364l-4.5 4.5a4.5 4.5 0 0 0 1.242 7.244" 42 - /> 43 - </svg> 44 - {/if} 25 + class="from-base-50/90 via-base-50/40 dark:from-base-950/90 dark:via-base-950/40 absolute inset-0 -z-10 bg-linear-to-t to-transparent" 26 + ></div> 27 + <div class="text-accent-600 dark:text-accent-400 text-xs font-semibold"> 28 + {item.cardData.domain} 45 29 </div> 46 30 <div 47 31 class={[ ··· 51 35 > 52 36 {item.cardData.title} 53 37 </div> 54 - <!-- <div class="text-base-800 dark:text-base-100 mt-2 text-xs">{item.cardData.description}</div> --> 55 - <div 56 - class="text-accent-600 accent:text-accent-950 dark:text-accent-400 mt-2 text-xs font-semibold" 57 - > 58 - {item.cardData.domain} 59 - </div> 60 - </div> 61 - 62 - {#if browser && ((isMobile() && item.mobileH >= 8) || (!isMobile() && item.h >= 4)) && item.cardData.image} 63 - <img 64 - class="mb-2 aspect-2/1 w-full rounded-xl object-cover opacity-100 transition-opacity duration-100 starting:opacity-0" 65 - src={getImage(item.cardData, did)} 66 - alt="" 67 - /> 68 - {/if} 69 - {#if item.cardData.href && !isEditing} 70 - <a 71 - href={item.cardData.href} 72 - class="absolute inset-0 h-full w-full" 73 - target="_blank" 74 - rel="noopener noreferrer" 75 - use:qrOverlay={{ 76 - context: { 77 - title: item.cardData.title 78 - } 79 - }} 80 - > 81 - <span class="sr-only"> 82 - {item.cardData.hrefText ?? 'Learn more'} 83 - </span> 38 + {#if item.cardData.href && !isEditing} 39 + <a 40 + href={item.cardData.href} 41 + class="absolute inset-0 h-full w-full" 42 + target="_blank" 43 + rel="noopener noreferrer" 44 + use:qrOverlay={{ 45 + context: { 46 + title: item.cardData.title 47 + } 48 + }} 49 + > 50 + <span class="sr-only"> 51 + {item.cardData.hrefText ?? 'Learn more'} 52 + </span> 84 53 54 + <div 55 + class="bg-base-800/30 border-base-900/30 absolute top-2 right-2 rounded-full border p-1 text-white opacity-50 backdrop-blur-lg group-focus-within:opacity-100 group-hover:opacity-100" 56 + > 57 + <svg 58 + xmlns="http://www.w3.org/2000/svg" 59 + fill="none" 60 + viewBox="0 0 24 24" 61 + stroke-width="2.5" 62 + stroke="currentColor" 63 + class="size-4" 64 + > 65 + <path 66 + stroke-linecap="round" 67 + stroke-linejoin="round" 68 + d="m4.5 19.5 15-15m0 0H8.25m11.25 0v11.25" 69 + /> 70 + </svg> 71 + </div> 72 + </a> 73 + {/if} 74 + </div> 75 + {:else} 76 + <div class="flex h-full flex-col justify-between p-4"> 77 + <div> 85 78 <div 86 - class="bg-base-800/30 border-base-900/30 absolute top-2 right-2 rounded-full border p-1 text-white opacity-50 backdrop-blur-lg group-focus-within:opacity-100 group-hover:opacity-100" 79 + class="bg-base-100 border-base-300 accent:bg-accent-100/50 accent:border-accent-200 dark:border-base-800 dark:bg-base-900 mb-2 inline-flex size-8 items-center justify-center rounded-xl border" 87 80 > 88 - <svg 89 - xmlns="http://www.w3.org/2000/svg" 90 - fill="none" 91 - viewBox="0 0 24 24" 92 - stroke-width="2.5" 93 - stroke="currentColor" 94 - class="size-4" 95 - > 96 - <path 97 - stroke-linecap="round" 98 - stroke-linejoin="round" 99 - d="m4.5 19.5 15-15m0 0H8.25m11.25 0v11.25" 81 + {#if item.cardData.favicon && !faviconHasError} 82 + <img 83 + class="size-6 rounded-lg object-cover" 84 + onerror={() => (faviconHasError = true)} 85 + src={getImage(item.cardData, did, 'favicon')} 86 + alt="" 100 87 /> 101 - </svg> 88 + {:else} 89 + <svg 90 + xmlns="http://www.w3.org/2000/svg" 91 + fill="none" 92 + viewBox="0 0 24 24" 93 + stroke-width="1.5" 94 + stroke="currentColor" 95 + class="size-4" 96 + > 97 + <path 98 + stroke-linecap="round" 99 + stroke-linejoin="round" 100 + d="M13.19 8.688a4.5 4.5 0 0 1 1.242 7.244l-4.5 4.5a4.5 4.5 0 0 1-6.364-6.364l1.757-1.757m13.35-.622 1.757-1.757a4.5 4.5 0 0 0-6.364-6.364l-4.5 4.5a4.5 4.5 0 0 0 1.242 7.244" 101 + /> 102 + </svg> 103 + {/if} 102 104 </div> 103 - </a> 104 - {/if} 105 - </div> 105 + <div 106 + class={[ 107 + 'text-base-900 dark:text-base-50 text-lg font-bold', 108 + (isMobile() && item.mobileH < 8) || (!isMobile() && item.h < 4) ? 'line-clamp-2' : '' 109 + ]} 110 + > 111 + {item.cardData.title} 112 + </div> 113 + <!-- <div class="text-base-800 dark:text-base-100 mt-2 text-xs">{item.cardData.description}</div> --> 114 + <div 115 + class="text-accent-600 accent:text-accent-950 dark:text-accent-400 mt-2 text-xs font-semibold" 116 + > 117 + {item.cardData.domain} 118 + </div> 119 + </div> 120 + 121 + {#if browser && ((isMobile() && item.mobileH >= 8) || (!isMobile() && item.h >= 4)) && item.cardData.image} 122 + <img 123 + class="mb-2 aspect-2/1 w-full rounded-xl object-cover opacity-100 transition-opacity duration-100 starting:opacity-0" 124 + src={getImage(item.cardData, did)} 125 + alt="" 126 + /> 127 + {/if} 128 + {#if item.cardData.href && !isEditing} 129 + <a 130 + href={item.cardData.href} 131 + class="absolute inset-0 h-full w-full" 132 + target="_blank" 133 + rel="noopener noreferrer" 134 + use:qrOverlay={{ 135 + context: { 136 + title: item.cardData.title 137 + } 138 + }} 139 + > 140 + <span class="sr-only"> 141 + {item.cardData.hrefText ?? 'Learn more'} 142 + </span> 143 + 144 + <div 145 + class="bg-base-800/30 border-base-900/30 absolute top-2 right-2 rounded-full border p-1 text-white opacity-50 backdrop-blur-lg group-focus-within:opacity-100 group-hover:opacity-100" 146 + > 147 + <svg 148 + xmlns="http://www.w3.org/2000/svg" 149 + fill="none" 150 + viewBox="0 0 24 24" 151 + stroke-width="2.5" 152 + stroke="currentColor" 153 + class="size-4" 154 + > 155 + <path 156 + stroke-linecap="round" 157 + stroke-linejoin="round" 158 + d="m4.5 19.5 15-15m0 0H8.25m11.25 0v11.25" 159 + /> 160 + </svg> 161 + </div> 162 + </a> 163 + {/if} 164 + </div> 165 + {/if}
+19 -1
src/lib/cards/core/LinkCard/LinkCardSettings.svelte
··· 1 1 <script lang="ts"> 2 2 import { validateLink } from '$lib/helper'; 3 3 import type { Item } from '$lib/types'; 4 - import { Button, Input, toast } from '@foxui/core'; 4 + import { Button, Checkbox, Input, Label, toast } from '@foxui/core'; 5 5 6 6 let { item, onclose }: { item: Item; onclose: () => void } = $props(); 7 7 ··· 48 48 <path stroke-linecap="round" stroke-linejoin="round" d="m4.5 12.75 6 6 9-13.5" /> 49 49 </svg> 50 50 </Button> 51 + <div class="flex items-center space-x- mt-4"> 52 + <Checkbox 53 + bind:checked={ 54 + () => Boolean(item.cardData.showBackgroundImage), 55 + (val) => (item.cardData.showBackgroundImage = val) 56 + } 57 + id="show-bg-image" 58 + aria-labelledby="show-bg-image-label" 59 + variant="secondary" 60 + /> 61 + <Label 62 + id="show-bg-image-label" 63 + for="show-bg-image" 64 + class="text-sm leading-none ml-2 font-medium peer-disabled:cursor-not-allowed peer-disabled:opacity-70" 65 + > 66 + Show background image 67 + </Label> 68 + </div>
-4
src/lib/cards/social/SembleCollectionCard/index.ts
··· 46 46 listRecords({ did, collection: 'network.cosmik.card', limit: 0 }).catch(() => []) 47 47 ]); 48 48 49 - console.log(allLinks); 50 - 51 49 if (!collection) return undefined; 52 50 53 51 const linkedCardUris = new Set( ··· 55 53 .filter((link: any) => link.value.collection?.uri === collectionUri) 56 54 .map((link: any) => link.value.card?.uri) 57 55 ); 58 - 59 - console.log(linkedCardUris); 60 56 61 57 const cards: SembleCard[] = allCards 62 58 .filter((card: any) => linkedCardUris.has(card.uri))