组件化编程

模块与组件、模块化与组件化

模块:
(1)理解:向外提供特定功能的 js 程序,一般就是一个 js 文件
(2)为什么:js 文件很多很复杂
(3)作用:复用、简化 js 的编写,提高 js 运行效率

组件:
(1)定义:用来实现局部功能的代码和资源的集合(html / css / js / image...)
(2)为什么:一个界面的功能很复杂
(3)作用:复用编码,简化项目编码,提高运行效率

模块化:当应用中的 js 都以模块来编写,那这个应用就是一个模块化的应用;

组件化:当应用中的功能都是多组件的方式来编写,那这个应用就是一个组件化的应用;

非单文件组件

提示

非单文件组件:一个文件中包含 n 个组件

基本使用

Vue 中使用组件的三大步骤:

(1)定义组件

使用Vue.extend(options)创建,其中options和new Vue(options)时传入的options几乎一样,但也有些许区别:

① el 不要写,因为最终所有的组件都要经过一个 vm 的管理,由 vm 中的 el 来决定服务于哪个容器;
② data 必须写成函数,避免组件被复用时,数据存在引用关系;
备注: 使用 template 可以配置组件结构

(2)注册组件

// 局部注册
new Vue() 的时候 options 传入 components 选项

// 全局注册
Vue.component('组件名', 组件);

(3)使用组件(写组件标签):直接写组件标签,如:<school></school>

代码示例
<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta http-equiv="X-UA-Compatible" content="IE=edge" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>组件</title>
    <script src="https://cdn.jsdelivr.net/npm/vue@2.5.16/dist/vue.js"></script>
  </head>

  <body>
    <div id="root">
      <!-- ③ 使用组件 -->
      <hello></hello>
      <hr />
      <h3>姓名:{{name}}</h3>
      <h3>地点:{{address}}</h3>
    </div>
    <script>
      Vue.config.productionTip = false;

      // ① 定义组件
      const hello = Vue.extend({
        template: `<h2>{{msg}}</h2>`,
        data() {
          return {
            msg: '你好!'
          };
        }
      });

      // ② 注册组件(全局)
      //   Vue.component('hello', hello);

      new Vue({
        // ② 注册组件(局部)
        components: {
          hello
        },
        el: '#root',
        data: {
          name: '李华',
          address: '深圳'
        }
      });
    </script>
  </body>
</html>

hello组件演示.png

注意事项

① 关于组件名

一个单词:hello(首字母小写) 或 Hello(首字母大写)

多个单词:my-school(kebab-case 命名) 或 MySchool(CamelCase 命名),后者需要 Vue 脚手架支持

⚠️:组件中尽可能回避 HTML 中已有的元素名称,例如 h2、H2 都不行,此外可以使用name配置项指定组件在开发者工具中呈现的名字

② 关于组件标签

<school></school>或<school/>,后者不使用脚手架时,会导致后续组件不渲染

③ 简写方式
const school = Vue.extend(options);
// 可以简写为下面这样
const school = options;

组件的嵌套

组件的嵌套示意.png
代码示例
<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta http-equiv="X-UA-Compatible" content="IE=edge" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>组件的嵌套</title>
    <script src="https://cdn.jsdelivr.net/npm/vue@2.5.16/dist/vue.js"></script>
  </head>

  <body>
    <div id="root">
      <hello></hello>
      <school></school>
    </div>
    <script>
      Vue.config.productionTip = false;

      const hello = Vue.extend({
        template: `<h2>{{msg}}</h2>`,
        data() {
          return {
            msg: '你好!'
          };
        }
      });

      const student = Vue.extend({
        template: `
        <div>
          <h2>姓名:{{name}}</h2>
          <h2>年龄:{{age}}</h2>
        </div>
      `,
        data() {
          return {
            name: '李华',
            age: 20
          };
        }
      });

      const school = Vue.extend({
        template: `
        <div>
          <h2>学校:{{name}}</h2>
          <h2>地址:{{address}}</h2>
          <student></student>
        </div>
      `,
        data() {
          return {
            name: '史莱克学院',
            address: '史莱克城'
          };
        },
        components: {
          student
        }
      });

      new Vue({
        el: '#root',
        data: {
          name: '唐三',
          address: '斗罗大陆'
        },
        components: {
          hello,
          school
        }
      });
    </script>
  </body>
</html>
组件嵌套演示.png

VueComponent

(1)组件的本质是一个名为VueComponent的构造函数,它不是程序员定义的,而是Vue.extend()生成的
(2)我们只需要写组件标签(如:<school/>),Vue 解析时会帮我们创建组件的实例对象,即 Vue 帮我们执行的new VueComponent(options)
(3)每次调用Vue.extend(),返回的都是一个全新的VueComponent,即不同组件是不同的对象
(4)关于 this 的指向:

① 组件配置中:data 函数、methods 中的函数、watch 中的函数、computed 中的函数,它们的 this 均为VueComponent 实例对象
② new Vue()配置中:data 函数、methods 中的函数、watch 中的函数、computed 中的函数,它们的 this 均为Vue 实例对象

(5)VueComponent 的实例对象(组件实例对象)简称 vc;Vue 的实例对象简称 vm

一个重要的内置关系

内置关系.png

提示

① 一个重要的内置关系:VueComponent.prototype.__proto__ === Vue.prototype

② 为什么要有这个关系:让组件实例对象 vc 可以访问到 Vue 原型上的属性、方法

单文件组件

提示

单文件组件:一个文件中只包含 1 个组件

单文件组件简单示例: