H5屏幕自适应

一、H5 的meta viewport

标签是 HTML 语言头部的一个辅助性标签,我们可以定义页面编码语言、搜索引擎优化、自动刷新并指向新的页面、控制页面缓冲、响应式视窗等,今天重点来说一下viewport。

语法:

1.width是什么

  1. layout viewport:layout viewport 是网页的所有内容,他可以全部或者部分展示给用户。

  2. visual viewport:visual viewport 就是当前显示给用户内容的窗口,你可以拖动或者放大缩小网页。

H5屏幕自适应_第1张图片        H5屏幕自适应_第2张图片

 2.viewport中各个属性

属性名 备注
width 设置layout viewport 的宽度,为一个正整数,使用字符串"width-device"表示设备宽度
initial-scale 设置页面的初始缩放值,为一个数字,可以带小数
minimum-scale 允许用户的最小缩放值,为一个数字,可以带小数
maximum-scale 允许用户的最大缩放值,为一个数字,可以带小数
height 设置layout viewport 的高度,这个属性对我们并不重要,很少使用
user-scalable 是否允许用户进行缩放,值为"no"或"yes", no 代表不允许,yes代表允许
target-densitydpi

值可以为一个数值或 high-dpi 、 medium-dpi、 low-dpi、 device-dpi 这几个字符串中的一个;

该属性为安卓特有,并且安卓已经决定要废弃target-densitydpi 这个属性了,所以这个属性我们要避免进行使用 。

 

 

 

 

 

 

 

 

 

 

3.devicePixelRatio 

 什么是devicePixelRatio呢,devicePixelRatio = 物理像素 / 独立像素

那么,物理像素是什么,独立像素又是什么???

物理像素(pt):pt(point,磅):是一个物理长度单位,指的是72分之一英寸。设备像素(物理像素),顾名思义,显示屏是由一个个物理像素点组成的,通过控制每个像素点的颜色,使屏幕显示出不同的图像,屏幕从工厂出来那天起,它上面的物理像素点就固定不变了,单位pt。比如 iPhone 6 的分辨率为 750 x 1334px

CSS 像素(CSS Pixel):又称为虚拟像素、设备独立像素或逻辑像素,也可以理解为直觉像素。CSS 像素是 Web 编程的概念,指的是 CSS 样式代码中使用的逻辑像素。比如 iPhone 6 的 CSS 像素数为 375 x 667px。

在pc端,因为屏幕足够大,一个css像素用一个物理像素来显示,完全可以,pc端默认情况下一个css像素就对应着一个物理像素,当你把分辨率调小以后,因为显示器的物理像素肯定不会变,这时候其实就是一个css像素对应着若干个物理像素了,因此显示的内容也会相对变大。

移动设备大小是有限的,而且分辨率不低,甚至比pc端更高,也就是可以显示的物理像素更多,如果和pc端一样,一个css的px和物理像素一一对应,可以想象,显示的内容有多小。这样肯定是不行的,因此,在移动设备上不是一一对应的,一个css的px对应多个物理像素,这样就不至于显示的内容过小了。所以,在开发时写的px和最终渲染显示的物理像素数不是一比一的,可能一个px对应2个物理像素,可能3个物理像素,设备显示的物理像素数和你css的px数的比值就叫做设备像素比(device pixel radio),简称dpr。

二、rem

rem 是相对于根元素字体尺寸的大小。如根元素文本大小设为 font-size: 10px,则 1rem = 10px。若根元素文本大小不设置,则使用默认文字大小,1rem=16px。

移动设备的宽度是各种各样的,因此如果把大小写死成多少px,在不同宽度的屏幕上,排版就会混乱,所以,不能写死,要动态的计算。那怎么计算呢,很简单,你把一个设备的样式写好了,其他的根据设备的宽度(px数)的比,来动态计算就行了。

rem就是解决这个问题的,rem并不是指具体的px,rem具体显示多少像素,是根据根元素的font-size来计算的,比如说你设置了width:1.2rem,而根元素的font-size是100px,那么这个元素动态算出来就是width:120px。不同宽度,设置不同px,这样就可以适配所有宽度的设备了。看一下实际开发中我们动态计算根元素font-size的代码:

var 根元素fontsize = 实际设备宽度 / 开发时设备宽度 * 开发时根元素font-size

假设UI给的图的宽度为375px,假设根元素的文字大小为100px(为了方便根据UI换算rem,即1rem=100px)以此宽度作为标准,则知道375/100=实际宽度/实际文字大小,计算可知:实际文字大小=实际宽度/375*100,由此得到:

document.documentElement.style.fontSize =(document.documentElement.offsetWidth/375)*100 + 'px' ;

 这样就可以了,其实我们还可以再除以2,为什么呢,因为我们现在设计稿量出来的是物理像素,iphone6的dpr是2,我们要把量出来的数除以2,就是实际的px,然后再除以100,就是rem,既然每次都要这么做,为什么不在根元素这里把除以2给统一做了,只需要把量出的数只要除以100就是rem了。此外,如果不想在这里除以2,我们可以用meta标签的viewport根据devicePixelRatio设置缩放比。

rem.js

(function(doc, win) {
    // 分辨率Resolution适配
    var docEl = doc.documentElement,
      resizeEvt = 'orientationchange' in window ? 'orientationchange' : 'resize',
      recalc = function() {
        var clientWidth = docEl.clientWidth;
        if (!clientWidth) return;
        docEl.style.fontSize = 100 * (clientWidth / 375) + 'px';
      };
    // Abort if browser does not support addEventListener
    if (!doc.addEventListener) return;
    win.addEventListener(resizeEvt, recalc, false);
    doc.addEventListener('DOMContentLoaded', recalc, false);
   
    // 一物理像素在不同屏幕的显示效果不一样。要根据devicePixelRatio来修改meta标签的scale,要注释上面的meta标签
    (function() {
    //   return;
      var dpr = scale = 1;
      var isIPhone = win.navigator.appVersion.match(/iphone/gi);
      var devicePixelRatio = win.devicePixelRatio;
      if (isIPhone) {
        // iOS下,对于2和3的屏,用2倍的方案,其余的用1倍方案
        if (devicePixelRatio >= 3 && (!dpr || dpr >= 3)) {
          dpr = 3;
        } else if (devicePixelRatio >= 2 && (!dpr || dpr >= 2)) {
          dpr = 2;
        } else {
          dpr = 1;
        }
      } else {
        // 其他设备下,仍旧使用1倍的方案
        dpr = 1;
      }
      scale = 1 / dpr;
   
      //
      var metaEl = "";
      metaEl = doc.createElement('meta');
      metaEl.setAttribute('name', 'viewport');
      metaEl.setAttribute('content', 'initial-scale=' + scale + ', maximum-scale=' + scale + ', minimum-scale=' + scale + ', user-scalable=no');
      if (docEl.firstElementChild) {
        docEl.firstElementChild.appendChild(metaEl);
      } else {
        var wrap = doc.createElement('div');
        wrap.appendChild(metaEl);
        doc.write(wrap.innerHTML);
      }
    })();
   
  })(document, window);

2.index.html引入rem.js



  
    
    
    
    
  
  
    
    

3.app.vue

 

 

 

你可能感兴趣的:(WEB)