移动端三种适配方案

5,256 阅读6分钟

1.meta-viewport适配

背景

viewport:中文的意思就是“视口”,通常就是浏览器用于显示页面的区域,但是在移动端,viewport一般都要大于浏览器的可视区域,保证PC页面在移动页面上面的可视性,这是因为考虑到移动设备的分辨率相对于桌面电脑来说都比较小,所以为了能在移动设备上正常显示那些传统的为桌面浏览器设计的网站,移动设备上的浏览器都会把自己默认的viewport设为980px或1024px(也可能是其它值,这个是由设备自己决定的),这样做是因为许多页面没有做移动端优化,在小窗口渲染时会乱掉(或看起来乱)。所以,这种虚拟视口是一种让未做移动端优化的网站在窄屏设备上看起来更好的办法。

三种类型

1.layoutviewport: 大于实际屏幕,元素的宽度继承于layoutviewport,用于保证网站的外观特性与桌面浏览器一样。

visualviewport: 当前显示在屏幕上的页面,即浏览器可视区域的宽度。

idealviewport: 为浏览器定义的可完美适配移动端的理想 viewport,固定不变,可以认为是设备视口宽度。比如 iphone 7 为 375px, iphone 7p 为 414px。 目前最常用的就是第三种,idealviewport,也就是设备宽度多大,css页面的宽度就多大,在移动端使用它非常简单, 只要在html页面的head标签之间添加:

<meta name="viewport" content="width=device-width, initial-scale=1.0, minimum-scale=1.0, maximum-scale=1.0, user-scalable=no"/>

五种属性

其中device-width意思是设备宽度,移动设备默认的viewport是layoutviewport,将width 设置为device-width,就会将宽度切换为idealviewport类型,下来分别说明下各个属性的意思: width:属性控制视口的宽度,可以设置具体的宽度如:width=700,但是一般这么使用,都是使用width=device-width

inital-scale:页面初始缩放值,默认为1;

maximum-scale:允许用户缩放到的最大比例。

minimum-scale:允许用户缩放到的最小比例。

user-scalable:用户是否可以手动缩放。

2.媒体查询适配

媒体查询是第二种移动端适配方案,它属于css3的属性,使用 @media 查询,你可以针对不同的媒体类型定义不同的样式。 @media 可以针对不同的屏幕尺寸设置不同的样式,特别是如果你需要设置设计响应式的页面,@media 是非常有用的。 当你重置浏览器大小的过程中,页面也会根据浏览器的宽度和高度重新渲染页面。

使用方法:

<link rel="stylesheet" media="(max-width: 800px)" href="example.css" />可以直接在link标签中插入媒体查询css 上面的意思表示如果浏览器可视区域小于等于800px时,就执行example.css中的样式。

<style>
@media (max-width: 600px) {
  body {
    background-color:red;
  }
}
</style>

也可以使用嵌入式css写法,效果同上 使用and可以将多个媒体查询属性,如: (min-width: 700px) and (orientation: landscape) { ... }

表示在宽度小于等于800px且横屏时应用这个css样式

使用(逗号)可以使得多个媒体查询属性中有任意一个属性符合要求,就应用后面的css样式

@media (min-width: 700px), handheld and (orientation: landscape) { ... }表示当符合前一项媒体查询属性或者后一项媒体查询属性时应用后面的css样式

使用not可以排除后面的媒体查询属性,在其余的媒体查询中应用css样式

@media not (max-width:700px){...}表示在宽度大于700px时,应用css样式

3.em和rem动态适配

em和rem都是相对单位长度,em是相对父级font-size来变化的,他会继承父级元素的字体大小,代表倍数, 如:浏览器默认font-size:16px,那么em就是1em,

<!DOCTYPE html>
<html>
<head>
  <meta charset="utf-8">
  <title>JS Bin</title>
  <style>
  body{
    font-size:20px;
  }
    div{
     font-size:2em
    }
  </style>
</head>
<body>
<div>nihao</div>
</body>
</html>

当给body设置font-size:20px,后,div设置font-size:2em,div的font-size实际变成了40px,

不过在实际布局中,如果嵌套过深,em计算起来比较的繁琐,容易出现错误,因此不见大范围使用,小范围可以结合其它长度单位来使用,

rem是相对于html根元素font-size来变化的,始终是基于根元素字体大小,也代表倍数,浏览器默认的font-size为16px,那么rem单位就是1rem;

<!DOCTYPE html>
<html>
<head>
  <meta charset="utf-8">
  <title>JS Bin</title>
  <style>
  body{
    font-size:20px;
  }
    div{
     font-size:2rem
    }
  </style>
</head>
<body>
<div>nihao</div>
</body>
</html>

当给body设置为font-size:20px,给div设置为font-size:2rem,div的实际font-size变成了32px,在移动端布局中使用rem,由于它是基于根元素的,所以只要根元素不发生变化,那么页面就不会发生变化,同时呢也没有em的繁琐嵌套计算,在配合上动态计算rem的javascript代码,使之在移动端布局中广受欢迎, 使用如下javascript代码即可动态计算

(function(win) {
	var doc = win.document;
	var docEl = doc.documentElement;
	var tid;
	function refreshRem() {
		var width = docEl.getBoundingClientRect().width;        
		if (width >=750) width = 750;
		if(width<=320) width=320;
		var rem = width / 7.5;
		docEl.style.fontSize = rem + 'px';		
	}
	win.addEventListener('resize', function() {
		clearTimeout(tid);
		tid = setTimeout(refreshRem, 300);
	}, false);
	refreshRem();
})(window);

在手机端和平板上面尺寸支持良好,虽然rem的使用看上去十分完美,但是在一些需要固定间距的地方使用会造成页面错乱或者样式出错,这种情况下建议搭配px来使用,另外 多种长度单位搭配使用,可以解决一些单一长度单位布局带来的bug,

对于这两年兴起的vw、vh响应式布局,由于vw,vh的特性,他们能够根据窗口大小来自动调节字体大小,而不用管使用设备的分辨率大小,这就能很轻松地完成响应式页面的布局,看似很美好,简单又快,但是在个别移动端浏览器上的兼容性还是有点小问题,如需使用的话,建议搭配rem来布局,后续我将再对其兼容性测试一番,满足使用需求的话,再行补充相关知识。