揚げログ

Karaage(krgpi)の技術開発関連のブログです

store.stateの読み込みは遅延する - Nuxt.js

概要

Nuxt.jsでvuex storeでデータのCRUDを行ってる状況を想定する。

すでにstate.userには他のページか親コンポーネントでの操作(dispatch, commit)で、undefinedではない何らかのObjectが入っている前提とします。

ダメなコード

このコードは動いたり動かなかったりします。(stateの読み込み速度によって結果が変わってしまう)

$store.getters を使っても、同様の症状になると思います。

<template>
    <v-container>
         <p>{{user}}</p>
    </v-container>
<template>

<script>
export default {
  beforeCreated() {
    this.user = this.$store.state.user;
  },
  data(){
    return {
      user: Object
    }
}
</script>

→ Error! user is undefined

ちゃんと動くコード

stateのLoad状況によって、表示を切り替え、undefinedエラーを防ぎます。

<template>
    <v-container>
         <p>{{user}}</p>
    </v-container>
<template>

<script>
export default {
  computed: {
    user() {
      const user = this.$store.state.user
        if (!!user) {
         return user;
      }
    else {
      return {};
    }
  }
}
</script>

SSRで使えないライブラリをSSRで使う - Nuxt.js

状況

Nuxt.jsでwebサービス開発をしていると、SSRで使えないライブラリをSSRで使いたい時がある。例えば、

  • DOMにアクセスするライブラリ

(SSRで使うと毎回orページリロード時にdocument is not defined, window is not definedのようなエラーが発生する)

回避方法

ここでは、vue-grid-layoutというライブラリを例にする。

エラーが出る例

<template>
  <v-container>
    <grid-layout>
     ...
    </grid-layout>
  </v-container>
</template>

<script>
import VueGridLayout from "vue-grid-layout"
...
export default {
...
}
</script>

成功例

<template>
  <v-container>
    <client-only>
        <grid-layout>
     ...
        </grid-layout>
    </client-only>
  </v-container>
</template>

<script>
// import VueGridLayout from "vue-grid-layout" ここでインポートしない
export default {
    ...
    created(){
           if (process.client) { //clientでの実行ならば
              require("vue-grid-layout");
          }
    }
}

まとめ

  1. ライブラリを使うコンポーネントのhtmlタグ部分を、 <client-only> で囲う

参考: https://ja.nuxtjs.org/api/components-client-only/

  1. ライブラリのインポートを created() で行う

createdはVueインスタンスが生成された直後に実行される。これをasyncDataとかでやると、まだDOMがないのでエラー(document is not defined)になる。

参考: http://lab.astamuse.co.jp/entry/2019/05/29/114500

  1. if (process.client) {} で囲む

created()はサーバー側・クライアント側両方で実行されるが、このif文を入れておくことで、確実にサーバー側での実行をブロックできる。

CSSアニメーション、使っていきたい

Webページを作るとき、画像でなくてもCSSで描ける記号やマークは、軽量化のためにCSSで書きたいと思っている。ブラウザのCSSレンダリングエンジンを有効活用でき、画像をダウンロードする無駄な通信を減らせる。

Googleのサイト評価サービスである「PageSpeed Insights」では、初期ロードの速さがスコアに大きく影響する。

PageSpeed Insights

サイト作成側としても、無駄なアセットが減り管理コストが低下する。当然コードベースなのでGitでデザイン変更の管理が出来ることも、メリットとして特筆すべきであろう。

予てより、github.ioにhexoを使って構築していた頃の私のブログは、CSSによるヘッダーデザインを採用していた。

f:id:krgpi:20200120235805p:plain
CSSで描画したタイル状の背景(jpg)

これにより、仮にYouTubeを見過ぎて通信制限になっていても、ヘッダー画像のロードを待機することなく、ページ全体が描画される。

このように、私のサイトでは積極的にCSSによるデザインを使ってきた。また、今後もCSSによる更に高度なデザインを作っていきたいのと同時に、動きのあるCSSにも触れていきたいと考えている。


CSSアニメーションとは

  • あるCSSのスタイル設定を別の設定へ遷移させる
  • アニメーションは2種類の要素で構成される
    • アニメーションについての記述するスタイル
    • アニメーションの始点と終点のスタイルを示すキーフレーム(通過点のスタイルも示すことができる)

JSのアニメーションに比べた利点

  • 単純なアニメーションには使いやすい
  • レンダリングエンジンのパフォーマンスを可能な限り滑らかに保てる(自動でフレームが省略されたり)
  • ブラウザはアニメーションの流れを制御してパフォーマンスと効率を最適化する

出典: animation - CSS: カスケーディングスタイルシート | MDN https://developer.mozilla.org/ja/docs/Web/CSS/animation


バイト先のエンジニアが作ってたCSSアニメーションは、もうもはや動画作品の域に達していて、凄すぎてもはや感動してしまった。

私としては、今後、自身の手がけた様々なことについて扱う、ポートフォリオのようなwebページを作りたいと考えており、そこでのデザインの一部として効果的にCSSを使っていきたいと思った。