一、组件复用(详细讲解)
配置项:props(让组件接受外部传来的数据)
app.vue:
<StudentLqj name="李四" sex="女" age="20"></StudentLqj>
<StudentLqj name="张三" sex="男" age="20"></StudentLqj>
通过在app.vue里面复制多个子组件来实现相同样式的不同数据显示(组件服用)
StudentLqj.Vue(这是自定义的子组件):
template:
<template>
<div>
<h1>{{msg}}</h1>
<h2>学生姓名:{{name}}</h2>
<h2>学生性别:{{sex}}</h2>
<h2>学生年龄:{{age}}</h2>
<button @click="dianji">点击修改姓名</button>
</div>
</template>
script:
1.简单接收
<script>
...
props:['name','sex','age']//简单接收
...
</script>
2.选择类型并接收,如果床过来的值与props里面的标志的值的类型不匹配,则在控制台会报错!
<script>
...
props:{
name:String,
sex:String,
age:Number
}//选择类型并接收
...
</script>
3.在接收的同时对每个参数的的类型以及必要或非必要进行判断(最终的接收数据的写法)
<script>
...
props:{
name:{
type:String,//name的类型
required:true//name是必须要传递的数据
},
sex:{
type:String,//sex的类型
required:true//sex是必须要传递的数据
},
age:{
type:Number,//age的类型
default:99//age默认是为99(上一个页面没有给age转递数据是,age将会采用默认值)
},
}
...
</script>
最终:
<script>
export default {
name:'StudentLqj',
data(){
return{
msg:'我是一个学生',
myname:this.name
// sex:'男',
// age:20
}
},
/*methods:{
dianji(){
this.myname='小胖子'
}
},*/
// props:['name','sex','age']
// props:{
// name:String,
// sex:String,
// age:Number
// }
props:{
name:{
type:String,//name的类型
required:true//name是必须要传递的数据
},
sex:{
type:String,//sex的类型
required:true//sex是必须要传递的数据
},
age:{
type:Number,//age的类型
default:99//age默认是为99(上一个页面没有给age转递数据是,age将会采用默认值)
},
}
}
</script>
注意:xxx=”…”,引号里面的数据默认都是字符串类型,我们需要在前面加上:(冒号)vue就自动帮我们把””里面的数转换成js表达式的形式。
如:
<StudentLqj name="李四" sex="女" :age="20"></StudentLqj>
<StudentLqj name="张三" sex="男" :age="20"></StudentLqj>
注意:
props是只读的,Vue底层会监视你对props的修改,
如业务需求要修改props中的数据,如下操作:
注意:props中接收的数据是不能直接在子组件中改动的(直接改动会报错)
如果像在自组加中修改props中接收的数据,可以借助子组件接收数据的优先级原理:
优先级:props>data
子组件中props接收的数据会先传到子组件(vm身上),也就是先传到了this中:
在子组件中的data(){console.log(this.name)}可以得到name的值,
借助这个可以:
再声明一个变量(myname)
template:
<h2>学生姓名:{{myname}}</h2>
<button @click="dianji">点击修改姓名</button>
script:
<script>
...
data(){
return{
msg:'我是一个尚硅谷的学生',
myname:this.name
// sex:'男',
// age:20
}
},
methods:{
dianji(){
this.myname='小胖子'
}
},
...
</script>
二、mixin(混入)(公共js调用;模块化)
···局部混入:
前提:如果子组件(SchoolLqj.vue),(StudentLqj.vue)要实现相同的功能
例如:点击时都要弹出名字(学校名字,学生名字)
1.首先要创建一个在crs目录下xxx.js(用于放公共js方法),这里我们为它起名字为mixin.js
mixin.js:
export const xxx //此export写法为:分别暴露
export const mixin = { //此export写法为:分别暴露
methods:{
dianji(){
alert(this.name)
}
}
}
StudentLqj.vue
template:
<template>
<div>
<h2 @click="dianji">学生姓名:{{name}}</h2>
<h2>学生性别:{{msg}}</h2>
</div>
</template>
script:
<script>
import {mixin} from '../mixin'
...
export default{
...
mixins:[mixin]
}
</script>
SchoolLqj.vue
template:
<template>
<div>
<h2 @click="dianji">学生姓名:{{name}}</h2>
<h2>学生性别:{{msg}}</h2>
</div>
</template>
script:
<script>
import {mixin} from '../mixin'
...
export default{
...
mixins:[mixin]
}
</script>
结果:我们想要的时点击<h1/>中的数据时会弹出窗口显示里面的数据
现在我们将一个mixin.js方法分别给StudentLqj.vue与SchoolLqj.vue调用
就会与分别在两个组件中写方法实现相同功能
·mixin(混入)优先级:
·mixin<子组件
(组件调用mixin.js之后,如果组件中有的按照组件中的显示,如果组件中没有的按照mixin.js中的显示)
例如:
mixin.js:
export const mixin2 = {
data(){
return{
lqj:100,
x:200
}
}
}
SchoolLqj.vue
template:
<template>
<div>
<h2 @click="dianji">学校姓名:{{name}}</h2>
<h2>{{lqj}}</h2>
<h2>{{x}}</h2>
<h2>学校地址:{{address}}</h2>
</div>
</template>
script:
<script>
import {mixin, mixin2} from '../mixin'
export default {
name:'SchoolLqj',
data(){
return{
address:'北京',
name:'尚硅谷',
lqj:'666'
}
},
mixins:[mixin,mixin2]
}
</script>
结果:在{
{lqj}}处显示666,{
{x}}处显示200。(mixin混入是把mixin.js中写的
方法与与调用的子组件进行合并,一起显示,但是由于优先级不同,所以如果mixin与子组件之间
都有同一个方法时,会显示组件中的!)
注意:对于生命周期钩子函数(mounted(){})来说,不管是在mixin.js所写的mounted(){}还是
在子组件中所写的mounted(){},vue给出的处理是,都要!但是mixin中的mounted会先执行!
优先级:
mixin>子组件
举例:
mixin.js:
export const mixin2 = {
mounted(){
console.log('我是lqj,你是小胖子吗?')
}
}
StudentLqj.vue:
<script>
import {mixin2} from '../minix'
export default {
...
mounted(){
console.log('我是lqj,你是小胖子吗?')
}
...
}
</script>
SchoolLqj.vue:
<script>
import {mixin2} from '../minix'
export default {
...
mounted(){
console.log('我是lqj,你是小胖子吗?')
}
...
}
</script>
结果:页面的控制台中会打印四次“我是lqj,你是小胖子吗?”,因为我们在mixin中写的打印的方法,并且供两个组件调用后,
两个组件里面也有打印方法,因为(对于生命周期函数(mounted来说,vue的处理时:都要!)),所以mixin中的mounted和
组件中的mounted都显示!
注意:mixin中的mounted会先执行!
…全局混入:
1.首先和上面一样先写好mixin.js公共js供main.js(全局调用)
2.在main.js中写入(如下:)
main.js:
import {mixin,mixin2} from ‘./mixin’
Vue.mixin(mixin)
Vue.mixin(mixin2)
注意:此时组件中不用再去调用mixin.js,全局混入会将main.js调用的mixin.js分配给所有的子组件!
四、
mounted(){}:钩子函数(在页面的dom元素全部渲染完毕后,自动执行函数里里面的方法),类型:函数(function)
五、plugins(自定义插件)
首先在src目录下创建一个plugins.js中写入(如下:)
plugins.js:
export const lqj={
install(Vue){
console.log('lqj666')
alert('111111111')
}
}
因为我们写的是自定义插件所以要在进入main.js中Vue之前先读取我们自定义的plugins.js插件
main.js:
...
import {lqj} from './plugins'
...
Vue.use(lqj)
// 创建vm
new Vue({
render: h => h(App),
}).$mount('#app')
结果:一件页面就会弹出111111111,以及控制台中打印lqj666
·下面是给vue原型添加一个方法(此方法vm,vc都可用!)
·Vue.prototype.hello = () =>{alert(‘nihao’)}
举例:
plugins.js:
export const lqj={
install(Vue){
Vue.prototype.hello = () =>{alert('nihao')}
}
}
下面同样是在main.js中使用自定义的插件
main.js:
...
import {lqj} from './plugins'
...
Vue.use(lqj)
// 创建vm
new Vue({
render: h => h(App),
}).$mount('#app')
既然是给vue原型添加的方法,所以我们可以在任何一个组件中使用,(SchoolLqj.vue为例):
SchoolLqj.vue
template:
<template>
<div>
<button @click="dianji">点击我显示nihao</button>
</div>
</template>
script:
<script>
export default {
...
methods:{
dianji(){
this.hello()
}
}
...
}
</script>
结果:点击button按钮后弹出nihao
今天vue2脚手架学习到此为止,明天见!
只要路飞还在笑,我的生活就没有苦恼!