我對移動端適配的瞭解

不知不覺作前端已經兩年了,從PC端,移動端,微信小程序一路走來到今天剛剛開放註冊的快應用(手機廠商對抗小程序的新技能,因此在註冊時用的是qq郵箱的話要去垃圾箱裏才能找到註冊郵件),對於前端圈突飛猛進的磅礴發展對於大前端發展是喜聞樂見的,此次的快應用的手機廠商們爲其開放了應用入口和系統推廣引流入口。這些新能力爲前端開發者們帶來更強的做戰能力。css

咱們在開發PC站時常常在瀏覽器兼容問題上耗費巨大的時間,到了移動端,面對webkit內核的Safari與Chrome會舒心不少。but,咱們要對於市面上的手機各式各樣的分辨率進行適配,剛接觸移動端開發的時候是否是有點猝不及防哈哈,尤爲是去年年中之前老版本的微信內置瀏覽器用的X5內核,給網友們戲稱移動端IE...
2.pnghtml

今天的主題是講的是我對移動端多終端適配的解決方案和移動端適配的有關佈局的知識總結,下面正式開始。前端

基本概念和原理

首先要了解的重要的基礎知識點:物理像素,設備獨立像素,設備像素比,css像素,佈局視口,可視視口,理想視口以及css單位rem。

物理像素(設備像素)
屏幕的物理像素,又被稱爲設備像素。任何設備屏幕的物理像素出廠時就肯定了,是固定不變的。
設備獨立像素
設備獨立像素也能夠理解爲CSS像素,能夠認爲是計算機座標系統中的一個點,這個點表明一個能夠由程序使用的虛擬像素(好比說CSS像素)。
設備像素比
設備像素比簡稱爲dpr,dpr = 物理像素 / 設備獨立像素。(以iphone6爲例: dpr = 750 / 375 , 因此它的像素密度比爲2,即 1個CSS像素 跨越了 2個物理像素),咱們能夠通多 window.devicePixelRatio 來獲取設備的像素密度,像素密度大於1就是高清屏。
CSS像素
在CSS、JS中使用的一個長度單位,單位px。
注:在pc端1物理像素等於1px,可是移動端1物理像素不必定等於1px(高清屏)。android

佈局視口(layout viewport
能夠看做是html元素的上一級容器即頂級容器,默認狀況或者將html元素的width屬性設爲100%時,會佔滿這個頂級容器,此時用 document.documentElement.clientWidth 獲取到html元素的佈局寬度也就是佈局視口的寬度,使用媒體查詢時 max-width 和 min-width 的值指的也是佈局視口的寬。
在html中通常在meta中的name爲viewport字段就是控制的佈局視口。佈局視口通常都是瀏覽器廠商給的一個值。在手機互聯網沒有普及前,網絡上絕大部分頁面都是爲電腦端瀏覽而作的,根本沒有作移動端的適配。
隨着移動端的發展,在手機上看電腦端的頁面已成爲很是普及現象。而電腦端頁面寬度較大,移動端寬度有限,要想看到整個網頁,會有很長的滾動條,看起來很是麻煩。因而瀏覽器廠商爲了讓用戶在小屏幕下網頁也可以顯示地很好,因此把佈局視口設置的很大,通常在768px ~ 1024px 之間,最經常使用的寬度就是 980。
這樣用戶就能看到絕大部份內容,並根據具體內容選擇縮放。
故佈局視口是看不見的,瀏覽器廠商設置的一個固定值,如980px,並將980px的內容縮放到手機屏內。一塊手機屏幕,物理像素的數量是固定不變的。
視覺視口的大小是繼承自佈局視口的大小,視覺視口和佈局視口的寬度爲CSS的px數(可變的)。web

理想視口
佈局視口雖然解決了移動端查看pc端網頁的問題,可是徹底忽略了手機自己的尺寸。因此蘋果引入了理想視口,它對設備來講是最理想的佈局視口,用戶不須要對頁面進行縮放就能完美的顯示整個頁面。最簡單的作法就是使佈局視口寬度設置爲手機屏幕的寬度。移動端到底怎麼適配不一樣的屏幕呢?最簡單的方法是設置以下視口:
<meta name="viewport" content="width=device-width,initial-scale=1, maximum-scale=1, minimum-scale=1, user-scalable=no">
複習一下: dpr = 物理像素 / 設備獨立像素。
以iphone6爲例,iphone6的物理像素爲750,若是沒有設置佈局視口時,佈局視口viewport默認爲980px
此時:dpr = 750 / 980 = 0.76531,等於1個CSS像素有0.76531個物理像素。接近於1像素密度因此pc端的頁面在手機端看時不會過小。
當在meta中設置了以下配置時:
<meta name="viewport" content="width=device-width">
至關於把佈局視口設置爲設備的寬度(即設備獨立像素),
iphone6的設備獨立像素爲 375px。
此時:dpr = 750 / 375 = 2,等於1個CSS像素有2個物理像素。此時把pc端的尺寸拿來手機端看時字體和元素會特別大隻。小程序

如今移動端設計稿都是基於iphone設計的,通常爲750px或640px,對應的是iphone6和iphone5的物理像素。在設計稿中,1px像素邊框對應的是1物理像素。而在iphone5和iphone6中,當佈局視口width=device-width時,css的1px顯示出來的是2個物理像素,因此用戶看到的是2px的邊框。怎麼解決呢?1px邊框效果其實有不少hack方法,其中一種就是經過縮放viewport。
<meta name="viewport" content="width=device-width,initial-scale=0.5, maximum-scale=0.5, minimum-scale=0.5, user-scalable=no">
viewport縮放
initial-scale是對佈局視口進行縮放,initial-scale是相對於理想視口的,即initial-scale=1與width=device-width是同樣的效果。initial-scale=0.5等效於width= 2倍的 device-width,因此設置initial-scale和width均可以改變佈局視口的大小。
對於可視視口的縮放能夠理解爲,用戶用雙指對頁面進行縮放,當用戶縮小頁面時,可視視口變大用戶能夠看到的東西越多,當用戶放大頁面時,可視視口
變小,用戶看到的東西越少。
對於iphone6當添加如上設置後,initial-scale=0.5時。
佈局視口: 375px * 2 = 750px;
因此此時佈局視口爲750px,此時1px等於1物理像素了。(移動端一像素有不少hack寫法好比用僞類實現,svg實現等等)
看到這是否是以爲要消化的知識點有點多,不怕,休息一下消化消化,每一個人都是這樣過來的。猥瑣發育~微信小程序

多種適配方案探究

當設計師給出ui圖時,面對市場上各式各樣的手機它們屏幕大小不一樣,dpr不一樣,屏幕尺寸也是各類大小,那麼咱們應該怎麼作到對ui設計圖的充分還原,使得項目在各式各樣的手機裏運行呢?爲了解決這種狀況出現了許多的適配方案,各方案的實現方法不同,還原程度也不同,下面來總結一下常見的幾種適配方案及其原理。
方案一:固定高度,使其寬度自適應
這也是我接觸移動端適配第一次使用的方案。
這個方案使用了理想視口,使得佈局視口等於設備寬度。
<meta name="viewport" content="width=device-width,initial-scale=1, maximum-scale=1, minimum-scale=1, user-scalable=no">
在佈局方面縱向使用固定px值,橫向使用自適應佈局(百分比,felx,小額定值)。
這種方案相對簡單,ui還原度比較低。瀏覽器

方案二:固定佈局視口寬度,使用viewport進行縮放(網易、荔枝FM)微信

if(/Android (\d+\.\d+)/.test(navigator.userAgent)){
        var version = parseFloat(RegExp.$1);
        if(version>2.3){
            var phoneScale = parseInt(window.screen.width)/640;
            if(/MZ-M571C/.test(navigator.userAgent)){
                document.write('<meta name="viewport" content="width=640, minimum-scale = 0.5, maximum-scale= 0.5">');
            }else if(/M571C/.test(navigator.userAgent)&&/LizhiFM/.test(navigator.userAgent)){
                document.write('<meta name="viewport" content="width=640, minimum-scale = 0.5, maximum-scale= 0.5">');
            }else{
                document.write('<meta name="viewport" content="width=640, minimum-scale = '+ phoneScale +', maximum-scale = '+ phoneScale +', target-densitydpi=device-dpi">');
            }
        }else{
            document.write('<meta name="viewport" content="width=640, target-densitydpi=device-dpi">');
        }
    }else{
        document.write('<meta name="viewport" content="width=640, user-scalable=no, target-densitydpi=device-dpi">');
    }

固定佈局視口,寬度設置固定的值,總寬度爲640px,根據屏幕寬度動態生成viewport。(設計稿寬度爲640px)
這種佈局方案頁面寬度始終爲640px經過設置縮放比例scale實現適配:
var scale = window.screen.width / 640;
當設計稿爲640px時,咱們能夠直接用1:1px來寫像素單位。這種佈局方案中的1px不必定等於1px,當設備爲iphone6時
1px(css) = window.screen.widthdpr = 640 = 375 2 / 640 = 1.171875(設備物理像素)
荔枝FM這種適配方案用到了target-densitydpi , 這是一個將被拋棄的屬性,所以不推薦使用這套方案(學習一下思路也不錯)網絡

方案三:根據不一樣屏幕動態寫入font-size,以rem做爲寬度單位,固定佈局視口。(網易新聞)
首先設置理想視口:
<meta name="viewport" content="width=device-width,initial-scale=1, maximum-scale=1, minimum-scale=1, user-scalable=no">
接下來計算 html 元素的 font-size,將可視視口的寬度乘以一個係數:

理論上這個係數能夠是任意值,假設將這個係數取 1,則 html 元素的 font-size 即1 rem等於可視視口的寬度,此時以 rem 爲單位的長度 n rem 就能夠理解爲 n 倍可視視口的長,這個係數取 0.01 時,1 rem 等於可視視口寬的 1/100,也就等於佈局視口寬的 1/100,也就等於 1vw。實際使用過程當中這個係數的選擇儘量方便將設計稿長度數值換算爲css中的長度數值
網易新聞 手機網易網選擇的係數爲 100 / 750,這個係數能夠以下推出:

750px 是設計稿的寬度(以iphone6的物理像素數爲標準),100是指望的換算比例,即設計稿中 100px 的長度對應css中 1rem,將設計稿中的長度數值除以 100 獲得的就是以 rem 爲單位的 css 長度的數值,設計稿的寬換算爲以 rem 爲單位的 css 長度應爲 (750/100) rem,同時設計稿的寬對應可視視口的寬,即有 (750/100) rem = 可視視口寬,1 rem = 可視視口寬 * (100/750),(100/750)就是咱們要的係數
在頁面初始化時設置一下 html 元素的 font-size:

在750寬的設計稿:document.documentElement.style.fontSize = window.innerWidth / 7.5 + 'px';
在640寬的設計稿:document.documentElement.style.fontSize = window.innerWidth / 7.5 + 'px';
這套方案能百分比還原設計稿。

方案四:根據不一樣屏幕動態寫入font-size和viewport,以rem做爲寬度單位.
將屏幕分爲固定的塊數10:

var width = document.documentElement.clientWidth; // 屏幕的佈局視口寬度
var rem = width / 10; // 將佈局視口分爲10份
這樣在任何屏幕下,總長度都爲10rem。1rem對應的值也不固定,與屏幕的佈局視口寬度有關。

動態縮放view:

var devicePixelRatio = window.devicePixelRatio;
var isIPhone = window.navigator.appVersion.match(/iphone/gi);
var dpr,scale;
if (isIPhone) {
  if (devicePixelRatio >=3) {
    dpr = 3;
  } else if (devicePixelRatio >=2) {
    dpr = 2;
  } else {
    dpr = 1;
  }
} else {
  dpr = 1;
}
scale = 1 / dpr;

淘寶只對iphone作了縮放處理,對於android全部dpr=1,scale=1即沒有縮放處理。

此方案與方案三類似,增進了viewport縮放使得在iphone上1px(css) = 1px(物理像素),這套方案能百分比還原設計稿。
Flexible實現手淘H5頁面的終端適配
方案五:
能夠來看看我總結的 : 大漠老師最新的vw移動端適配方案


最後看到這裏相信你們內心都有個底,知道選擇哪種方案更能適配本身所開發的項目

(~ ̄▽ ̄)~

see u ~

相關文章
相關標籤/搜索