組件中的data
組件是一個具有單獨自身功能模塊的封裝,這個模塊有屬於自己的HTML模板,也應該有屬於自己的數據data,組件也有自己的方法methods
注意:組件不能直接訪問Vue實例中定義的數據。就算可以訪問,若將所有的數據都放在Vue實例中,Vue實例就會變得非常臃腫(數據很多),所以組件應該有自己保存數據的地方
因此,data屬性必須是一個函數,並且這個函數返回一個對象,在對象內部保存數據
實例
<body>
<div id="app">
<cpn1></cpn1>
</div>
<template id="cpn">
<div>
<h2>{{message}}</h2>
//不會渲染,控制檯報錯
<h2>{{title}}</h2>
</div>
</template>
<script src="../vue.js"></script>
<script>
const app = new Vue({
el:'#app',
data:{
title:"Vue"
},
components:{
"cpn1":{
template:"#cpn",
//data位一個函數返回對象
data(){
return {
message:"hello vue"
}
}
}
}
})
</script>
</body>
data是函數----原理
function知識
在解釋原理之前先來看兩個個有關函數的例子
示例一:
<script>
function person() {
return {
name:"a",
age:22
}
};
var obj1 = person();
var obj2 = person();
obj1.name = 'b';
console.log(obj1);
console.log(obj2);
</script>
示例二:
<script>
const obj = {
name:"a",
age:22
}
function person() {
return obj;
};
var obj1 = person();
var obj2 = person();
obj1.name = 'b';
console.log(obj1);
console.log(obj2);
</script>
總結:第一個示例中每調用一次函數都返回一個新的對象,而在第二個示例中所共用一個對象。所以,在改變其中一個對象某一屬性的值時,第一個示例中的兩個對象不會相互影響,而第二個示例中則是相互影響的。
data是函數的原理
有了上面知識的基礎,就很好理解原理了。還是用實例來解釋,該實例中是用組件實現多個計數器功能
<body>
<div id="app">
<cpn></cpn>
<cpn></cpn>
<cpn></cpn>
</div>
<template id="cpn">
<div>
<h2>當前計數:{{count}}</h2>
<button @click="sub">-</button>
<button @click="add">+</button>
</div>
</template>
<script src="../vue.js"></script>
<script>
Vue.component('cpn',{
template:"#cpn",
//調用data函數,每次調用都返回一個新的對象
data(){
return {
count:0
}
},
//組件中的methods
methods:{
add() {
this.count++;
},
sub() {
this.count--;
}
}
})
const app = new Vue({
el:'#app',
})
</script>
</body>
案例總結
創建了三個組件實例計數器,每個計數器可以完成自己的計數功能,互不影響。即實例中的data對象都是不同的(沒有共享data對象),可以參考function知識中的示例一
舉一反三
還是以上面這個計數器的例子,對代碼稍作更改(更改部分已作註釋),也會有不一樣的效果。
<body>
<div id="app">
<cpn></cpn>
<cpn></cpn>
<cpn></cpn>
</div>
<template id="cpn">
<div>
<h2>當前計數:{{count}}</h2>
<button @click="sub">-</button>
<button @click="add">+</button>
</div>
</template>
<script src="../vue.js"></script>
<script>
//更改部分
const counter = {
count:0
};
Vue.component('cpn',{
template:"#cpn",
//更改部分
data(){
return counter
},
methods:{
add() {
this.count++;
},
sub() {
this.count--;
}
}
})
const app = new Vue({
el:'#app',
})
</script>
</body>
總結:這一個例子共用了一個對象,可以參考function知識示例二,這種連鎖反應一般在組件中很少應用到,因爲組件是複用的,自然就不希望數據共享,而是有自己的邏輯,保存自己數據的實例