【自适应】px 转 rem,你还在手算么?

23,994 阅读4分钟

小知识,大挑战!本文正在参与“程序员必备小知识”创作活动。

前言

8.29日发布了一篇CSS预处理器,你还是只会嵌套么 ?的文章,幸运地被挂在热榜上好几天😁。

目前为止,文章收获阅读量1093、点赞数58、收藏数34。在数据上,还是比较可观。所以,我草率地得出一个结论:和我一样CSS不咋地的人有很多,不承认的,你能从网线另一端爬过来打我么😶?

小故事

大佬:rem,em,px有什么区别?

我:rem是相对单位,值基于根元素设置的字体尺寸(默认16px);em是相对单位,值相对当前对象内文本的字体尺寸,px是相对单位,值根据屏幕分辨率来确定😁。

大佬:px怎么转rem ?

我:16px = 1rem,所以将 转换值 / 16 就可转换。

大佬:那每个地方我都手算一遍 ?

我:... 不然呢。

一个bad ending😫,感谢大佬最后告诉我一个关键词PostCss,涨姿势了。

抛砖引玉,今天的主题就是PostCss官网

PostCss

官方话术:是一个用JavaScript工具和插件转换CSS代码的工具。

声明:它不是 “ 预处理器 ”,因它没有像使用预处理那些功能,且能和预处理器结合使用;它也不是一个真正的 “ 后处理器 ”。因后处理器通常被视为在完成的样式表中根据CSS规范处理CSS,常做的是CSS属性添加浏览器私有前缀,但PostCSS并不局限于此。所以,最好的解释,它是个处理器(平台),拥有多样化的功能插件,可根据自己的需要配置需要的功能,甚至你自己都可编写PostCSS插件。

常用的插件有autoprefixer添加浏览器私有前缀,cssnext允许使用浏览器不支持的CSS新特性。感兴趣的可以根据关键词查一查,用一用。

回到主题,px自动化转rem需要什么插件? 答案是postcss-pxtorem

方法简单,效果惊人,还不快来学习!!!

实战教学

实践是检验真理的唯一标准【Vue3为例】。

安装

npm i postcss-pxtorem --save

配置Postcss

项目下新建postcss.config.js文件

module.exports = {
  plugins: {
    'postcss-pxtorem': {
       //根元素字体大小
       rootValue: 16,
       //匹配CSS中的属性,* 代表启用所有属性
       propList: ['*'],
       //转换成rem后保留的小数点位数
       unitPrecision: 5//小于12px的样式不被替换成rem
       minPixelValue: 12,
       //忽略一些文件,不进行转换,比如我想忽略 依赖的UI框架
       exclude: ['node_modules']
     }
  }
}

添加完毕,尝试重启下项目,使文件生效~

重启后,打开Chrome控制台,可以发现所有的px都被自动转化为rem😁。

image.png

image.png

根据配置可知,我们是以font-size为基准实现页面尺寸布局的,但如果一直写死16,如何实现自适应布局?

为了达到在不同设备宽度下对应不同的基准值,还需新建rem.js,代码如下。
核心思想: 以设计稿定义的宽1920,根元素字体大小16为基准,动态计算不同屏幕下的不同根元素的字体大小。

const baseSize = 16
function setRem() {
  const scale = document.documentElement.clientWidth / 1920
  document.documentElement.style.fontSize = baseSize * scale + 'px'
}
setRem()
window.onresize = function () {
  setRem()
}

main.js引入

import './rem.js'

在线案例地址,拖拽感受一下。

总结

自适应的认知之前一直停留在媒体查询,才发现还有如此好用的插件平台!!!打开新世界大门(虽然查资料,发现早就有这个东西了,拖后腿了...)

结合媒体查询 + postcss-pxtorem相信能高效解决大部分自适应问题。

若没有效果,可以查看评论区,是不是也是版本的问题~


敲黑板

em 的定义很细节,它的值是相对于当前对象内文本的字体尺寸。

默认情况下 1em = 16px。如果 父元素设置1.2em,子类又设置1.2em,实际上子元素字体大小为1.2 * 1.2 = 1.44em,转化为 px 则是 1.44 * 16 = 23.04 px。

关于 em 是相对于父元素的大小的草率定论。原因在于父元素不设置时,默认是 1em,又由于 em 会继承父级字体大下,所以子元素也是 1 * 1 = 1em,从而造成一种相对于父元素的错觉。

查阅 MDN 文档的一个 em 小技巧

设置body元素的字体大小为62.5% (即默认大小16px的62.5%),等于10px。现在你可以通过计算基准大小10px的倍数,在任何元素上方便的使用em单位。这样有6px = 0.6em, 8px = 0.8em, 12px = 1.2em, 14px = 1.4em, 16px = 1.6em

感谢评论区 月半流云 大佬的点拨。✌

参考

PostCSS深入学习:你需要知道什么
对比下px、em、rem有什么不同