zishu's blog

zishu's blog

一个热爱生活的博主。https://zishu.me

vue学習ノート(3)--computed, watch, class, style

一、計算プロパティ computed#

1. 例#

<div id="app">
  <div>{{message}}</div>
  <div>{{revermessage}}</div>
</div>

<script>
  var vm = new Vue({
    el: '#app',
    data: {
      message: 'hello,wolrd'
    },
    computed: {
      revermessage: function() {
        return this.message.split('').reverse().join('')
      }
    }
  })
</script>

計算プロパティsevermessageを宣言し、computed内でmessageに対していくつかのメソッド操作を行った後の戻り値に指し示します。

この時vm.severmessagevm.messageの変化に依存し、messageのデータが変更されるとsevermessageが更新されます。

2. 計算プロパティのキャッシュとメソッド#

式内でメソッドを呼び出すことで、望む効果を得ることもできます。

<div id="app">
  <div>{{message}}</div>
  <div>{{revermessage()}}</div>
</div>

<script>
  var vm = new Vue({
    el: '#app',
    data: {
      message: 'hello,wolrd'
    },
    methods: {
      revermessage: function() {
        return this.message.split('').reverse().join('')
      }
    }
  })
</script>

テストの結果、両者の結果は同じです。

同じ関数を計算プロパティではなくメソッドとして定義することもできます。最終的な結果は確かに完全に同じです。

違いは:計算プロパティはその応答性依存に基づいてキャッシュされ、応答性依存、つまりmessageが変更された時のみ再評価されます。これは、messageが変更されない限り、revermessage計算プロパティに何度アクセスしても以前の計算結果のキャッシュを返すだけで、計算プロパティの関数を直接実行することはありません。

一方、メソッドは、再描画がトリガーされるたびに、メソッドを呼び出すと関数が一度実行されます。これには追加のオーバーヘッドがあります。

なぜキャッシュが必要なのでしょうか?性能オーバーヘッドが大きい計算プロパティ A があり、それが巨大な配列を遍歴し大量の計算を行う必要があると仮定します。その後、他の計算プロパティが A に依存している可能性があります。キャッシュがなければ、A のゲッターを何度も実行することは避けられません!キャッシュを望まない場合は、メソッドを使用してください。

3. 計算プロパティとウォッチプロパティ#

vue には、vue インスタンス上のデータの変化を観測するもう一つの方法があります:ウォッチプロパティ--watch

<div id="app">
  {{fullname}}
</div>

<script>
  var vm = new Vue({
    el: '#app',
    data: {
      firstname: 'a',
      lastname: 'b',
      fullname: 'ab'
    },
    watch: {
      firstname: function(val) {
        this.fullName = val + ' ' + this.lastName
      },
      lastname: function(val) {
        this.fullName = this.firstName + ' ' + val
      }
    }
  })
</script>

使用過程は非常に煩雑で繰り返しが多いので、計算プロパティを使ってみましょう。

<div id="app">
  {{fullname}}
</div>

<script>
  var vm = new Vue({
    el: '#app',
    data: {
      firstname: 'a',
      lastname: 'b'
    },
    computed: {
      fullname: function() {
        return this.firstname + this.lastname
      }
    }
  })
</script>

非常に簡単かつ迅速に、我々が望む関数表現を得ることができました。

4. 計算プロパティの setter#

computed: {
  fullName: {
    // getter
    get: function () {
      return this.firstName + ' ' + this.lastName
    },
    // setter
    set: function (newValue) {
      var names = newValue.split(' ')
      this.firstName = names[0]
      this.lastName = names[names.length - 1]
    }
  }
}

今、コンソールにvm.fullName = 'John Doe'と入力すると、ページが反応し、setterが呼び出され、vm.firstnamevm.lastnameもそれに応じて更新されます。

二、class と style のバインディング#

1. オブジェクト構文#

v-bind:classにオブジェクトを渡すことで、動的にclassを切り替えることができます。

<div v-bind:class="{active: ok}"></div>

okのブール値を制御することで、動的に class を制御できます。

複数のフィールドを作成することもでき、通常のclassNameの存在に影響を与えません。

html:

<div
  class="static"
  v-bind:class="{ active: isActive, 'text-danger': hasError }"
></div>

data:

data{
  isActive: true,
  hasError: false
}

結果は:

<div class="static active"></div>

isActiveまたはhasErrorが変化すると、class リストがそれに応じて更新されます。例えば、hasErrorの値がtrueの場合、class リストは"static active text-danger"に変わります。

バインディングするデータオブジェクトは、インラインテンプレート内に直接書く必要はありません。

<div id="app">
  <div v-bind:class="classobject"></div>
</div>

<script>
  var vm = new Vue({
    el: '#app',
    data: {
      classobject: {
        active: true,
        'text-danger': true
      }
    },
  })
</script>

<!-- <div class="active text-danger"></div> -->

classNameに特殊な記号がある場合は、必ず引用符''または""を付ける必要があります。

2. 配列構文#

配列をv-bind:classに渡すことで、class リストを適用できます。

<div v-bind:class="[activeClass, errorClass]"></div>
data: {
  activeClass: 'active',
  errorClass: 'text-danger'
}

レンダリング結果は:

<div class="active text-danger"></div>

3. コンポーネントでの使用#

カスタムコンポーネントでclassプロパティを使用する場合、これらの class はそのコンポーネントのルート要素に追加されます。この要素に既に存在する class は上書きされません。

Vue.component('my-component', {
  template: '<p class="foo bar">Hi</p>'
})

そして使用時にいくつかのclassを追加します:

<my-component class="baz boo"></my-component>

html は次のようにレンダリングされます:

<p class="foo bar baz boo">Hi</p>

データバインディングされたclassにも同様に適用されます。

<my-component v-bind:class="{ active: isActive }"></my-component>

isActiveが truthy の場合、HTML は次のようにレンダリングされます:

<p class="foo bar active">Hi</p>

4. インラインスタイル style のバインディング#

v-bind:styleのオブジェクト構文は非常に直感的で、CSS に非常に似ていますが、実際には JavaScript オブジェクトです。CSS プロパティ名はキャメルケースまたは引用符付きのハイフンで命名できます。

<div v-bind:style="{ color: activeColor, fontSize: fontSize + 'px' }"></div>

js:

data: {
  activeColor: 'red',
  fontSize: 30
}

または、オブジェクトに直接バインドすることで、テンプレートをより明確にすることができます。

<div v-bind:style="styleObject"></div>

js:

data: {
  styleObject: {
    color: 'red',
    fontSize: '13px'
  }
}

複数のオブジェクトを一つの要素に適用することもできます。

<div v-bind:style="[baseStyles, overridingStyles]"></div>

自動的にプレフィックスを追加

v-bind:styleがブラウザのプレフィックスを使用する必要がある場合、例えば-webkit-など、vue は自動的に検出し、適切なプレフィックスを生成します。

読み込み中...
文章は、創作者によって署名され、ブロックチェーンに安全に保存されています。