本文只介绍深浅两种主题换肤作为参考。
1.创建配置动态样式的scss文件,路径为/src/assets/scss/_theme.scss。
$themes: (
light: (
//字体
font_color1: #000,
//背景
background_color1: #fff,
// 背景渐变
background_gradient1:#F8FBFD ,
//边框
border_color1: #e8ebf0,
//边框阴影
box_shadow_color1: rgba(127, 131, 168, 0.2)
),
dark: (
//字体
font_color1: #fff,
//背景
background_color1: #000,
//背景渐变
background_gradient1:#DD1C1C,
//边框
border_color1: #34383c,
// 阴影
box_shadow_color1: rgba(0, 0, 0, 0.4)
),
);
2.创建样式封装的scss文件,路径为/src/assets/scss/_handle.scss。
@import "./_theme.scss";
//遍历主题map
@mixin themeify {
@each $theme-name, $theme-map in $themes {
//!global 把局部变量强升为全局变量
$theme-map: $theme-map !global;
//判断html的data-theme的属性值 #{}是sass的插值表达式
//& sass嵌套里的父容器标识 @content是混合器插槽,像vue的slot
[data-theme="#{$theme-name}"] & {
@content;
}
}
}
//声明一个根据Key获取颜色的方法
@function themed($key) {
@return map-get($theme-map, $key);
}
//获取背景颜色
@mixin background_color($color) {
@include themeify {
background-color: themed($color) ;
}
}
//获取字体颜色
@mixin font_color($color) {
@include themeify {
color: themed($color) ;
}
}
//获取边框颜色
@mixin border_color($color) {
@include themeify {
border-color: themed($color) !important;
}
}
//获取阴影颜色
@mixin box_shadow($color) {
@include themeify {
box-shadow: 0px 2px 4px 0px themed($color) !important;
}
}
// 获取背景色渐变
@mixin linear-gradient($from, $to) {
@include themeify {
background: linear-gradient(to bottom, themed($from),themed($to));
}
}
/*px转rem*/
@mixin px2rem($property,$px,$px2:false,$px3:false,$px4:false){
$rem:75px;/* 设计稿尺寸/10 */
@if $px and $px2 and $px3 and $px4 {
#{$property}: ($px / $rem) + rem ($px2 / $rem) + rem ($px3 / $rem) + rem ($px4 / $rem) + rem;
}
@else if $px and $px2 {
#{$property}: ($px / $rem) + rem ($px2 / $rem) + rem;
//[data-model='pad'] & {#{$property}: ($px * 1.4 / $rem) + rem ($px2 * 1.4 / $rem) + rem;}
}
@else{
#{$property}: ($px / $rem) + rem!important;
//[data-model='pad'] & {#{$property}: ($px * 1.4 / $rem) + rem;}
}
}
/*根据dpr计算font-size*/
@mixin font-dpr($font-size){
font-size: $font-size;
//[data-model="pad"] & { font-size: $font-size * 1.4; }
[data-dpr="2"] & { font-size: $font-size * 2;}
[data-dpr="3"] & { font-size: $font-size * 3;}
}
/*弹性盒属性*/
%flexbox{
display: inline-flex;display: -webkit-flex;display: flex;
}
/*弹性盒比例*/
@mixin flex($num:1){
-webkit-box-flex:$num;-moz-box-flex:$num;-webkit-flex:$num;-ms-flex:$num;flex:$num;
}
/*超行溢出显示省略号*/
@mixin overflow($num:1,$fontSize:0,$lineHeight:1.5){
display: -webkit-box;-webkit-line-clamp:$num; overflow: hidden;
/*! autoprefixer: off */
-webkit-box-orient: vertical;
/* autoprefixer: on */
@if $fontSize!=0 and $lineHeight{/*高度需要撑开*/
line-height:$lineHeight;
@if $lineHeight < 1.2 {
line-height:1.2; /*最小需要1.2,否则在部分安卓机下第$num+1行会顶部漏出*/
}
height: $num * $fontSize * $lineHeight;
[data-dpr="2"] & { height: $num * $fontSize * $lineHeight * 2!important;}
[data-dpr="3"] & { height: $num * $fontSize * $lineHeight * 3!important;}
}
}
//transition兼容写法
@mixin transition($content:all .2s){
-moz-transition: $content;
-webkit-transition: $content;
-o-transition: $content;
transition: $content;
}
//transfrom兼容
@mixin translateX($num:-50%){
-ms-transform: translateX($num);
-moz-transform: translateX($num);
-webkit-transform: translateX($num);
-o-transform: translateX($num);
transform: translateX($num);
}
@mixin translateY($num:-50%){
-ms-transform: translateY($num);
-moz-transform: translateY($num);
-webkit-transform: translateY($num);
-o-transform: translateY($num);
transform: translateY($num);
}
@mixin rotate($deg:90deg){
-ms-transform:rotate($deg);
-moz-transform:rotate($deg);
-webkit-transform:rotate($deg);
-o-transform:rotate($deg);
transform:rotate($deg);
}
3.根据不同的主题颜色设置全局属性
//项目登录/主题更换时调用
//已知type="0"为深色主题,type="1"为浅色主题。
changeTheme(type = 1){
const themeArr = ['dark', 'light'];
const themeShow= themeArr [type];
window.document.documentElement.setAttribute("data-theme", themeShow);
}
4.index.vue中使用
<style lang="scss" scoped>
@import "@/assets/scss/_handle.scss";
span{
@include font_color("font_color1");
@include border_color("border_color1");
@include background_color("background_color1");
@include box_shadow("box_shadow_color1");
...
}
</style>