android 布局長度單位深入研究(2)

2021-06-01 08:55:56 字數 3402 閱讀 5178

先上乙個網上copy的

px:是螢幕的畫素點

in:英吋

mm:公釐

pt:磅,1/72 英吋

dp:乙個基於density的抽象單位,如果乙個160dpi的螢幕,1dp=1px

dip:等同於dp

sp:同dp相似,但還會根據使用者的字型大小偏好來縮放。

建議使用sp作為文字的單位,其它用dip

然後是我自己的理解:

android的螢幕密度是以160為基準的,

螢幕密度(densitydpi)為160時, 是將一英吋分為160份, 每乙份是1畫素. 如果螢幕密度(densitydpi)為240時, 是將一英吋分為240份, 每乙份是1畫素. 1英吋/160(機器x)  =  1英吋/240(機器y)  =  1px

打個比方, 乙個三英吋的顯示螢幕的機器, 如果螢幕密度(densitydpi)為160, 即密度比(density)1.0時, 畫一條160dip和160px的線條, 兩個都是1英吋. 可如果還是三英吋的螢幕, 如果螢幕密度(densitydpi)變為320, 即密度比(density)2.0時,1英吋有320畫素了, 此時160px顯示就是半英吋. 160dip顯示還是1英吋, 因為 1dip = 1px * density .

可是你有沒有注意到, 同樣寬的螢幕, 比如3英吋, 如果density 是1.0的話, 解析度就是480dip*x或480px,*x 如果還是3英吋的, density 是1.5的話 , 解析度就是480*1.5 = 720px*x 或480dip*x. (這裡的x代表螢幕的高度). 如果同樣是240dip, 在兩款機器上顯示都是一半的長度, 這樣就保證了比例. 這樣的話如果是480解析度和720解析度的話, 可以採用同乙個布局檔案了.

又但可是, 我見過的機器只有320*240(0.75) , 480*320(1.0) , 800*480(1.5), 854*480(1.5) , 如果是480 和 800 兩個版本, 同一條線480dip , 480顯示全屏, 800則顯示 480 / (800 / 1.5)  屏 . 其中800/1.5是螢幕的總dip . 我們平時說的解析度都是以畫素px為單位的.  

由此可見, 就算是用dip, 也不能保證不同解析度的機器的布局比例完全一樣.  但還是有好處的. 因為如果是用px的話, 有些時候一些布局直接跑到了螢幕外邊, 除錯起來很麻煩. 

還有, google**裡邊所用的單位都是以px為預設單位的. 

apk的資源包中,當螢幕density=240時使用hdpi標籤的資源

當螢幕density=160時,使用mdpi標籤的資源

當螢幕density=120時,使用ldpi標籤的資源。

在每英吋160點的顯示器上,1dp = 1px。

下面是幾種不同單位的相互轉換.

public static int dip2px(context context, float dipvalue) 

public static int px2dip(context context, float pxvalue) 

public static int dip2px(context context, float dipvalue) 

public static int px2dip(context context, float pxvalue) 

下面說下如何獲取解析度:

在乙個activity的oncreate方法中,寫入如下**:

displaymetrics metric = new displaymetrics();

getwindowmanager().getdefaultdisplay().getmetrics(metric);

int width = metric.widthpixels;  // 螢幕寬度(畫素)

int height = metric.heightpixels;  // 螢幕高度(畫素)

float density = metric.density;  // 螢幕密度(0.75 / 1.0 / 1.5)

int densitydpi = metric.densitydpi;  // 螢幕密度dpi(120 / 160 / 240)

這還是挺簡單的, 可是你有沒有在800*480的機器上試過, 是不是得到的寬度是533 ? 因為android剛開始時預設的density是1.0 , 此時你可以再manifest.xml中加入

1.uses-sdk節點, , 表示不sdk1.6以下的機器不能安裝你的apk了.

2.supports-screens 節點. 

system.out.println("density="+mdisplaymetrics.density);

}3.densitydpi與drawable-(hdpi,mdpi,ldpi)之間的關係

系統drawable有hdpi,mdpi,ldpi三個資料夾下面存放不同尺寸的,使用哪個檔案下的檔案,與系統densitydpi值是有關係的

densitydpi=120:ldpi

densitydpi=160:mdpi

densitydpi=240:hdpi

前面我又說過densitydpi取決於顯示屏,這樣你就了解了為什麼不同顯示屏wvga,hvga,qvga會採用不同drawable-(hdpi,mdpi,ldpi)

解析度為240px*400px,densitydpi=120-->qvga:ldpi

解析度為320px*533px,densitydpi=160 -->hvga:mdpi

解析度為480px*800px,densitydpi=240 -->wvga:wvga

4.儘管了解上面這些理論值,但是有時候發現設定了不同長度單位,可顯示出來的效果卻出人預想,我曾經就碰到過這種撓頭的問題,為解決這個問題,只有

深入**,一**竟了。

在深入**前我們首先要搞清楚乙個問題,那就是**中所有長度值的單位都是px,

手上沒有現成的例子就以現在我研究的/launcher2/res/layout-land/workspace_screen.xml為例,看乙個自定義屬性:

launcher:cellwidth="105pt"

該屬性自定義了乙個桌面快捷圖示的寬度,若讀者自己測試,自己寫個測試view,設定屬性

android:layout_width="800px"

是一樣的。

當view 被建立的時候,xml中的屬性值存在引數attributeset attrs中

public celllayout(context context, attributeset attrs, int defstyle)

繼續看該建構函式的實現**

public celllayout(context context, attributeset attrs, int defstyle)

實現長度單位換算的關鍵**就在a.getdimensionpixelsize(r.styleable.celllayout_cellwidth,

Android支援的長度單位

為了使使用者介面能夠在現在和將來的顯示器型別上正常顯示,建議大家始終使用sp作為文字大小的單位,android預設的字型大小也是用的sp。將dip作為其他元素的單位,比如長度 高度。當然,也可以考慮使用向量圖形,而不是用位圖。dp是與密度無關,sp除了與密度無關外,還與scale無關。如果螢幕密度為...

關於Android中長度單位

看到有很多不太理解dp sp和px的區別 現在這裡介紹一下dp和sp。dp也就是dip。這個和sp基本類似。如果設定表示長度 高度等屬性時可以使用dp 或sp。但如果設定字型,需要使用sp。dp是與密度無關,sp除了與密度無關外,還與scale無關。如果螢幕密度為160,這時dp和sp和px是一樣的...

Android 中的長度單位 px dp sp

一 介紹一下px 但如果使用 px 作單位,如果螢幕大小不變 假設還是3.2 寸 而螢幕密度變成了320。那麼原來 textview 的寬度設成160px,在密度為320 的3.2 寸螢幕裡看要比在密度為160 的3.2 寸螢幕上看短了一半。二 介紹一下 dp 和 sp。dp 也就是 dip。這個和...