画面外のときは描画しないようにし、無限ローディング時の性能改善したときの備忘録。
vue-observe-visibilityを使って、画面内かを検知して表示を切り替えてみた。
インストール
まずはインストール。
$ npm install --save vue-observe-visibility # IEなどIntersection Observer APIに対応してないブラウザ用のpolyfill $ npm install --save intersection-observer
プラグインの作成
plugins/observe-visibility.ts
を作成
// polyfillは最初に読み込む require('intersection-observer'); import Vue from "vue"; import VueObserveVisibility from "vue-observe-visibility"; Vue.use(VueObserveVisibility);
nuxt.config.tsに追加
作ったpluginを追加する
import { Configuration } from "@nuxt/types"; const config: Configuration = { plugins: [ { src: "~/plugins/observe-visibility", ssr: false }, ], }
使い方
使い方はこんな感じ。v-observe-visibility
ディレクティブで設定する。
callback
には、画面内かの変数(isVisible
)などを受け取るコールバックを指定once
には、初めて画面内になったら監視をやめるかどうかを指定intersection
には、検出に関する設定を指定。
<template> <section v-observe-visibility="{ callback: visibilityChanged, once: false, intersection: { rootMargin: '100px' } }" > <div v-if="isInview"><!-- 略 --></div> </section> </template> <script lang="ts"> import { Component, Vue } from "nuxt-property-decorator"; @Component export default class RankingMiniPanel extends Vue { private isInview: boolean = false; // **************************** // * Method // **************************** private visibilityChanged(isVisible, entry) { if (isVisible) this.isInview = true; } } </script>
コールバックは、マウント時を含めて、画面の中か外かが切り替わるときに呼ばれる。
なので、マウント時に画面外だと、isVisbleがfalseで呼ばれ、
画面内に入ると、isVisbleがtrueで呼ばれる。
コールバック内で、画面の中にあるかを変数(isInview
)に保持しておき、
それによって描画する内容を変えるなどするといい感じになる。
画面内になったときにアニメーションさせるならvue-inviewがよいかも
今回は表示/非表示の切り替えのために検知したかったけど、
パラドックスのようなアニメーションをさせたい場合はvue-inviewがよさそう。
animate.cssと連動させて、いろいろできるっぽい。
以上!!