iOS client for Grain grain.social
ios photography atproto
7
fork

Configure Feed

Select the types of activity you want to include in your feed.

refactor: simplify story loading placeholder to sharp thumb only

Drop the .blur(radius: 20) modifier and the ProgressView spinner from
the LazyImage placeholder. The thumb CDN image is a high-enough
resolution that it reads as a clean progressive-enhancement step before
the fullsize arrives — the blur and spinner just added noise on top of
it. With the blur modifier gone, there's no composite-filter race on
first render, so the clear→blurred→sharp flash is gone as well.

authored by

Hima Aramona and committed by
Chad Miller
939a732b b463e1a8

+15 -31
+15 -31
Grain/Views/Stories/StoryViewer.swift
··· 438 438 } 439 439 } 440 440 } else { 441 - ZStack { 442 - if let thumbURL = URL(string: story.thumb), 443 - let cachedThumb = ImagePipeline.shared.cache 444 - .cachedImage(for: ImageRequest(url: thumbURL))?.image 445 - { 446 - Image(uiImage: cachedThumb) 447 - .resizable() 448 - .aspectRatio(story.aspectRatio.ratio, contentMode: .fit) 449 - .blur(radius: 20) 450 - .clipped() 451 - // .overlay(alignment: .topLeading) { 452 - // // DEBUG: yellow = thumb sync-pulled from memory cache 453 - // Color.yellow.opacity(0.35).ignoresSafeArea() 454 - // Text("thumb · cache").font(.caption2.bold()).padding(6).background(.black.opacity(0.5)).foregroundStyle(.white).padding(8) 455 - // } 456 - } else { 457 - LazyImage(url: URL(string: story.thumb)) { thumbState in 458 - if let thumb = thumbState.image { 459 - thumb 460 - .resizable() 461 - .aspectRatio(story.aspectRatio.ratio, contentMode: .fit) 462 - .blur(radius: 20) 463 - .clipped() 464 - // .overlay(alignment: .topLeading) { 465 - // // DEBUG: red = thumb from network (cache miss) 466 - // Color.red.opacity(0.35).ignoresSafeArea() 467 - // Text("thumb · network").font(.caption2.bold()).padding(6).background(.black.opacity(0.5)).foregroundStyle(.white).padding(8) 468 - // } 469 - } 441 + if let thumbURL = URL(string: story.thumb), 442 + let cachedThumb = ImagePipeline.shared.cache 443 + .cachedImage(for: ImageRequest(url: thumbURL))?.image 444 + { 445 + Image(uiImage: cachedThumb) 446 + .resizable() 447 + .aspectRatio(story.aspectRatio.ratio, contentMode: .fit) 448 + .clipped() 449 + } else { 450 + LazyImage(url: URL(string: story.thumb)) { thumbState in 451 + if let thumb = thumbState.image { 452 + thumb 453 + .resizable() 454 + .aspectRatio(story.aspectRatio.ratio, contentMode: .fit) 455 + .clipped() 470 456 } 471 457 } 472 - ProgressView() 473 - .tint(.white) 474 458 } 475 459 } 476 460 }