rem在响应式布局中的应用

rem在响应式布局中的应用


最近做了一些响应式的页面,遇到了一些问题,想了些解决方法,在这里总结一下。目前响应式的主流实现方式是百分比布局,加上媒体查询@media screen。关于媒体查询还有媒体查询的一些兼容性问题,网上介绍的很多

其实响应式布局中主要困扰我们的问题还是元素的等比缩放。目前的元素的等比缩放主要有以下两种解决方案。

实现等比缩放的一些方案
1. 利用img元素的等比缩放特点
这种情况最为常见,只需要百分比设置img元素的宽度,img元素的高度就会随着宽度等比缩放。这也是我们在响应式界面中遇到的最主要的场景。基本上如果是图片都会下意识的用img来引入,即使是背景图片也常用这种方式来撑开父元素然后用img做背景。
如果是正常的一个img元素,使用这种方式进行等比缩放自然是最优的做法,但是用这种方式做容器的背景图片就会有些问题,例如,当在不同尺寸下需要替换背景图片时,这种方式就没有通过css的中的background设置背景图片来的灵活了。

2. 利用padding的百分比是以父元素的宽度为基准的这个特性
这种方式也可以解决等比缩放的问题,例如我们想实现video元素的等比缩放,我们就可以这样写:

 .out{
        position: relative;
        width: 40%;
        border: 1px solid #ff3e51;
    }
    .in{
        width: 100%;
        height: 0
        padding-bottom: 100%;
    }
    video{
        position: absolute;
        width: 100%;
        height: 100%;
        left: 0;
        top: 0;
        border: 1px solid #3247ff;
    }
   
从css可以看出上面外层的div元素的高是被里面的div元素通过padding-bottom撑开的,padding-bottom的百分比是基于父元素宽度的,这样就建立起父元素高与宽的联系。这种方式最大的问题就是为了布局效果添加了一些冗余的dom元素。

有没有更优雅的解决方案
从上面可以看出一个普通的非img的容器元素,要想实现等比缩放要么借助img,要么通过添加一些冗余的dom元素来实现。这两种方案都破坏了简洁的dom结构,实现起来都不是很优雅。其实一般容器无法实现等比缩放的根本原因是height属性的百分比值是相对父元素height的,它与元素宽度没有任何关联,如何建立起关联,是我们解决这个问题的切入点。

下面就给大家推荐一种更优雅的实现方案,利用rem来实现。

1. rem是的啥
rem是css中的尺寸单位,rem是以根元素html的font-size的大小为基准的,例如2rem就是跟元素font-size两倍的大小,一般浏览器默认是16px。rem在h5开发中用的比较多,为了适配不同的手机尺寸。

2. rem兼容性
既然要在pc端使用rem,自然需要关心rem的兼容性问题,在http://caniuse.com/#search=rem我们可以看到ie9及以上都兼容rem,只不过ie9和ie10,rem不能用在font的简写中和伪元素(:before:after)中,这两点基本上不会影响使用。至于ie8及一下,什么?你们的响应式界面还要兼容ie8,好吧,你可以让你的产品从兼容无线端与兼容ie8二选一了。实在不行也还可以通过css hack来降级个ie8的不响应式版本,也是可以的。总之,不能因为这种市场占有率低,又快死掉的产品阻碍咱们探索新技术的道路。

3. 实现方案
实现方案很简单,直接上代码

function changeFontSize() {
    //设置根元素的font-size为当前视口宽度
    document.getElementsByTagName('html')[0].style.cssText += ';font-size:'+document.body.clientWidth + 'px;'; 
    //设置body的font-size为默认大小,防止根元素的font-size向下污染
    document.getElementsByTagName('body')[0].style.cssText += ';font-size:16px;';
}
changeFontSize();
//视口改变时动态修改根元素的font-size
window.onresize = changeFontSize;  
既然rem是跟元素的font-size属性的百分比。如果我们始终将跟元素的font-size的大小赋值为视口的宽度,那么所有以rem为单位的尺寸都是视口宽度的百分比。这样我们就可以用rem做为元素高度的单位,他将随着视口的宽度而变化。
同样实现video的等比缩放,使用rem的方式,只需要引用上面的js代码,然后就可以如下实现了:

video{
        width: .4rem;
        height: .4rem;
       }    

是不是更加简洁明了。

使用rem的优点
刚开始是为了解决元素等比缩放的问题,才用上rem的,但是在试用过程中发现rem的响应式布局方案拥有以下一些优点。

1. 环保无污染
rem可以和px、百分比等尺寸方案一起用,互不干扰。rem会在特定场景中帮助到你,而不需要你处处使用它。

2. 比百分比布局更具优势
百分比布局始终是相对父元素的,对于嵌套比较深的元素,大家是不是在计算百分比的时候异常头疼,稍不留神就弄错分母了,并且,嵌套过深也会影响精度。而rem布局的分母只有一个就是视口宽度。妈妈再也不用担心我弄错分母了。

3. 构建方便、简单,无需冗余dom
从上面video的例子中大家应该可以看出,从此咱们的图片想做背景就做背景,video想放哪就放哪。再也不用担心,拖动时会变形了。