1.组件简介
组件: Vue最强大的功能之一,其作用如下图:
- 模块: 向外提供特定功能的 js 程序,一般就是一个 js 文件。
作用:复用 js,简化 js 的编写,提高 js 运行效率。 - 组件: 用来实现局部功能的代码和资源的集合(html/css/js/image…)。
作用:复用编码,简化项目编码,提高运行效率。 - 模块化: 当应用中的 js 都以模块来编写的,那这个应用就是一个模块化的应用。
- 组件化: 当应用中的功能都是多组件的方式来编写的,那这个应用就是一个组件化的应用。
2.非单文件组件
1.组件的基本使用
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>组件案例1</title>
<script type="text/javascript" src="js/vue.js"></script>
</head>
<body>
<div id="root" :style="{width: '100%',height: `${height}px`}">
<button @click='chgView'>{{nameP}}</button>
<!-- 3)使用子组件 -->
<demo1 v-if='viewD'></demo1>
</div>
</body>
<script>
/* 1)创建子组件demo1 */
const demo1 = Vue.extend({
template:`
<div class="demo1">
<h1>{{nameD}}</h1>
</div>
`,
data() {
return {
nameD: '这里是子组件',
}
}
})
/* 2)注册组件——全局注册 */
Vue.component('demo1', demo1)
const vm = new Vue({
el: '#root',
/* 2)注册组件——局部注册*/
/* components: {
// 也可以这样写 Demo1:demm1,Demo1是组件别名,上面的标签也要改成Demo1
demo1,
}, */
data () {
return {
nameP:'点击显示/隐藏子组件',
height: document.documentElement.clientHeight,
viewD: false
}
},
methods: {
chgView() {
this.viewD = !this.viewD;
}
},
})
</script>
</html>
2.小结一
小结:
- Vue中使用组件的三大步骤:
-
- 定义组件(创建组件)
-
-
- 使用
Vue.extend(options)
创建,其中options
和new Vue(options)
时传入的options
几乎一样,但也有点区别:
- 使用
-
-
-
-
- 不用写
el
,因为最终所有的组件都要经过一个vm的管理,由vm中的el决定服务哪个容器
- 不用写
-
-
-
-
-
data
必须写成函数,避免组件被复用时,数据存在引用关系
-
-
-
- 注册组件
-
-
- 局部注册:
new Vue
的时候传入components
选项
- 局部注册:
-
-
-
- 全局注册:
Vue.component('组件名',组件)
- 全局注册:
-
-
- 使用组件(写组件标签)
-
-
<demo1 v-if='viewD'></demo1>
-
注意事项:
- 组件名规范:
-
- 单个单词:首字母可以大写,也可以小写
-
- 多个单词:kebab-case命名,CamelCase命名(需要Vue脚手架支持)
-
- 别使用HTML已有的元素名
- 组件标签:
-
- 写法:
<demo1></demo1>
、<demo1/>
不使用脚手架时,<demo1/>
会导致后续组件不能渲染
- 写法:
- 创建子组件的简写:
const demo1 = Vue.extend(options)
→const demo1 = options
3.组件的嵌套
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>组件嵌套</title>
<script type="text/javascript" src="js/vue.js"></script>
</head>
<body>
<div id="root" :style="{width: '100%',height: `${height}px`}">
<button @click='chgView'>{{nameP}}</button>
<!-- 使用子组件 -->
<app v-if='viewD'></app>
</div>
</body>
<script>
const demo1_1 = Vue.extend({
template:`
<div class="demo1_1">
<h3>{{nameD}}</h3>
</div>
`,
data() {
return {
nameD: '这里是子组件demo1_1',
}
}
})
const demo1 = Vue.extend({
template:`
<div class="demo1">
<h2>{{nameD}}</h2>
<button @click='chgViewD1'>点击显示/隐藏子组件</button>
<demo1_1 v-if='viewD1'></demo1_1>
</div>
`,
data() {
return {
nameD: '这里是子组件demo1',
viewD1: false,
}
},
methods: {
chgViewD1() {
this.viewD1 = !this.viewD1
}
},
components: {
demo1_1,
}
})
const demo2 = Vue.extend({
template:`
<div class="demo2">
<h2>{{nameD}}</h2>
</div>
`,
data() {
return {
nameD: '这里是子组件demo2',
}
}
})
const demo3 = Vue.extend({
template:`
<div class="demo3">
<h2>{{nameD}}</h2>
</div>
`,
data() {
return {
nameD: '这里是子组件demo3',
}
}
})
const app = Vue.extend({
template:`
<div>
<demo1></demo1>
<demo2></demo2>
<demo3></demo3>
</div>
`,
components: {
demo1,
demo2,
demo3,
}
})
const vm = new Vue({
el: '#root',
/* 注册组件——局部注册*/
components: {
app,
},
data () {
return {
nameP:'点击显示/隐藏子组件',
height: document.documentElement.clientHeight,
viewD: false
}
},
methods: {
chgView() {
this.viewD = !this.viewD;
}
},
})
</script>
</html>
4.小结二
组件的嵌套: 就是把一个子组件A注册到另一个子组件B里面。
- 注意:
-
- 子组件A需要定义在子组件B之前
-
- 子组件A只能在子组件B的标签内使用
- 在实际开发中,通常使用一个最外部的子组件(一般被叫做 app)来统一管理其他组件
注意:可以不在body中使用app标签,可以直接写在vm中:
template:`
<app></app>
`,
5.VueComponent
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>VueComponent</title>
<script type="text/javascript" src="js/vue.js"></script>
</head>
<body>
<div id="root" :style="{width: '100%',height: '100%'}">
</div>
</body>
<script>
const demo1 = Vue.extend({
template:`
<div class="demo1">
<h1>{{nameD}}</h1>
</div>
`,
data() {
return {
nameD: '这里是子组件',
}
}
})
console.log(demo1)
const vm = new Vue({
template:`
<demo1/>
`,
el: '#root',
components: {
demo1,
},
})
</script>
</html>
VueComponent:
- demo1组建的本质是一个名为
VueComponent
的构造函数,且不是程序员定义的,是Vue.extend
生成的 - 使用子组件的标签
<demo1></demo1>
、</demo1>
,Vue解析时会帮我们创建demo1组件的实例对象,即Vue帮我们执行的:new VueComponent(options) - 每次调用
Vue.extend
,返回的都是一个全新的VueComponent
!
注意:对于同一个组件,多次使用其标签,只会调用一次对应的Vue.extend
,即,同一组件只会返回一个VueComponent
- 关于this指向:
-
- 组件配置中:
data
函数、methods
中的函数、watch
中的函数、computed
中的函数 它们的this均是VueComponent实例对象
- 组件配置中:
-
new Vue(options)
配置中:data
函数、methods
中的函数、watch
中的函数、computed
中的函数 它们的this均是Vue实例对象
6.一个重要的内置关系
不明白prototype
和_proto_
关系的可以看这篇文章:prototype和__proto__
prototype
是函数才有的属性__proto__
是每个对象都有的属性- 大多数情况:
__proto__
可以理解为“构造器的原型”,即__proto__=== constructor.prototype
一个重要的内置关系: VueComponent.prototype._proto_ === Vue.prototype
3.单文件组件
1.对外暴露组件的写法
不明白 es6模块化 的可以看这篇文章:一篇文章帮你弄懂ES6模块化
暴露组件的写法:
<script>
/* 交互代码
export 暴露接口
此处是分别暴露
import {xxx} from xxxx
*/
export const demo1 = Vue.extend({
data() {
},
methods: {
}
})
/* 统一暴露
import {xxx} from xxxx
*/
// export {demo1}
/* 默认暴露
一般都用默认暴露——import xxx from xxxx
*/
// export default demo1
</script>
默认暴露的另一写法:
export default Vue.extend({
data() {
},
methods: {
}
})
默认暴露最常用的写法:
export default {
// 这里最好写一个name,最好与文件名一致
name:'Demo1',
data() {
},
methods: {
}
}
2.单文件组件结构
组件部分: xxx.vue
template
div容器部分(唯一根节点,必须部分)script
Vue实例部分-
export default
暴露组件(默认暴露)
-
import xxxfrom './xxx.vue'
引入组件并使用
-
components
注册组件
style
容器样式部分
组件注册部分: mian.js
import xxxfrom './xxx.vue'
new Vue({
//template:`<App></App>`, 这里写了,就不用在index.html中写标签
el:'#root',
components:{App}
})
容器部分: index.html
- 所有组件标签都是在这里被使用,并显示在页面上
<script src="../js/vue.js"></script>
<script src="./main.js"></script>
单文件组件剩余部分需要用到脚手架,下一章再见。
![](https://i-blog.csdnimg.cn/blog_migrate/ecca1bd56c5d477e0aba793e9f111b51.png)