menu
書いてる野郎
orebike@gmail.com
厳密には、コンポーネントを使って作られた Vue オブジェクト同士のやり取り。
Vue の世界ではコンポーネント同士が自由に何でもできるわけでなく、 親子関係になっているオブジェクト間でのみやり取りができるようになっている。
それは JS の世界まで広げればデータのプロパティは Vue では外にオープンになっているわけだから、 なんでもありであるが、つまりこういう仕組みを用意してくれているということだから、 JS の世界で何でもやるのはやめましょうという設計指針をしめしてくれているということである。
親はどの子を持つかの自由度は大きいので、子側に親から値の受け入れ口を作ることになる。
この口は props という設定で入れる。意味としては「依存性」みたいな意味だろうか。
子供を想定した hogehoge コンポーネントを作る。
Vue.component("hogehoge", { props: { oya: { type: Object, default: {name:"oya"}, required: true, validator: function(v){ return true; } } }, template: '<div>hoge {{ oya.name }} hoge</div>' });
受ける名前は oya として、いくつかの設定を書く。
影響がわかるようにその受けた prop の名前(oya)で template を記述しておく。
親を想定した piyopiyo コンポーネントを作る
Vue.component("piyopiyo", { data: function(){ return { oyav: { name: "oya1" } }; }, template: '<div>piyo <hogehoge v-bind:oya="oyav" /> piyo</div>' });
コンポーネントなので data には data したいオブジェクトを返す関数を指定する。 そこで oyav というキーのオブジェクトを1つ登録する。
template で子のタグに対して v-bind:子のprop名 で関係するデータをバインドする。 これで親と子が繋がったので
親の変化が子供の伝わって再描画される。
イベント・ドリブンの UIのプログラムでは子からイベントが発火してそれによって子以外の全体の挙動を動かすということがよくある。このような場合親子は相互参照になっているような場合が多いのだが、 Vue はそこにも設計指針があって、子からはイベント発火できるようになっている。
子供から呼ばれる関数を作る。そしてこのメソッドを名前をつけて子供にバインドして接続する
Vue.component("piyopiyo", { methods: { oyafunc: function(){ console.log("oya oya"); } } template: '<div>piyo <hogehoge v-on:oyaoya="oyafunc" /> piyo</div>' });
ここの v-on:関数呼び出し名(oyaoya) で指定しているメソッドはメソッド名のみ指定する。
子側ではメソッド中で $emit
メソッドを呼び出してそこに親で v-bind した名前で呼び出せる。
Vue.component("hogehoge", { methods: { kofunc: function(){ // 親から指定した名前を使う this.$emit("oyaoya"); } }, // わかるようにクリックイベントにメソッドをバインドする template: '<div v-on:click="kofunc()">hogehoge</div>' });
このようにするとイベントを伝播させられる。
この場合に自分自身を渡しておけば、親側の関数呼び出し時に引数として渡してくれる。
this.$emit("oyaoya", this);
親側も this の情報が取れれば子供が複数あった場合にハンドリングしやすいだろう。