フロントエンドでなんとかがんばっていくブログ

JavaScript【Vue.js】v-forでタグをネストして出力する方法

2020/11/14

v-forで配列をリストレンダリングする際に、<ul>タグを途中で分割して出力したい場合の方法です。

リストを分割するというのはhtmlの構造上正しくない場合もありますが、デザインによっては分割せざるを得ない場合があります。

やりたいこと

これを
■ before

<ul class="lists">
  <li class="list></li>
  <li class="list></li>
  <li class="list></li>
  <li class="list></li>
 </ul>


こうしたい
■ after

<ul class="lists">
  <li class="list></li>
  <li class="list></li>
 </ul>
 <ul class="lists">
  <li class="list></li>
  <li class="list></li>
 </ul>


v-forの基本的な使い方

まずbeforeの実装は特に問題ありません。

一次元配列postsがあったとして、

new Vue({
  el: "#app",
  data: {
    posts: [
      0, 1, 2, 3
    ]
  },
  template: `
    <div>
      <ul class="lists">
        <li v-for="(post, index) in posts" :key="index" class="list">{{post}}</li>
      </ul>
    </div>
  `
 })


v-if や v-show を使ってみる

v-for のインデックスを用いて v-if や v-show でタグの出力を制御してみます。



・・・・・難しいです。

もっとスマートなやり方を模索してみます。

配列postsを二次元配列にする

new Vue({
  el: "#app",
  data: {
    posts: [
      [0, 1],
      [2, 3]
     ]
    },
    template: `
     <div>
      <ul v-for="(items, index) in posts" :key="index">
       <li v-for="(post, index) in items" :key="index">{{post}}</li>
      </ul>
     </div>
    `
  })



二次元配列にすることにより、html側でv-forをネストすると「after」の結果が得られました。

最後に

javascript側では、一次元配列を二次元配列にする or 配列を生成する段階で二次元配列にする、という処理が必要になりますが、こちらの方が明らかにスマートに実装できます。

v-if や v-show も便利ですが、冗長な処理になりそうだったら少し発想を変えることで簡単に実装できることもあるかもしれません。