前言
適配可以說是Android的老大難問題了,Android廠商眾多,設備碎片化嚴重.大屏小屏,全面屏,異形屏數(shù)不勝數(shù)
以下是10分鐘內(nèi)能找到的數(shù)據(jù)統(tǒng)計
友盟+,全域羅盤
截止2020年6月,左邊統(tǒng)計了22種不同的屏幕尺寸
共有11種分辨率
這些還僅是占比較多的設備,并不全面
而且同樣的屏幕尺寸也存在不同的分辨率
按照友盟的粗劣統(tǒng)計,就算主流10種屏幕尺寸,加上每種尺寸又有不同的寬高比和分辨率.
取10種尺寸,平局每種尺寸有2種寬高比,又有3種分辨率
那么就需要適配1023=60種
但是實際上需要適配的主流手機設備至少也要超過100種吧(單指國內(nèi)范圍)
適配方案
- AutoLayout 鴻洋大神出品 已經(jīng)停止維護
- dp適配. 見過最多一套寫了50多個xml配置文件的,應該算是窮舉法做適配了吧,但是沒法覆蓋更多設備
- 手動百分比適配. Web端常用的適配方式,適配方式復雜,需要每個控件都根據(jù)設備屏幕寬度計算控件寬度,然后按照比例計算控件高度
- 各中大公司自己的適配框架. 認識一些外包公司的朋友,公司都有自己的框架,但是不開源而且加密,只能初步分析是用了百分比的方式適配.具體原理不明
- 今日頭條AutoSize. 也是我現(xiàn)在用的適配框架.
SVG
如果你已經(jīng)解決了適配的問題,那么SVG仍然能帶給你一些方便
什么是SVG
VG是指可伸縮矢量圖形 (Scalable Vector Graphics)镐依,它不同于傳統(tǒng)的位圖,不是通過存儲圖像中每一點的像素值來保存與使用圖形,而是通過 XML 文件來定義一個圖形戚嗅,通過一些特定的語法和規(guī)則來繪制出我們所需的圖像——同樣是使用一張圖片,SVG 的方式是事先定義好怎么去畫這個圖,然后等要用的時候再把它去畫出來,而使用傳統(tǒng)的位圖的話就是已經(jīng)有了畫出來的圖阔逼,然后要用的時候直接把畫好的圖拿出來用。
SVG和平時用的位圖有什么區(qū)別
- SVG是需要顯示的時候再把圖形繪制出來,所以顯示的時候肯定會耗費一些資源(但是位圖也需要渲染,具體誰占用的資源更多,需要根據(jù)設備來看)
- 因為是用的時候?qū)崟r繪制,所以SVG不適合太過復雜的圖片
- SVG屬于矢量圖片,不怕縮放失真
- SVG使用代碼繪制,體積小
總結(jié)來看,如果是特定的icon圖標或者一些不復雜的地方,使用SVG會更好
SVG怎么用
- Android對SVG的支持從Android L開始,對于大家minSDK19的開發(fā)習慣來說,還是有一些限制的,而且目前沒有什么辦法統(tǒng)一適配21以下.但是實測部分國產(chǎn)機型在4.4.4上可以完美運行(酷派的一臺充話費送的手機).
使用Android Studio制作一個SVG圖形
創(chuàng)建一個xml文件在drawable中
<?xml version="1.0" encoding="utf-8"?>
<vector xmlns:android="http://schemas.android.com/apk/res/android"
android:width="120dp"
android:height="120dp"
android:viewportWidth="120"
android:viewportHeight="120">
<path
android:pathData="M40,40 L80,40 L80,80 L40,80 Z"
android:strokeWidth="8"
android:strokeColor="#e33e2b" />
</vector>
語法
SVG使用了</vector>
標簽,內(nèi)容的繪制使用了<path/>
標簽.
-
</vector>
中參數(shù)的意義
-
android:width="120dp"
dimen類型 繪制出的圖片寬度 -
android:height="120dp"
dimen類型 繪制出的圖片高度 -
android:viewportWidth="120"
float類型 畫布的寬度,這里沒有具體單位,指代的意思把畫布平均分成多少等分 -
android:viewportHeight="120"
loat類型 畫布的寬度,這里沒有具體單位,指代的意思把畫布平均分成多少等分
后面2個屬性比較難理解,我把他理解為平時切圖中的透明片大小
比如一張圖片10001000px大小,但是除了中間一個200200px的icon,其他都是透明.
那么icon尺寸200200就是width
和height
的尺寸,圖片尺寸10001000就是viewportWidth
和viewportHeight
的尺寸.
-
</path>
中參數(shù)的意義
-
pathData
String類型 有固定語法,可以理解為畫筆 -
strokeColor
color類型 畫筆的顏色 -
name
String類型</path>
的name,可以作為id從其他地方獲取到這個path -
strokeWidth
float類型 畫筆的寬度 -
fillColor
color類型 如果畫筆的路徑是閉合的,則填充閉合圖形的顏色,如果圖形不是閉合的,就把起點和終點連接起來填充這個顏色
- pathData的語法
M = moveto(M X,Y):將畫筆移動到指定的坐標位置地沮,但未發(fā)生繪制
L = lineto(L X,Y):畫直線到指定的坐標位置
H = horizontal lineto(H X):畫水平線到指定的X軸坐標
V = vertical lineto(V Y):畫垂直線到指定的Y軸坐標
C = curveto(C X1,Y1,X2,Y2,ENDX,ENDY):三次貝塞曲線
S = smooth curveto(S X2,Y2,ENDX,ENDY):三次貝塞曲線
Q = quadratic Belzier curveto(Q X,Y,ENDX,ENDY):二次貝塞曲線
T = smooth quadratic Belzier curveto(T ENDX,ENDY):映射前面路徑后的終點
A = elliptical Arc(A RX,RY,XROTATION,FLAG1,FLAG2,X,Y):弧線
Z = closepath():關閉路徑
參考文章 Android vector 標簽 pathData 詳解
所以上面的語法解釋為:
M40,40 L80,40 L80,80 L40,80 Z
- M40,40 將畫筆移動到40,40的坐標點
- L80,40 從40,40繪制到80,40(上面的橫線)
- L80,80 從80,40繪制到80,80(右邊的豎線)
- L40,80 從80,80繪制到40,80(下面的橫線)
-
Z 關閉路徑 自動從40,80繪制到40,40(起點),如果寫Z 效果如下圖
新建一個SVG圖片
這里可以生成兩種方式,
- Clip Art 使用預設圖案
- Local File 使用本地文件(就和上面一樣我們手寫自定義圖案)
這里有很多很多圖案,甚至還有一些Ios的預設圖標
這樣一個看似復雜的圖片就搞定了
其實AS4.0中新創(chuàng)建的項目中的2個圖標也都是用SVG生成的(可能是我默認minSDK是23的原因,沒細究)
ic_launcher_background
中寫多個path標簽的方式能讓繪制內(nèi)容更有閱讀性,更易后期修改維護,但是點擊標簽右邊是看不到對應哪一個位置的.盡量給每個path再加上注釋就方便日后讀寫了.