响应式开发的本质是针对多种屏幕做适配,首先需要掌握几个基本概念:
- 物理像素:设备的屏幕实际像素点,如常说的
iPhone 6 Plus
的分辨率是 1920 * 1080 像素。 - 设备独立像素:逻辑像素,用于定义应用的UI。
- 屏幕像素比(devicePixeRatio):物理像素与设备独立像素的比值。
使用 rem 实现响应式布局
rem
(font size of the root element)是 CSS
的计量单位,表示相对于根(即 html
)元素的字体大小。其主要用于移动 Web
开发,以适配不同尺寸的屏幕。
rem
的兼容可以通过 caniuse 查询
由于 rem
单位是相对于网页根元素的字号大小而定,所以实现 rem
布局开发时,首先要做的就是对根元素的字号赋值。
html{ font-size:12px; }
我们将网页根元素的字号设置为 12px
,此时 rem
相对于网页根元素字号为 1rem = 12px
。故此转换 rem
的公式则为
rem值 = 元素实际 px 值 / 网页根元素的字号
下面通过 rem
实现一个简单的布局 【预览】
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>Rem Case</title>
<style>
body {
font-size: 12px;
margin: auto;
}
.btns {
width: 10rem;
margin: 0 auto;
}
.btns > a {
float: left;
width: 2.5rem;
text-align: center;
padding-top: 0.2rem;
}
.btns > a > i {
display: inline-block;
width: 1.2rem;
height: 1.2rem;
background: gray;
border-radius: 50%;
}
.btns>a>span {
display: block;
line-height: 0.8rem;
font-size: 14px;
}
</style>
</head>
<body>
<div class="btns">
<a>
<i></i>
<span>英语</span>
</a>
<a>
<i></i>
<span>日语</span>
</a>
<a>
<i></i>
<span>德语</span>
</a>
<a>
<i></i>
<span>法语</span>
</a>
<a>
<i></i>
<span>韩语</span>
</a>
<a>
<i></i>
<span>小语种</span>
</a>
<a>
<i></i>
<span>教学</span>
</a>
<a>
<i></i>
<span>职场</span>
</a>
</div>
</body>
</html>
最后加上最关键的重置元素字号脚本
(function (window, document) {
'use strict';
// 获取网页根元素
var html = document.documentElement || document.querySelector('html');
// 重置根元素字号
function resetFontSize() {
// 获取根元素的宽度
var width = html.getBoundingClientRect().width;
// 设置一个最大宽度值
if (width > 640) width = 640;
html.style.fontSize = (width / 10) + 'px';
}
resetFontSize();
window.addEventListener('resize', resetFontSize, false);
})(window, document);
rem
确实有效的解决了响应式布局,但却并非完美:
- 对于脚本的依赖,需要使用
js
脚本对其根元素的字号动态计算与赋值。 - 只能针对一个基准值去动态计算根元素字号大小,面对于宽高自适应且不出现滚动条这种布局,
rem
则显得无能为力,因为它基准值只能是一个,高度或宽度。
使用 vw、vh、vmin、vmax 实现响应式布局
vw
、vh
、vmin
、vmax
与 rem
相同都是 CSS3
中新引入的一种计量单位。不同于 rem
它们所表达的含义如下:
vw | 等于视口宽度的 1% |
vh | 等于视口高度的 1% |
vmin | 相视的宽度或高度,取决于哪个更小 |
vmax | 相对于视的宽度或高度,取决于哪个更大 |
vw
、vh
、vmin
、vmax
的兼容可以通过 caniuse 查询
在使用 vw
、vh
、vmin
、vmax
之前我们需要认识一下视口。
以 PPK大神 在其文章 A tale of two viewports (一)、A tale of two viewports (二) 以及 Meta viewport 三篇文章 中提出关于视口的解释:
- 在桌面端:
以上是我在原文中截取的两段关于桌面端的视口概念,从中总结得知:在桌面端,视口就是浏览器的可视化区域,其只是具有浏览器窗口的高度和宽度,使用 document.documentElement.clientWidth/Height
获取视口宽高。
- 在移动端:
以上是我在原文中对移动端视口概念的截取,从中总结可得知:
移动端的视口分为三部分:
视觉视口(visual viewport)
:就是设备的屏幕区域,但是它所对应的并不是指屏幕区域里的物理像素,而是CSS
像素。当用户缩小或放大时,测量会发生变化,因为更多或更少的CSS
像素会融入屏幕。使用window.innerWidth/Height
获取视觉视口的宽高。布局视口(layout viewport)
:与视觉视口不一样,它是为了解决PC 端网站在移动端显示不佳的一个解决方案,它宽高不会改变,使用document.documentElement.clientWidth/Height
来获取布局视口的宽高。理想视口(ideal viewport)
:它是基于布局视口的,用于调整布局视口端口的大小。
既然提到了 理想视口(ideal viewport)
,那么就不得不普及一下 <meta name="viewport">
。
viewport 属性
viewport
是指屏幕上能用来显示网页的区域,默认情况下大多数设备的 viewport
的宽度都是 980
像素,可以通过在 heade
元素中增加 meta
标签来设置 viewport
属性:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
</head>
<body></body>
</html>
viewport
下包含以下属性:
width
:设置viewport
的宽度,为正整数,或者字符串 “device-width”。initial-scale
:设置viewport
的初始缩放值,为数字,可以带小数。minimum-scale
:设置viewport
的最小缩放值,为数字,可以带小数。maximum-scale
:设置viewport
的最大缩放值,为数字,可以带小数。height
:设置viewport
的高度。user-scalable
:是否允许用户缩放,值为 "yes" 或 "no"。
通过设置 viewport
属性,可以调整用户界面的逻辑大小,页面 CSS
中的大小均以 viewport
为基准。
vw、vh、vmin、vmax 的使用
基础的东西说完了,接着回到 vw
、vh
、vmin
、vmax
的使用,它们相对于 PC 端浏览器的视口就是浏览器的可视化区域 ,而在移动端则为布局视口,还是以第一个案例为例,使用 vw
实现布局【预览】:。
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>VW Case</title>
<link rel="shortcut icon" href="../../assets/images/icon/favicon.ico" type="image/x-icon">
<style>
body {
font-size: 12px;
margin: auto;
}
.btns {
width: 80vw;
margin: 0 auto;
}
.btns>a {
float: left;
width: 20vw;
text-align: center;
padding-top: 10px;
}
.btns>a>i {
display: inline-block;
width: 10vw;
height: 10vw;
background: gray;
border-radius: 50%;
}
.btns>a>span {
display: block;
line-height: 3vw;
font-size: 14px;
}
</style>
</head>
<body>
<div class="btns">
<a>
<i></i>
<span>英语</span>
</a>
<a>
<i></i>
<span>日语</span>
</a>
<a>
<i></i>
<span>德语</span>
</a>
<a>
<i></i>
<span>法语</span>
</a>
<a>
<i></i>
<span>韩语</span>
</a>
<a>
<i></i>
<span>小语种</span>
</a>
<a>
<i></i>
<span>教学</span>
</a>
<a>
<i></i>
<span>职场</span>
</a>
</div>
</body>
</html>
vw
、vh
、vmin
、vmax
的出现给我的感觉显得有些鸡肋,有点像 %
,但与百分比最大的不同则是 %
是相对于父元素的大小设定的比率,vw
、vh
是视口大小决定的。在使用它的过程中,个人认为它并不适合去做布局,而是去做一些元素大小的限制。当然,也是因为个人能力有限,并没有悟透,希望能够得到大神的指点。