前端-Vue2组件化编程

什么是组件

组件的定义-实现应用中局部 功能代码和资源集合

非单文件组件

非单文件组件:

一个文件中包含有n个组件。

单文件组件:

一个文件中只包含有1个组件。

基本使用

介绍

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

一、定义组件(创建组件)

二、注册组件

三、使用组件(写组件标签)

一、如何定义一个组件?

使用**Vue.extend(options)**创建,其中options和new Vue(options)时传入的那个options几乎一样,但也有点区别;

区别如下:

1.el不要写 ,为什么? --------- 最终所有的组件都要经过一个vm的管理,由vm中的el决定服务哪个2.data必须写成函数,为什么? ------------ 避免组件被复用时,数据存在引用关系。

备注:使用template可以配置组件结构。

二、如何注册组件?

1.局部注册:靠new Vue的时候传入components选项

2.全局注册:靠Vue.component('组件名',组件),那么全局的vm都能用到这个组件

三、编写组件标签:<school></school>

组件的语法

一、定义组件

定义组件时,使用**Vue.extend 方法创建组件构造器**。

在构造器中,可以定义组件的 template(HTML)datamethods 等选项。

示例代码

javascript 复制代码
const school = Vue.extend({
  template: `
    <div class="demo">
      <h2>学校名称:{{schoolName}}</h2>
      <h2>学校地址:{{address}}</h2>
      <button @click="showName">点我提示学校名</button>  
    </div>
  `,
  data() {
    return {
      schoolName: '尚硅谷',
      address: '北京昌平'
    };
  },
  methods: {
    showName() {
      alert(this.schoolName);
    }
  }
});

二、注册组件

注册组件有两种方式:

  1. 全局注册 :使用 **Vue.component**方法将组件构造器注册为全局组件。

  2. 局部注册 :在 Vue 实例的 **components**选项中注册组件构造器。

示例代码

javascript 复制代码
// 全局注册 hello 组件
Vue.component('hello', hello);
​
// 创建 Vue 实例,局部注册 school 和 student 组件
new Vue({
  el: '#root',
  data: {
    msg: '你好啊!'
  },
  components: {
    school,
    student
  }
});

三、使用组件

在 Vue 实例的模板中通过自定义标签使用注册的组件。

示例代码

html 复制代码
<div id="root">
  <hello></hello>
  <hr>
  <h1>{{msg}}</h1>
  <hr>
  <!-- 使用组件标签 -->
  <school></school>
  <hr>
  <!-- 使用组件标签 -->
  <student></student>
</div>

详细代码

这是上面讲解语法的详细代码

html 复制代码
<!DOCTYPE html>
<html>
	<head>
		<meta charset="UTF-8" />
		<title>基本使用</title>
		<script type="text/javascript" src="../js/vue.js"></script>
	</head>
	<body>
		<!-- 准备好一个容器-->
		<div id="root">
			<hello></hello>
			<hr>
			<h1>{{msg}}</h1>
			<hr>
			<!-- 第三步:编写组件标签 -->
			<school></school>
			<hr>
			<!-- 第三步:编写组件标签 -->
			<student></student>
		</div>

		<div id="root2">
			<hello></hello>
		</div>
	</body>

	<script type="text/javascript">
		Vue.config.productionTip = false

		//第一步:创建school组件
		const school = Vue.extend({
			template:`
				<div class="demo">
					<h2>学校名称:{{schoolName}}</h2>
					<h2>学校地址:{{address}}</h2>
					<button @click="showName">点我提示学校名</button>	
				</div>
			`,
			// el:'#root', //组件定义时,一定不要写el配置项,因为最终所有的组件都要被一个vm管理,由vm决定服务于哪个容器。
			data(){
				return {
					schoolName:'尚硅谷',
					address:'北京昌平'
				}
			},
			methods: {
				showName(){
					alert(this.schoolName)
				}
			},
		})

		//第一步:创建student组件
		const student = Vue.extend({
			template:`
				<div>
					<h2>学生姓名:{{studentName}}</h2>
					<h2>学生年龄:{{age}}</h2>
				</div>
			`,
			data(){
				return {
					studentName:'张三',
					age:18
				}
			}
		})
		
		//第一步:创建hello组件
		const hello = Vue.extend({
			template:`
				<div>	
					<h2>你好啊!{{name}}</h2>
				</div>
			`,
			data(){
				return {
					name:'Tom'
				}
			}
		})
		
		//第二步:全局注册组件
		Vue.component('hello',hello)

		//创建vm
		new Vue({
			el:'#root',
			data:{
				msg:'你好啊!'
			},
			//第二步:注册组件(局部注册)
			components:{
				school,
				student
			}
		})

		new Vue({
			el:'#root2',
		})
	</script>
</html>

几个要注意的点

1.关于组件名:

一个单词组成:

第一种写法(首字母小写):school

第二种写法(首字母大写):School

多个单词组成:

第一种写法(kebab-case命名):my-school

第二种写法(CamelCase命名):MySchool (需要Vue脚手架支持)

备注:

(1).组件名尽可能回避HTML中已有的元素名称,例如:h2、H2都不行。

(2).可以使用name配置项指定组件在开发者工具中呈现的名字。也就是图中的这个

2.关于组件标签:

第一种写法:<school></school>

第二种写法:<school/>

备注:不用使用脚手架时,<school/>会导致后续组件不能渲染。

3.一个简写方式:

const school = Vue.extend(options) 可简写为:const school = options

实例

html 复制代码
<!DOCTYPE html>
<html>
	<head>
		<meta charset="UTF-8" />
		<title>几个注意点</title>
		<script type="text/javascript" src="../js/vue.js"></script>
	</head>
	<body>

		<!-- 准备好一个容器-->
		<div id="root">
			<h1>{{msg}}</h1>
			<school></school>
		</div>
	</body>

	<script type="text/javascript">
		Vue.config.productionTip = false
		
		//定义组件
		const s = Vue.extend({
			name:'atguigu',
			template:`
				<div>
					<h2>学校名称:{{name}}</h2>	
					<h2>学校地址:{{address}}</h2>	
				</div>
			`,
			data(){
				return {
					name:'尚硅谷',
					address:'北京'
				}
			}
		})

		new Vue({
			el:'#root',
			data:{
				msg:'欢迎学习Vue!'
			},
			components:{
				school:s
			}
		})
	</script>
</html>

组件的嵌套

语法

组件嵌套是 Vue.js 中一个非常重要的特性,允许你将组件嵌套在其他组件中,从而构建复杂的用户界面。以下是组件嵌套的语法总结,并结合您提供的示例代码进行详细说明。

组件嵌套的语法总结

  1. 定义组件

    • 使用 Vue.extend 创建组件构造器。

    • 在构造器中定义组件的 templatedatamethods 等选项。

  2. 注册组件

    • 在父组件的 components 选项中注册子组件。

    • 子组件可以在父组件的 template 中通过自定义标签使用。

  3. 嵌套组件

    • 在父组件的 template 中使用子组件的标签。

    • 子组件可以进一步嵌套其他组件,形成多层嵌套结构。

示例代码分析

定义组件

student 组件

复制代码
const student = Vue.extend({
  name: 'student',
  template: `
    <div>
      <h2>学生姓名:{{name}}</h2>
      <h2>学生年龄:{{age}}</h2>
    </div>
  `,
  data() {
    return {
      name: '尚硅谷',
      age: 18
    };
  }
});

school 组件

复制代码
const school = Vue.extend({
  name: 'school',
  template: `
    <div>
      <h2>学校名称:{{name}}</h2>
      <h2>学校地址:{{address}}</h2>
      <student></student> <!-- 嵌套 student 组件 -->
    </div>
  `,
  data() {
    return {
      name: '尚硅谷',
      address: '北京'
    };
  },
  components: {
    student // 注册 student 组件
  }
});

hello 组件

复制代码
const hello = Vue.extend({
  template: `<h1>{{msg}}</h1>`,
  data() {
    return {
      msg: '欢迎来到尚硅谷学习!'
    };
  }
});

app 组件

复制代码
const app = Vue.extend({
  template: `
    <div>
      <hello></hello> <!-- 嵌套 hello 组件 -->
      <school></school> <!-- 嵌套 school 组件 -->
    </div>
  `,
  components: {
    school,
    hello // 注册 school 和 hello 组件
  }
});
创建 Vue 实例
复制代码
new Vue({
  template: '<app></app>', // 使用 app 组件作为根组件
  el: '#root',
  components: {
    app // 注册 app 组件
  }
});

组件嵌套的语法要点

  1. 定义组件

    • 使用 Vue.extend 创建组件构造器。

    • 在构造器中定义组件的 templatedata 方法。

  2. 注册组件

    • 在父组件的 components 选项中注册子组件。

    • 子组件可以在父组件的 template 中通过自定义标签使用。

  3. 嵌套组件

    • 在父组件的 template 中使用子组件的标签。

    • 子组件可以进一步嵌套其他组件,形成多层嵌套结构。

示例代码的执行流程

  1. 定义组件

    • 定义 studentschoolhelloapp 组件。
  2. 注册组件

    • school 组件中注册 student 组件。

    • app 组件中注册 schoolhello 组件。

    • 在 Vue 实例中注册 app 组件。

  3. 使用组件

    • school 组件的 template 中使用 <student> 标签。

    • app 组件的 template 中使用 <hello><school> 标签。

    • 在 Vue 实例的 template 中使用 <app> 标签。

注意,我们一般会定义一个最高级的组件app,成为祖先组件,也是最高级的组件。一人之下。万人之上。在vm之下。

实例

体会一下组件的嵌套

html 复制代码
<!DOCTYPE html>
<html>
	<head>
		<meta charset="UTF-8" />
		<title>组件的嵌套</title>
		<!-- 引入Vue -->
		<script type="text/javascript" src="../js/vue.js"></script>
	</head>
	<body>
		<!-- 准备好一个容器-->
		<div id="root">
			
		</div>
	</body>

	<script type="text/javascript">
		Vue.config.productionTip = false //阻止 vue 在启动时生成生产提示。

		//定义student组件
		const student = Vue.extend({
			name:'student',
			template:`
				<div>
					<h2>学生姓名:{{name}}</h2>	
					<h2>学生年龄:{{age}}</h2>	
				</div>
			`,
			data(){
				return {
					name:'尚硅谷',
					age:18
				}
			}
		})
		
		//定义school组件
		const school = Vue.extend({
			name:'school',
			template:`
				<div>
					<h2>学校名称:{{name}}</h2>	
					<h2>学校地址:{{address}}</h2>	
					<student></student>
				</div>
			`,
			data(){
				return {
					name:'尚硅谷',
					address:'北京'
				}
			},
			//注册组件(局部)
			components:{
				student
			}
		})

		//定义hello组件
		const hello = Vue.extend({
			template:`<h1>{{msg}}</h1>`,
			data(){
				return {
					msg:'欢迎来到尚硅谷学习!'
				}
			}
		})
		
		//定义app组件
		const app = Vue.extend({
			template:`
				<div>	
					<hello></hello>
					<school></school>
				</div>
			`,
			components:{
				school,
				hello
			}
		})

		//创建vm
		new Vue({
			template:'<app></app>',
			el:'#root',
			//注册组件(局部)
			components:{app}
		})
	</script>
</html>

最终的嵌套关系

VueComponent

关于VueComponent:

1.组件本质是一个名为VueComponent的构造函数,且不是程序员定义的,是Vue.extend生成的。

2.我们只需要写<school/>或<school></school>,Vue解析时会帮我们创建school组件的实例对象,即Vue帮我们执行的:new VueComponent(options)。

3.特别注意:每次调用Vue.extend,返回的都是一个全新的VueComponent!!!!

4.关于this指向:

(1).组件配置中:data函数、methods中的函数、watch中的函数、computed中的函数 它们的this均是【VueComponent实例对象】

(2).new Vue(options)配置中:data函数、methods中的函数、watch中的函数、computed中的函数 它们的this均是【Vue实例对象】

5.VueComponent的实例对象,以后简称vc(也可称之为:组件实例对象)。

Vue的实例对象,以后简称vm。

单文件操作

如何分离组件

接下来我们沿用组件基本使用时候的完整代码里面的例子写的School组件,转成单文件操作。

html 复制代码
<!DOCTYPE html>
<html>
	<head>
		<meta charset="UTF-8" />
		<title>组件的嵌套</title>
		<!-- 引入Vue -->
		<script type="text/javascript" src="../js/vue.js"></script>
	</head>
	<body>
		<!-- 准备好一个容器-->
		<div id="root">
			
		</div>
	</body>

	<script type="text/javascript">
		Vue.config.productionTip = false //阻止 vue 在启动时生成生产提示。

		//定义school组件
		const school = Vue.extend({
			name:'school',
			template:`
				<div>
					<h2>学校名称:{{name}}</h2>	
					<h2>学校地址:{{address}}</h2>	
				</div>
			`,
			data(){
				return {
					name:'尚硅谷',
					address:'北京'
				}
			},
		})


		//创建vm
		new Vue({
			template:'<app></app>',
			el:'#root',
			//注册组件(局部)
			components:{school }
		})
	</script>
</html>

我们先创建一个School.vue文件,写出他的结构。template,script,style。

html 复制代码
<template>

</template>

<script>

</script>

<style scoped>

</style>

然后将School分别放进去,并把js暴露出去。

html 复制代码
<template>
  <div class="demo">
    <h2>学校名称:{{ name }}</h2>
    <h2>学校地址:{{ address }}</h2>
    <button @click="showX">点我输出x</button>
  </div>
</template>

<script>
export default {
  name: "School",
  data() {
    return {
      name: "尚硅谷",
      address: "北京昌平",
    };
  },
  methods: {
    showName() {
      alert(this.name);
    },
  },
};
</script>

<style scoped>
.demo {
  background-color: orange;
}
</style>

这就是一个完整的vue2的组件。

以此类推,我们将Student组件也分离一下

html 复制代码
<template>
  <div>
    <h2>学生姓名:{{ studentName }}</h2>
    <h2>学生年龄:{{ age }}</h2>
  </div>
</template>

<script>
    export default {
        name:'Student',
        data () {
            return {
                studentName:'张三',
                age:18
            }
        },
        methods: {
            
        }
    };
</script>

知识补充:export

这里涉及到一个新的知识点。也就是如何把交互代码暴露出去。

在 ES6 模块化中,export 用于导出模块中的函数、类或变量,以便其他模块可以导入和使用它们。以下是 export 的三种常见用法:

1. 命名导出(Named Export)

可以导出多个函数、类或变量,并给它们指定名称。这种方式允许你在导入时选择性地导入需要的成员。

javascript 复制代码
// module.js
export function greet(name) {
  console.log(`Hello, ${name}!`);
}
​
export const PI = 3.14159;
​
export class Person {
  constructor(name) {
    this.name = name;
  }
}
​
// 使用
import { greet, PI, Person } from './module.js';
greet('World'); // 输出: Hello, World!
console.log(PI); // 输出: 3.14159
const person = new Person('Alice');

2. 默认导出(Default Export)(用的多!!!)

每个模块只能有一个默认导出。默认导出可以是函数、类或对象。

函数的默认导出
javascript 复制代码
// module.js
export default function School() {
  return {
    name: "School",
    data() {
      return {
        name: "尚硅谷",
        address: "北京昌平",
      };
    },
    methods: {
      showName() {
        alert(this.name);
      },
    },
  };
}

// 使用
import School from './module.js';
const school = School();
console.log(school.name); // 输出: School
school.methods.showName(); // 弹出: 尚硅谷
对象的默认导出

就是直接将这个组件当成一个对象输出,就可以省略一点

javascript 复制代码
// module.js
export default {
  name: "School",
  data() {
    return {
      name: "尚硅谷",
      address: "北京昌平",
    };
  },
  methods: {
    showName() {
      alert(this.name);
    },
  },
};

// 使用
import School from './module.js';
const school = School;
console.log(school.name); // 输出: School
school.methods.showName(); // 弹出: 尚硅谷

3. 批量导出(Bulk Export)

可以将其他模块的导出内容重新导出,或者将多个命名导出一次性导出。

javascript 复制代码
// moduleA.js
export const a = 1;
export const b = 2;
​
// moduleB.js
export const c = 3;
​
// moduleC.js
export * from './moduleA.js'; // 批量导出 moduleA 的所有内容
export * from './moduleB.js'; // 批量导出 moduleB 的所有内容
​
// 使用
import { a, b, c } from './moduleC.js';
console.log(a, b, c); // 输出: 1 2 3

使用组件

前面我们创建了Student和School组件,接着我们需要用到这两个组件。这时候App.vue就派上用场了。之前说过他是一人之下万人之上,由他来使用我们前面分离出来的组件

创建App.vue

包括import引入,并使用

html 复制代码
<template>
  <div>
    <School></School>
    <Student></Student>
  </div>
</template>

<script>
import School from "./School.vue";
import Student from "./Student.vue";
export default {
  name: "App",
  components: {
    School,
    Student,
  },
};
</script>

<style>
</style>

创建main.js

用app组件使用完前面分离的组件之后,毕竟他还在一人之下,也就是vm,所以我们需要创建一个Vue实例,来使用这个组件,这个实例就包含在main.js下面。

将app注册到main.js里面,并绑定id为root的容器。容器我们创建在哪呢?在index.html

javascript 复制代码
import App from './App.vue'

new Vue({
    el:'#root',
    // 可以写在index.html里面
    // template:`
    //     <App></App>
    // `,

    components: {
        App,
    }
})

创建index.html

我们创建一个id为root的容器,并使用app组件。然后引入vue和main

html 复制代码
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
</head>
<body>
    <div id="root">
        <App></App>

    </div>
    <script type="text/javascript" src="../js/vue.js"></script>  
    <script type="text/javascript" src="./main.js"></script>
    
</body>
</html>
相关推荐
江城开朗的豌豆几秒前
在写vue公用组件的时候,怎么提高可配置性
前端·javascript·vue.js
江城开朗的豌豆1 分钟前
Vue路由跳转的N种姿势,总有一种适合你!
前端·javascript·vue.js
江城开朗的豌豆1 分钟前
Vue路由玩法大揭秘:三种路由模式你Pick谁?
前端·javascript·vue.js
江城开朗的豌豆2 分钟前
Vue路由守卫全攻略:给页面访问装上'安检门'
前端·javascript·vue.js
小磊哥er9 分钟前
【前端工程化】前端组件模版构建那些事
前端
前端 贾公子10 分钟前
monorepo + Turborepo --- 开发应用程序
java·前端·javascript
江城开朗的豌豆14 分钟前
Vue路由传参避坑指南:params和query的那些猫腻
前端·javascript·vue.js
十里青山22 分钟前
超好用的vue图片预览插件更新啦,hevue-img-preview 7.0.0版本正式发布,支持vue2/vue3/移动/pc,增加缩略图、下载、自定义样式等
前端·javascript·vue.js
lichenyang45331 分钟前
css模块化以及rem布局
前端·javascript·css
小熊哥^--^33 分钟前
条件渲染 v-show与v-if
前端