NuxtにLazyLoadを入れてみた
2019/3/5 追記
LazyLoadを導入しましたが、サイト速度が向上したかに関して、現状測定していません。 Page Speed Insight の点数が向上したという結果のみ得ています。 そのため、実際にパフォーマンス向上に貢献できているかは不明です。
Webパフォーマンスの振り返り 2018 - Webパフォーマンスについて
上記のtakehora様の記事にあるように、<img decoding ="async">
を用いる方がいいのではないかと思います。
(ただ、そこに関しても自身で測定できてないので、全体のパフォーマンス測定したら追記します。)
経緯
画像がいっぱい表示されるサイトをNuxt&SSRで、作っている。 なので、画像を読み込む時間が結構かかって困ってた。 LazyLoadすればいいことはわかってたけど、SEOへの影響がよくわからなくて、プロダクト的にNGだった...
しかし、Googleが11月にこのような実装方法を出してくれたので、Goサインがでた! developers.google.com
やったこと
まず、VueLazyLoadがめっちゃ便利なので、それをインストール
import Vue from 'vue'; import VueLazyload from 'vue-lazyload'; Vue.use(VueLazyload, { preLoad: 1.1, attempt: 1, observer: true, observerOptions: { rootMargin: '0px', threshold: 0.1 } });
上記のように、pluginファイル作って、nuxt.config.js に ssr: false
にして、追記
observerをtrueにすることが必要で、そうすると、Googleの解説記事にある ブラウザnativeの IntersectionObserver を使ってくれる。
ただ、これだけだとIEとか動かないので、app.htmlに、直接polyfillを追加した。
<script async src="https://cdn.polyfill.io/v2/polyfill.min.js?features=IntersectionObserver" ></script>
困ったこと
初期表示時は、SSRしたもの画像が表示されるので、vue-lazyloadのマニュアル通りに、初期画像を設定しても上手くいかなかった。 なので、下のようなコンポーネント作って、Lazyload使うときは、常にこれ使うようにしたらいい感じになった!
<template lang="pug"> img(src="~assets/images/background/pixel.png" :alt="alt" v-lazy="src") </template> <script> export default { props: { src: { type: String, required: true }, alt: { type: String, required: true } } }; </script>
LazyLoadめっちゃ便利!
追記
下記の記事を見つけた。
画像の非同期デコーディング
Webパフォーマンスの振り返り 2018 - Webパフォーマンスについて
<img decoding ="async">
とつけると、画像デコーディングが非同期で行われ、ページ表示まで早くなるらしい。
自分の環境(通信速度が早い)だと、LazyLoadした時と比べて、初期表示とかの体感では変わらなかった。
むしろ、LazyLoadしてると、表示後画像が出るまでにどうしても遅れる(特に画像が大きい時)ので、しない方が体感としては良い。
一方、audit(lighthouse)で試してみたら、点数がLazyLoadと比較して、明らかに下がっていた。
ということは、page speed insight でも点数は下がるはずで、これがSEOとかに影響与えないか(多分ないはずだけど)不安。
ただ、ユーザ体験を考えると、LazyLoadないほうがいいのかもと思った。
あとは、コストの問題だなって感じ。
大規模にならないとあんまり変わんないけど。
将来は、LazyLoadがブラウザ標準になるっぽいから、<img decoding='async' lazyload='on'>
という書き方がデフォルトになっていくのかも。