更新记录

1.0.3(2025-11-18) 下载此版本

同步 npm 插件 style-class 到 dcloud 市场


平台兼容性

uni-app(3.6.14)

Vue2 Vue3 Chrome Safari app-vue app-nvue Android iOS 鸿蒙
微信小程序 支付宝小程序 抖音小程序 百度小程序 快手小程序 京东小程序 鸿蒙元服务 QQ小程序 飞书小程序 快应用-华为 快应用-联盟

uni-app x(3.6.14)

Chrome Safari Android iOS 鸿蒙 微信小程序

style-class插件使用文档

简介

style-class 是一款支持原子化 CSS 的 插件,适用于 Vue/uni-app等项目。

🚀 特性

  • 🎯 渐进式设计:插件本身不内置规则,可根据需求灵活扩展
  • 🔧 扩展包支持:推荐安装 @style-class/preset-tailwind 获取 Tailwind-V3 规则(安装 Tailwind-V3 预设之后就可以根据 Tailwind 文档使用)
  • 🌐 多端兼容:解决 uni-app nvue、uvue 选择器限制问题
  • 🎨 高级功能:支持 CSS 变量、主题、CSS3动画、单位转换、快捷方式等
  • 智能扫描:自动扫描项目文件,实时生成 CSS
  • 🔥 热更新:开发时自动热更新,提升开发效率

🎯 解决问题

  • ✅ uni-app nvue、uvue 只能用 class 选择器,现有市场原子化CSS无法使用
  • ✅ uni-app nvue、uvue 不能使用 tag、#id、[attr] 等选择器,现有市场原子化CSS无法使用
  • ✅ uni-app nvue、uvue 的 class 选择器仅支持 A-Z、a-z、0-9、_、- 字符,现有市场原子化CSS无法使用

📦 安装

基础插件(HBuilderX 方式可忽略)

npm install style-class -D

推荐扩展包(可选-自定义规则)

# 获取 Tailwind-V3 规则(推荐)
npm install @style-class/preset-tailwind -D

⚡ 快速开始

初始化 style-class

HBuilderX 方式不需要执行这个命令,但需要在项目根目录手动创建 style-class.scss 文件

npx style-class init

配置

HBuilderX 项目

vite.config.js

import { defineConfig } from 'vite'
import uni from '@dcloudio/vite-plugin-uni'
import styleClass from './js_sdk/style-class/dist/vite/index.esm.js'
// 使用 Tailwind 预设
import { theme, rules, keyframes, selectorVariants } from '@style-class/preset-tailwind'
// https://vitejs.dev/config/
export default defineConfig({
  plugins: [
    uni(),
    styleClass({
      extractorClass: ['class', ':class', 'className', ':className', 'paging-class', 'placeholder-class'],
      // CSS 主题,具体可参考 Tailwind 文档
      theme: {
        // 导入 Tailwind 预设主题
        ...theme,
        // 扩展主题,避免覆盖 Tailwind 预设 colors 主题
        extend: {
          colors: {
            primary: '#007aff',
            secondary: '#ff9900',
          }
        },
      },
      // CSS 正则
      rules: [
        // 导入 Tailwind 预设正则
        ...rules,
      ],
      // CSS 动画
      keyframes: {
        // 导入 Tailwind 预设动画
        ...keyframes,
      },
      // 选择器变体
      selectorVariants: [...selectorVariants],
    }),
  ],
})

Vite 项目

vite.config.js

import styleClass from 'style-class'
// 使用 Tailwind 预设
import { theme, rules, keyframes, selectorVariants } from '@style-class/preset-tailwind'

export default {
  plugins: [
    styleClass({
      // CSS 主题,具体可参考 Tailwind 文档
      theme: {
    // 导入 Tailwind 预设主题
        ...theme,
    // 扩展主题,避免覆盖 Tailwind 预设 colors 主题
    extend: {
      colors: {
            primary: '#007aff',
            secondary: '#ff9900',
          }
    }
      },
      // CSS 正则
      rules: [
    // 导入 Tailwind 预设正则
        ...rules
      ],
      // CSS 动画
      keyframes: {
    // 导入 Tailwind 预设动画
        ...keyframes
      },
      // 选择器变体
      selectorVariants: [
        ...selectorVariants
      ]
    })
  ]
}

Webpack 项目

vue.config.js

const { theme, rules, keyframes, selectorVariants } = require('@style-class/preset-tailwind');
module.exports = {
  ...
  module: {
    rules: [
      ...
      {
        test: /\.vue$/,
        use: [
          {
            loader: 'vue-loader'
          },
          {
            loader: 'style-class/webpack',
            options: {
              // 主题配置
              theme: {
                ...theme,
        // 扩展主题,避免覆盖 Tailwind 预设 colors 主题
        extend: {
          colors: {
                    primary: '#007aff',
                    secondary: '#ff9900',
                  }
            }
              },
              // 规则配置
              rules: [
                ...rules,
              ],
          // CSS 动画
              keyframes: {
                ...keyframes
              },
              // 选择器变体
              selectorVariants: [
               ...selectorVariants
              ],
              include: [/\.vue$/],
              exclude: [/node_modules/]
            }
          }
        ],
      },
    ]
  },
  ...
};

引入生成的 CSS

main.js 中引入 style-class.scss 文件:

style-class.scss 一般在 package.json 文件同级目录(HBuilderX 方式在项目根目录)

非 HBuilderX 方式创建项目

import '../style-class.scss'

HBuilderX 方式创建的项目

import './style-class.scss'

开始使用

<template>
  <!-- 基础原子类 -->
  <div class="flex flex-col items-center gap-4 p-4">
    <div class="w-full h-[32px] bg-primary text-[white] rounded-lg"></div>
    <button class="px-4 py-2 bg-secondary text-white rounded hover:opacity-80">
      按钮
    </button>
  </div>
</template>

⚙️ 配置选项

CSS 主题

类型

type Theme = Record<string, any>;

自定义主题

theme: {
  colors: {
    primary: '#409EFF',
    success: '#67C23A',
  }
}

扩展已有主题

前面自定义主题如果主题已存在会覆盖之前的,如果希望扩展而不是覆盖,需要使用 extend 字段

theme: {
  // 自定义 colors 主题
  colors: {
    primary: '#409EFF',
    success: '#67C23A',
  },
  extend: {
    // 扩展 colors 主题
    colors: {
      warning: '#E6A23C',
      danger: '#F56C6C',
    },
  }
}

CSS 变量

类型

type Variable = Record<string, string>;

自定义 CSS 变量

variable: {
  "--primary": '#409EFF',
  "--success": '#67C23A',
}

CSS 动画

类型

type KeyframesConfig = Record<
  string, // 动画名
  Record<
    string, // 关键帧百分比,如 '0%', '100%', 'to'
    Record<string, string> // CSS 属性对象
  >
>;

自定义 CSS 动画

const keyframes = {
    "spin": {
        "from": {
            "transform": "rotate(0deg)",
        },
        "to": {
            "transform": "rotate(360deg)",
        },
    }
};

CSS 规则

类型

type Rule = [string | RegExp, ((match: RegExpMatchArray, ctx: { theme: Theme, variable: Variable }) => Record<string, string> | undefined) | Record<string, string>];

静态规则

以此为例:

rules: [
  ['text-red', { 'color': 'red' }],
]

使用:

<span class="text-red">文本颜色</span>

动态规则

以此为例:

rules: [
  [/^text-\[(.+)\]$/, ([, value]) => ({ color: value })],
]

使用:

<span class="text-[#ff0000]">文本颜色</span>

规则中使用 CSS 主题

以此为例:

rules: [
  [/^text-(.*)$/, ([, value], { theme }) => {
    if (theme.colors[value]) return { color: theme.colors[value] };
  }],
]

使用:

<span class="text-primary">文本颜色</span>

规则中使用 CSS 变量

以此为例:

rules: [
  [/^text-\((.+)\)$/, ([, value], { _, variable }) => {
    if (variable[value]) return {
      [`${value}`]: variable[value],
      color: `var(${value})`
    };
  }],
]

使用:

<span class="text-(--primary)">文本颜色</span>

快捷方式

快捷方式可让你将多个规则组合成一个简写

类型

type Shortcuts = Record<string, string>;

自定义快捷方式

以此为例:

shortcuts: {
  // 按钮样式
  'btn': 'px-4 py-2 rounded font-medium transition-colors',
  'btn-primary': 'btn bg-primary text-white hover:bg-blue-600',
  'btn-secondary': 'btn bg-gray-200 text-gray-800 hover:bg-gray-300',

  // 卡片样式
  'card': 'bg-white rounded-lg shadow-md overflow-hidden',
  'card-header': 'px-6 py-4 border-b border-gray-200',
  'card-body': 'px-6 py-4',

  // 表单样式
  'form-input': 'w-full px-3 py-2 border border-gray-300 rounded-md focus:outline-none focus:ring-2 focus:ring-primary',
  'form-label': 'block text-sm font-medium text-gray-700 mb-1',

  // 布局样式
  'container': 'max-w-7xl mx-auto px-4 sm:px-6 lg:px-8',
  'flex-center': 'flex items-center justify-center',
  'flex-between': 'flex items-center justify-between'
}

使用

<div class="container">
  <div class="card">
    <div class="card-header">
      <h2 class="text-xl font-bold">标题</h2>
    </div>
    <div class="card-body">
      <p class="text-gray-600">内容区域</p>
      <div class="flex-between mt-4">
        <button class="btn-secondary">取消</button>
        <button class="btn-primary">确认</button>
      </div>
    </div>
  </div>
</div>

CSS 伪类支持

支持丰富的伪类和伪元素,通过配置 pseudoMap 映射表实现。

类型

Record<string, string>

自定义伪类映射表

以此为例:

pseudoMap: {
  // 伪类
  hover: ':hover',
  active: ':active',
  focus: ':focus',
  visited: ':visited',
  disabled: ':disabled',
  first: ':first-child',
  last: ':last-child',
  odd: ':nth-child(odd)',
  even: ':nth-child(even)',

  // 伪元素
  before: '::before',
  after: '::after',
  placeholder: '::placeholder'
}

使用方式:

<span class="hover:text-primary">文本颜色</span>

生成的类名:

.hover\:text-primary:hover { color: #409EFF; }

选择器变体

扩展复杂选择器,比如:兄弟选择器、伪类(推荐使用伪类映射表)

类型

type SelectorVariants = Array<{
  match: string | RegExp,
  selector: (s: string) => string
}>;

自定义选择器变体

以此为例:

selectorVariants: [
    {
        match: /^divide-/,
        selector: s => {
            return `${s} > * + *`
        }
    },
    {
        match: /^space-/,
        selector: s => {
            return `${s} > * + *`
        }
    }
]

使用方式:

<div class="divide-solid"></div>

生成的类名:

.divide-solid > * + * {
  border-style: solid;
}

特殊符号替换

用于将特殊符号替换为安全字符串,防止类名冲突或语法错误。例如 : 替换为 -c111-

类型

Record<string, string>

自定义特殊符号替换

以此为例:

replacements: {
    "\.": "-d111-",
    "/": "-s111-",
    ":": "-c111-",
    "%": "-p111-",
    "!": "-e111-",
    "#": "-w111-",
    "(": "-b111l-",
    ")": "-b111r-",
    "[": "-f111l-",
    "]": "-f111r-",
    $: "-r111-",
    ",": "-r222-",
    "\"": "-r333-",
    "\'": "-r444-",
  }

使用方式:

<span class="text-[16px]">文本颜色</span>

生成的类名:

.text-f111l-16px-f111r- { color: #409EFF; }

属性模式配置

属性模式让你可以通过 HTML 属性而非 class 来书写样式,与传统 class 写法对比

配置选项:

参数名 类型 默认值 说明
prefix string "css-" 属性前缀,用于区分普通 HTML 属性和样式属性
prefixedOnly boolean false 是否仅匹配带前缀的属性,设为true 时将忽略不带前缀的样式属性
splicing boolean false 是否拼接属性名和属性值生成类名,设为true 时会将 bg="primary" 转换为 bg-primary 为类名,否则为 false 时会将 box="bg-primary" 直接提取 bg-primary 为类名不会拼接属性名
import styleClass from 'style-class'

export default {
  plugins: [
    unitCss({
      prefix: "css-",           // 属性前缀,默认值:"css-"
      prefixedOnly: false,     // 仅匹配带前缀的属性,默认值:false
      splicing: false          // 属性名拼接属性值:默认值:false
    })
  ]
}

与传统 class 写法对比

写法 代码示例 特点
传统 class `` 传统 class所有样式集中在 class 属性,适合简单场景
属性模式 `` 样式分散在多个属性,结构更清晰,可读性更好

示例:

前缀可选
{ prefix: "css-", prefixedOnly: false, splicing: false }

使用方式:

<!-- 会被处理 -->
<div css-bg="bg-primary"></div>
<!-- 会被处理 -->
<div text="text-white"></div>

生成的类名:

.bg-primary {
  background-color: #409EFF;
}
.text-white {
  color: #ffffff;
}
仅匹配带前缀
{ prefix: "css-", prefixedOnly: true, splicing: false }

使用方式:

<!-- 会被处理 -->
<div css-bg="bg-primary"></div>
<!-- 不会被处理 -->
<div text="text-white"></div>

生成的类名:

.bg-primary {
  background-color: #409EFF;
}
不拼接
{ prefix: "css-", prefixedOnly: false, splicing: false }

使用方式:

<!-- 会被处理 -->
<div bg="bg-primary"></div>
<!-- 不会被处理 -->
<div text="white"></div>

生成的类名:

.bg-primary {
  background-color: #409EFF;
}
拼接
{ prefix: "css-", prefixedOnly: false, splicing: true }

使用方式:

<!-- 不会被处理 -->
<div bg="bg-primary"></div>
<!-- 会被处理 -->
<div text="white"></div>

生成的类名:

.text-white {
  color: #ffffff;
}

最佳实践

  1. 组件开发:推荐使用属性模式,使模板结构更清晰
  2. 简单元素:可使用传统 class 写法,更简洁
  3. 团队协作:建议统一配置,避免混合使用不同模式
  4. 前缀策略:在大型项目中保留前缀,避免与其他属性冲突

单位转换

自动转换不同单位,适配不同设备

类型

type UnitConversionRule = {
  /** 匹配的CSS属性名(支持正则表达式) */
  property: string | RegExp;
  /** 源单位 */
  fromUnit: string;
  /** 目标单位 */
  toUnit: string;
  /** 转换函数 */
  converter: UnitConverter;
};

自定义转换规则

以此为例:

{
  enableUnitConversion: true,
  unitConversions: [
    // px 转 rem(移动端适配)
    {
      property: /^(width|height|padding|margin|font-size).*$/,
      fromUnit: 'px',
      toUnit: 'rem',
      converter: (value) => `${value / 16}rem`
    },

    // px 转 rpx(小程序适配)
    {
      property: /^(width|height|padding|margin).*$/,
      fromUnit: 'px',
      toUnit: 'rpx',
      converter: (value) => `${value * 2}rpx`
    },

    // 自定义转换
    {
      property: 'line-height',
      fromUnit: 'px',
      toUnit: '',
      converter: (value) => String(value / 16) // 转换为相对值
    }
  ]
}

使用方式:

<div class="w-[320px] h-[240px] p-[16px] text-[14px]">
  内容区域
</div>

生成 CSS 样式:

.w-[320px] { width: 20rem; }
.h-[240px] { height: 15rem; }  
.p-[16px] { padding: 1rem; }
.text-[14px] { font-size: 0.875rem; }

高级功能配置

配置注意事项:

属性处理优先级:局部 specialAttributes > 局部 ignoreAttributes > 全局 specialAttributes > 全局 ignoreAttributes

文件匹配优先级:exclude > include

include

只处理匹配这些正则的文件,默认只处理 .vue.nvue.uvue 文件。

类型
RegExp[]
自定义 include
include: [/\.(vue|nvue|uvue)$/],

exclude

排除匹配这些正则的文件,默认排除 uni_modules 目录

类型
RegExp[]
自定义 exclude
exclude: [/uni_modules/]

extractorClass

支持从这些属性名中直接提取 class,用于解决动态绑定类名场景

类型
string[]
自定义 extractorClass
extractorClass: [
  "class",
  ":class",
  "className",
  ":className"
]

ignoreAttributes

提取 class 时会忽略这些属性,避免误处理某些组件非 class 属性冲突生成样式问题。

类型

全局

string[]

局部

string
自定义 ignoreAttributes

全局

ignoreAttributes: [
  'style',
  'src',
  'placeholder',
  'key',
  'ref',
  'placeholderStyle',
  'placeholder-style'
],

局部

<view ignoreAttributes="style"></view>

specialAttributes

处理特殊被 ignoreAttributes 属性,适用于需要特殊转换的场景,比如:特定组件某属性被 ignoreAttributes,但是这个组件不需要 ignoreAttributes

类型

全局

string[]

局部

string
自定义 specialAttributes

全局

specialAttributes: ['class']

局部

<view specialAttributes="class"></view>

ignoreTags

忽略特殊标签,不做任何处理,默认忽略 <template> 标签。

类型

string[]
自定义 ignoreTags
ignoreTags: ['template']

className

指定用于识别类名的属性,默认是 "class"

类型
string
自定义 className
className: "class",

❓ 常见问题

Q: 样式未生效或更新慢?

A: 检查以下几点:

  1. 确认 style-class.scss 已在 main.js 中正确引入
  2. 检查类名是否匹配配置的规则
  3. 保存文件触发重新生成,或手动刷新页面
  4. 查看控制台是否有错误信息

Q: 如何调试生成的 CSS?

A:

  1. 查看项目根目录的 style-class.scss 文件
  2. 检查是否有对应的 CSS 规则生成
  3. 使用浏览器开发者工具检查元素样式

Q: 可以与其他 CSS 框架一起使用吗?

A: 可以,但建议:

  1. 使用不同的类名前缀避免冲突
  2. 通过 include/exclude 配置限制作用范围
  3. 注意 CSS 优先级问题

Q: 如何在 TypeScript 项目中使用?

A: 支持 TypeScript

Q: 支持哪些文件类型?

A: 默认支持:

  • .vue - Vue 单文件组件
  • .nvue - uni-app 原生渲染页面
  • .uvue - uni-app Vue3 页面

可通过 include 配置扩展更多文件类型。


📚 更多资源


📄 许可证

MIT License

隐私、权限声明

1. 本插件需要申请的系统权限列表:

2. 本插件采集的数据、发送的服务器地址、以及数据用途说明:

3. 本插件是否包含广告,如包含需详细说明广告表达方式、展示频率:

许可协议

MIT协议