0.样式多类名写法
--html--
<i :class="{'iconfont':true, 'icon-default':!isCheck, 'icon-select': isCheck}"></i>
--js--
data(){
return :{
isCheck:false
}
}
当isCheck 为true时,显示为 <i class="iconfont icon-select"></i>
当isCheck 为false时,显示为 <i class="iconfont icon-default"></i>
1.includes()方法(适用于多种条件判断时使用)
Item.status 是1,2,3,4,5 时 显示
<view v-if=“[1,2,3,4,5].includes(item.status)”></view>
2.不同状态不同样式
<text :class="item.status | orderStatus">订单中</text>
filters: {
orderStatus(status){
if(status === 6 || status === 7 || status === 8){
return 'gray'
}else if(status === 0){
return 'state'
}else{
return 'color3'
}
}
},
3.?.和??使用
当对象里的属性不确定是否存在时使用,双问号??后是默认值
例:res.data?.list ?? []
4.async await 一个方法里多个请求
async function fn(){
const p1 = getUserInfo({toke:token});
const p2 = getData();
const result = await Promise.all([p1,p2]);
console.log(result[0],result[1])
}
5.如何判断一个对象是不是空对象?
// 方法1 Object.keys(obj).length === 0
// 方法2 JSON.stringify(obj) === '{}'
6.require.context()
1.场景:如页面需要导入多个组件,原始写法:
import titleCom from '@/components/home/titleCom'
import bannerCom from '@/components/home/bannerCom'
import cellCom from '@/components/home/cellCom'
components:{titleCom,bannerCom,cellCom}
2.这样就写了大量重复的代码,利用 require.context 可以写成
const path = require('path')
const files = require.context('@/components/home', false, /\.vue$/)
const modules = {}
files.keys().forEach(key => {
const name = path.basename(key, '.vue')
modules[name] = files(key).default || files(key)
})
components:modules
这样不管页面引入多少组件,都可以使用这个方法
3.API 方法
实际上是 webpack 的方法,vue 工程一般基于 webpack,所以可以使用
require.context(directory,useSubdirectories,regExp)
接收三个参数:
directory:说明需要检索的目录
useSubdirectories:是否检索子目录
regExp: 匹配文件的正则表达式,一般是文件名
7.watch的用法:
1.场景:页面初始进来需要查询接口 getList(),然后input 改变会重新查询
created(){
this.getList()
},
watch: {
inpVal(){
this.getList()
}
}
2.其实可以直接利用 watch 的immediate和handler属性简写
watch: {
inpVal:{
handler: 'getList',
immediate: true
}
}
3.watch 的 deep 属性,深度监听,也就是监听复杂数据类型
watch:{
inpValObj:{
handler(newVal,oldVal){
console.log(newVal)
console.log(oldVal)
},
deep:true
}
}
此时发现oldVal和 newVal 值一样; 因为它们索引同一个对象/数组,Vue 不会保留修改之前值的副本; 所以深度监听虽然可以监听到对象的变化,但是无法监听到具体对象里面哪个属性的变化
8.$attrs和$listeners
这两个是不常用属性,但是高级用法很常见;
1.attrs场景:如果父传子有很多值,那么在子组件需要在props定义多个值解决:
attrs获取子传父中未在 props 定义的值
// 父组件
<home title="这是标题" width="80" height="80" name="lili"/>
// 子组件
mounted() {
console.log(this.$attrs) //{title: "这是标题", width: "80", height: "80", name: "lili"}
},
相对应的如果子组件定义了 props,打印的值就是除去定义的属性
//子组件
props: {
width: {
type: String,
default: ''
}
},
mounted() {
console.log(this.$attrs) //{title: "这是标题", height: "80", name: "lili"}
},
2.listeners场景:子组件需要调用父组件的方法解决:父组件的方法可以通过v−on="listeners 传入内部组件——在创建更高层次的组件时非常有用
// 父组件
<home @change="change"/>
// 子组件
mounted() {
console.log(this.$listeners) //即可拿到 change 事件
}
9. .sync
在 vue@1.x 的时候曾作为双向绑定功能存在,即子组件可以修改父组件中的值; 在 vue@2.0的由于违背单项数据流的设计被干掉了; 在vue@2.3.0+ 以上版本又重新引入了这个 .sync 修饰符;
// 父组件
<home :title.sync="title" />
//编译时会被扩展为
<home :title="title" @update:title="val => title = val"/>
// 子组件
// 所以子组件可以通过$emit 触发 update 方法改变
mounted(){
this.$emit("update:title", '这是新的title')
}
10.v-slot
2.6.0 新增
1.slot,slot-cope,scope 在 2.6.0 中都被废弃,但未被移除
2.作用就是将父组件的 template 传入子组件 3.插槽分类:
A.匿名插槽(也叫默认插槽): 没有命名,有且只有一个;
// 父组件
<todo-list>
<template v-slot:default>
任意内容
<p>我是匿名插槽 </p>
</template>
</todo-list>
// 子组件
<slot>我是默认值</slot>
//v-slot:default写上感觉和具名写法比较统一,容易理解,也可以不用写
B.具名插槽: 相对匿名插槽组件slot标签带name命名的;
// 父组件
<todo-list>
<template v-slot:todo>
任意内容
<p>我是匿名插槽 </p>
</template>
</todo-list>
//子组件
<slot name="todo">我是默认值</slot>
C.作用域插槽: 子组件内数据可以被父页面拿到(解决了数据只能从父页面传递给子组件)
// 父组件
<todo-list>
<template v-slot:todo="slotProps" >
{{slotProps.user.firstName}}
</template>
</todo-list>
//slotProps 可以随意命名
//slotProps 接取的是子组件标签slot上属性数据的集合所有v-bind:user="user"
// 子组件
<slot name="todo" :user="user" :test="test">
{{ user.lastName }}
</slot>
data() {
return {
user:{
lastName:"Zhang",
firstName:"yue"
},
test:[1,2,3,4]
}
},
// {{ user.lastName }}是默认数据 v-slot:todo 当父页面没有(="slotProps")
11.数组扁平化
常规操作
let arr = [1, [2, [3, 4,5]]];
function flatten(arr) {
while (arr.some(item => Array.isArray(item))) {
arr = [].concat(...arr);
}
return arr;
}
console.log(flatten(arr))// [1, 2, 3, 4,5]
骚操作
let arr = [1, [2, [3, 4]]];
console.log(arr.flat(Infinity)); // [1, 2, 3, 4]
解析
我们还可以直接调用 ES6
中的flat
方法来实现数组扁平化。flat
方法的语法:
arr.flat([depth])
其中depth
是flat
的参数,depth
是可以传递数组的展开深度(默认不填、数值是 1
),即展开一层数组。如果层数不确定,参数可以传进 Infinity
,代表不论多少层都要展开
12.扩展运算符的应用
1.数组去重
let arr = [3, 5, 2, 2, 5, 5];
let setArr = new Set(arr) // 返回set数据结构Set(3) {3, 5, 2}
//方法一 es6的...解构
let unique1 = [...setArr ]; //去重转数组后 [3,5,2]
//方法二 Array.from()解析类数组为数组
let unique2 = Array.from(setArr ) //去重转数组后 [3,5,2]
2.字符串去重
let str = "352255";
let unique = [...new Set(str)].join(""); // 352
3.实现并集、交集、和差集
let a = new Set([1, 2, 3]);
let b = new Set([4, 3, 2]);
// 并集
let union = new Set([...a, ...b]); // Set {1, 2, 3, 4}
// 交集
let intersect = new Set([...a].filter(x => b.has(x))); // set {2, 3}
// (a 相对于 b 的)差集
let difference = new Set([...a].filter(x => !b.has(x))); // Set {1}
13.网站置灰
CSS滤镜 -webkit-filter
一行代码足以
#app { filter: grayscale(100%); -webkit-filter: grayscale(100%); }
blur 模糊-webkit-filter:blur(2px);
brightness 亮度-webkit-filter:brightness(25%);
contrast 对比度-webkit-filter: contrast(50%);
drop-shadow 阴影-webkit-filter: drop-shadow(5px 5px 5px rgba(0, 0, 0, 0.5));
opacity 透明度-webkit-filter: opacity(50%);
grayscale 灰度-webkit-filter: grayscale(80%);
sepia 褐色-webkit-filter: sepia(100%);
invert 反色-webkit-filter: invert(100%);
hue-rotate 色相旋转-webkit-filter:hue-rotate(180deg);
saturate 饱和度-webkit-filter: saturate(1000%);