ホームページ >ウェブフロントエンド >jsチュートリアル >Vue.js で折りたたみ可能なツリー メニューを実装する方法

Vue.js で折りたたみ可能なツリー メニューを実装する方法

亚连
亚连オリジナル
2018-06-15 16:42:164602ブラウズ

この記事では、再帰コンポーネントを効果的に使用する方法を説明し、展開/折りたたみ可能なツリー メニューを構築することを段階的に説明します。この記事では、Vue.js の再帰コンポーネントを使用して折りたたみ可能なツリー メニューを実装する方法を共有します。必要な友達はそれを参照してください

Vue.js では、再帰コンポーネントは次のようにそれ自体を呼び出します。

Vue.component('recursive-component', {
  template: `<!--Invoking myself!-->
       <recursive-component></recursive-component>`
 });

再帰コンポーネントは、コメント、ネストされたメニュー、または基本的には、内容は異なっていても同じタイプの親と子を表示するためにブログでよく使用されます。例:

次に、再帰コンポーネントを効果的に使用する方法を示し、展開/折りたたみ可能なツリー メニューを構築していきます。

データ構造

ツリー UI の再帰コンポーネントは、再帰データ構造の視覚的表現になります。このチュートリアルでは、各ノードがオブジェクトであるツリー構造を使用します:

ラベル プロパティ。

子ノードがある場合、nodes プロパティは 1 つ以上のノードの配列プロパティです。

すべてのツリー構造と同様に、ルート ノードが必要ですが、無限に深くすることができます。

let tree = {
  label: &#39;root&#39;,
  nodes: [
   {
    label: &#39;item1&#39;,
    nodes: [
     {
      label: &#39;item1.1&#39;
     },
     {
      label: &#39;item1.2&#39;,
      nodes: [
       {
        label: &#39;item1.2.1&#39;
       }
      ]
     }
    ]
   }, 
   {
    label: &#39;item2&#39; 
   }
  ]
 }

再帰コンポーネント

TreeMenu というデータ構造を表示する再帰コンポーネントを作成しましょう。現在のノードのラベルのみを表示し、それ自体を呼び出して子ノードを表示します。ファイル名: TreeMenu.vue、内容は次のとおりです:

<template>
  <p class="tree-menu">
   <p>{{ label }}</p>
   <tree-menu 
    v-for="node in nodes" 
    :nodes="node.nodes" 
    :label="node.label"
   >
   </tree-menu>
  </p>
 </template>
 <script>
  export default { 
   props: [ &#39;label&#39;, &#39;nodes&#39; ],
   name: &#39;tree-menu&#39;
  }
 </script>

コンポーネントを再帰的に使用する場合は、最初に Vue.component のグローバル定義を作成するか、それに name 属性を与える必要があります。そうしないと、子コンポーネントはそれ以上呼び出すことができなくなり、未定義の「未定義コンポーネント エラー」エラー メッセージが表示されます。

基本イベント

他の再帰関数と同様に、再帰を終了するには基本イベントが必要です。そうしないと、レンダリングが無限に続き、最終的にはスタック オーバーフローが発生します。

ツリーメニューでは、子のないノードに到達したときに再帰を停止したいと考えています。これは v-if を介して実行できますが、 v-for を使用することを選択すると、暗黙的にそれが実装されます。ノード配列にそれ以上の定義がない場合は、ツリーメニュー コンポーネントが呼び出されます。 template.vue ファイルは次のとおりです:

<template>
  <p class="tree-menu">
   ...
   <!--If `nodes` is undefined this will not render-->
   <tree-menu v-for="node in nodes"></tree-menu>
 </template>

Usage

このコンポーネントを今どのように使用しますか?まず、データ属性と定義されたツリーメニュー コンポーネントを含むデータ構造を持つ Vue インスタンスを宣言します。 app.js ファイルは次のようになります:

import TreeMenu from &#39;./TreeMenu.vue&#39;
 let tree = {
  ...
 }
 new Vue({
  el: &#39;#app&#39;,
  data: {
   tree
  },
  components: {
   TreeMenu
  }
 })

データ構造にはルート ノードがあることを思い出してください。ルート ノード属性を小道具に使用して、メイン テンプレートの TreeMenu コンポーネントの再帰呼び出しを開始します。

<p id="app">
  <tree-menu :label="tree.label" :nodes="tree.nodes"></tree-menu>
 </p>

現在は次のようになります:

正しい姿勢

「深さ」を視覚的に識別しますサブコンポーネントの「」は、ユーザーが UI からデータ構造を把握できるようにするのに適しています。これを実現するには、各レベルで子ノードをインデントします。

これは、TreeMenu を通じて深度プロパティ定義を追加することで実現されます。この値を使用して、インライン スタイルを動的に変換にバインドします。transform:translate の CSS ルールが各ノードのラベルに使用され、インデントが作成されます。 template.vue は次のように変更されます**:**

<template>
  <p class="tree-menu">
   <p :style="indent">{{ label }}</p>
   <tree-menu 
    v-for="node in nodes" 
    :nodes="node.nodes" 
    :label="node.label"
    :depth="depth + 1"
   >
   </tree-menu>
  </p>
 </template>
 <script>
  export default { 
   props: [ &#39;label&#39;, &#39;nodes&#39;, &#39;depth&#39; ],
   name: &#39;tree-menu&#39;,
   computed: {
    indent() {
     return { transform: `translate(${this.depth * 50}px)` }
    }
   }
  }
 </script>

Depth 属性は、メイン テンプレートでは 0 から始まります。上記のコンポーネント テンプレートでは、この値が子ノードに渡されるたびに増加することがわかります。

<p id="app">
  <tree-menu 
   :label="tree.label" 
   :nodes="tree.nodes"
   :depth="0"
  ></tree-menu>
 </p>

注: 深さの値が文字列ではなく JavaScript の数値型であることを確認するために、必ず深さの値を v バインドしてください。

展開/折りたたみ

再帰的なデータ構造は大きくなる可能性があるため、それらを表示するための UI の優れたトリックは、ユーザーが必要に応じてノードを展開または折りたたむことができるように、ルート ノードを除くすべてのノードを非表示にすることです。

これを行うには、ローカル プロパティ showChildren を追加します。値が False の場合、子ノードはレンダリングされません。この値はノードをクリックすることで切り替える必要があるため、クリック イベント リスナー メソッド toggleChildren を使用して管理する必要があります。 template.vue ファイルは次のように変更されます**:**

<template>
  <p class="tree-menu">
   <p :style="indent" @click="toggleChildren">{{ label }}</p>
   <tree-menu 
    v-if="showChildren"
    v-for="node in nodes" 
    :nodes="node.nodes" 
    :label="node.label"
    :depth="depth + 1"
   >
   </tree-menu>
  </p>
 </template>
 <script>
  export default { 
   props: [ &#39;label&#39;, &#39;nodes&#39;, &#39;depth&#39; ],
   data() {
    return { showChildren: false }
   },
   name: &#39;tree-menu&#39;,
   computed: {
    indent() {
     return { transform: `translate(${this.depth * 50}px)` }
    }
   },
   methods: {
    toggleChildren() {
     this.showChildren = !this.showChildren;
    }
   }
  }
 </script>

Summary

このようにして、作業ツリー メニューが完成しました。最後の仕上げとして、プラス/マイナスのアイコンを追加して、UI をより見やすくすることができます。また、オリジナルの showChildren に優れたフォントとコンピューティング機能を追加しました。

CodePen (https://codepen.io/anthonygore/pen/PJKNqa) にアクセスして、実装方法を確認してください。

以上は皆さんのためにまとめたもので、今後皆さんのお役に立てれば幸いです。

関連記事:

Vue-Router2 での複数のルーティング実装の実装

Vuejs 単一ファイル コンポーネント (詳細なチュートリアル)

vue-lazyload での画像遅延読み込みプラグインの使用

以上がVue.js で折りたたみ可能なツリー メニューを実装する方法の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

声明:
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。