Improved image lazy loader
This commit is contained in:
parent
873be1849f
commit
c6694aef8c
@ -2,4 +2,4 @@ component AnimeGrid(animeList []*arn.Anime)
|
|||||||
.anime-grid
|
.anime-grid
|
||||||
each anime in animeList
|
each anime in animeList
|
||||||
a.anime-grid-cell.ajax(href="/anime/" + toString(anime.ID))
|
a.anime-grid-cell.ajax(href="/anime/" + toString(anime.ID))
|
||||||
img.anime-grid-image(src=anime.Image.Small, alt=anime.Title.Romaji, title=anime.Title.Romaji + " (" + toString(anime.Rating.Overall) + ")")
|
img.anime-grid-image.lazy(data-src=anime.Image.Small, alt=anime.Title.Romaji, title=anime.Title.Romaji + " (" + toString(anime.Rating.Overall) + ")")
|
@ -4,7 +4,7 @@ component Avatar(user *arn.User)
|
|||||||
|
|
||||||
component AvatarNoLink(user *arn.User)
|
component AvatarNoLink(user *arn.User)
|
||||||
if user.HasAvatar()
|
if user.HasAvatar()
|
||||||
img.user-image(src=user.SmallAvatar(), alt=user.Nick)
|
img.user-image.lazy(data-src=user.SmallAvatar(), alt=user.Nick)
|
||||||
else
|
else
|
||||||
SVGAvatar
|
SVGAvatar
|
||||||
|
|
||||||
|
@ -57,7 +57,7 @@ component Profile(viewUser *arn.User, user *arn.User, animeList *arn.AnimeList,
|
|||||||
else
|
else
|
||||||
each item in animeList.Items
|
each item in animeList.Items
|
||||||
a.profile-watching-list-item.ajax(href=item.Anime().Link(), title=item.Anime().Title.Canonical + " (" + toString(item.Episodes) + " / " + arn.EpisodesToString(item.Anime().EpisodeCount) + ")")
|
a.profile-watching-list-item.ajax(href=item.Anime().Link(), title=item.Anime().Title.Canonical + " (" + toString(item.Episodes) + " / " + arn.EpisodesToString(item.Anime().EpisodeCount) + ")")
|
||||||
img.anime-cover-image.profile-watching-list-item-image(src=item.Anime().Image.Tiny, alt=item.Anime().Title.Canonical)
|
img.anime-cover-image.profile-watching-list-item-image.lazy(data-src=item.Anime().Image.Tiny, alt=item.Anime().Title.Canonical)
|
||||||
|
|
||||||
.profile-category.mountable
|
.profile-category.mountable
|
||||||
h3
|
h3
|
||||||
|
@ -87,39 +87,34 @@ export class AnimeNotifier {
|
|||||||
actions[actionName](this, element, e)
|
actions[actionName](this, element, e)
|
||||||
})
|
})
|
||||||
|
|
||||||
|
// Use "action assigned" flag instead of removing the class.
|
||||||
|
// This will make sure that DOM diffs which restore the class name
|
||||||
|
// will not assign the action multiple times to the same element.
|
||||||
element["action assigned"] = true
|
element["action assigned"] = true
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
lazyLoadImages() {
|
lazyLoadImages() {
|
||||||
for(let element of findAll("user-image")) {
|
for(let element of findAll("lazy")) {
|
||||||
this.lazyLoadImage(element as HTMLImageElement)
|
|
||||||
}
|
|
||||||
|
|
||||||
for(let element of findAll("anime-cover-image")) {
|
|
||||||
this.lazyLoadImage(element as HTMLImageElement)
|
this.lazyLoadImage(element as HTMLImageElement)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
lazyLoadImage(img: HTMLImageElement) {
|
lazyLoadImage(img: HTMLImageElement) {
|
||||||
// Prevent browser from loading it instantly
|
|
||||||
img["original source"] = img.src
|
|
||||||
img.src = ""
|
|
||||||
|
|
||||||
// Once the image becomes visible, load it
|
// Once the image becomes visible, load it
|
||||||
img["became visible"] = () => {
|
img["became visible"] = () => {
|
||||||
img.src = img["original source"]
|
img.src = img.dataset.src
|
||||||
|
|
||||||
if(img.naturalWidth === 0) {
|
if(img.naturalWidth === 0) {
|
||||||
img.onload = function() {
|
img.onload = function() {
|
||||||
this.classList.add("user-image-found")
|
this.classList.add("image-found")
|
||||||
}
|
}
|
||||||
|
|
||||||
img.onerror = function() {
|
img.onerror = function() {
|
||||||
this.classList.add("user-image-not-found")
|
this.classList.add("image-not-found")
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
img.classList.add("user-image-found")
|
img.classList.add("image-found")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -32,6 +32,7 @@ mixin grid-image
|
|||||||
height 100%
|
height 100%
|
||||||
border-radius 3px
|
border-radius 3px
|
||||||
object-fit cover
|
object-fit cover
|
||||||
|
default-transition
|
||||||
|
|
||||||
mixin grid-icon
|
mixin grid-icon
|
||||||
font-size 2.5rem
|
font-size 2.5rem
|
||||||
|
11
styles/images.scarlet
Normal file
11
styles/images.scarlet
Normal file
@ -0,0 +1,11 @@
|
|||||||
|
.lazy
|
||||||
|
visibility hidden
|
||||||
|
opacity 0
|
||||||
|
|
||||||
|
.image-found
|
||||||
|
visibility visible
|
||||||
|
opacity 1 !important
|
||||||
|
|
||||||
|
.image-not-found
|
||||||
|
visibility hidden
|
||||||
|
opacity 0 !important
|
@ -4,13 +4,6 @@
|
|||||||
height avatar-size
|
height avatar-size
|
||||||
border-radius 100%
|
border-radius 100%
|
||||||
object-fit cover
|
object-fit cover
|
||||||
opacity 0
|
|
||||||
default-transition
|
default-transition
|
||||||
:hover
|
:hover
|
||||||
box-shadow outline-shadow-heavy
|
box-shadow outline-shadow-heavy
|
||||||
|
|
||||||
.user-image-found
|
|
||||||
opacity 1 !important
|
|
||||||
|
|
||||||
.user-image-not-found
|
|
||||||
opacity 0 !important
|
|
Loading…
Reference in New Issue
Block a user