はじめに
watchは特定のデータや算出プロパティの状態の変化を監視して、変化があったときに登録した処理を実行するプロパティ。
データや算出プロパティの変更が処理のトリガー(きっかけ)となる。
使い方
watchオプションに監視するデータの名前
と変化した時に呼び出されるハンドラ(関数)
を定義する。
データの比較が必要な場合は、第1引数として新しい値
、第2引数として古い値
が受け取れる。
※ここではインスタンスが生成されると同時にwatchが呼び出されている。
基本的な書き方
new Vue({
watch: {
監視するデータ: function(新しい値, 古い値) {
// データが変化した時に行いたい処理
},
// ↓ オブジェクトのプロパティも監視できる
'item.value': function(新しい値, 古い値) {
// 処理
}
}
})
↓ データ等を入れて記述してみる
new Vue({
el: 'app',
data: {
flag: true
},
methods: {
changeFlag: function() {
this.flag = !this.flag
}
},
// データflagをwatchオプションに定義
watch: {
flag: function(newVal, oldVal) {
// データの値が変化した時にコンソールに新しい値と古い値を出力
console.log(newVal, oldVal)
}
}
});
watchのオプション
下記のオプションを任意で設定できる(デフォルトではfalse)
プロパティ | 値 | 説明 |
---|---|---|
deep | Boolean | ネストされたオブジェクトも監視する |
immediate | Boolean | 初期読み込み時にも呼び出す |
オプションを使用する際はオブジェクトにまとめ、handler
プロパティにハンドラを定義する。
new Vue({
el: 'app',
data: {
list: [
{ name: '鉛筆', price: 98 },
{ name: '消しゴム', price: 100 }
]
},
watch: {
// listもしくはlist内のプロパティに変更があった場合に処理が実行される
list: {
handler: function(newVal, oldVal) {
console.log(newVal)
},
// deepがfalseだとオブジェクト内の値が変更されても処理が実行されない
deep : true,
immediate: true
}
}
});
watchオプションとcomputedオプションの違い
同じようなプロパティとしてデータ変更時にのみ処理を実行するcomputedオプションがある。
→ computedオプションについてこちら
まずはwatchプロパティとcomputedプロパティで同じ処理を記述して比較してみる。
↓ firstNum と secondNum を掛けてresultNumを表示する
// watchの場合
new Vue({
el: 'app',
data: {
firstNum: 2,
secondNum: 3,
resultNum: 6
},
watch: {
firstNum: function(newVal) {
this.resultNum = newVal * this.secondNum;
},
secondNum: function(newVal) {
this.resultNum = this.secondNum * newVal;
},
}
})
// computedの場合
new Vue({
el: 'app',
data: {
firstNum: 2,
secondNum: 3
},
computed: {
resultNum: function() {
return this.firstNum * secondNum;
}
}
})
このようにcomputedオプションの方が簡潔で可読性の高いコードが記述できる。そのため、computedオプションで記述できる場合はcomputedオプションを使用するのが望ましい。
watchオプションは下記のような場面で使う。
◎ 非同期通信(APIアクセス)などの複雑な処理を行う場合
(computedオプションでは処理できない)
◎ 更新前と更新後の値を使う場合
◎ 処理を実行してもデータを返さない場合
メソッド内でwatchを登録
インスタンスメソッドとしてthis.$watch
と定義することでメソッド内でもwatchが登録できる。
今までの書き方とは少し異なり、下記のように引数を渡してあげる。
// 書き方
this.$watch('監視したいデータ',ハンドラ(関数),オプション)
// ライフサイクルのcreatedにwatchを登録してみる
created() {
this.$watch('value', function(newVal, oldVal) {
// 処理
}, {
deep: true,
immediate: true
})
}
監視の解除
返り値を使って監視を解除することができる。
var unwatch = this.$watch('value' function() {})
unwatch()
一度だけ監視
一度しか監視しないwatchをunwatch()
を使って登録する。
new Vue({
el: 'app',
data: {
edited: false,
list: [
{ name: '鉛筆', price: 98 },
{ name: '消しゴム', price: 100 }
]
},
created() {
var unwatch = this.$watch('list', function() {
// データlistが変更されたらeditedをtrueにする
this.edited = true
// データが変更されたら監視を解除
unwatch()
}, {
deep: true
})
}
})