
組件化
組件化是任何一個(gè)框架必須實(shí)現(xiàn),如何將定義組件(js 對(duì)象)轉(zhuǎn)化為 dom 對(duì)象,以及組件的屬性轉(zhuǎn)換為 dom 屬性,這是每一個(gè)前端框架在設(shè)計(jì)時(shí)需要認(rèn)真思考和設(shè)計(jì)的問題。
const vm= new Vue({
el:'#root',
data:{},
props:{},
methods:{},
watch:{},
computed:{},
template:"...",
components:{},
});
| 屬性名 | 說明 |
|---|---|
| el | 用來加載 Vue 對(duì)象的元素 |
| data | 綁定的數(shù)據(jù) |
| props | 用來接收外部數(shù)據(jù)的屬性 |
| methods | 定義 Vue 對(duì)象內(nèi)部使用的方法 |
| watch | 用于觀察 Vue 對(duì)象內(nèi)部資料的更新 |
| computed | 自動(dòng)為內(nèi)部數(shù)據(jù)計(jì)算過的屬性 |
| template | 存放 Vue 對(duì)象編譯后生成的模板 |
| components | 定義子元素 |
昨天寫 react,今天朋友讓我來談?wù)?vue,個(gè)人對(duì)于 vue 了解并不多。先接觸的 angular 隨后是 react ,vue 是這兩年市場推動(dòng)不得不也看一看 vue。最近聽了 Evan 關(guān)于 vue3 介紹,vue3 還是很吸引人,一堆提高性能的優(yōu)化。
按作用域范圍
-
區(qū)域性(具有作用域)注冊(cè)組件
register_scope
其實(shí)渲染出來并不是 javascript 提供自定義組件而是一個(gè) div
render_div_for_register_scope
所謂區(qū)域(作用域)注冊(cè)中區(qū)域指的就是這些元素父級(jí)元素<div id="app">
<div id="app">
<zi-comp></zi-comp>
<zi-comp></zi-comp>
<zi-comp></zi-comp>
</div>
<div id="app2">
<zi-comp></zi-comp>
</div>
這樣在 app2 作用域內(nèi)是無法識(shí)別到在 app 作用域注冊(cè)的組件 zi-comp

關(guān)于組件中 data 的屬性
這里有一個(gè)我們需要注意的,也是我們對(duì) vue 設(shè)計(jì)理念有點(diǎn) confusing 的。data 屬性值是一個(gè)函數(shù)返回一個(gè)對(duì)象,而不是直接接收一個(gè)對(duì)象作為 data 的屬性值。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
<title>Document</title>
</head>
<body>
<div id="app">{{msg}}<zi-comp></zi-comp>
</div>
<script>
Vue.component('zi-comp', {
template: '<div class="comp">{{msg}}</div>',
data: function () {
return {
msg: "A custom component of Vue"
}
}
});
new Vue({
el: "#app",
data: {
msg: 'A root msg of Vue'
}
});
</script>
</body>
</html>
在組件中對(duì) data 屬性
data: function () {
return {
msg: "A custom component of Vue"
}
}
為什么會(huì)這樣,可以簡單思考一下,因?yàn)樵?javascript 語言中沒有大括號(hào)的作用域,最小作用域范圍就是函數(shù),如果沒有通過 function 來限制數(shù)據(jù) data 作用范圍,data 就會(huì)把全局 data 覆蓋掉,就這么簡單。
大家可以通過運(yùn)行下面的代碼來觀察問題,以及我們?yōu)槭裁匆?data 屬性通過一個(gè)函數(shù)返回值來給 data 屬性賦值的原因。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
<title>Document</title>
<style>
.container {
width: 100vw;
height: 50vh;
display: flex;
justify-content: center;
align-items: center;
flex-direction: column;
}
.comp {
height: 48px;
background: dodgerblue;
padding: 12px 24px;
display: flex;
color: white;
font-size: 1.2em;
margin-bottom: 6px;
justify-content: center;
align-items: center;
}
</style>
</head>
<body>
<div id="app" class="container">
<zi-comp></zi-comp>
<zi-comp></zi-comp>
<zi-comp></zi-comp>
<zi-comp></zi-comp>
<zi-comp></zi-comp>
</div>
<script>
var data = {
count: 0
}
Vue.component('zi-comp', {
template: '<div class="comp"><span>{{count}}</span> <button @click="count++">add</button> </div>',
data: function () {
return data;
}
});
new Vue({
el: "#app"
});
</script>
</body>
</html>
通過修改 zi-comp 的 data 屬性,返回一個(gè)對(duì)象,這樣 count 屬性就不會(huì)覆蓋外面屬性,這時(shí)的 count 只屬于該 zi-comp 組件實(shí)例化對(duì)象的 count。通過這個(gè)示例我想大家可能對(duì)為什么在 vue 的組件定義數(shù)據(jù) data 屬性時(shí),需要提供函數(shù)然后在其中將數(shù)據(jù)對(duì)象返回原因了吧。
Vue.component('zi-comp', {
template: '<div class="comp"><span>{{count}}</span> <button @click="count++">add</button> </div>',
data: function () {
return {
count:0
};
}
});
模板文件
在 vue 中,避免大家在 vue 對(duì)象中的 template 寫一些復(fù)雜 html 結(jié)構(gòu),vue 和其他框架一樣提供在 vue 外部寫 html 模板,然后在 vue 對(duì)象通過模板 id 來引用模板的方式來寫模板。
<body>
<div id="app">
<zi-comp></zi-comp>
</div>
<script type="text/x-template" id="zi-comp">
<div class="comp">A custom component of Vue!</div>
</script>
<script>
//register
Vue.component('zi-comp', {
template: "#zi-comp"
});
new Vue({
el: "#app"
});
</script>
</body>

