概念

Vue遵循Web Component规范,提供了自己的组件系统。组件是一段独立的代码,代表页面中某个功能块,拥有自己的数据、JS、样式,以及标签。组件的独立性是指形成自己独立的作用域,不会对其它组件产生任何副作用。

Vue 组件是可复用 Vue 实例,接受相同的选项option对象 (除了一些根级特有的选项) 和使用相同的生命周期钩子,以及模板调用方式。

Vue 组件可以嵌套,所以组件之间可以进行引用和通信

组件定义

Vue提供了专用的API来定义组件,组件构造器函数: Vue.extend()

    const MyComponent = Vue.extend(option)
// option跟new Vue(option)时基本相同(除了el/data)

这样,我们就构建好了一个组件,但现在还无法使用这个组件。还需要将这个组件注册到对应的应用中。

组件的注册

为了能在模板中使用,这些组件必须注册以便 Vue 能够识别。有两种注册方式:全局注册和局部注册

全局注册

使用API:Vue.component就可以完成组件全局注册,全局注册的组件可以被多个Vue实例复用。

Vue.component('my-component', MyComponent)
// 组件注册语句必须在new Vue(option)之前

局部注册

使用Vue实例的components属性注册局部组件,局部注册的组件只在包含它的父组件作用域内有效。

const MyChild = Vue.extend({
template: `<p>{{ childMsg }}</p>`
data: function() {
return {
childMsg: 'This is a child component'
}
}
}) const vm = new Vue({
el: "#app",
data: {
msg: 'This is a parent component'
},
components: {
MyChild: MyChild
}
})

上述Child组件只在vm实例内有效。在其它新建的实例内无法引用。

注册语法糖

Vue对全局注册和局部注册都提供了简写方法,可以在注册的同时定义组件,Vue内部会自动调用extend方法构建组件。

Vue源码解读之Component组件注册

// 全局注册
Vue.component('MyChild', {
template: `<p>{{ childMsg }}</p>`
data: function() {
return {
childMsg: 'This is a child component'
}
}
}) // 局部注册
new Vue({
el: "#app",
data: {
msg: 'This is a parent component'
},
components: {
MyChild: {
template: `<p>{{ childMsg }}</p>`
data: function() {
return {
childMsg: 'This is a child component'
}
}
},
}
})

组件的使用

在注册组件同时,也声明了一个自定义标签,即组件名。在Vue模板需要调用的地方使用组件名作为自定义的标签,直接调用组件。

<My-Child></My-Child>

注意事项:

option的区别

const MyChild = Vue.extend(option)
const vm = new Vue(option)
  • data必须是一个函数

    因为组件是可复用的,如果组件的data是一个对象的直接引用,那复用多个组件将共享一个对象,其中一个组件修改了对象属性,其它组件引用了该对象属性的值也会变化,这是我不希望看到的。而通过函数返回值,将实现每个组件拥有独立的数据对象。

    点击查看官方示例解释
new Vue({
el: "#app",
data: {
msg: 'This is a parent component'
},
components: {
MyChild: {
template: `<p>{{ childMsg }}</p>`
data: function() {
return {
childMsg: 'This is a child component'
}
}
},
}
})

解析 DOM 模板时的注意事项

有些 HTML 元素,诸如 <ul><ol><table><select>,对于哪些元素可以出现在其内部是有严格限制的。而有些元素,诸如 <li><tr><option>,只能出现在其它某些特定的元素内部。

这会导致我们使用这些有约束条件的元素时遇到一些问题。例如:

<table>
<blog-post-row></blog-post-row>
</table>

这个自定义组件 会被作为无效的内容提升到外部,并导致最终渲染结果出错。幸好这个特殊的 is 特性给了我们一个变通的办法:

<table>
<tr is="blog-post-row"></tr>
</table>

需要注意的是如果我们从以下来源使用模板的话,这条限制是不存在的:

组件的命名规范

官方组件命名风格指南

  • 在JS域中使用PascalCase,在DOM模板域中使用kebab-case
  • 以父组件或更高级别的单词开头,使用语义完整的单词
  • 由于 HTML 是大小写不敏感的,在 DOM 模板中必须使用 kebab-case
  • 在 JavaScript 中,PascalCase 是类和构造函数 (本质上任何可以产生多份不同实例的东西) 的命名约定,Vue 组件也可以有多份实例,所以同样使用 PascalCase 是有意义的。

点击查看DEMO

<div id="app">
<p>{{ msg }}</p>
<com-local></com-local>
<com-global></com-global>
</div>
<p>=================================</p>
<div id="other">
<p>{{ msg }}</p>
<com-other-local></com-other-local>
<com-global></com-global>
</div>
// 使用构造器函数定义组件
const ComLocal = Vue.extend({
data: function() {
return {
msg: 'This is a local component'
}
},
template: `<p>{{ msg }} by Vue.extend</p>`
}) // 全局注册组件,并且必须在new Vue()之前
Vue.component('ComGlobal', {
data: () => {
return {
msg: 'this is a global component'
}
},
template: `<p>{{ msg }} by Vue.component`
}) // 创建一个Vue 实例对象vm,调用全局组件和使用extend定义的局部组件
const vm = new Vue({
el: "#app",
data: {
msg: 'This is a vm'
},
components: {
ComLocal
} }) // 创建另一个Vue实例对象otherVm,调用全局组件和使用内部components属性定义的局部组件
const otherVm = new Vue({
el: '#other',
data: {
msg: 'This is other Vue'
},
components: {
comOtherLocal: {
template: `<p>This is a local component by components properity</p>`
}
}
})
// 输出
This is a vm
This is a local component by Vue.extend
this is a global component by Vue.component
=================================
This is other Vue
This is a local component by components properity
this is a global component by Vue.component

最新文章

  1. 【Python④】python恼人的字符串,格式化输出
  2. Java集合的10个最常见问题
  3. zzy:java采用的是16位的Unicode字符集作为编码方式------理解
  4. hdu 2041 超级楼梯
  5. openstack(liberty): devstack中的iniset/iniget函数分析
  6. SQL 中delete和truncate区别
  7. QT的Paint 系统
  8. 前端资源多个产品整站一键打包&amp;包版本管理(二)——如何在bower的配置文件加上注释
  9. Linux后门入侵检测工具,附bash漏洞解决方法[转载]
  10. Andorid第三方库
  11. linux下使用scp远程传输自动输入密码
  12. Nomad入门
  13. unity中使用www的库读取数据里面的数据
  14. MySQL 官方 Docker 镜像的使用
  15. STL set简单用法
  16. poj2823 单调队列初步
  17. Handler具体解释系列(七)——Activity.runOnUiThread()方法具体解释
  18. LeetCode 笔记系列一 Median of Two Sorted Arrays
  19. day18 分页+form验证+中间件
  20. div,css常用技术

热门文章

  1. Leetcode783.Minimum Distance Between BST Nodes二叉搜索树结点最小距离
  2. char和achar互转
  3. osgi实战学习之路:4.Bundle
  4. 在WPF中绘制多维数据集
  5. 使用 Javascript 将二进制字符串转成数字
  6. 【vb.net机房收费系统】之sqlhelper 标签: 数据库 2015-05-17 10:47 819人阅读 评论(15)
  7. Python基础:04映射类型
  8. 交互式计算和开发环境:IPython
  9. Hbase数据模型概念视图
  10. PHP中__FUNCTION__与__METHOD__的区别