• 浅谈移动端三大viewport


    我们通常在写移动端页面时,往往都会在html页面中加入这样一段话

    <meta name="viewport" content="width=device-width,initial-scale=1,user-scalable=no">

    可能我们只知道这三个字段的含义(视口宽度等于设备宽度,屏幕缩放为1,禁止用户缩放),但是为什么要这么写,其原理又是什么呢?

    我们先看一个简单的demo吧。

    <!doctype html>
    <html lang="en">
    <head>
    <meta charset="UTF-8">
    <title>Test 02</title>
    </head>
    <style>
        body{
            margin: 0;
        }
        .pic{
            width: 320px;
            height: 568px;
            background-color: #72DFFF;
            color: white;
            font-size: 60px;
            text-align: center;
            line-height: 568px;
            font-family: cursive; 
        }
    </style>
    <body>
        <div class="pic"> 320*568 </div>    
    </body>
    </html>

    该demo展示一个宽度为320px的div,我们在iphone5上面打开看一下。

    有没有感觉很诡异?明明iphone5的分辨率是320px*568px(我使用的是谷歌的mobile模拟),但是只显示了三分之一左右。

    在回答此问题之前,我们需要先普及一下一些移动端的概念。

    px:逻辑像素

    dp:设备像素(物理像素)

    dpr:设备像素缩放比

    (某一方向上-->计算:dpr = 设备像素/逻辑像素,平面上-->计算:1px = (dpr)² *dp)

    ppi:屏幕每英寸的像素数量,即单位英寸内的像素密度(计算:分辨率平方后开跟/屏幕尺寸)

    ppi与dpr的关系表

      ldpr mdpr hdpr xhdpr
    ppi 120 160 240 320
    默认缩放比 0.75 1.0 1.5 2.0

     

     

     

    我们得知iphone5的尺寸为4英寸,设备分辨率为1136dp*640dp,由此我们可以得出iphone5的分辨率为320px*568px,如下图(retina为高清)。

    该页面展示三分之一的原因是ios中默认的布局viewport是980px,然后根据刚才的计算的iphone5分辨率才会出现此情况。

    逻辑像素(css pixels)与设备像素(device pixels)的区别------------

    我们姑且认定设备的pixels为正确(标准)的pixels宽度。这些pixels决定了你工作所用的那些设备上正式的分辨率。

    如果用户缩放(zoom)了浏览器,当然必须改变计算方式。

    现代浏览器上的缩放,是基于“伸展”pixels。结果是,html元素上的宽度并没有因为缩放200%而由128pix变成256px,而是真实的pixels的被计算成了双倍。html元素在形式上依然是128CSS的pixels,即便它占用了256设备的pixels 。

    换言之,缩放200%将一个单位的CSS的pixels变成了4倍的设备的pixels那么大,即宽度 * 2、高度 * 2,面积扩大了2 * 2.

    下列图片将清楚的解释这个概念。如图1-1.有4个1像素,缩放为100%的html元素,CSS的pixels完整的和设备的pixels重叠

    Viewport剖析

    当我们缩小浏览器时,CSS的pixels开始收缩,导致1单位的设备的pixels上重叠了多个CSS的pixels,如图1-2

    Viewport剖析

    同理,放大浏览器时,相反的事情发生了,CSS的pixels开始扩大,导致1单位的CSS的pixels上重叠了多个设备的pixels,如图1-3

    Viewport剖析

    总体而言,你只需要关注CSS的pixels,这些pixels指定你的样式被如何渲染。

    就像刚开始的那个小demo,在pc以及iphone5上展示是两种完全不同的效果。

    在这里我普及一个知识点,对于viewport,苹果手机浏览器默认做了两件事——

    1.页面渲染在一个980px(IOS)的viewport(安卓viewport宽度不固定)

     2.缩放 

    说的详细一些,viewport,就是手机浏览器把页面放到一个虚拟的窗口中,窗口可大于或小于手机的可视区域,一般会大于可视区域。这样不会破坏没有针对手机浏览器优化的网页的布局,用户可以通过平移或缩放来看网页的其它部分。

    这也就是为什么我们没写viewport,手机会默认将布局宽度置为980px的原因。

    为什么要有viewport?
    一个300多像素的屏幕,放一个1000多像素的页面,会混乱,所以要先虚拟一个980像素的页面,然后进行缩放。

    为什么不使用默认980px的布局viewport
    1.宽度不可控,不同设备(安卓)默认值可能不同
    2.页面缩小版展示,交互不友好
    3.有缩放,缩放后有滚动
    4.font-size 可能要设置40px才等于pc上12px,不规范

    然后为了在iphone5上正常展示,我们需要写这样一个viewport

    <meta name="viewport" content="width=320">

    这样效果ok,但是如果我们的设备是iphone6,iphone6s呢?

    <meta name="viewport" content="width=375">

    显然是不符合规定的,所以我们需要设置

    <meta name="viewport" content="width=device-width">

    但是每个不同的设备都会有不同的缩放比
    window.innerWidth/document.body.clientWidth 为 initial-scale
    度量viewport/布局viewport [Layout Viewport(布局视口)]
    比如如果要让iphone6展示1000px的页面,只设置"width=device-width",肯定都会挤在一起。

    所以需要让缩放比为1,设置initial-scale=1,所以最终版本是这样

    <meta name="viewport" content="width=device-width,initial-scale=1,user-scalable=no">

     最后总结一下移动端中的三个viewport——

    1.布局视口 

    document.body.clientWidth 为手机浏览器viewport宽度(布局viewport),默认980
    跟width=device-width相关,其值等于meta标签中的width
    initial-scale = 2 ,它会跟着缩小一倍
    当你需要使用js而不是媒体查询来编写业务逻辑的时候,这很有帮助
    if(document.body.clientWidth >= 400){

      .class{...}
    }
    等价于
    @media all and (max-width>=400){

      .class{...}
    }

    我们用到的vw,vh尺寸单位代表视口的百分比,比如50vh,这里的视口就是指布局视口,因为如果是视觉视口,每次用户缩放都会导致元素狂傲发生变化,先不说这个变化带来的大计算量,这种设计对用户来说本身就是毫无意义的。

    2.视觉视口

    window.innerWidth
    屏幕上显示的网站区域尺寸,会受缩放的影响

    3.理想视口

    screen.width

    它是对设备来说最理想的布局视口尺寸。

    -----------------------------------------------------------------------------------------------------------------------

    在手机上,桌面视口被拆分成两个——布局视口限制你的css布局,视觉视口决定用户能看到什么。

    其实这么多的viewport看起来可能会乱一点,但事实并不是这样。最佳实践就是让浏览器直接使用它的理想视口,即把布局视口设置为理想视口,然后使用媒体查询来响应不同的理想视口就OK。

    响应式设计的核心——
    width和height的媒体查询设置了当前布局视口的宽高。
    使用最佳mate标签后,就可以放心的抛开布局视口的宽度,只专注于理想视口
    @media all and (max-400) {
      .class {
        ...
      }
    }

  • 相关阅读:
    git
    界面编程与视图(View)组件
    genymotion的安装
    210中断故障分析
    6410/210按键中断编程
    2440按键中断编程
    中断处理流程深度剖析
    scrapy 写文件进行debug调试
    scrapy 爬虫中间件-offsite和refer中间件
    scrapy文件管道
  • 原文地址:https://www.cnblogs.com/ssh-007/p/7196748.html
Copyright © 2020-2023  润新知