返回顶部
首页 > 资讯 > 前端开发 > JavaScript >Vue3 style CSS 变量注入的实现
  • 685
分享到

Vue3 style CSS 变量注入的实现

2024-04-02 19:04:59 685人浏览 泡泡鱼
摘要

目录摘要基础示例动机设计细节编译细节采用策略实践提示绑定恰当的属性注意 style 的更新参考资料摘要 在单文件组件样式中支持使用组件状态驱动的 CSS 变量( CSS 自定义属性

摘要

在单文件组件样式中支持使用组件状态驱动的 CSS 变量( CSS 自定义属性)。

基础示例


<template>
  <div class="text">hello</div>
</template>

<script>
  export default {
    data() {
      return {
        color: 'red',
        font: {
          size: '2em',
        },
      }
    },
  }
</script>

<style>
  .text {
    color: v-bind (color);

    
    font-size: v-bind ('font.size');
  }
</style>

动机

Vue SFC 样式提供了直接的 CSS 搭配和封装,但它是纯粹的静态的 —— 这意味着到目前为止,我们没有能力在运行时根据组件的状态动态更新样式。

现在,随着大多数现代浏览器支持原生 CSS 变量,我们可以利用它来轻松连接组件的状态和样式。

设计细节

SFC 中的标签现在支持一个自定义 CSS 函数 v-bind:


<!-- in Vue SFC -->
<style>
  .text {
    color: v-bind (color);
  }
</style>

正如预期的那样,这将把声明的值绑定到组件状态的属性上,Reactively.color color

该函数内部可以支持任意的 javascript 表达式,但由于 JavaScript 表达式可能包含在 CSS 标识符中无效的字符,因此在大多数情况下需要用引号来包裹它们:v-bind


.text {
  font-size: v-bind ('theme.font.size');
}

当检测到这种 CSS 变量时,SFC 编译器将执行以下操作:

重写到一个带有哈希变量名称的本机。上面的内容将被改写为:v-bind () var ()


.text {
  color: var (--6b53742-color);
  font-size: var (--6b53742-theme_font_size);
}

请注意,hash 将应用于所有情况,无论标签是否有范围。这意味着注入的 CSS 变量不会意外地泄漏到子组件中。

相应的变量将作为内联样式被注入到组件的根元素中。对于上面的例子,最终渲染的 DOM 将看起来像这样:


<div style="--6b53742-color:red;--6b53742-theme_font_size:2em;" class="text">
  hello
</div>

注入是响应式的 ——所以如果组件的属性发生变化,注入的 CSS 变量将被相应地更新。这种更新是独立于组件的模板更新的,所以对一个纯 CSS 的响应式属性的改变不会触发模板的重新渲染。

编译细节

为了注入 CSS 变量,编译器需要生成并注入如下代码到组件的 setup ()


import { useCssVars } from 'vue'

export default {
  setup() {
    //...
    useCssVars(_ctx => ({
      color: _ctx.color,
      theme_font_size: _ctx.theme.font.size,
    }))
  },
}

... 这里,运行时帮助器设置了一个将变量响应性地应用到 DOM.useCssVars watchEffect 上。

该编译策略要求脚本编译时首先对标签内容进行简单的重码解析,以确定要暴露的变量列表。然而,这个解析阶段不会像基于 AST 的完整解析 <style> 那样耗费开销。

在生产中,变量名可以被进一步 hash,以减少 CSS 的占用。


.text {
  color: var (--x3b2fs2);
  font-size: var (--29fh29g);
}

相应的生成的 JavaScript 代码将相应地使用相同的哈希值。

采用策略

这是一个完全向后兼容的新功能。然而,我们应该明确指出,它依赖于本地的 CSS 变量,所以用户需要了解浏览器的支持范围。

实践

在 script 中声明两个响应式的属性,分别是 wallpaperBlur 和 wallpaperMask。wallpaperBlur 表示壁纸的模糊程度, wallpaperMask 表示遮罩的透明度。通过 v-bind 将它们应用到 style,这意味着当我们在 script 中改变这两个值时,样式会响应更改。


// script
const wallpaperBlur = ref('0px')
const wallpaperMask = ref('rgba(0, 0, 0, 0)')

// style
.wallpaper {
  filter: blur(v-bind(wallpaperBlur));
  bottom: calc(v-bind(wallpaperBlur) * -2);
  left: calc(v-bind(wallpaperBlur) * -2);
  right: calc(v-bind(wallpaperBlur) * -2);
  top: calc(v-bind(wallpaperBlur) * -2);
  .wallpaper-image {
    transition: background-image 0.6s, background-color 0.4s;
  }
  .wallpaper-mask {
    background-color: v-bind(wallpaperMask);
  }
}

提示

绑定恰当的属性

在上面的例子中,你可能想到到更改遮罩的透明度仅需要声明一个 0-1 的数字,之后在 style 中这样写:


.wallpaper-mask {
  background-color: rgba(0, 0, 0, v-bind(wallpaperMask));
}

上文已经提到在编译阶段会将 style 中的 v-bind 改写为 CSS 变量的形式,上面的代码会被改写为这样:


.wallpaper-mask {
  background-color: rgba(0, 0, 0, var (--[hash]-wallpaper_mask));
}

rgba(0, 0, 0, var (--[hash]-wallpaper_mask)) 在 CSS 中是无法被解析的。所以这就是为什么将 wallpaperMask 的初始值声明为 rgba(0, 0, 0, 0) 的原因。这是需要十分注意的一点,CSS 中还有许多类似的情况。

注意 style 的更新

在设计细节中提到相应的变量将作为内联样式被注入到组件的根元素中。最终渲染的 DOM 将看起来像这样:


<div style="--6b53742-color:red;--6b53742-theme_font_size:2em;"></div>

当你在 <script> 中改变 <style> 中绑定的属性时,内敛样式中的 CSS 变量将会响应更改。但是,并不能单独更新内敛样式其中的一个 CSS 变量,这意味着更新一个组件中的任意一个“动态样式”,都将引起根组件中的内敛样式全部更新。当 style 属性的值包含大量 CSS 变量时,你需要考虑重新组织组件。因为编译生成的 CSS 变量都将作为内联样式被注入到组件的根元素中,我们无法控制这种行为,将一个引起更新的 CSS 变量和其他 CSS 变量解耦。

试想这种情况, style 中编译生成的 CSS 变量中包含一个其值为庞大的 base64 的 CSS 变量。当更新该组件中其他 CSS 变量时,整个 style 都将更新,这将带来额外的硬件开销。我们需要将这个生成 base64 CSS 变量的组件单独抽离,以使该 CSS 变量注入到该组件的根元素,不受其他 CSS 变量更新影响。

参考资料

https://GitHub.com/vuejs/rfcs/pull/231

到此这篇关于vue3 style CSS 变量注入的实现的文章就介绍到这了,更多相关Vue3 style CSS变量注入内容请搜索编程网以前的文章或继续浏览下面的相关文章希望大家以后多多支持编程网!

--结束END--

本文标题: Vue3 style CSS 变量注入的实现

本文链接: https://lsjlt.com/news/130895.html(转载时请注明来源链接)

有问题或投稿请发送至: 邮箱/279061341@qq.com    QQ/279061341

猜你喜欢
  • Vue3 style CSS 变量注入的实现
    目录摘要基础示例动机设计细节编译细节采用策略实践提示绑定恰当的属性注意 style 的更新参考资料摘要 在单文件组件样式中支持使用组件状态驱动的 CSS 变量( CSS 自定义属性...
    99+
    2024-04-02
  • SpringBoot使用@Value实现给静态变量注入值
    SpringBoot中使用@Value()只能给普通变量注入值,不能直接给静态变量赋值 例如 application-dev.properties 配置文件有如下配置: 给普通变量...
    99+
    2024-04-02
  • vue3中如何实现定义全局变量
    目录vue3定义全局变量vue3全局变量app.config.globalProperties的使用globalPropertiesvue3定义全局变量 在vue2中,我们知道vue...
    99+
    2024-04-02
  • MySQL怎么注入利用的变量
    这篇文章主要介绍“MySQL怎么注入利用的变量”,在日常操作中,相信很多人在MySQL怎么注入利用的变量问题上存在疑惑,小编查阅了各式资料,整理出简单好用的操作方法,希望对大家解答”MySQL怎么注入利用的...
    99+
    2024-04-02
  • SpringBoot通过@Value实现给静态变量注入值详解
    目录一、简介二、@Value给静态变量注入值方案一方案二三、总结一、简介 SpringBoot 中给普通变量注入值只需在变量上添加 @Value 注解即可。 application....
    99+
    2024-04-02
  • CSS变量如何实现暗黑模式
    这篇文章主要介绍CSS变量如何实现暗黑模式,文中介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们一定要看完!使用 CSS变量 和 @media查询 实现暗黑模式。 CSS Dark Mode我定义了变量以设置主题的颜色,我建议...
    99+
    2023-06-08
  • Vue3中的依赖注入与组件定义怎么实现
    本篇内容主要讲解“Vue3中的依赖注入与组件定义怎么实现”,感兴趣的朋友不妨来看看。本文介绍的方法操作简单快捷,实用性强。下面就让小编来带大家学习“Vue3中的依赖注入与组件定义怎么实现”吧!provide() & inject()...
    99+
    2023-07-05
  • Spring 父类变量注入失败的解决
    目录Spring 父类变量注入失败下面小记下这个过程Spring通过父类注入公用属性的技巧XML配置方式提取父类Annotation方式提取父类Spring 父类变量注入失败 昨天遇...
    99+
    2024-04-02
  • 深入理解python类的实例变量和类变量
    本python是python 3.5版本~!!!class aa:       w = 10       def __init__(self):            self.x = 11            self.y = 12  ...
    99+
    2023-01-31
    变量 实例 python
  • Mybatis-Plus通过SQL注入器实现批量插入的实践
    目录前言一、mysql批量插入的支持二、Mybatis-Plus默认saveBatch方法解析1、测试工程建立2、默认批量插入saveBatch方法测试3、saveBatch方法实现...
    99+
    2022-11-13
    Mybatis-Plus SQL注入器批量插入 Mybatis-Plus 批量插入
  • 深入了解Python中的变量类型标注
    目录一、概述1、描述2、常用的数据类型3、mypy模块二、使用1、基本使用2、函数参数返回值添加类型标注3、混合类型检查改进4、类型别名更改一、概述 1、描述 变量类型注解是用来对变...
    99+
    2023-05-15
    Python变量类型标注 Python 类型标注 Python标注
  • spring注入静态变量的方式有哪些
    在Spring中,无法直接通过注解的方式将静态变量注入到Bean中,因为静态变量属于类级别的,而Spring的注入是依赖于对象实例的...
    99+
    2023-08-24
    spring
  • docker环境变量注入的方法是什么
    在Docker中,可以通过以下几种方法注入环境变量: 使用Dockerfile中的ENV指令:在Dockerfile中使用`EN...
    99+
    2023-10-27
    docker
  • 怎么使用CSS变量实现心动效果
    本篇内容介绍了“怎么使用CSS变量实现心动效果”的有关知识,在实际案例的操作过程中,不少人都会遇到这样的困境,接下来就让小编带领大家学习一下如何处理这些情况吧!希望大家仔细阅读,能够学有所成! 前...
    99+
    2024-04-02
  • JS监听变量改变的实现
    目录需求和背景Object.defineProperty用法如下:入参用法:例子:对一个对象进行整体响应式监听:缺陷Proxy例子在React中的实践Object.definePro...
    99+
    2023-05-16
    JS监听变量改变 JS监听变量
  • vue3实战教程之axios的封装和环境变量
    目录axios基本使用配置封装请求时添加loading环境变量总结axios axios: ajax i/o system. 一个可以同时在浏览器和node环境进行网络请求的第三方库...
    99+
    2024-04-02
  • springboot 注解方式批量插入数据的实现
    目录一.使用场景二.实现方法1.mysql表结构2.domain3.mapper4.测试类5.测试结果三.插入效率对比1.批量插入2.一条一条插入一.使用场景 一次请求需要往数据库插...
    99+
    2024-04-02
  • 基于@PostConstruct注解的使用,解决向静态变量注入值
    目录@PostConstruct注解的使用,向静态变量注入值说说思路@PostConstruct和静态变量注入和spring初始化执行顺序关于spring初始化操作@PostCons...
    99+
    2024-04-02
  • Spring对静态变量无法注入的解决方案
    Spring对静态变量无法注入 问题 今天在学习的过程中想写一个连接和线程绑定的JDBCUtils工具类,但测试时发现一直报空指针异常,上网查了之后Spring并不支持对静态成员变量...
    99+
    2024-04-02
  • Python基础之变量和变量实现的简单乘
    上篇我们知道了关于python的一个hello world的简单程序代码,现在我们来了解关于python里面的变量,我们来了解下,变量是什么? 变量:变量是为了存储程序运算过程中的一些中间结果,为了方便之后的调用,同一变量可以重新赋值。 ...
    99+
    2023-01-30
    变量 简单 基础
软考高级职称资格查询
编程网,编程工程师的家园,是目前国内优秀的开源技术社区之一,形成了由开源软件库、代码分享、资讯、协作翻译、讨论区和博客等几大频道内容,为IT开发者提供了一个发现、使用、并交流开源技术的平台。
  • 官方手机版

  • 微信公众号

  • 商务合作