移动端适配,自适应布局的各种方案与最佳实践

知识预备:

1. 像素

像素分为css像素物理像素(设备像素)
在css和js中写的px单位,都属于css像素;
物理像素只和设备或者说硬件有关,同样尺寸的屏幕,设备的密度越高,物理像素越多。
细节可参考:你真的了解css像素嘛?

2. 视口

广义的视口,是指浏览器显示内容的屏幕区域,狭义的视口包括了布局视口视觉视口理想视口
在移动端中,理想视口或者说分辨率跟物理像素之间有什么关系呢?
DPR(Device pixel ratio)设备像素比1 DPR = 物理像素/分辨率
不缩放的情况下,1 CSS像素 = 物理像素/分辨率 = 1 DPR
在移动端的布局中,我们可以通过viewport元标签来控制布局

    

细节可参考:viewport详解

3. 自适应

在pc端的布局视口通常情况下为980px,移动端以iphone6为例,分辨率为375 * 667,也就是说布局视口在理想的情况下为375px。

    PC端: 1 CSS像素 = 物理像素/分辨率 = 750 / 980 =0.76 px

    iphone6:1 CSS像素 = 物理像素 /分辨率 = 750 / 375 = 2 px

也就是1个CSS像素可以表示的物理像素是不同的,因此如果在css中仅仅通过px作为长度和宽度的单位,造成的结果就是无法通过一套样式,实现各端的自适应。

自适应方案:

一、 媒体查询

使用@media媒体查询可以针对不同的媒体类型定义不同的样式,特别是响应式页面,可以针对不同屏幕的大小,编写多套样式,从而达到自适应的效果。
举例:

@media screen and (max-width: 960px){
    body{
      background-color:#FF6699
    }
}

@media screen and (max-width: 768px){
    body{
      background-color:#00FF66;
    }
}

@media screen and (max-width: 550px){
    body{
      background-color:#6633FF;
    }
}

@media screen and (max-width: 320px){
    body{
      background-color:#FFFF00;
    }
}

通过max-width设置样式生效时的最大分辨率,上述的代码分别对分辨率在0~320px,320px~550px,550px~768px以及768px~960px的屏幕设置了不同的背景颜色。
缺点:
这样做会比较麻烦,只能在选取的几个主流设备尺寸下呈现完美适配。

二、 百分比

比如当浏览器的宽度或者高度发生变化时,通过百分比单位,通过百分比单位可以使得浏览器中的组件的宽和高随着浏览器的变化而变化,从而实现响应式的效果。

缺点:

  1. 计算困难,如果我们要定义一个元素的宽度和高度,按照设计稿,必须换算成百分比单位。
  2. 各个属性中如果使用百分比,相对父元素的属性并不是唯一的。比如width和height相对于父元素的width和height,而margin、padding不管垂直还是水平方向都相对比父元素的宽度,border-radius则是相对于元素自身等等,造成我们使用百分比单位容易使布局问题变得复杂。

三、 Rem

内嵌一段脚本去动态计算根元素大小。

rem单位都是相对于根元素html的font-size来决定大小的,根元素的font-size相当于提供了一个基准,当页面的size发生变化时,只需要改变font-size的值,那么以rem为固定单位的元素的大小也会发生响应的变化。

function refreshRem() {
    var docEl = doc.documentElement;
    var width = docEl.getBoundingClientRect().width;
    var rem = width / 10;
    docEl.style.fontSize = rem + 'px';
    flexible.rem = win.rem = rem;
}
win.addEventListener('resize', refreshRem);

px变成rem单位的两种方案:

  1. webpack loader配置:px2rem-loader
  2. webpack plugin配置: postcss-loader

缺点:
必须通过js来动态控制根元素font-size的大小。

也就是说css样式和js代码有一定的耦合性。且必须将改变font-size的代码放在css样式之前。

四、 Vh/vw

视口单位中的“视口”,桌面端指的是浏览器的可视区域;移动端指的就是Viewport中的Layout Viewport。

移动端适配,自适应布局的各种方案与最佳实践_第1张图片

根据设计稿的尺寸转换为vw单位(SASS函数编译)

//iPhone 6尺寸作为设计稿基准
$vm_base: 375; 
@function vm($px) {
    @return ($px / 375) * 100vw;
}

使用vm()来写其他css配置

最佳实践:vw配合rem方案!

根元素font-size利用视口单位实现,依赖于视口大小而自动缩放

  1. 给根元素大小设置vw。
  2. 限制根元素font-size的最大最小值,配合body加上最大最小宽度。
// rem 单位换算:定为 75px 只是方便运算,750px-75px、640-64px、1080px-108px,如此类推
$vm_fontsize: 75; // iPhone 6尺寸的根元素大小基准值
@function rem($px) {
     @return ($px / $vm_fontsize ) * 1rem;
}
// 根元素大小使用 vw 单位
$vm_design: 750;
html {
    font-size: ($vm_fontsize / ($vm_design / 2)) * 100vw; 
    // 同时,通过Media Queries 限制根元素最大最小值
    @media screen and (max-width: 320px) {
        font-size: 64px;
    }
    @media screen and (min-width: 540px) {
        font-size: 108px;
    }
}
// body 也增加最大最小宽度限制,避免默认100%宽度的 block 元素跟随 body 而过大过小
body {
    max-width: 540px;
    min-width: 320px;
}

你可能感兴趣的:(架构,CSS学习)