遥想去年入前端坑的时候,就很快遇到了移动端页面的开发,天(er)真(bi)的我立马上去量设计稿,然后撸起袖子就是干!可是打开调试一看乱套了,先不说布局上的问题,就是大小看起来也不太对啊,太大了!然后就去问老司机,他说尺寸你要除以2才行,我心里挺郁闷的,为啥啊。。当时羡慕紧,就先这么搞,然后加上百分比布局,完成了第一次的开发任务。。。
但是!这只是叫完成,我非常不喜欢心里有梗的感觉,我觉得这事儿没这么简单,而且随着后期开发的进行,有一天设计mm给我说你这个线好粗啊,能不能再细点儿,我心中一万个不(cao)情(ni)愿(ma)飞过,我这已经是1px了啊。。。
还有最关键的我发现用百分比布局有个极大的缺陷,就是当你感知设计的 设计意图 的时候,(我们的设计师同学们的 设计意图 有多重要,我觉得好的设计师一定是设计意图非常犀利的),有些设计元素并不是单纯的左对齐,右对齐,或者和某个元素有某种视觉上的联系。也就是说,这个时候百分比布局就要头疼了,这个元素到底是百分之多少呢,用尺子量一下,可以啊,可是你把设备屏幕放大或者缩小看看,哭还是不哭?。。。。
是的,没错,我哭了。。。
痛定思痛~我觉得开始调研,开始搞一个让我以后开发再也不哭的方案,之后的一个星期内我调研了当时所有的开发方案,那个时候不光调研还一边理解了一些新的概念来辅助我进行改革,那时候我才知道了尼玛为啥我要除以2,知道了设备分辨率,设备像素,css像素,页面视口,em和rem等等玩意儿。最终我选择了flexible.js这个库来帮助我做这件事儿,其实这个库代码很短,完全可以理解,代码可以去github上瞅一瞅,其实简单说,它利用 动态读取设备宽度并结合设备的像素比 =》动态改变html的font-size大小 + 页面缩放比例 =》影响以rem为单位的元素的最终呈现 。嗯嗯就是这么回事儿。
所以呢,要快速搭建移动页面适配还是需要一步一步准备好的:
<!DOCTYPE html> <html lang="en"> <head> <meta charset="utf-8"> <meta content="yes" name="apple-mobile-web-app-capable"> <meta content="yes" name="apple-touch-fullscreen"> <meta content="telephone=no,email=no" name="format-detection"> <script type="text/javascript" src="./flexible.min.js' ?>"></script> </head> <body> </body> </html>
@charset "utf-8"; /* @author xiao @des: APP端基础方法 @使用心得: -适配方案参考淘宝开源库lib.flexible -布局rem动态适配 -字体dpr动态适配 -和文字相关的布局用px写死比较好。。。因为用rem会和没有用rem布局的字体有错位 -目前市面上有三种代表的适配方案: 1. 直接750设计稿除以2适配所有机型,布局采用百分比:代表网站 拉勾网 2. 动态改变html font-size基准,所有元素以rem适配:代表网站 小米网 3. 动态改变html font-size基准,所有除字体相关元素以外的rem适配,字体只按分辨率适配:代表网站 淘宝网 */ /** * 基本思想描述: * 多屏适配布局问题 * 移动端布局,为了适配各种大屏手机,目前最好用的方案莫过于使用相对单位rem。 * 基于rem的原理,我们要做的就是: 针对不同手机屏幕尺寸和dpr动态的改变根节点html的font-size大小(基准值)。 * 这里我们提取了一个公式(rem表示基准值) * rem = document.documentElement.clientWidth * dpr / 10 * 说明: * 1)乘以dpr,是因为页面有可能为了实现1px border页面会缩放(scale) 1/dpr 倍(如果没有,dpr=1)。 * 2)除以10,是为了取整,方便计算(理论上可以是任何值) * 所以就像下面这样,html的font-size可能会: * iPhone3gs: 320px / 10 = 32px * iPhone4/5: 320px * 2 / 10 = 64px * iPhone6: 375px * 2 / 10 = 75px * iPhone6plus: 414 * 3 / 10 = 124.2px */ /* px转换成rem */ @function px2rem($px, $base-font-size: 75px) { @if (unitless($px)) { //@warn "Assuming #{$px} to be in pixels, attempting to convert it into pixels for you"; @return px2rem($px + 0px); // That may fail. } @else if (unit($px) == rem) { @return $px; } @return ($px / $base-font-size) * 1rem; } /* 默认已iPhone6的750为基准开发 font-size 不推荐转换成rem 原因:我们不希望文本在Retina屏幕下变小, 另外,我们希望在大屏手机上看到更多文本, 以及,现在绝大多数的字体文件都自带一些点阵尺寸,通常是16px和24px,所以我们不希望出现13px和15px这样的奇葩尺寸。 注意设计稿是2x屏幕, 所以1x屏幕需要除以2 */ @mixin font-dpr($font-size){ font-size: $font-size / 2; [data-dpr="2"] & { font-size: $font-size; } [data-dpr="3"] & { font-size: $font-size * 1.5; } } /** * 为了和字体适配一样的非字体元素准备的转化方法 */ @mixin px-dpr($property, $size, $others:""){ #{$property}: $size / 2 #{$others}; [data-dpr="2"] & { #{$property}: $size #{$others}; } [data-dpr="3"] & { #{$property}: $size * 1.5 #{$others}; } }
需要注意的就是,一般设计稿都是以750像素宽设计的,所以$base-font-size默认是75,如果你们的设计稿不是这个750,相应的$base-font-size也应该进行修改。
.box { width: px2rem(14); height: px2rem(14); }
使用上应该没有什么问题了,就是有时可能页面缩放会导致一些问题,比如echarts使用时缩放页面会导致其显示不正常,这时候在头上加入:
<meta name="viewport" content="initial-scale=1, maximum-scale=1, minimum-scale=1, user-scalable=no">
flexible就不会再缩放,也就牺牲了1px和高清图片的问题,影响不大,其他问题我暂时还没遇到过,总之,快速搭建完成后,在移动端适配上你就不用再费任何精力了~看着设计稿还原就好啦~!