Vue.jsで属性かv-bindかの応用
Vue.jsで属性かv-bindかの応用:
まずはじめに、私はVue.js初心者です。
ラジオボタンで選択したものを後から出てくるコンテンツでテキストを切り替えて表示したく、
かつ、タイトルのコンポーネント内で表示したいという時につまずき、いろいろ模索した結果解決出来たので、
ちょっと細かく残しておきます。
(タイトルのコンポーネント)
親のテンプレート
子コンポーネント
実際の表示
ここで使われているものを簡単に説明
このような感じで、選択したものを次のタイトルに表示したかったが、
これでは、
これで、私がやりたかったことはできました。
赤を選択した時には、タイトルは「あなたが赤から連想するものはなんですか?」となります。
ちなみに、
では、「'あなたが' + selectColor + 'から連想するものはなんですか?'」と表示されてしまいます。
ポイントとなるのは、
子コンポーネントに
上記では正しく動きません。
これが正しいです。
ちなみに、
挙動が確認できるコードを載せておきます。
経緯
まずはじめに、私はVue.js初心者です。ラジオボタンで選択したものを後から出てくるコンテンツでテキストを切り替えて表示したく、
かつ、タイトルのコンポーネント内で表示したいという時につまずき、いろいろ模索した結果解決出来たので、
ちょっと細かく残しておきます。
まず、コンポーネントで親から子へデータをもたせるとき
(タイトルのコンポーネント)親のテンプレート
<com-child title-text="タイトルを表示する">コンテンツ内容</com-child>
Vue.component('com-child',{
template: '<section><h1>{{ titleText }}</h1><slot></slot></section>',
props: ['titleText']
})
<section><h1>タイトルを表示する</h1>コンテンツ内容</section>
- component:同じHTML構造を繰り返し使える機能
- props:親で定義した属性を子のtemplate内で使うことができる(ケバブケースとキャメルケースが混ざることに注意)
- slot:親のコンテンツを子のテンプレートに反映させる
やりたかったけど、できなかったこと
<input type="radio" value="赤" v-model="selectColor">
<input type="radio" value="青" v-model="selectColor">
<com-child title-text="あなたが{{ selectColor }}から連想するものはなんですか?">コンテンツ内容</com-child>
これでは、
{{ selectColor }}の部分がそのまま表示されてしまう
解決方法
v-bind ディレクティブを使う。<com-child v-bind:title-text="'あなたが' + selectColor + 'から連想するものはなんですか?'">コンテンツ内容</com-child>
赤を選択した時には、タイトルは「あなたが赤から連想するものはなんですか?」となります。
ちなみに、
<com-child title-text="'あなたが' + selectColor + 'から連想するものはなんですか?'">コンテンツ内容</com-child>
ポイントとなるのは、
属性かv-bindかです。
属性とv-bind
子コンポーネントにpropsを定義しておけば、コンポーネントの呼び出し時に属性にアクセスすることができます。v-bindは属性に対して埋め込みたい時に使います。<a href="{{ url }}">リンク</a>
<a v-bind:href="url">リンク</a>
ちなみに、
v-bindは省略できるので、以下でも同じです。<a :href="url">リンク</a>
※ここの部分がきちんと理解できてなかった
- 属性値は文字列扱いとなる。
- 数値として値を渡したい場合は
v-bind:your-name="1"のように表す - v-bindで文字列を渡す場合は、
v-bind:your-name="'山田'"のようにダブルクォートの中をシングルクォートでくくる
v-bindを使い、テキストの部分はシングルクォートでくくり、+で連結することで解決できました。
最後に
挙動が確認できるコードを載せておきます。<div id="app">
<com-child title-text="好きな色はなんですか?">
<input type="radio" value="赤" v-model="selectColor">赤
<input type="radio" value="青" v-model="selectColor">青
</com-child>
<com-child v-bind:title-text="'あなたが' + selectColor + 'から連想するものはなんですか?'">
<template v-if="selectColor === '赤'">
<input type="radio" value="りんご" v-model="selectThing">りんご
<input type="radio" value="ポスト" v-model="selectThing">ポスト
</template>
<template v-if="selectColor === '青'">
<input type="radio" value="空" v-model="selectThing">空
<input type="radio" value="サファイア" v-model="selectThing">サファイア
</template>
</com-child>
</div>
<script src="https://cdn.jsdelivr.net/npm/vue@2.5.16/dist/vue.min.js"></script>
Vue.component('com-child',{
template: '<section><h1>{{ titleText }}</h1><slot></slot></section>',
props: ['titleText']
})
new Vue({
el: '#app',
data: {
selectColor: '',
selectThing: ''
}
})
コメント
コメントを投稿