scoped样式冲突p48
默认情况:写在组件中的样式会全局生效-因此很容易造成多个组件之间的样式冲突问题。
- 全局样式:默认组件中的样式会作用到全局
- 局部样式:可以给组件加上scoped属性,可以让样式只作用于当前组件
scoped原理:
3. 给当前组件模板的所有元素,都会被添加上一个自定义属性data-v-hash值
4. css选择器后面,被自动处理,添加上了属性选择器
data是一个函数p49
一个组件的data选项必须是一个函数。-保证每个组件实例,维护独立的一份数据对象。
export default {
data(){
return{
count:999
}
}
}
什么是组件通信p50
组件通信,就是指组件与组件之间的数据传递。
- 组件的数据是独立的,无法直接访问其他组建的数据。
- 想用其他组件的数据-组件通信
组件关系分类只有是否父子关系。
- 父子关系:props(父传子,写在子接收export那里)和$emit(子传父)
- 非父子关系:(1)provide &inject (2)eventbus
- 通用解决方案:vuex(适合复杂业务场景)
props
<!-- 1.给组件标签,添加属性的方式,传值 -->
<SbHeader :title="mytitle"></SbHeader>
export default {
//2.子通过props接收(数组接受多个传值)
props:['title']
}
<div>
<!-- 3.渲染使用 -->
我是son组件{{ title }}
</div>
&emit
methods:{
handleClick(){
//子中 $emit1.$emit触发事件,给父元素发送消息通知
this.$emit('changeTitle','传值')
}
}
<!-- 父中$emit2.父组件监听事件 -->
<SbHeader :title="mytitle" @changeTitile="changeFn"></SbHeader>
methods:{
//父中$emit3.提供处理函数,形参中获取参数
changeFn(newTitle){
this.mytitle =newTitle
}
}
props详解p51
定义:组件上注册的一些自定义属性
作用:向子组件传递数据
props效验: 不能乱传,控制台会有错误提示-帮助开发者快速发现错误
语法:
- 类型校验 2. 非空校验,必传属性 3. 默认值 4. 自定义校验
(1)类型校验
export default {
// props:[w]
props:{
w:Number//校验的属性名:类型
}
};
(2)1. 类型校验 2. 非空校验,必传属性 3. 默认值 4. 自定义校验
export default {
// props:[w]
props:{
w:Number,//类型校验
required:true,//必传的属性
default:0,//默认值
validator(){
return false//自定义校验
}
}
};
prop&data 单向数据流
共同点:都可以给组件提供数据
区别:
- data数据自己的-随便改
- prop数据外部的-不能直接改,要遵循单向数据流,要通过$emit给父改
非父子通信(拓展)-event bus 事件总线p55
作用:非父子组件之间(倾向于同层级),进行简易消息传递。(复杂场景-vuex)
- 创建一个都能访问到的事件总线(空vue实例)-utils/EventBus.js
- A组件(接收方),监听Bus实例的事件。
- B组件(发送方),触发Bus实例的事件。
//在js中,创建一个都能访问到的事件总线(空vue实例)-utils/EventBus.js
import Vue from 'vue'
const Bus =new Vue()
export default Bus
created(){
//非父子2.在接收方,进行监听Bus的事件($on是监听)
Bus.$on('sendMsg',(msg)=>{
this.msg=msg
})
},
clickSend(){
//非父子3.发送方触发事件的方式传递参数(发布消息)(触发事件用$emit)
Bus.$emit('sendMsg','有病')
}
非父子通信(拓展)provide&inject p56
provide&inject作用:跨层级共享数据
- 父组件provide提供数据
- 子/孙组件inject取值使用
v-model详解p57
v-model原理
表单类组件封装&v-model简化代码
- 表单类组件封装
(1)父传子:数据应该是父组件props传递过来的,v-model拆解绑定数据
(2)子传父:监听输入,子传父给父组件修改
<template>
<div>
<select :value="cityId" @change="handleChange">
<option value="101">101</option>
<option value="102">102</option>
<option value="103">103</option>
</select>
</div>
</template>
<script>
export default {
props: {
cityId: String,
},
methods: {
handleChange(e) {
// console.log(e.target.value);
this.$emit('changeId',e.target.value)
},
},
};
</script>
<style>
</style>
<template>
<div class="app">
<BaseSelect :cityId="selectId"
@changeId="selectId=$event"></BaseSelect>
</div>
</template>
<script>
import BaseSelect from "./components/BaseSelect.vue";
export default {
data() {
return {
selectId: '102',
};
},
components: {
BaseSelect,
},
};
</script>
<style>
</style>
.sync修饰符p58
作用:可以实现子组件与父组件的双向绑定,简化代码
特点:prop属性名,可以自定义,非固定为value
场景:封装弹框类的基础组件,visible属性true显示false隐藏
本质 就是:属性名和@uodate:属性名 合写
<div class="app">
<!-- :visible.sync =>:visible+ @update:visible-->
<BaseSelect :visible.sync="showoff"></BaseSelect>
</div>
close(){
this.$emit('update:visible',false)
}
ref和$refs p59
作用:利用ref和$refs可以用于获取dom元素,或组件实例
特点:查找范围-当前组件内(比queryselect更精确稳定)
(1)获取dom
- 目标标签-添加ref属性
- 恰当时机,通过this.$refs.xxx获取目标标签
<option ref="sb" value="101">101</option>
const myChat =echarts.init(this.$refs.sb)
(2)获取组件:
- 目标组件-添加ref属性
- 恰当时机,通过this.$refs.xxx获取目标组件,就可以调用组件对象里面的方法
<BaseSelect ref="baseherf"></BaseSelect>
<button @click="handleset">set</button>
methods:{
handleset(){
console.log(this.$refs.baseherf.close())
}
},
vue异步更新和$nextTick p60
显示之后立刻获取焦点是不能成功的
vue是异步更新dom(提升性能·)
this.isShowEdit=true//显示输入框
this.$refs.inp.focus()//获取焦点
n e x t T i c k : 等 d o m 更新后,才会触发执行此方法里的函数体语法 : t h i s . nextTick:等dom更新后,才会触发执行此方法里的函数体 语法:this. nextTick:等dom更新后,才会触发执行此方法里的函数体语法:this.nextTick(函数体)
this.$nextTick(()=>{
this.$refs.inp.focus()
})