第一章 組件化
1.1 認(rèn)識(shí)組件化
組件(Component)是對(duì)
數(shù)據(jù)
和方法
的簡(jiǎn)單封裝
1.2 組件的基本使用過(guò)程
<div id="app">
<!-- 3. 使用組件 -->
<my-cpn></my-cpn>
<my-cpn></my-cpn>
<my-cpn></my-cpn>
</div>
<script src="../js/vue.js"></script>
<script>
// 1. 創(chuàng)建組件構(gòu)造對(duì)象
const cpnC = Vue.extend({
template: `
<div>
<h2>標(biāo)題</h2>
<p>內(nèi)容:哈哈哈哈~~~~~</p>
</div>`,
})
// 2. 注冊(cè)組件
// Vue.component(`組件的標(biāo)簽名`,cpnC)
Vue.component(`my-cpn`, cpnC)
const app = new Vue({
el: '#app',
})
</script>
1.3 全局組件和局部組件
全局組件
// 注冊(cè)組件(全局組件, 可以在多個(gè)Vue的實(shí)例下面使用)
Vue.component(`my-cpn`, cpnC)
局部組件
const app2 = new Vue({
el: '#app2',
/* 1. 局部組件 */
components: {
cpn: cpnC,
},
})
1.4 父組件和子組件
const childC = Vue.extend({
// 子組件
template: `
<div>
<h2>I am son component</h2>
<p>i has any money</p>
</div>
`,
})
const parentC = Vue.extend({
// 父組件
template: `
<div>
<h2>I am father component</h2>
<p>I have many son</p>
<child></child>
</div>
`,
components: {
/* 建立子組件 */
child: childC,
},
})
const app = new Vue({
el: '#app',
components: {
parent: parentC,
},
})
1.5 組件注冊(cè)的語(yǔ)法糖
// 全局組件
Vue.component(`my-cpn`, {
template: `
<div>
<h2>全局組件</h2>
<p>內(nèi)容:哈哈哈哈~~~~~</p>
</div>
`,
})
// 局部組件
const app = new Vue({
el: '#app',
data: {
message: 'hello',
},
components: {
cpn1: {
template: `
<div>
<h2>局部組件</h2>
<p>內(nèi)容:哈哈哈哈~~~~~</p>
</div>
`,
},
},
})
1.6 模板的分離寫(xiě)法
- script(不常用)
<!-- 1. script標(biāo)簽,類(lèi)型必須是 text/x-template -->
<script type="text/x-template" id="cpn">
<div>
<h2>{{title}}</h2>
<p>{{message}}</p>
</div>
</script>
<script src="../js/vue.js"></script>
<script>
Vue.component(`cpn`, {
template: `#cpn`,
data() {
return {
title: '全局組件',
message: '內(nèi)容:我是全局組件 哈哈哈哈~~~~~',
}
},
})
const app = new Vue({
el: '#app',
components: {
cpn1: {
template: `#cpn`,
},
},
})
</script>
- template(如果內(nèi)部的標(biāo)簽大于 1 烁设,則需要有一個(gè)根 div 來(lái)包含內(nèi)容)
<template id="cpn1">
<div>
<h2>局部組件</h2>
<p>內(nèi)容:哈哈哈哈~~~~~</p>
</div>
</template>
<script src="../js/vue.js"></script>
<script>
const app = new Vue({
el: '#app',
components: {
cpn1: {
template: `#cpn1`,
},
},
})
</script>
1.7 數(shù)據(jù)的存放
- 子組件不能訪問(wèn)父組件
- 子組件有自己的 data,而且必須是一個(gè)函數(shù)
Vue.component(`cpn`, {
template: `#cpn1`,
data() {
return {
counter: 0
}
}
- 為什么是一個(gè)函數(shù)?
目的:讓每一個(gè)控件獨(dú)立的存在厨喂,不發(fā)生多個(gè)綁定在一起
1.8 父子組件的通信
父?jìng)髯?: props
/* v-bind 目前不支持駝峰,或者寫(xiě)成 c-movies */
const cpn = {
template: '#cpn',
/* 1. 數(shù)組形式 */
// props: ['c-movies', 'c-message'],
props: {
/* 2. 類(lèi)型限制 */
// c-movies: Array,
// c-message: String
/* 3. 提供一些默認(rèn)值(以及必傳值) */
c-message: {
type: String,
default: '沒(méi)有信息', // 沒(méi)有傳值時(shí)則顯示默認(rèn)值
},
c-movies: {
type: Array,
default() {
return ['沒(méi)有發(fā)現(xiàn)']
},
required: true, // 表示必須傳該數(shù)組 否則報(bào)錯(cuò)
},
},
data() {
return {}
},
}
子傳父 : $emit
<!-- 父組件模板 -->
<div id="app">
<!-- 父組件監(jiān)聽(tīng)子組件發(fā)送的請(qǐng)求 -->
<cpn @itemclick="cpnClick"></cpn>
</div>
<!-- 子組件模板 -->
<template id="cpn">
<div>
<button v-for="item in categories" @click="btnClick(item)">
{{item.name}}
</button>
</div>
</template>
<script src="../js/vue.js"></script>
<script>
/* 子組件 */
const cpn = {
template: '#cpn',
data() {
return {
categories: [
{id: 'a1', name: '熱門(mén)推薦'},
{id: 'a2', name: '手機(jī)數(shù)碼'},
{id: 'a3', name: '家用家電'},
]
}
},
methods: {
btnClick(item) {
// 發(fā)射事件: 自定義事件
/* itemclick 表示事件的名稱(chēng) */
this.$emit('itemclick', item){
console.log();
}
}
}
}
/* 父組件 */
const app = new Vue({
el: '#app',
components: {
cpn
},
methods: {
cpnClick(item) {
console.log(item);
}
}
})
</script>
第二章 組件化開(kāi)發(fā)
2.1 父子組件的訪問(wèn)
- 父組件 訪問(wèn) 子組件
- $children (不常用)
<div id="app">
<cpn></cpn>
<button @click="btnClick">按鈕</button>
</div>
<template id="cpn">
<div>我是子組件</div>
</template>
<script src="../js/vue.js"></script>
<script>
const app = new Vue({
el: '#app',
methods: {
btnClick() {
console.log(this.$children)
this.$children[0].name
for (let c of this.$children) {
console.log(c.name)
}
},
},
components: {
cpn: {
template: '#cpn',
data() {
return {
name: '我是子組件的name',
}
},
},
},
})
</script>
- $refs
<div id="app">
<cpn ref="aaa"></cpn>
<button @click="btnClick">按鈕</button>
</div>
<template id="cpn">
<div>我是子組件</div>
</template>
<script src="../js/vue.js"></script>
<script>
const app = new Vue({
el: '#app',
methods: {
btnClick() {
console.log(this.$refs.aaa.name)
},
},
components: {
cpn: {
template: '#cpn',
data() {
return {
name: '我是子組件的name',
}
},
},
},
})
</script>
- 子組件 訪問(wèn) 父組件 (不常用)
- $parent <訪問(wèn)父組件>
<div id="app">
<cpn></cpn>
</div>
<template id="cpn">
<div>
<h3>我是子組件</h3>
<button @click="btnClick">按鈕</button>
</div>
</template>
<script src="../js/vue.js"></script>
<script>
const app = new Vue({
el: '#app',
components: {
cpn: {
template: '#cpn',
methods: {
btnClick() {
// 訪問(wèn)父組件
console.log(this.$parent)
},
},
},
},
})
</script>
- $root <訪問(wèn)根組件>
<div id="app">
<cpn></cpn>
</div>
<template id="cpn">
<div>
<h3>我是子組件</h3>
<button @click="btnClick">按鈕</button>
</div>
</template>
<script src="../js/vue.js"></script>
<script>
const app = new Vue({
el: '#app',
components: {
cpn: {
template: '#cpn',
methods: {
btnClick() {
// 訪問(wèn)根組件 $root
console.log(this.$root)
},
},
},
},
})
</script>
2.2 插槽(slot)的使用
- 基本使用
<div id="app">
<!-- 1. 未設(shè)置插槽的標(biāo)簽 -->
<cpn></cpn>
<!-- 2. 設(shè)置一個(gè)插槽的值 -->
<cpn><i>我是i標(biāo)簽</i></cpn>
<!-- 3. 設(shè)置多個(gè)插槽的值 -->
<cpn>
<div>我是div標(biāo)簽</div>
<a>我是a標(biāo)簽</a>
</cpn>
</div>
<template id="cpn">
<div>
<h3>我是h3標(biāo)簽</h3>
<p>我是p標(biāo)簽</p>
<!-- slot 中設(shè)置默認(rèn)標(biāo)簽, 如果沒(méi)有替換的標(biāo)簽, 顯示默認(rèn)的標(biāo)簽 -->
<slot>
<button>我是btn按鈕</button>
</slot>
</div>
</template>
- 具名插槽
<div id="app">
<!-- 定位替換 確定好插槽的名字 -->
<cpn>
<span slot="center">我是新的span標(biāo)簽</span>
</cpn>
</div>
<template id="cpn">
<div>
<!-- 寫(xiě)入每個(gè)插槽的名字 -->
<slot name="left"><span>左邊</span></slot>
<slot name="center"><span>中間</span></slot>
<slot name="right"><span>右邊</span></slot>
</div>
</template>
- 編譯的作用域
<div id="app">
<!-- 1. 直接顯示 -->
<cpn></cpn>
<cpn>
<!-- 2. 轉(zhuǎn)換顯示方式 -->
<template slot-scope="slot">
<p v-for="item in slot.data">{{item}} -</p>
<p>{{slot.data.join(' - ')}}</p>
<p>{{slot.data.join(' * ')}}</p>
</template>
</cpn>
</div>
<template id="cpn">
<div>
<slot :data="pLanguages">
<ul>
<li v-for="item in pLanguages">{{item}}</li>
</ul>
</slot>
</div>
</template>
<script src="../js/vue.js"></script>
<script>
const app = new Vue({
el: '#app',
components: {
cpn: {
template: '#cpn',
data() {
return {
pLanguages: [
'JavaScript',
'Python',
'C++',
'C#',
'Swift',
],
}
},
},
},
})
</script>
- 作用域插槽
第三章 前端模塊化
3.1 為什么使用模塊化
- 簡(jiǎn)單寫(xiě) js 代碼帶來(lái)的問(wèn)題
- 閉包引起代碼不可復(fù)用
- 自己實(shí)現(xiàn)了簡(jiǎn)單的模塊化
- AMD/CMD/CommonJS
3.2 ES6 中模塊化的使用
- export (導(dǎo)出)
// 1. CommonJS 模塊化 導(dǎo)出
module.export = {
add,
mul,
}
// 2. ES6 模塊化 導(dǎo)出
export const name = 'Tom'
export const age = 18
export const height = 1.88
- import (導(dǎo)入)
/* 1. CommonJs 模塊化 導(dǎo)入 */
const { add, mul } = require('./js/mathUtils.js')
/* 2. ES6 模塊化導(dǎo)入 */
import * as info from './js/info.js'
// 例外
/* 3. 依賴(lài) 文件 導(dǎo)入 */
require('./css/normal.css')