有一篇非常棒的關(guān)于vue.js的組件的文章银酬,寫的特別好嘲更,特別清楚,容易理解揩瞪。鏈接:上篇:http://www.cnblogs.com/keepfool/p/5625583.html 下篇:http://www.cnblogs.com/keepfool/p/5637834.html
以下是我學(xué)習(xí)鏈接所對應(yīng)的這兩篇文章的學(xué)習(xí)摘要赋朦。
1.組件的創(chuàng)建和注冊
1.1 創(chuàng)建組件構(gòu)造器(使用Vue.extend({模板}))
var child = Vue.extend({
template:'<div>This is my first component!</div>'
})
1.2 注冊組件:Vue.component({'組件名',組件構(gòu)造器名})
Vue.component('my-component',myComponent)
1.3 使用組件
new Vue({
el:'#app'
});
<div id="app">//組件需掛載到對應(yīng)的vue實例的掛載范圍內(nèi)
<my-component></my-component>
</div>
1.4 全局注冊
eg:
<div id="example">
<my-component></my-component>
</div>
<script>
//注冊,這種是全局注冊
Vue.component('my-component',{
template:'<div>A component!</div>'
})
//創(chuàng)建根實例
new Vue({
el:'#example'
})
</script>
渲染為:
<div id="example">
<div>A component!</div>
</div>
1.5 局部注冊
eg:
<div id="example">
<my-component></my-component>
</div>
<script>
var myComponent = Vue.extend( {
template: '<div>A component!</div>'
})
new Vue({
el:'#example',
components: {
'my-component':myComponent//用實例選項“components”注冊李破,局部注冊
}
})
</script>
1.3 全局注冊和局部注冊區(qū)分
在new Vue ()中注冊的為局部注冊宠哄,只能掛到id值與new Vue()中的el值相同的Vue實例,而在new Vue外注冊的為全局注冊的喷屋,可以掛到各個Vue實例琳拨。
eg:
<div id="example">
<my-component></my-component>
</div>
<div id="example-2">
<my-component></my-component>//將局部注冊的組件掛到不對應(yīng)的組件上,無法正確顯示
</div>
<script>
var child = {
template: '<div>A component!</div>'
}
new Vue({
el:'#example',
components: {
'my-component':child//局部注冊的組件
}
})
</script>
eg:
<div id="example">
<my-component></my-component>
</div>
<div id="example-2">
<my-component></my-component>//將全局注冊的組件掛到不同id值的組件上
</div>
<script>
//全局注冊
Vue.component('my-component',{
template:'<div>A component!</div>'
})
//創(chuàng)建根實例
var vm1 = new Vue({
el:'#example'
})
var vm2 = new Vue({
el:'#example-2'
})
</script>
2.父組件和子組件
在一個組件的模板(template)中使用了其他組件屯曹,這兩個組件之間就構(gòu)成了父子關(guān)系狱庇,該組件是父組件,父組件的模板中的組件是子組件恶耽。
子組件只能在父組件的template中使用密任。
- 創(chuàng)建父組件構(gòu)造器
- 創(chuàng)建子組件構(gòu)造器
- 注冊父組件
- 注冊子組件
- 使用組件
<div id="app">
<parent-component>
</parent-component>
</div>
<script>
//創(chuàng)建父組件構(gòu)造器,模板中使用了子組件<child-component></child-component>
var parent = Vue.extend({
template:'<div>This is a parent component!and <child-component></child-component></div>'
})
//創(chuàng)建子組件構(gòu)造器
var child = Vue.extend({
template:'<div>This is a child component!</div>'
})
//注冊父組件和子組件
Vue.component('child-component',child)
Vue.component('parent-component',parent)
//vue實例
new Vue({
el:'#app'
});
</script>
3.組件注冊語法糖:Vue.js簡化組件注冊的過程
3.1 使用Vue.component()直接創(chuàng)建和注冊組件:
// 全局注冊偷俭,my-component1是標(biāo)簽名稱
Vue.component('my-component1',{
template: '<div>This is the first component!</div>'
})
var vm1 = new Vue({
el: '#app1'
})
使用這種方式浪讳,Vue在背后會自動地調(diào)用Vue.extend()。
3.2 在選項對象的components屬性中實現(xiàn)局部注冊:
var vm2 = new Vue({
el: '#app2',
components: {
// 局部注冊涌萤,my-component2是標(biāo)簽名稱
'my-component2': {
template: '<div>This is the second component!</div>'
},
// 局部注冊淹遵,my-component3是標(biāo)簽名稱
'my-component3': {
template: '<div>This is the third component!</div>'
}
}
})
4. 使用script或template標(biāo)簽:分離js代碼template中的HTML元素
4.1 使用<script>標(biāo)簽
將原本寫在template的內(nèi)容寫在<script type="text/x-template" id="myComponent"></script>標(biāo)簽中口猜,而組件的template的值為<script>標(biāo)簽的“id”值。
Vue.js根據(jù)template里面的id值透揣,找到對應(yīng)的<script>標(biāo)簽济炎,將標(biāo)簽中的HTML作為模板進行編譯。
注意:使用<script>標(biāo)簽時辐真,type指定為text/x-template须尚,意在告訴瀏覽器這不是一段js腳本,瀏覽器在解析HTML文檔時會忽略<script>標(biāo)簽內(nèi)定義的內(nèi)容侍咱。
<div id="app">
<my-component></my-component>
</div>
<script type="text/x-template" id="myComponent">
<div>This is a component!</div>
</script>
<script>
Vue.component('my-component',{
template: '#myComponent'
})
new Vue({
el: '#app'
})
</script>
4.2 使用<template>標(biāo)簽
<template id="template選項的值">
//這里是原來寫在template選項中的HTML
</template>
<div id="app">
<my-component></my-component>
</div>
<template id="myComponent">
<div>This is a component!</div>
</template>
<script>
Vue.component('my-component',{
template: '#myComponent'
})
new Vue({
el: '#app'
})
</script>
建議使用<script>或<template>標(biāo)簽來定義組件的HTML模板耐床。
這使得HTML代碼和JavaScript代碼是分離的,便于閱讀和維護楔脯。
5. 組件的el和data選項
Vue.extend() 或Vue.component()中的data 和el必須是函數(shù)撩轰。
eg:
Vue.component('my-component', {
data: function(){
return {a : 1}
}
})
6.使用props
6.1基礎(chǔ)示例
var vm = new Vue({
el: '#app',
data: {
name: 'keepfool',
age: 28
},
components: {
'my-component': {
template: '#myComponent',
props: ['myName', 'myAge']
}
}
})
這個vue實例可以看作'my-component'組件的父組件。要使用父組件的數(shù)據(jù)例如'data'就要先在子組件中定義props屬性淤年。在定義屬性的時候用的是駝峰命名钧敞。在使用組件時引用props屬性的內(nèi)容時需要轉(zhuǎn)為 kebab-case(短橫線隔開)命名。
將父組件數(shù)據(jù)通過已定義好的props屬性傳遞給子組件:
<div id="app">
<my-component v-bind:my-name="name" v-bind:my-age="age"></my-component>
//"my-name"對應(yīng)props的"myName","name"對應(yīng)父組件的數(shù)據(jù)"name","my-age"對應(yīng)props的"myAge","age"對應(yīng)父組件的數(shù)據(jù)"age"
</div>
定義子組件的HTML模板:
<template id="myComponent">
<table>
<tr>
<th colspan="2">
子組件數(shù)據(jù)
</th>
</tr>
<tr>
<td>my name</td>
<td>{{ myName }}</td>//在props屬性中定義麸粮,將父組件對應(yīng)的數(shù)值傳遞過來
</tr>
<tr>
<td>my age</td>
<td>{{ myAge }}</td>////在props屬性中定義溉苛,將父組件對應(yīng)的數(shù)值傳遞過來
</tr>
</table>
</template>
加上自定義的CSS樣式,最終效果圖如下:
在父組件中使用子組件時弄诲,通過以下語法將數(shù)據(jù)傳遞給子組件:
<child-component v-bind:子組件prop="父組件數(shù)據(jù)屬性"></child-component>
6.2 props的綁定類型
6.2.1 單向綁定
- 修改父組件的數(shù)據(jù)會影響子組件的數(shù)據(jù)愚战;
- 修改子組件的數(shù)據(jù)不會影響父組件的數(shù)據(jù)。
6.2.2 雙向綁定
可以在使用子組件時齐遵,使用.sync顯式地指定雙向綁定寂玲,這使得子組件的數(shù)據(jù)修改會回傳給父組件。
<child-component v-bind:my-name.sync="name" v-bind:my-age.sync="age"></child-component>
6.2.3 單次綁定
可以使用.once顯式地指定單次綁定梗摇,單次綁定在建立之后不會同步之后的變化拓哟,這意味著即使父組件修改了數(shù)據(jù),也不會傳導(dǎo)給子組件伶授。
<child-component v-bind:my-name.once="name" v-bind:my-age.once="age"></child-component>
6.3 props驗證
props: {
data: Array,
columns: Array,
filterKey: String
}
這段代碼表示:父組件傳遞過來的data和columns必須是Array類型断序,filterKey必須是字符串類型。
7. 解決IE不支持<template>標(biāo)簽
IE不支持<template>標(biāo)簽糜烹,所以<template>標(biāo)簽中的內(nèi)容在IE瀏覽器中會被顯示出來违诗,所以要將<template>的display設(shè)置為none。
template{
display: none;
}
8. 使用slot:內(nèi)容分發(fā)
8.1 單個slot
<div id="app">
<my-component>
<h1>Hello vue.js!</h1>
</my-component>
<my-component></my-component>
</div>
<template id="temp">
<h2>this is a component!</h2>
<slot>slot</slot>
</template>
<script type="text/javascript">
var vm = new Vue({
el:'#app',
components:{
'my-component':{
template:'#temp',
}
}
})
</script>
<template>標(biāo)簽中的<slot>疮蹦,如果在使用該組件的時候诸迟,組件中包含了其他內(nèi)容,就會替換掉<slot>的內(nèi)容,如果組件沒有包含其他內(nèi)容阵苇,<slot>中的內(nèi)容就會直接顯示壁公。組件中包含的內(nèi)容叫做分發(fā)的內(nèi)容。
8.2 多個slot:指定名字绅项,對應(yīng)slot
<div id="app">
<my-component>
<div slot="slot1">
<h1>Hello slot1!</h1>
</div>
<div slot="slot2">
<h1>Hello slot2!</h1>
</div>
<div slot="slot3">
<h1>Hello slot3!</h1>
</div>
</my-component>
<my-component></my-component>
</div>
<template id="temp">
<h2>this is a component!</h2>
<slot name="slot1">slot1</slot>
<slot name="slot2">slot2</slot>
<slot name="slot3">slot3</slot>
</template>
<script type="text/javascript">
var vm = new Vue({
el:'#app',
components:{
'my-component':{
template:'#temp',
}
}
})
</script>
9.父子組件之間的訪問
9.1父組件訪問子組件
9.1.1 $children
父組件.$children[i]
9.1.2 $refs
在子組件上使用v-ref指令贮尖,可以給子組件指定一個索引ID:
<template id="parent-component">
<child-component1 v-ref:cc1></child-component1>
<child-component2 v-ref:cc2></child-component2>
<button v-on:click="showChildComponentData">顯示子組件的數(shù)據(jù)</button>
</template>
在父組件中,則通過$refs.索引ID訪問子組件的實例:
showChildComponentData: function() {
alert(this.$refs.cc1.msg);
alert(this.$refs.cc2.msg);
}
9.2 子組件訪問父組件
alert(子組件.$parent.msg)
10.自定義事件
10.1 派發(fā)事件$dispatch()
<div id="app">
<p>Messages: {{ messages | json }}</p>
<child-component></child-component>
</div>
<template id="child-component">
<input v-model="msg" />
<button v-on:click="notify">Dispatch Event</button>
</template>
<script src="js/vue.js"></script>
<script>
// 注冊子組件
Vue.component('child-component', {
template: '#child-component',
data: function() {
return {
msg: ''
}
},
methods: {
notify: function() {
if (this.msg.trim()) {
this.$dispatch('child-msg', this.msg)
this.msg = ''
}
}
}
})
// 初始化父組件
new Vue({
el: '#app',
data: {
messages: []
},
events: {
'child-msg': function(msg) {
this.messages.push(msg)
}
}
})
</script>
- 子組件的button元素綁定了click事件趁怔,該事件指向notify方法
- 子組件的notify方法在處理時,調(diào)用了$dispatch薪前,將事件派發(fā)到父組件的child-msg事件润努,并給該該事件提供了一個msg參數(shù)
- 父組件的events選項中定義了child-msg事件,父組件接收到子組件的派發(fā)后示括,調(diào)用child-msg事件铺浇。