昨日作业
Proxy 和DefineProperty的区别
Object.defineProperty()
方法会直接在一个对象上定义一个新属性,或者修改一个对象的现有属性,并返回此都对象
proxy
对象用于定义基本操作的自定义行为。返回值是一个Proxy代理的对象,操作这个对象会触发handler对应操作。改变原始对象不会触发。
区别:
- proxy使用上比Object.defineProperty方便的多
- Proxy代理整个对象,Object.defineProperty只代理对象上的某个属性。
- vue中,Proxy在调用时递归,Object.defineProperty在一开始就全部递归,Proxy性能优于Object.defineProperty
- 对象上定义新属性时,Proxy可以监听到,Object.defineProperty监听不到。
- 数组新增删除修改时,Proxy可以监听到,Object.defineProperty监听不到。
- Proxy不兼容IE,Object.defineProperty不兼容IE8及以下。
指令
v-bind
v-bind动态属性数据绑定
语法:
标准语法:v-bind:属性=“动态数据”
简写语法::属性 = “动态数据” , 这也是我们常用的语法
数据固定
<img src="./img/a.jpg">
使用v-bind动态属性绑定
通过动态数据绑定,根据data数据源中的src的值来改变更新图片的地址
<img :src="src">
<img v-bind:src="src">
v-for
遍历数组的语法
语法:<div v-for="(元素,索引) in/of 数组"></div>
遍历对象的语法
语法:<div v-for="(元素,键名,索引) in/of 对象"> </div>
循环 v-for vue中对于v-for进行了增强,它可以用for in或者 for of 都可以而且两者都可以进行对象迭代,在vue2的语法中,小括号可以写,可以不写,但是在vue3中小括号必须写
注:
- vue2中如果在同一个标签中同时添加v-if和v-for,则v-for 的优先级高于v-if,所以在vue2中不推荐两者在一个标签中
- vue3中v-if的优先级高于v-for的优先级
- v-for,建议给循环项每个添加一个key来作标识,用于提升性能,key值,一定要唯一不重复的,不太建议使用循环的索引当作key值,一般在和后台请求数据时,要求后台提供一个唯一的id给我们
数组的循环
第两种方法只有在vue2中可以去掉小括号
<li v-for="(item,index) in user">{{index}} -- {{item}}</li>
<li v-for="item,index in user">{{index}} -- {{item}}</li>
<li v-for="item,index in user" :key="item.id">{{item.name}}</li>
<script>
const vm = new Vue({
el: '#app',
data: {
user: ['张三', '李四', '王五']
}
})
</script>
注: v-for,建议给循环项每个添加一个key来作标识,用于提升性能,key值,一定要唯一不重复的,不太建议使用循环的索引当作key值,一般在和后台请求数据时,要求后台提供一个唯一的id给我们,给每一个数据添加辨识度,key的作用在vue进行新旧数据比对渲染页面里
循环对象
<div v-for="item,key,index in user" :key="key">{{index}} -- {{key}} -- {{item}}</div>
<script>
const vm = new Vue({
el: '#app',
data: {
user: {id:1,name:张三,age:18}
}
})
</script>
v-on
语法:
标准语法:v-on:事件名=“实现的方法[此方法定义在vue配置中的methods中]”
频繁使用语法: @时间名=“方法”,
绑定方法,可以写小括号,也可以不写,
如果你绑定方法时,没有写小括号,则vue在解析时,会自动给你映射一个event给绑定方法
可以实现点击按钮让num加1
<div id="app">
<div>{{num}}</div>
<button @click="clickFn">点击事件</button>
</div>
<script src="vue.js"></script>
<script>
const vm = new Vue({
el: '#app',
data: {
num: 1
},
methods: {
clickFn(e) {
this.num++
}
}
})
</script>
注 在methods中定义方法不使用箭头函数,但是方法体中建议使用箭头函数。如果定义方法时,使用箭头函数,会改变this指向
如果没有参数时,可以不写小括号,默认就会把event事件对象绑定到实现的方法中,如果需要传参数时,则通过 $event 来手动传递到实现的方法中
<button @click = "say($event)"
事件修饰符
用来处理事件的特定行为
阻止冒泡
<button @click.stop=“dothis"></button>
按键修饰符和系统修饰键
事件修饰符和按键修饰符可以让我们的 效率更高
更多的可以去查看官方文档vue2的官方文档
样式绑定
class样式的动态添加,有对象和数组两种方式
对象的方式
一般用于开关显示的样式,不太适合添加新的属性样式
对象:{key它就是样式名称:布尔值[true生效,false不生效]}
.active {
color: red;
}
<div v-bind:class="{active: isActive}">class样式</div>
data: {
isActive: true
}
<!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>Document</title>
<style>
.active {
color: red;
}
.font30 {
font-size: 30px;
}
</style>
</head>
<body>
<div id="app">
<div :class="title">动态样式</div>
<button @click="addClass">点击</button>
</div>
<script src="./vue.js"></script>
<script>
const vm = new Vue({
el: '#app',
data: {
title: { active: false}
},
methods: {
addClass() {
// vue中给对象动态添加的属性是不会被劫持的所以导致字体不会变大
// data数据源中的title被数据劫持了,但是它后面添加的的属性值不会被劫持所以导致字体不会变大,所以数据不是响应式的所以视图不会改变
this.title.font30 = true
}
}
})
</script>
</body>
</html>
解决方法
改变title.active的值就会引发视图更新所以会更新数据
在视图更新的时候会更新一次数据,此时font30就会被劫持
methods: {
addClass() {
this.title.active = true
this.title.font30 = true
}
}
另一种解决方法
因为this.title对象的地址发生改变就会更新
addClass() {
this.title={...this.title,font30:true}
}
这样也可以
let titleClass = JSON.parse(JSON.stringify(this.titleClass))
titleClass.font30 = true
this.titleClass = titleClass
调用数组方法时,都会进行视图更新
this.titleStyle.push('active')
数组的方式
一般对于追加新样式,使用数组
<div :class="titleStyle">我是一个标题</div>
titleStyle:['active']
style样式
style样式的动态添加,对象和数组方式,主要用于使用其他组件库更改其样式的时候
对象方式
<div :style:{color:'red';fontSize:'30px'}></div>
数组方式
<div :style="[{color:'red'},{fontSzie:'30px'}]"></div>
v-model
v-model是一个语法糖,其实就是input框中 value和时间的综合体,数据双向绑定
作用: 表单元素的绑定,实现了双向数据绑定,通过表单项可以更改数据。v-model会忽略所有表单元素的value、checked、selected特性的初始值,而总是将Vue实例的数据作为数据来源,应该在data选项中声明初始值。
使用于复选框和单选框以及下拉框
绑定单个复选框
<input type="checkbox" v-model="checked">
data:{
checked:true
}```
绑定多个复选框
data:{ // 如果数组中有对应的value值,则此checkbox会被选中 checkedNames:[] } ``` 绑定单选框 需要input提供value属性的值 ``` 男 女 data: { sex: '' } ``` 绑定下拉框
<select v-model="selected">
<option>请选择</option>
<option>HTML</option>
<option>CSS</option>
<option>JS</option>
</select>
data: {
selected: ''"
}
v-model修饰符
.lazy 失去焦点时触发(延时更新数据源)
.trim 去除空格
.number 转换数值
自定义指令
自定义指令分为:全局指令和局部指令,当全局指令和局部指令同名时以局部指令为准
自定义指令常用的钩子函数:
- bind 第一次绑定到元素时调用
- inserted 被绑定元素插入父节点时调用(仅保证父节点存在,但不一定已被插入文档中)
- update 数据更新时调用
- componentUpdated 指令所在组件的VNode及其子VNode全部更新后调用
- unbind 只调用一次,指令与元素解绑时调用。
定义自定义指令
分为全局定义和局部定义
全局定义 ,所有的组件或vue的实例都会生效,可以使用
对象写法
指令名称不需要v-开头,但是在调用的时候还是会使用v-
Vue.directive('指令名称',对象或函数)
Vue.directive("red",{
bind(el,bindings){
},
inserted(el,bindings){
},
update(el,bindings){
},
componentUpdated (el,bindings){
},
unbind(el,bindings){
}
})
当元素初始化的时候调用bind 和inserted
当元素里面有元素更新的时候 调用 update componentUpdate
当元素销毁时调用unbind