親子コンポーネントの通信を解決するための3つのVueスロット

親子コンポーネントの通信を解決するための3つのVueスロット

序文

スロットは Vue の非常に重要な部分と言えます。学習と実践の過程で、コンポーネントをスロットと一緒に使用すると、パフォーマンスが向上することがわかりました。より多くの時間、より便利になるでしょう。

今日は、Vue の 3 種類のスロット、デフォルト スロット、名前付きスロット、スコープ スロットを紹介します。

環境の準備

まず、全員が確認できるように初期環境を設定しましょう。このスロットについて段階的に説明しましょう。

これら 3 種類のデータをそれぞれレンダリングするには、カテゴリ コンポーネントを記述するだけです。

画像-20211120150949138

カテゴリコンポーネント

<テンプレート>
  <div class="カテゴリ">
    <h1>{{タイトル}}</h1>
    <ul>
      <li 
      v-for="(item,index) in listData"
      :key="index">{{item}}</li>
    </ul>
  </div>
</テンプレート>
<スクリプト>
エクスポートデフォルト{
  小道具: {
    リストデータ:配列、
    タイトル: 文字列
  }
}
</スクリプト>
<スタイルスコープ>
。カテゴリ{
  幅: 200ピクセル;
  高さ: 300px;
  背景色:ピンク;
}
</スタイル>

アプリのコンポーネント

<テンプレート>
  <div id="アプリ">
    <Category :listData="ゲーム" :title="'ゲーム'" />
    <Category :listData="映画" :title="'映画'" />
    <Category :listData="食品" :title="'食品'" />
  </div>
</テンプレート>
<スクリプト>
'./components/Category.vue' からカテゴリーをインポートします。
エクスポートデフォルト{
  名前: 'アプリ'、
  コンポーネント:
    カテゴリ
  },
  データ () {
    戻る {
      ゲーム:['クロスファイア','QQスピード','ロックキングダム'],
      映画:[『こんにちは、李華英』、『青春』、『つかの間の時間』]、
      食べ物:['邵陽米麺'、'長沙茶'、'重慶火鍋']
    }
  }
}
</スクリプト>
<スタイル>
#アプリ {
  フォントファミリー: Avenir、Helvetica、Arial、sans-serif;
  -webkit-font-smoothing: アンチエイリアス;
  -moz-osx-font-smoothing: グレースケール;
  テキスト配置: 中央;
  色: #2c3e50;
  上マージン: 60px;
  ディスプレイ: フレックス;
  コンテンツの両端揃え: スペースの間;
}
</スタイル>

当初の要件は上の写真のとおりでしたが、現在ではビジネス要件が変わりました。映画はそのうちの 1 つだけを宣伝し、他のものは宣伝していません。食べ物もそのうちの 1 つだけを宣伝しています。

以下のように表示されます。

画像-20211120151432264

どうすれば適切にできるでしょうか?

カテゴリ コンポーネントに if ステートメントを追加して、1 つずつ判断を下していますか?それとももっと良い方法があるのでしょうか? ? ?

一つ一つ判断するのは不可能で、コードが非常に複雑になり、読みにくくなります。将来、業務要件の変更が必要になった場合、コードの変更が困難になります。

次に、デフォルトのスロットを見てみましょう。

1. デフォルトスロット

データを受信したり子コンポーネントでレンダリングしたりするために props を使用する必要はなくなり、代わりにスロットを定義します。

<テンプレート>
<div class="カテゴリ">
    <!-- スロット、スロットのデフォルト コンテンツを定義 -->
    <slot>親コンポーネントが値を渡さない場合は、このデフォルトが表示されます</slot>
    </div>
</テンプレート>
<スクリプト>
    エクスポートデフォルト{
        小道具: {
        }
    }
</スクリプト>

アプリのコンポーネントも変更されました

<テンプレート>
<div id="アプリ">
    <カテゴリー>
        <h1>ゲーム</h1>
        <!-- <ul>
<li v-for="(item, index) ゲーム内" :key="index">{{ item }}</li>
    </ul> -->
        <img src="https://gimg2.baidu.com/image_search/src=http%3A%2F%2Fi0.hdslb.com%2Fbfs%2Farticle%2Fb352264fa7bfdb6d211f2e71e87cc2c48d85b805.jpg&refer=http%3A%2F%2Fi0.hdslb.com&app=2002&size=f9999,10000&q=a80&n=0&g=0n&fmt=jpeg?sec=1639931135&t=0b2c6c622c84a1e387196cce8f50455e">
    </カテゴリー>
    
    <カテゴリー>
        <h1>映画</h1>
        <img class="movies" src="https://gimg2.baidu.com/image_search/src=http%3A%2F%2Finews.gtimg.com%2Fnewsapp_bt%2F0%2F13236694597%2F641.jpg&refer=http%3A%2F%2Finews.gtimg.com&app=2002&size=f9999,10000&q=a80&n=0&g=0n&fmt=jpeg?sec=1639931502&t=f89c2197bda9bb129d9404d3c4b30f2f">
        <!-- <ul> -->
        <!-- <li v-for="(item, index) 映画内" :key="index">{{ item }}</li> -->
        <!-- </ul> -->
    </カテゴリー>
    <カテゴリー>
        <h1>食品</h1>
        <ul>
            <li v-for="(item, index) 食品内" :key="index">{{ item }}</li>
    </ul>
    </カテゴリー>
    
    <!-- 何も書いていないときに何が表示されるか確認します -->
    <カテゴリー>
    </カテゴリー>
    </div>
</テンプレート>
 
<スクリプト>
    './components/Category.vue' からカテゴリーをインポートします。
 
    エクスポートデフォルト{
        名前: 'アプリ'、
        コンポーネント:
            カテゴリ
        },
        データ () {
            戻る {
                ゲーム:['クロスファイア','QQスピード','ロックキングダム'],
                映画:[『こんにちは、李華英』、『青春』、『つかの間の時間』]、
                食べ物:['邵陽米麺'、'長沙茶'、'重慶火鍋']
            }
        }
    }
</スクリプト>

表示効果:

画像-20211120152024922

説明する:

子コンポーネントに <slot>親コンポーネントが値を渡さない場合は、このデフォルトを表示する</slot> タグを記述しました。これは、位置を占有することと同じです。

親コンポーネントでは、以前のように自己終了とタグ <Category/> を記述せず、代わりに非自己終了とタグ <Category> content</Category> を記述します。こうすることで、Vue はデフォルトでコンポーネント タグに記述されたコンテンツをレンダリングし、それを子コンポーネントの <slot></slot> に戻します。

注: CSS スタイルはレンダリング後に子コンポーネントに戻されるため、親コンポーネントまたは子コンポーネントのどちらにも記述できます。子コンポーネントに記述すると、子コンポーネントに戻されたときにレンダリングされます。

これを書いた後、クライアントは突然あなたがとても有能だと思い、不満になり、再びあなたに迷惑をかけ始めます。

画像-20211120152906020

次に、名前付きスロットが表示されます。

2. 名前付きスロット

1 つのスロットを使用することは考えられるので、2 つのスロットを使用してみることはできないでしょうか?

サブコンポーネントの変換

<テンプレート>
  <div class="カテゴリ">
    <!-- 親コンポーネントに名前を付けて、どのスロットに配置するかを指定する必要があります。これが名前付きスロットと呼ばれる理由です--->
    <slot name="slot1">親コンポーネントが値を渡さない場合は、このデフォルトが表示されます</slot>
    <スロット名="スロット2"></スロット>
  </div>
</テンプレート>
<スクリプト>
エクスポートデフォルト{
  小道具: {
  }
}
</スクリプト>

親コンポーネント

<テンプレート>
	<div id="アプリ">
    	<カテゴリー>
       	 <テンプレートスロット="スロット1">
          	  <h1>ゲーム</h1>
            <img src="https://gimg2.baidu.com/image_search/src=http%3A%2F%2Fi0.hdslb.com%2Fbfs%2Farticle%2Fb352264fa7bfdb6d211f2e71e87cc2c48d85b805.jpg&refer=http%3A%2F%2Fi0.hdslb.com&app=2002&size=f9999,10000&q=a80&n=0&g=0n&fmt=jpeg?sec=1639931135&t=0b2c6c622c84a1e387196cce8f50455e"
                 />
	</テンプレート>
	<テンプレートスロット="スロット2">
		<button >qq ログイン</button>
		<button >WeChatでログイン</button>
	</テンプレート>
 
</カテゴリー>
<カテゴリー>
    <テンプレートスロット="スロット1">
		<h1>映画</h1>
			<画像
     クラス="映画"
     src="https://gimg2.baidu.com/image_search/src=http%3A%2F%2Finews.gtimg.com%2Fnewsapp_bt%2F0%2F13236694597%2F641.jpg&refer=http%3A%2F%2Finews.gtimg.com&app=2002&size=f9999,10000&q=a80&n=0&g=0n&fmt=jpeg?sec=1639931502&t=f89c2197bda9bb129d9404d3c4b30f2f"
     />
    </テンプレート>
    <テンプレートスロット="スロット2">
		<button >クリックしてチケットを購入</button>
    </テンプレート>
</カテゴリー>
 
<カテゴリー>
    <テンプレートスロット="スロット1">
		<h1>食品</h1>
		<ul>
    		<li v-for="(item, index) 食品内" :key="index">{{ item }}</li>
        </ul>
    </テンプレート>
</カテゴリー>
 
<!-- 何も書いていないときに何が表示されるか確認します -->
<カテゴリー> </カテゴリー>
</div>
</テンプレート>
 
<スクリプト>
    './components/Category.vue' からカテゴリーをインポートします。
 
    エクスポートデフォルト{
        名前: 'アプリ'、
        コンポーネント:
            カテゴリ
        },
        データ () {
            戻る {
                ゲーム:['クロスファイア','QQスピード','ロックキングダム'],
                映画:[『こんにちは、李華英』、『青春』、『つかの間の時間』]、
                食べ物:['邵陽米麺'、'長沙茶'、'重慶火鍋']
            }
        }
    }
</スクリプト>

エフェクト表示

画像-20211120153500451

説明する:

コンポーネントに複数のスロットを配置できますが、複数のスロットがある場合は、欠落しないように親コンポーネントで名前を付けて指定する必要があります。

3. スコープ付きスロット

スコープ付きスロットは、以前のものとは少し異なります。以前は、データは親コンポーネントにありましたが、スコープ付きスロットは子コンポーネントにあり、それが親コンポーネントに渡され、親コンポーネントがレンダリングの構造を定義できるようになりました。

変更されたサブコンポーネント

<テンプレート>
  <div class="カテゴリ">
    <slot name="slot1">親コンポーネントが値を渡さない場合は、このデフォルトが表示されます</slot>
    <slot name="slot2" :foods="foods">親コンポーネントが値を渡さない場合は、このデフォルト値が表示されます</slot>
  </div>
</テンプレート>
<スクリプト>
エクスポートデフォルト{
  データ () {
    戻る {
      食べ物:['邵陽米麺'、'長沙茶'、'重慶火鍋']
    }
  }
}
</スクリプト>

親コンポーネント

<テンプレート>
  <div id="アプリ">
    <カテゴリー>
      <テンプレートスロット="スロット1">
        <h1>食品</h1>
      </テンプレート>
      <テンプレート スロット="スロット2" スコープ="リストデータ">
        <!-- わからない場合は、これが何であるかを出力できます。 {{listData}} -->
        <ul>
          <li v-for="(item, index) in listData.foods" :key="index">
            {{ アイテム }}
          </li>
        </ul>
      </テンプレート>
    </カテゴリー>
    <カテゴリー>
      <テンプレートスロット="スロット1">
        <h1>食品</h1>
      </テンプレート>
      <テンプレート スロット="スロット2" スコープ="リストデータ">
        <オル>
          <li v-for="(item, index) in listData.foods" :key="index">
            {{ アイテム }}
          </li>
        </ol>
      </テンプレート>
    </カテゴリー>
    <カテゴリー>
      <テンプレートスロット="スロット1">
        <h1>食品</h1>
      </テンプレート>
      <テンプレート スロット="スロット2" スコープ="リストデータ">
          <h4 v-for="(item, index) in listData.foods" :key="index">
            {{ アイテム }}
          </h4>
      </テンプレート>
    </カテゴリー>
    <カテゴリー>
      <テンプレート スロット="スロット1" スコープ="リストデータ">	
{{リストデータ}}
      </テンプレート>
    </カテゴリー>
  </div>
</テンプレート>
 
<スクリプト>
'./components/Category.vue' からカテゴリーをインポートします。
 
エクスポートデフォルト{
  名前: 'アプリ'、
  コンポーネント:
    カテゴリ
  }
}
</スクリプト>

レンダリング

画像-20211120154438477

学習や実践の中ではこのような活用シーンは思い浮かばなかったのですが、公式サイトには事例が載っていました。存在意義があるんだろうなとは思うのですが、知識が足りず、活用できていません。

説明する:

子コンポーネントは、変数名 = "定義されたデータ"を介して親コンポーネントに値を渡します。親コンポーネントは、子コンポーネントに到達する前にもう1つのレイヤーがあるため、<template slot = "slot2" scope = "子コンポーネントによって渡された名前と同じ名前を使用しない">でそれを受け取ります。

<テンプレート スロット="スロット2" スコープ="リストデータ">
<!-- わからない場合は、これが何であるかを出力できます。 {{listData}} -->
<ul>
    <li v-for="(item, index) in listData.foods" :key="index">
        {{ アイテム }}
    </li>
    </ul>
</テンプレート>

要約する

この記事はこれで終わりです。皆さんのお役に立てれば幸いです。また、123WORDPRESS.COM のその他のコンテンツにも注目していただければ幸いです。

以下もご興味があるかもしれません:
  • Vue3の7つのコンポーネント通信方式の詳細説明
  • Vue3における7種類のコンポーネント通信の詳細
  • Vueコンポーネント通信方法事例まとめ
  • Vue がコンポーネント通信を実装する 8 つの例
  • Vue におけるコンポーネント通信の詳細説明 (父子コンポーネント、祖父孫コンポーネント、兄弟コンポーネント)
  • Vueコンポーネント間の通信方法はいくつかある

<<:  HTML リンク アンカー タグと SEO におけるその役割の概要

>>:  アクセス速度を上げるためにウェブサイトを最適化する方法の更新

推薦する

jQuery Ajax チャットボットの実装事例

チャットボットは多くの手作業を省くことができ、顧客サービス、天気予報対応など、さまざまな状況で使用で...

Vueでミックスインを使用する方法

目次序文使い方要約する序文Vue にはコードの再利用に使われる mixins という設定項目がありま...

MySQL Innodbインデックスの原理の詳細な説明

導入振り返ってみると、4年前、私がMySQLのインデックスについて学んでいたとき、先生はインデックス...

Mysql sql スロークエリ監視スクリプトコード例

1. my.cnfを変更する #全体的な効果としては、グローバルがオンになっている場合はテーブルとロ...

MySQLでテーブル名を変更する方法と注意すべき点

目次1. テーブル名を変更する方法2. 注記要約: 1. テーブル名を変更する方法RENAME TA...

docker に openjdk をインストールして jar パッケージを実行する方法

画像をダウンロード docker プル openjdkデータボリュームの作成java_appデータボ...

Node.js のワーカー スレッドの詳細な理解

目次概要Node.js における CPU バウンド アプリケーションの歴史CPUを集中的に使用する操...

Docker を使用して Go Web アプリケーションをデプロイする方法

目次なぜ Docker が必要なのでしょうか? Docker デプロイメントの例コードの準備Dock...

React Hooks の一般的な使用シナリオ (概要)

目次1. ステートフック1. 基本的な使い方2. 更新3. 合併を実現する4. 遅延初期化状態5. ...

Momentsで写真を整理するためのCSSコード

まず、Moments を開いて、写真の数が異なるいくつかのレイアウトを確認するか、以下の例を参照して...

js でシンプルなタブを実装する

タブ選択カードは、実際の Web ページで非常に頻繁に使用されます。基本的に、すべての Web ペー...

HTMLフォーム属性のreadonlyとdisabledの使い方

1. readonly 読み取り専用属性なので、値を取得できます2. 無効: 無効な属性、値を取得で...

MYSQL updatexml() 関数のエラーインジェクション分析

まず、updatexml()関数を理解する UPDATEXML (XML ドキュメント、XPath ...

Vue で Google サードパーティ ログインを実装するためのサンプル コード

目次1. 開発者プラットフォームの構成問題を解決する1. 開発者プラットフォームの構成1. 開発者プ...

CSS 3.0とビデオを組み合わせることでクリエイティブなオープニング効果を実現

CSS 3.0 とビデオを組み合わせて実現したクリエイティブなオープニングをご紹介します。効果は次の...