このkeyを使ってVueコンポーネントを再レンダリングできることを知らない人が多い!

18499 ワード

場合によっては、Vueにコンポーネントの再レンダリングを強制しなければなりません.もしなければ、あなたのビジネスはまだ責任が足りないかもしれません.どうせ私は常にコンポーネントの再レンダリングが必要です.ははは.
Vueが自動的に更新されないことは比較的少ないが、この問題が発生したときに修復する方法を知っておくと役に立つ.
多くの場合、この問題の根源は私たちがVueに対する応答的な理解が足りないことです.そのため、私たちがVueを正しく使用していることをできるだけ確保しなければなりません.応答式は時には厄介で、私もよく困っています.
このセクションでは、keyでコンポーネントを再レンダリングします.
この記事では、このいくつかの知識点について説明します.
  • keyは、コンポーネント
  • をどのように変更するか
  • keyは、複数のサブコンポーネントとともにどのように動作するか
  • サブアセンブリが
  • を更新するように強制する方法
    キーの値を変更してコンポーネントを再レンダリングする
    私が一番好きな方法はkey属性を使うことです.keyの方法を使うと、Vueは特定のコンポーネントが特定のデータに関連していることを知っています.
    keyが変わらない場合、コンポーネントは変更されません.ただし、keyが変更された場合、Vueは古いコンポーネントを削除し、新しいコンポーネントを作成すべきであることを知っています.
    以下は非常に基本的な方法です.
    <template>
      <ComponentToReRender
        :key="componentKey"
      />
    </template>
    
    <script>
      export default {
        data() {
          return {
            componentKey: 0,
          };
        },
        methods: {
          forceRerender() {
            this.componentKey += 1;
          }
        }
      }
    </script>
    
    forceRerenderが呼び出されるたびに、componentKeyの値が変更されます.componentKeyの値が変更されると、Vueは、ComponentToReRenderコンポーネントを削除し、新しいコンポーネントを作成することを知っている.
    これにより、ComponentToReRenderは内部の状態を再レンダリングしてリセットします.nice nice!
    複数のサブノードの更新を強制
    同様に、複数のサブコンポーネントにも使用できます.
    <template>
      <div>
        <Child
          :key="key1"
        />
        <Child
          :key="key2"
        />
      </div>
    </template>
    
    <script>
      export default {
        data() {
          return {
            key1: 0,
            key2: 0,
          };
        },
        methods: {
          forceRerender(child) {
            if (child === 1) {
              this.key1 += 1;
            } else if( child === 2) {
              this.key2 += 1;
            }
          }
        }
      }
    </script>
    

    ここでは、2つの個別keyを使用して、各サブコンポーネントが再レンダリングされるかどうかをそれぞれ制御します.これらを分離するのは、1つのサブコンポーネントのレンダリングのためであり、他のコンポーネントには影響しません.
    ただし、2つのサブコンポーネントを常に一緒に更新する場合は、同じkyeを使用できます.しかし、keyは唯一でなければならないので、次のような方法では仕事ができません.
    <template>
      <div>
        <Child
          :key="componentKey"
        />
        <Child
          :key="componentKey"
        />
      </div>
    </template>
    
    <script>
      export default {
        data() {
          return {
            componentKey: 0,
          };
        },
        methods: {
          forceRerender(child) {
            this.componentKey += 1;
          }
        }
      }
    </script>
    

    ここでは、最初のChildコンポーネントのみがレンダリングされます.2つ目は重複するkeyを持っているため無視されます.
    この問題を解決するために、componentKeyに基づいて子供一人一人に新しいkeyを構築することができます.
    <template>
      <div>
        <Child
          :key="`${componentKey}-1`"
        />
        <Child
          :key="`${componentKey}-2`"
        />
      </div>
    </template>
    
    <script>
      export default {
        data() {
          return {
            componentKey: 0,
          };
        },
        methods: {
          forceRerender(child) {
            this.componentKey += 1;
          }
        }
      }
    </script>
    

    コンポーネントキーの後に-1と-2を追加するたびに、この2つのキーは常に一意であり、この2つのコンポーネントは再レンダリングされます.
    リストにある場合は、次のように使用できます.
    <template>
      <div>
        <Child
          v-for="(item, index) in list"
          :key="`${componentKey}-${index}`"
        />
      </div>
    </template>
    
    <script>
      export default {
        data() {
          return {
            list: [
              // ...
            ],
            componentKey: 0,
          };
        },
        methods: {
          forceRerender(child) {
            this.componentKey += 1;
          }
        }
      }
    </script>
    

    ここでは、keyを${componentKey}-${index}として構築するので、componentKeyが変更されると、リスト内のすべてのコンポーネントが同時に再レンダリングされます.
    もちろん、もっと簡単な方法は、divでリストを包んで、divを直接更新すればいいということです.
    <template>
      <div :key="componentKey">
        <Child
          v-for="item in list"
          :key="item.id"
        />
      </div>
    </template>
    
    <script>
      export default {
        data() {
          return {
            list: [
              // ...
            ],
            componentKey: 0,
          };
        },
        methods: {
          forceRerender(child) {
            this.componentKey += 1;
          }
        }
      }
    </script>
    

    この考えは多くの場所で使うことができて、私たちのためにとても苦境から抜け出すことができて、みんなはしっかり覚えていなければなりません.
    では、今日は皆さんと分かち合います.次の号で会いましょう.見てくれてありがとう.
    作者:Michael Thiessen訳者:先端小智源:medium
    原文:https://morioh.com/p/08963bf07353