vue[css换肤功能的多种实现⽅式]
vue中换肤功能有着好⼏种实现⽅式,如下:
1. 利⽤class 命名空间,同时命名多套主题如:black-theme、light-theme等,按需加载主题类名(简单 - 常⽤)
2. 准备多套CSS样式,利⽤link标签的ref切换(简单 - 按需加载主题,但是管理配置没1⽅便)
3. 使⽤CSS预处理器(如:scss)⽣成多套主题样式(复杂 - webpack打包处理)
4. CSS3的变量功能⽣成多套主题样式(复杂 - 兼容性问题(详见css3))
5. 动态换肤(复杂-适⽤性⼴)
不同的实现⽅式有着不同的优缺点,我们可以根据需要来进⾏选择,个⼈优先推荐1、3、5⽅案。
实现⽅式⼀:利⽤class 命名空间,引⼀个⽂件,多套主题类切换
实现如下:(我使⽤的是sass预编译器)
第⼀步:在 assets ⽂件夹中定义主题的⽂件theme.scss,其内容如下:
注意每⼀套主题中的类命名必须和实际的层级结构⼀样,且提取出所有需要修改覆盖的类名,并且给其附上相关值
层级结构如:
这个样式的层级结构会根据vue的组件嵌套层级来决定,相信使⽤过vue的都应该知道vue中样式的层
级情况。
第⼆步:在main.js中全局引⼊主题
第三步:切换主题操作,给app添加主题类
注意:在提取相关样式类的颜⾊的时候有可能会忘记将原先的样式类去掉相关的颜⾊,此时需要给theme.scss主题中的css都加
上!important才能够将内容替换掉
优点:
1.实现简单,只需要提取出需要改变样式的类名,按照其层级结构进⾏修改即可。
2所有的主题都是统⼀在⼀个⽂件中管理,⽅便维护
缺点
1.主题多了就会造成体积变⼤问题。
2.可能会出现主题样式不能覆盖问题:如:组件内的某些样式使⽤了!important 等,或者组件内某个插件重写了样式如:引⼊elmentUI重写table样式等,因此需要注意权限层级问题。
这种⽅式适⽤于轻改
实现⽅式⼆:准备多套CSS样式,利⽤link标签的ref切换
实现⽅式:
第⼀步:在public/static⽂件夹中准备好需要引⽤的主题⽂件如:
注意:link引⽤的⽂件必须要在public/static中,且结尾只能是.css的⽂件,scss⽂件不会被编译
第⼆步:在app.vue中的mounted⽣命周期中创建link
var link = ateElement('link');
link.id = "theme";
link.href = './static/css/theme-default.css';
第三步:在需要切换内容的组件中进⾏逻辑操作如:
注意:⽅法要在mouted周期⾥⾯
优点:
实现简单,只需要写⼀套css样式代码,然后后续的所有主题都可以根据这套代码进⾏复制修改即可。与⽅式⼀的区别在于⼀个全部引⼊进来(⽅式⼀),这⾥则是按照需要引⽤,因此相对⽽⾔css的体积会⼩好多。
缺点
需要⼿写多份CSS配⾊样式; ⽽且切换样式需要下载CSS的时间,如果样式内容⽐较多,单个⽂件体
积⽐较⼤的时候,可能在切换的时候会出现细微的卡顿。
实现⽅式三:使⽤CSS预处理器(scss)或者CSS3的变量功能⽣成多套主题样式
实现⽅式四:使⽤CSS3的变量功能⽣成多套主题样式
第⼀步:认识css3⾃定义属性
在需要的作⽤域中定义变量(在任意的全局css⽂件或者style中定义即可),如:
//:root作⽤于全局
:root{
--theme-color:red; // 这⾥定义了⼀个--theme-color变量,值为black
}
//#app作⽤于id为app的节点内
css变量#app{
-
-theme-back-color: black; // 这⾥定义了⼀个--theme-back-color变量,值为black
}
使⽤⽅式:1.在css中使⽤,如:在.title中使⽤:
.title{
color: var(--theme-color)
}
使⽤⽅式:2.在js中使⽤,如:
// document.documentElement 代表相关的容器如:#box
//js中获取--theme-color的值
var value = getComputedStyle(document.documentElement).getPropertyValue("--theme-color");
//js中更改--theme-color的值
document.documentElement.style.setProperty("--theme-color","black");
优点:只需⼀套CSS⽂件;换肤不需要延迟等候;对浏览器性能要求低;可⾃动适配多种主题⾊;缺点:兼容性问题、不⽀持IE, 2016年前的chrome,safari;
实现⽅式五:动态换肤
这是elementUi的⼀种换肤⽅式
demo代码:
<html lang="en">
<head>
<title>js 动态换肤</title>
<!-- 利⽤axios 实现异步加载样式-->
<script src="cdn.bootcss/axios/0.19.0-beta.1/axios.min.js"></script>
</head>
<body>
<h3 class="title">js 动态换肤</h3>
<script>
// 1. 主题颜⾊配置
var colors = {
red: {
themeColor: '#FF0000'
},
blue: {
themeColor: '#0000FF'
}
}
// 2. 异步获取样式
var styles = ''
<('theme.css').then((resp=> {
const colorMap = {
'#FF0000': 'themeColor'
}
styles = resp.data
Object.keys(colorMap).forEach(key => {
const value = colorMap[key]
styles = place(new RegExp(key, 'ig'), value)
console.log(styles)
})
writeNewStyle (styles, d)
}))
// 3.换⾊
// console.log 中输⼊ writeNewStyle (styles, colors.blue)可以换蓝⾊主题
// console.log 中输⼊ writeNewStyle (styles, colors.blue)可以换红⾊主题
function writeNewStyle (originalStyle, colors) {
let oldEl = ElementById('temp-style')
let cssText = originalStyle
Object.keys(colors).forEach(key => {
cssText = place(new RegExp(key, 'ig'), colors[key])
})
const style = ateElement('style')
style.innerText = cssText
style.id = 'temp-style'
oldEl ? placeChild(style, oldEl) : document.head.appendChild(style) }
</script>
</body>
</html>
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。
发表评论