em px rem 相对单位
写了很多css代码,但一直都是在使用“px”来设置元素的相关属性,偶尔也使用“em”,基本很少使用rem。主要原因是,对其了解的不深,往往只知道一点概念性的,所以特意查找资料重新学习一回。今天整理了一份文章与大家分享,也算是记录自己点滴的学习,希望能对大家有所帮助。
px:绝对单位,按像素展示
"px"是我们用的最多也是最常见的,但是使用它虽然方便,但会带来一些小小的问题。不知道你们有没有这样的经历,辛辛苦苦把页面的代码码完了,在自己的电脑能正常显示,换一个电脑整个页面崩溃了(内心也崩溃了)。。。
接着就会想到比较熟悉的百分比来写css,但百分比到底是谁的百分比?有人说是相对于父元素的宽度(width),也有人说不仅仅相对于这个,相信大家也会有点迷糊吧!百分比布局虽然好用,但搞清楚是相对于谁的百分比非常重要,来点干货:
- 参照父元素宽度的元素:padding margin width text-indent
- 参照父元素高度的元素:height
- 参照父元素属性:font-size line-height(如果自身有font-size属性,相对于自身)
- 特殊:相对定位的时候,top(bottom) left(right) 参照的是父元素的内容参照的是父元素的内容区域的高度与宽度;而绝对定位的时候参照的是最近的定位元素包含padding的高度与宽度;对于position:fixed的元素,则一直基于body元素
这么很容易记混乱,当然用熟练了也不是什么事!!(具体的栗子我就不写了)
em:相对单位
除了"px"和百分比布局,第三个想到的就是“em”了。em也是一个相对单位,既然是相对单位,相对的计算必然会有一个参考物,那么这里相对所指的是相对于父元素的font-size属性。一般来说,如果没有特意设置font-size,那么就是相对于body的font-size,即16px;
比如说:如果在一个div中设置字体大小为"16px",此时div的后代将继承它的字体大小(除非重新在其后代元素中设置font-size),也就是说此时1em = 16px
,如果你设置了子元素的width为0.75em,那么在浏览器中显示的width为12px0.75 * 16px = 12px
。是不是相对于百分比来说更不容易混淆,这个转化可以总结为一个公式:
元素自身没有设置字体大小时,元素的width、height等值按下面的公式转换:
需要转换的像素值/父元素的font-size = em值
注:若子元素设置了font-size(设置为em),子元素的font-size值是根据父元素字体大小来设置,其它的按照自身的字体大小设置。
你可能会说这个计算好麻烦,确实,写css估计要带一个计算器。。
一个小技巧:
我们经常会在页面上看到根元素写的font-size:62.5%,这样em就相当于 16px * 62.5% = 10px ,也就是说12px = 1.2em,16px = 1.6em,即只要将你原来的px数值除以10,换上em单位即可。
html,body{font-size:62.5%;}
但如果嵌套了多个元素,要计算它需要明确每个父元素的font-size 值,这是件很头疼的事情,这种情况下css3就出现了rem.
rem:相对单位,“root em”
rem是相对根节点即html的字体大小来计算,属于css3新加属性,chrome/firefox/IE9+支持。//目前用的比较多的也是最流行的。
之所以前端做移动端普遍默认用rem或em,是因为可以通过js控制根元素(或者用@media)来达到适配各种分辨率的字体大小的效果。
rem在移动端应用可参考淘宝的页面http://m.taobao.com (html的font-size通过动态计算获取)
介绍几种常见的使用rem的方案:
- 简单版:页面基准750px,html font-size的计算:
(function(doc,win){
var htmlFont = function(){
var docEl = doc.documentElement,
w = docEl.clientWidth,
resizeEvt = 'orientationchange' in window ? 'orientationchange' : 'resize',
f;
f = w/7.5;
w > 750 ? docEl.style.fontSize = 100 + "px" : docEl.style.fontSize = f + "px";
}
htmlFont();
win.addEventListen("resizeEvt",htmlFont,false);
})(document,window)
注: 需要设置meta标签,缩放比为1:1,把上面这段js放到html 的head标签中
- 进阶版 --高清方案
把这段js放到HTML的head标签中即可,注:不需要手动设置viewport,该方案自动帮你设置,通过修改viewport 属性放大缩小 initial-scale
!function(e){function t(a){if(i[a])return i[a].exports;var n=i[a]={exports:{},id:a,loaded:!1};return e[a].call(n.exports,n,n.exports,t),n.loaded=!0,n.exports}var i={};return t.m=e,t.c=i,t.p="",t(0)}([function(e,t){"use strict";Object.defineProperty(t,"__esModule",{value:!0});var i=window;t["default"]=i.flex=function(e,t){var a=e||100,n=t||1,r=i.document,o=navigator.userAgent,d=o.match(/Android[\S\s]+AppleWebkit\/(\d{3})/i),l=o.match(/U3\/((\d+|\.){5,})/i),c=l&&parseInt(l[1].split(".").join(""),10)>=80,p=navigator.appVersion.match(/(iphone|ipad|ipod)/gi),s=i.devicePixelRatio||1;p||d&&d[1]>534||c||(s=1);var u=1/s,m=r.querySelector('meta[name="viewport"]');m||(m=r.createElement("meta"),m.setAttribute("name","viewport"),r.head.appendChild(m)),m.setAttribute("content","width=device-width,user-scalable=no,initial-scale="+u+",maximum-scale="+u+",minimum-scale="+u),r.documentElement.style.fontSize=a/2*s*n+"px"},e.exports=t["default"]}]); flex(100, 1);
代码优势:(不需要理解每一行的意思,这是经过压缩的)
引用简单,布局简便
根据设备屏幕的DPR,自动设置最合适的高清缩放。
保证了不同设备下视觉体验的一致性。(老方案是,屏幕越大元素越大;此方案是,屏幕越大,看的越多)
-
有效解决移动端真实1px问题(这里的1px 是设备屏幕上的物理像素)
想要搞清楚移动端适配问题,可访问https://github.com/riskers/blog/issues/17
分享一个关于移动端屏幕,设备像素,css像素的链接:https://riskers.github.io/share/share/flexible.htm#403
只写了一点关于rem的使用,具体的以后再补!!!