国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁 > 學院 > 開發設計 > 正文

移動端多屏適配fis3+rem方案

2019-11-09 15:15:48
字體:
來源:轉載
供稿:網友

移動端多屏適配rem方案

 

背景

1. 開發移動端H5頁面

2. 面對不同分辨率、dPR的手機

3. 面對不同屏幕尺寸的手機

 

一、概念

1、物理像素(physical pixel)

一個物理像素是顯示器(手機屏幕)上最小的物理顯示單元,在操作系統的調度下,每一個設備像素都有自己的顏色值和亮度值。

2、設備獨立像素(density-independent pixel)

設備獨立像素(也叫密度無關像素),可以認為是計算機坐標系統中得一個點,這個點代表一個可以由程序使用的虛擬像素(比如: CSS像素),然后由相關系統轉換為物理像素。

所以說,物理像素和設備獨立像素之間存在著一定的對應關系,這就是接下來要說的設備像素比。

3、設備像素比(device pixel ratio )

設備像素比(簡稱dpr)定義了物理像素和設備獨立像素的對應關系,它的值可以按如下的公式的得到:

設備像素比 = 物理像素 / 設備獨立像素 // 在某一方向上,x方向或者y方向

javascript中,可以通過window.devicePixelRatio獲取到當前設備的dpr。

在css中,可以通過:

-webkit-device-pixel-ratio,

-webkit-min-device-pixel-ratio,

 -webkit-max-device-pixel-ratio

進行媒體查詢,對不同dpr的設備,做一些樣式適配(這里只針對webkit內核的瀏覽器和webview)。

 

綜合上面幾個概念,一起舉例說明下:

以iphone6為例:

1. 設備寬高為375×667,可以理解為設備獨立像素(或css像素)。

2. dpr為2,根據上面的計算公式,其物理像素就應該×2,為750×1334。

用一張圖來表現,就是這樣:

上圖中可以看出,對于這樣的css樣式:

width: 2px;

height: 2px;

在不同的屏幕上(普通屏幕 vs retina屏幕),css像素所呈現的大小(物理尺寸)是一致的,不同的是1個css像素所對應的物理像素個數是不一致的。

在普通屏幕下,1個css像素 對應 1個物理像素(1:1)。在retina 屏幕下,1個css像素對應 4個物理像素(1:4)。

二、視覺稿要求

1. 現主流的iphone6寬度750px(以前是iphone4的320)

2. 在設計過程中注意兼容最小尺寸(320),如圖片中的文字、最小字體等...

問題:

1. 對于dpr=2的手機,為什么畫布大小×2,就可以解決高清問題?

2. 對于2倍大小的視覺稿,在具體的css編碼中如何還原每一個區塊的真實寬高(也就是布局問題)?

三、圖片問題

一個位圖像素是柵格圖像(如:png, jpg, gif等)最小的數據單元。每一個位圖像素都包含著一些自身的顯示信息(如:顯示位置,顏色值,透明度等)。

1、retina下,圖片高清問題

解決方案:@2x/@3x,然后圖片容器縮小。

2、背景圖片問題

解決方案:

width: 200px;

height: 300px;

background-image: url(image@2x.jpg);

background-size: 200px 300px; // 或者: background-size: contain;

缺點:

1. 普通屏幕下同樣下載了@2x的圖片,造成資源浪費。

2. 普通屏幕下圖片由于downsampling,會失去了一些銳利度(或是色差)。

所以最好的解決辦法是:不同的dpr下,加載不同的尺寸的圖片。

不管是通過css媒體查詢,還是通過Javascript條件判斷都是可以的。

那么問題來了,這樣的話,不就是要準備兩套圖片了嘛?(@1x 和@2x)

我想,做的好的公司,都會有這么一個圖片服務器,通過url獲取參數,然后可以控制圖片質量,也可以將圖片裁剪成不同的尺寸。

所以我們只需上傳大圖(@2x),其余小圖都交給圖片服務器處理,我們只要負責拼接url即可。

如,這樣一張原圖:

https://img.alicdn.com/tps/TB1AGMmIpXXXXafXpXXXXXXXXXX.jpg // 原圖

可以類似這樣,進行圖片裁剪:

// 200×200

https://img.alicdn.com/tps/TB1AGMmIpXXXXafXpXXXXXXXXXX.jpg_200x200.jpg

 

// 100×100

https://img.alicdn.com/tps/TB1AGMmIpXXXXafXpXXXXXXXXXX.jpg_100x100.jpg

(ps: 當然裁剪只是對原圖的等比裁剪,得保證圖片的清晰嘛~)

四、border:1px問題

 

解決方案:border使用1px而非rem單位,且div的盒子模型為:border-box

這大概是前端最敏感,最關心的問題了。

先來,來看看下面的圖:

上面兩張圖分別是在iphone3gs(dpr=1)和iphone5(dpr=2)下面的測試效果,對比來看,對于1px的border的展示,它們是一致的,并無區別。

那么retina顯示屏的優勢在哪里,設計師為何覺得高清屏下(右圖)這個線條粗呢?明明和左右一樣的~

還是通過一張圖來解釋:

上圖中,對于一條1px寬的直線,它們在屏幕上的物理尺寸(灰色區域)的確是相同的,不同的其實是屏幕上最小的物理顯示單元,即物理像素,所以對于一條直線,iphone5它能顯示的最小寬度其實是圖中的紅線圈出來的灰色區域,用css來表示,理論上說是0.5px。

五、前端布局要求

方案:

使用rem 針對不同手機屏幕尺寸和dpr動態的改變根節點html的font-size大小(基準值),再使用fis3-px2rem插件讓px自動轉化成rem

1)、配置代碼(750px的設計稿):

fis.match('*css', {

    postprocessor: fis.plugin('px2rem', {

        baseDpr: 2,  // dpr基準

        remUnit: 75,  // rem 基準,由設計稿決定(750/10)

        remPrecision: 6  // rem 精確位數

    });

});

這樣fis3就會自動按照750的大小將px轉換為rem單位;前端無需自己計算轉換;

對于動態改變根節點html的font-size,要求CSS和JS配合使用(解決閃爍問題)。

2)、CSS設置(通過設備寬度來媒體查詢來改變html的font-size,即min-device-width/10,與fis3配置對應):

@media(min-device-width:320px){html{font-size: 32px;/*no*/}}

@media(min-device-width:360px){html{font-size: 36px;/*no*/}}

@media(min-device-width:375px){html{font-size: 37.5px;/*no*/}}

@media(min-device-width:384px){html{font-size: 38.4px;/*no*/}}

@media(min-device-width:412px){html{font-size: 41.2px;/*no*/}}

@media(min-device-width:414px){html{font-size: 41.4px;/*no*/}}

@media(min-device-width:480px){html{font-size: 48px;/*no*/}}

@media(min-device-width:540px){html{font-size: 54px;/*no*/}}

@media(min-device-width:560px){html{font-size: 56px;/*no*/}}

@media(min-device-width:600px){html{font-size: 60px;/*no*/}}

@media(min-device-width:768px){html{font-size: 76.8px;/*no*/}}

@media(min-device-width:800px){html{font-size: 80px;/*no*/}}

@media(min-device-width:1080px){html{font-size: 108px;/*no*/}}

@media(min-device-width:1280px){html{font-size: 128px;/*no*/}}

@media(min-device-width:1440px){html{font-size: 144px;/*no*/}}

@media(min-device-width:1600px){html{font-size: 160px;/*no*/}}

缺點:不夠精確。

3)、javascript設置,通過上面的公式,計算出基準值rem,然后寫入樣式,大概如下:

var dpr, rem;

var docEl = document.documentElement;

var fontEl = document.createElement('style');

 

dpr = window.devicePixelRatio || 1;

rem = docEl.clientWidth / 10;

 

// 設置data-dpr屬性,留作的css hack之用

docEl.setAttribute('data-dpr', dpr);

 

// 動態寫入樣式

docEl.firstElementChild.appendChild(fontEl);

fontEl.innerHTML = 'html{font-size:' + rem + 'px!important;}';

 

// 給js調用的,某一dpr下rem和px之間的轉換函數

window.rem2px = function(v) {

v = parseFloat(v);

return v * rem;

};

window.px2rem = function(v) {

    v = parseFloat(v);

    return v / rem;

};

 

window.dpr = dpr;

window.rem = rem;

這種方式,可以精確地算出不同屏幕所應有的rem基準值,缺點就是要加載這么一段js代碼,但個人覺得是這是目前最好的方案了。


發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
主站蜘蛛池模板: 玉龙| 宁远县| 和田县| 福安市| 慈利县| 抚远县| 榆林市| 依安县| 仪陇县| 禹城市| 呼玛县| 沾化县| 东至县| 巴林右旗| 冷水江市| 高清| 寿光市| 苗栗市| 临西县| 仲巴县| 溆浦县| 大理市| 荣成市| 仙居县| 邮箱| 宣城市| 当涂县| 黄平县| 安龙县| 双江| 兰西县| 吉木萨尔县| 齐齐哈尔市| 定州市| 论坛| 靖安县| 济源市| 海林市| 德昌县| 固原市| 且末县|