style-vw-loader适配vite

style-vw-loader这个插件是基于webpack的插件,不适用于vite,因为vite是基于rollup的。
rollup的插件和webpack的插件写法略有不通。

查看style-vw-loader源码将其移植即可。
源码比较简单:
https://github.com/hyy1115/style-vw-loader

rollup的插件编写也和webpack类似,可以参考这里:
https://juejin.cn/post/7060806475907596319

改造后如下:
/stylePxToVw.js

// 默认参数
let defaultsProp = {
  unitToConvert: "px",
  viewportWidth: 750,
  unitPrecision: 5,
  viewportUnit: "vw",
  fontViewportUnit: "vw",
  minPixelValue: 1,
};
function toFixed(number, precision) {
  var multiplier = Math.pow(10, precision + 1),
    wholeNumber = Math.floor(number * multiplier);
  return (Math.round(wholeNumber / 10) * 10) / multiplier;
}

function createPxReplace(
  viewportSize,
  minPixelValue,
  unitPrecision,
  viewportUnit
) {
  return function ($0, $1) {
    if (!$1) return;
    var pixels = parseFloat($1);
    if (pixels <= minPixelValue) return;
    return toFixed((pixels / viewportSize) * 100, unitPrecision) + viewportUnit;
  };
}
const templateReg = /<template>([\s\S]+)<\/template>/gi;
const pxGlobalReg = /(\d+)px/gi;

// 生成插件的工厂方法
const pluginGenerator = (customOptions = defaultsProp) => {
  // 返回插件
  return {
    // 插件名称
    name: "postcss-px-to-viewport",

    // transform 钩子
    async transform(code, id) {
      let _source = "";
      if (/.vue$/.test(id)) {
        let _source = "";
        if (templateReg.test(code)) {
          _source = code.match(templateReg)[0];
        }
        if (pxGlobalReg.test(_source)) {
          let $_source = _source.replace(
            pxGlobalReg,
            createPxReplace(
              customOptions.viewportWidth,
              customOptions.minPixelValue,
              customOptions.unitPrecision,
              customOptions.viewportUnit
            )
          );

          code = code.replace(_source, $_source);
          console.log(code);
        }
      }
      return { code };
    },
  };
};

export default pluginGenerator;

然后,只需要vite.config.js里使用这个插件即可

import { defineConfig } from 'vite'
import vue from '@vitejs/plugin-vue'
import postcsspxtoviewport from 'postcss-px-to-viewport';

export default defineConfig({
  plugins: [
    stylePxToVw(), // 插件的引用顺序要注意 一定要放在第一位
    vue(),
    
  ]
})

效果

posted @ 2022-07-08 10:18  丁少华  阅读(1183)  评论(7)    收藏  举报