欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  IT编程

Vue 3.0.3 : 新增CSS变量传递以及最新的Ref提案

程序员文章站 2022-06-26 16:19:42
前言在 Vue 3.03 版本中,Ref 语法糖已经实现,即使反对的人再多,尤雨溪也坚信这一语法糖会像 TypeScript 一样,用之前都觉得不好,用过之后说真香。所以不顾大家的反对,毅然决然的实现了这一需求,首先我们先来简单的回顾一下这个语法糖是干什么的:Ref 语法糖在之前,我们想要定义一个基本数据类型的响应式变量需要写成这样:import { ref } from 'vueconst a = ref(0)当使用时要写成这样:a.value = a.value + 10// 或...

前言

在 Vue 3.03 版本中,Ref 语法糖已经实现,即使反对的人再多,尤雨溪也坚信这一语法糖会像 TypeScript 一样,用之前都觉得不好,用过之后说真香

所以不顾大家的反对,毅然决然的实现了这一需求,首先我们先来简单的回顾一下这个语法糖是干什么的:

Ref 语法糖

在之前,我们想要定义一个基本数据类型的响应式变量需要写成这样:

import { ref } from 'vue

const a = ref(0)

当使用时要写成这样:

a.value = a.value + 10
// 或 a.value += 10

这个value属性就很烦人了,因为咱们定义了一个数字0,给它取了个名字叫a,虽然咱们并不是写成了这样:

const a = 0

但是在好多人的心目中,这个a就像上面这行代码一样,觉得它应该是基础类型,一方面不符合直觉,经常会忘记写.value。另一方面写起来也很麻烦,而且有时候需要写.value,有时候又不需要,比如用在<template>标签中时就不需要写.value,或者把ref赋值给reactive对象时:

import { ref, reactive } from 'vue'

const obj = reactive({
	a: ref(0)
})

// 这里不需要写成obj.a.value
console.log(obj.a)

这无疑为我们增加了许多的心智负担,尤雨溪希望通过编译来实现像使用基础类型一样使用ref,写法如下:

// 声明一个变量(这个变量将会被编译成一个ref)
ref: count = 1

function inc() {
  // 该变量可以像普通变量那样使用
  count++
}

// 想要获取到原本的变量的话需要在变量前面加一个????符号
console.log($count.value)

Vue 3.0.3 CHANGELOG

通过 GitHub 中尤雨溪的 CHANGELOG 我们可以得知:

Vue 3.0.3 : 新增CSS变量传递以及最新的Ref提案
前半段写的修复的 Bug???? 先暂且不提,咱们只看新的实验性特性有哪些:

  • compileScript inline render function mode
  • new script setup implementation
  • new SFC css varaible injection implementation
  • support kebab-case components in <script setup> sfc template
  • explicit expose API
    这里面重点是第二条、第三条以及最后一条:
  • 实现了新的 <script setup>
  • 实现了新的单文件组件注入 CSS 变量
  • 控制导出的 expose API

那么新的<script setup>就包含了这个 Ref 语法糖

CSS 变量注入

那么这个CSS变量注入又是个什么鬼呢?

其实有篇文章已经把这个特性说的相当详细了:

《Vue超好玩的新特性:在CSS中引入JS变量》

总结起来就是:

  1. 以前在 JS 中的变量不能直接和 CSS 变量产生联系
  2. 现在可以在 <style> 标签中将 JS 变量与 CSS 变量进行关联
  3. 同时还具有响应性,比如改变了 JS 中 this.xxx 的值,同名的 CSS 变量也会随之改变,视图随之进行更新:
<template>
  <h1>Vue</h1>
</template>

<script>
export default {
  data () {
    return {
      opacity: 0
    }
  },
  mounted () {
    setInterval(_ => {
      this.opacity >= 1 && (this.opacity = 0)
      this.opacity += 0.2
    }, 300)
  }
}
</script>

<style vars="{ opacity }">
h1 {
  color: rgb(65, 184, 131);
  opacity: var(--opacity);
}
</style>

运行结果:
Vue 3.0.3 : 新增CSS变量传递以及最新的Ref提案
可以看到有了这一特性,我们只需要改变同名的 JS 变量即可,这会让我们的项目更加的灵活,比如根据用户输入的合法颜色值来进行动态换肤等功能。

但这次更新改变了写法,在<style>标签中不需要再写vars="{ xxx }"了,在 CSS 代码中也不需要再写原生的 CSS 变量引用了(var(--xxx)),取而代之的是v-bind()这个函数,注意 ⚠️ 这个函数虽然跟 JS 里的v-bind很像,但只能用在 CSS 中,写法如下:

<template>
  <h1> shit! </h1>
</template>

<script>
export default {
  data () {
    return {
      color: 'yellow'
    }
  }
}
</script>

<style>
h1 {
  color: v-bind(color)
}
</style>

如果是 JS 变量是xxx.xxx这种形式的话,比如这样:

export default {
  data () {
    return {
      font: {
      	weight: 100
      }
    }
  }
}

那么 CSS 不能直接写成这样:

h1 {
	font-weight: v-bind(font.weight)
}

而是需要用一对引号扩起来,类似于字符串的那种形式:

h1 {
	font-weight: v-bind('font.weight')
}

expose API

那么这又是个什么鬼呢?

在 Vue 2 时期我们是通过 Options API 来写代码的,也就是说需要导出一个对象,对象的键无非就是那些耳熟能详的:

export default {
    data () {},
    mounted () {},
    computed: {},
    methods: {},
    // 省略若干 Options ...
}

而现在新加了一个 expose:

export default {
    data () {},
    mounted () {},
    computed: {},
    methods: {},
    // 省略若干 Options ...
    expose: []
}

这玩意是干嘛的呢?首先它的用法和 props 的数组形式差不多:

export default {
    data () {
    	return {
            x: 1,
            y: 2
        }
    },
    expose: [ 'x' ]
}

这样的话在父组件中用 ref 获取子组件实例时,子组件身上只有x这个变量,y是获取不到的!

而在 Composition API 中的用法是这样的:

export default defineComponent((_, { expose }) => {
    expose({
      x: ref(1)
    })
    
    return {
      x: ref(2),
      y: ref(3)
    }
  }
})

看!咱们这里有两个x,你们猜哪个x会被导出?

答案是如果有两个导出的变量的话,以 expose 导出的为准。

那么 Composition API 和 Options API 混合用法会是什么样的呢:

expotr default defineComponent({
  expose: ['x'],
  data () {
    return {
      x: 1
    }
  },
  setup (_, { expose }) {
    expose({
      y: ref(2)
    })
    
    return {
      y: ref(3),
      z: ref(4)
    }
  }
})

正确答案是:

  • x = 1
  • y = 2
  • z = undefined

当然这些只在组件外起作用,组件内部还是能获取到z的,而且y也还是等于 3 的。

结语

Vue 现在已经不是我以前认识的那个 Vue 了,有些功能挺好挺实用,但有些……我都不知该说啥好了,大家是怎么看待现在已经改的面目全非了的 Vue 呢?

本文首发于公众号:《前端学不动》

本文地址:https://blog.csdn.net/GetIdea/article/details/110209508

相关标签: vue.js