#What is this ?
プログラミングの「プ」の字もわからなかった入社2年目が新たにVue.jsを学習していき、分かったことをまとめる日記です。
次章: Re:ゼロから始めるVue.js生活
Why Vue ?
会社の新プロジェクトでVueを使って新しく画面設計を行うことになりました。
Vueの他にもReactなどのフレームワークも候補に上がりました。
ただ、VueはHTMLベースでコードを書くことができることや、便利なディレクティブなど、比較的学習コストを抑えて実装に取り掛かることができるようです。
今回は、納期に限りがある中、早めに取り掛かることが可能なVueに軍配が上がりました。
Vue.jsを始めてみよう!
まずは手軽にVue.jsを始めてみよう
↓こちらで試し撃ちができるようです。
CodePen Home Vue.js Playground
また、CDNとしても提供されているので、HTML中にこちらを挿入することでローカル環境でも使えるようになリマス。
<script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
ゼロから始めるVue.js生活
Vueインスタンスを使いこなす
まずは以下のコードを打ち込んだhtmlを表示して、画面に「ほげぇぇぇぇぇぇぇぇ」を出力してみよう
<!-- HTML -->
<div>--------------</div>
<div id="hoge">
{{ message }}
</div>
<div>--------------</div>
<!-- HTML -->
<!-- Vue -->
<script>
var app = new Vue({
el: '#hoge',
data: {
message: 'ほげぇぇぇぇぇぇぇぇ'
}
})
</script>
<!-- Vue -->
..するとこのような表示が確認できる
--------------
ほげぇぇぇぇぇぇぇぇ
--------------
このとき、
Vueコード側では
-
new Vue()
でVueインスタンスを作成 -
el:
で適用する範囲を指定 -
data:
でプロパティを設定(app.message
として参照可)
一方、HTML側では、
-
{{ message }}
でdata: {message:
を参照し、展開している
dataに階層構造を作る
dataプロパティはこのように子プロパティをネストすることが可能
<!-- HTML -->
<div>--------------</div>
<div id="hoge">
{{ oya_hoge.kodomo_hoge }} <!-- hogeeeee -->
</div>
<div>--------------</div>
<!-- HTML -->
<!-- Vue -->
<script>
var app = new Vue({
el: '#hoge',
data: {
oya_hoge:
{
kodomo_hoge: 'hogeeeee'
}
}
})
</script>
<!-- Vue -->
mustache {{ }} について
{{ }}
では、vueのプロパティだけではなく、JavaScriptコードを展開可能
<!-- HTML -->
<div class="hoge">
{{ message + '?????' }} <!--ほげぇぇぇぇぇぇぇぇ?????-->
{{ Math.abs(-999999)}} <!--999999-->
</div>
<!-- HTML -->
el: について
el:
で指定したタグ以外では、message
は展開できない
<!-- HTML -->
<div class="not_hoge">
{{ message }} <!--{{ message }}-->
</div>
<div class="hoge">
{{ message }} <!--ほげぇぇぇぇぇぇぇぇ-->
</div>
<!-- HTML -->
<!-- Vue -->
<script>
var app = new Vue({
el: ".hoge",
data: {
message: "ほげぇぇぇぇぇぇぇぇ",
},
});
</script>
<!-- Vue -->
ただし、指定したタグ配下であれば、どこであっても展開できる
<!-- HTML -->
<div class="hoge">
{{ message }} <!--ほげぇぇぇぇぇぇぇぇ-->
<div class="in_hoge">
{{ message }} <!--ほげぇぇぇぇぇぇぇぇ-->
</div>
</div>
<!-- HTML -->
<!-- Vue -->
<script>
var app = new Vue({
el: ".hoge",
data: {
message: "ほげぇぇぇぇぇぇぇぇ",
},
});
</script>
<!-- Vue -->
複数のタグを対象とすることはできない
el:
が適用されるタグは必ず1つ。
したがって、同じクラス名をもつタグを複数作っても、先頭のタグ内のみmessage
が展開される。
<!-- HTML -->
<div class="hoge">
{{ message }} <!--ほげぇぇぇぇぇぇぇぇ-->
</div>
<div class="hoge">
{{ message }} <!--{{ message }}-->
</div>
<!-- HTML -->
<!-- Vue -->
<script>
var app = new Vue({
el: ".hoge",
data: {
message: "ほげぇぇぇぇぇぇぇぇ",
},
});
</script>
<!-- Vue -->
同一の親ノード内で、既にあるプロパティは定義できない
今回は、app.message
を先に定義しているのでmessage: "ほげぇぇぇぇぇぇぇぇ"
が優先されて適用されている。
ノードの親子関係は関係なく、先に書いてある方が優先して適用されるので注意されたし。
<!-- HTML -->
<div class="hoge">
<div class="under_hoge">
{{ message }} <!-- ほげぇぇぇぇぇぇぇぇ -->
</div>
</div>
<!-- HTML -->
<!-- Vue -->
<script>
var app = new Vue({
el: ".hoge",
data: {
message: "ほげぇぇぇぇぇぇぇぇ",
},
});
var app2 = new Vue({
el: ".under_hoge",
data: {
message: "Hogeeee",
},
});
</script>
<!-- Vue -->
ディレクティブを使いこなす
ディレクティブというのはv-bind
やv-html
など、v-
で始まる命令文のこと。
v-
の後に続く命令によってVueは処理を切り替えている。
v-bindを使いこなす
v-bind
では、htmlタグの属性値(href,class,id...)を動的に変化させることができる。
<script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
<!-- HTML -->
<ul id="hoge">
<li v-for="hoge in hoges" v-bind:key="hoge.id">
{{ hoge.name }}
{{ hoge.id }}
</li>
</ul>
<!-- HTML -->
<!-- Vue -->
<script>
var example1 = new Vue({
el: '#hoge',
data: {
hoges: [{
name: 'hoge_FIRST',
id: 1
},
{
name: 'hoge_SRCOND',
id: 2
}
]
}
})
</script>
<!-- Vue -->
-
v-bind:href
で、href属性を変更することを宣言 -
v-bind:href="vue_href"
で、data: {vue_href:
を参照し、展開
classを変更する時は、既存classに加えて、新たにclassを追加する。
<!-- HTML -->
<div class='hoge' v-bind:class="vue_class"></div> <!--<div class="hoge hogeeeee"></div>-->
<!-- HTML -->
<!-- Vue -->
<script>
var app = new Vue({
el: ".hoge",
data: {
vue_class: "hogeeeee",
},
});
</script>
<!-- Vue -->
idを変更する場合は、既存idを上書きしてしまうので注意
v-bindの省略記法
また、v-bind
はよく使われるため、このように省略されることがままある。
<div class='hoge' v-bind:class="vue_class"></div>
これを、v-bind:
を省略して:
と書くことが可能
<div class='hoge' :class="vue_class"></div>
v-htmlを使いこなす
v-html
を使うことで、エスケープ処理が行われなくなる。
任意のHTML要素を動的に出したい場合に役に立つ
<!-- HTML -->
<div>-----------</div>
<div class='hoge' v-html="html_message"></div>
<div>-----------</div>
<!-- HTML -->
<!-- Vue -->
<script>
var app = new Vue({
el: ".hoge",
data: {
html_message: "<h1>ほげええええええ</h1>",
},
});
</script>
<!-- Vue -->
v-ifを使いこなす
visible = true
であれば<button>
タグが生成される
<!-- HTML -->
<div id="hoge">
<button v-if="visible">ほげボタン</button> <!-- ほげボタン -->
</div>
<!-- HTML -->
<!-- Vue -->
<script>
var app = new Vue({
el: '#hoge',
data: {
visible: true
}
})
</script>
<!-- Vue -->
else文もこのように使うことができる
<!-- HTML -->
<div id="hoge">
<div>{{now}}</div>
<button v-if="visible">ほげボタン</button>
<button v-else="visible">ホゲってないぞ</button> <!-- ホゲってないぞ -->
</div>
<!-- HTML -->
<!-- Vue -->
<script>
var app = new Vue({
el: '#hoge',
data: {
visible: false
}
})
</script>
<!-- Vue -->
v-showを使いこなす
visible = true
であれば<button>
タグが生成される
<!-- HTML -->
<div id="hoge">
<button v-show="visible">ほげボタン</button> <!-- ほげボタン -->
</div>
<!-- HTML -->
<!-- Vue -->
<script>
var app = new Vue({
el: '#hoge',
data: {
visible: true
}
})
</script>
<!-- Vue -->
v-ifとの違いについて
v-if
では、条件がfalse
の場合、タグ自体が生成されない
のに対して、
v-show
ではタグそのものは存在するが見えない(display: none;)
となる
したがって、表示切り替えを頻繁に行うならv-show
、
たまに行う程度ならv-if
という使い分けになると考えられる。
v-forを使いこなす
v-forを使うことで、入れ子状になったプロパティや配列を順に取り出すことができる
<!-- HTML -->
<ul id="hoge">
<li v-for="hoge in hoges" v-bind:key="hoge.id">
{{ hoge.name }}
{{ hoge.id }}
</li>
</ul>
<!-- Vue -->
<script>
var example1 = new Vue({
el: '#hoge',
data: {
hoges: [{
name: 'hoge_FIRST',
id: 1
},
{
name: 'hoge_SRCOND',
id: 2
}
]
}
})
</script>
流れとしては、
-
v-bind:key
で重複しない一意なプロパティ名を指定(Vue.js 2.2.0よりv-bind:key
の指定は必須) -
hoge in hoges
でhoges
から要素を一つずつ、hoge
として取り出す -
{{ hoge.name }},{{ hoge.id }}
でプロパティにアクセス - 次の
hoge
を取り出す...
データオブジェクトに対してv-forを使った場合
第二引数を指定できる
第一引数(value)にプロパティの値が、第二引数(property_name)にプロパティ名が入ってくる
<!-- HTML -->
<ul id="hoge">
<li v-for="(value,property_name) in hoge_obj">
{{ property_name }}, {{ value }}
</li>
</ul>
<!-- Vue -->
<script>
var example1 = new Vue({
el: '#hoge',
data: {
hoge_obj: {
name: 'hoge_FIRST',
id: 1
}
}
})
</script>
第三引数を指定できる
第三引数にはインデックス番号(何番目の要素か)が格納されている
<!-- HTML -->
<ul id="hoge">
<li v-for="(value,property_name,index) in hoge_obj">
{{ property_name }}, {{ value }}, {{index}}
</li>
</ul>
<!-- Vue -->
<script>
var example1 = new Vue({
el: '#hoge',
data: {
hoge_obj: {
name: 'hoge_FIRST',
id: 1
}
}
})
</script>
メソッドを使いこなす
<!-- HTML -->
<div class='hoge'>
{{hoge_func()}} <!-- ほげえええええええ -->
</div>
<!-- HTML -->
<!-- Vue -->
<script>
var app = new Vue({
el: ".hoge",
methods: {
hoge_func: function () {
return "ほげえええええええ"
}
},
});
</script>
<!-- Vue -->
メソッドに引数をとる
<!-- HTML -->
<div class='hoge'>
{{hoge_func('ほゲゲゲゲゲゲ')}} <!-- ほゲゲゲゲゲゲ?????? -->
</div>
<!-- HTML -->
<!-- Vue -->
<script>
var app = new Vue({
el: ".hoge",
methods: {
hoge_func: function (argument) {
return argument+'??????'
}
},
});
</script>
<!-- Vue -->
算出プロパティ(computed)を使いこなす
<!-- HTML -->
<div id="hoge">
{{ hogeReverse }} <!-- ぇぇぇぇぇぇぇぇげほ -->
</div>
<!-- HTML -->
<!-- Vue -->
<script>
var app = new Vue({
el: '#hoge',
data: {
message: 'ほげぇぇぇぇぇぇぇぇ'
},
computed: {
hogeReverse: function () {
return this.message.split("").reverse().join(""); //文字列を反転させる
}
}
})
</script>
<!-- Vue -->
ここで、
-
this
はappインスタンスを表している(this.hogeReverse = app.hogeReverseと同等) - このthisは省略できない(
message is not defined
)
また、
あくまでcomputedで定義されるのはプロパティ
であって、メソッド
ではないので引数を取ることはできない
hogeReverse() ❌
hogeReverse(arg) ❌