Vue项目切换主题颜色(mixin + scss)

Vue项目切换主题颜色(mixin + scss)

一、引入scss依赖(node-sass, sass-loader,sass-resources-loader,style-resources-loader等)
npm install node-sass sass-loader sass-resources-loader --save-dev

package.json截图
Vue项目切换主题颜色(mixin + scss)_第1张图片

二、 项目样式引入

项目中的公共样式文件放到了 src/styles目录下 。 theme.scss, mixins.scss两个文件为我们稍后进行主题颜色配置的文件,在vue.config.js中引入.

  • 在main.js中引入index.scss(基本公共样式)
import '@/styles/index.scss' 
  • 在vue.config.js中引入主题样式mixins.scss,theme.scss在mixins.scss中引入,截图中base.scss是封装的scss计算函数
    • 引入theme.scss在mixins.scss
    @import './theme.scss';
    
    • 引入mixins.scss
      Vue项目切换主题颜色(mixin + scss)_第2张图片
三、 主题scss文件配置
  1. theme.scss文件内容,这边我这是两个主题颜色,暗色和亮色
  $default: (
  // 默认图片地址
        baseImageURL: '~@/assets/images/',
  // label颜色
        blackGray: #d6d6d6,
  // 单位颜色
        unitColor: rgba(255, 255, 255, 0.4),
  // 部分色块背景色
        baseColor: #0b8cff,
  // 盒子背景色
        bgColor: rgba(10, 16, 28, 0.18),
  // 公共盒子分割线
        commonBlockColor: #d0deee,
  // 公共盒子分割块
        commonShapeColor: rgba(255, 201, 122, 1),
        partBorderColor: #fff,
  // 公共盒子背景
        commBoxTitleBg: linear-gradient(
                        90deg,
                        rgba(106, 112, 124, 0.4) 0%,
                        rgba(106, 112, 124, 4e-5) 70%,
                        rgba(106, 112, 124, 4e-5) 100%
        ),
  // 主题边框颜色
        themeBorderColor: rgba(255, 255, 255, 0.2),
  // 主题文字颜色
        themeTextColor: #fff,
  // 地图标题下划线边框颜色
        mapBorder: rgba(255, 255, 255, 0.1),
  // 下拉框移入颜色
        themeHoverColor: rgba(11, 140, 255, 0.1),
  // 下拉框选中字体颜色
        activeFontColor: #0b8cff,
  // 默认字体颜色
        defaultFontColor: #fff,
  // 下拉框背景色
        selectBgColor: #1d232b,
  // 框架头部样式 
        headerBg: linear-gradient(180deg, #0b1015 0%, rgba(16, 22, 28, 0.2) 100%),
        headerTabChooseColor: #fff,
        headerTabFontColor: rgba(255, 255, 255, 0.6),
  // 天气标题颜色
        nameColor: rgba(255, 255, 255, 0.5),
  // 饼状图上升颜色
        distanceColor: #76f03c,
  // 饼状图下降颜色
        distanceRedColor: #ff6a3a,
);
$light: (
  // 默认图片地址
        baseImageURL: '~@/assets/themeA/',
  // label颜色
        blackGray: #d6d6d6,
  // 单位颜色
        unitColor: rgba(255, 255, 255, 1),
  // 部分色块背景色
        baseColor: #0b8cff,
  // 盒子背景色
        bgColor: rgba(10, 16, 28, 0.18),
  // 公共盒子分割线
        commonBlockColor: #d0deee,
  // 公共盒子分割块
        commonShapeColor: rgba(255, 201, 122, 1),
        partBorderColor: #fff,
  // 公共盒子背景
        commBoxTitleBg: linear-gradient(
                        90deg,
                        rgba(106, 112, 124, 0.4) 0%,
                        rgba(106, 112, 124, 4e-5) 70%,
                        rgba(106, 112, 124, 4e-5) 100%
        ),
  // 主题边框颜色
        themeBorderColor: rgba(255, 255, 255, 0.2),
  // 主题文字颜色
        themeTextColor: #fff,
  // 地图标题下划线边框颜色
        mapBorder: rgba(255, 255, 255, 0.1),
  // 下拉框移入颜色
        themeHoverColor: rgba(11, 140, 255, 0.1),
  // 下拉框选中字体颜色
        activeFontColor: #0b8cff,
  // 默认字体颜色
        defaultFontColor: #fff,
  // 下拉框背景色
        selectBgColor: #1d232b,
  // 框架头部样式 
        headerBg: linear-gradient(180deg, #0b1015 0%, rgba(16, 22, 28, 0.2) 100%),
        headerTabChooseColor: #fff,
        headerTabFontColor: rgba(255, 255, 255, 0.6),
  // 天气标题颜色
        nameColor: rgba(255, 255, 255, 0.5),
  // 饼状图上升颜色
        distanceColor: #76f03c,
  // 饼状图下降颜色
        distanceRedColor: #ff6a3a,
);
$themes: (
        default: $default,
        light: $light
)

  1. 在mixins.scss中操作theme.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
@function themed($key) {
  @return map-get($theme-map, $key);
}
// 主题图片加载混合器 $path 图片名称地址
@mixin imageURL($path) {
  @include themeify {
    background-image: url(map-get($theme-map, 'baseImageURL')+$path);
    background-repeat: no-repeat;
  }
}

//获取背景颜色
@mixin background_color($color,$important: false) {
  @include themeify {
    background: themed($color) if($important, !important, null);
  }
}

//获取字体颜色
@mixin font_color($color) {
  @include themeify {
    color: themed($color);
  }
}

//获取边框颜色
@mixin border_color($color) {
  @include themeify {
    border-color: themed($color);
  }
}
// 设置边框样式
@mixin border_style($height,$color) {
  @include themeify {
    border: $height solid themed($color);
  }
}
//获取边框颜色
@mixin border_bottom_color($color,$height:vh(2)) {
  @include themeify {
    border-bottom: $height solid themed($color);
  }
}
//获取边框颜色
@mixin border_top_color($color,$height:vh(2)) {
  @include themeify {
    border-top: $height solid themed($color);
  }
}

  1. 在vue页面使用
//引入图片
.bgImg{
  @include imageURL('leftMask.png');
}
//引入背景颜色,传true代表添加!important
.bgColor {
@include background_color('selectBgColor',true);
}
//引入文字颜色
.font{
  @include font_color('unitColor')
}


四、 切换主题

根据以下配置后,调用handleChange就可以切换主题了

 

你可能感兴趣的:(vue.js,scss,前端)