Android6.0至9.0版本適配總結(jié)
簡(jiǎn)要列舉下Android6到Android9在開發(fā)中需要適配的問(wèn)題碍舍,做到心中有數(shù),用到時(shí)再去查開發(fā)文檔,文章非原創(chuàng)戳吝,后面已黏貼引用鏈接。
Android6.0
- 對(duì)危險(xiǎn)權(quán)限申請(qǐng)適配(推薦AndPermission)
Android7.xx
-
目錄被限制訪問(wèn)
- 私有文件的文件權(quán)限不在放權(quán)給所有的應(yīng)用贯涎,使用MODE_WORLD_READABLE或MODE_WORLD_WRITEABLE進(jìn)行操作將觸發(fā)SercurityException听哭,場(chǎng)景有SharePreference的模式
- 傳遞file://URI類型的Uri,導(dǎo)致無(wú)法訪問(wèn)該路徑,會(huì)觸發(fā)FileUriException,可使用FileProvider解決這問(wèn)題陆盘,應(yīng)用場(chǎng)景:apk安裝普筹,拍照
- DownloadManager不再按文件名分享私人存儲(chǔ)的文件。COLUMN_LOCAL_FILENAME在Android7.0中被標(biāo)記為depreciated隘马,嘗試在AndroidN以上版本訪問(wèn)該字段將觸發(fā)SecurityException太防,可以使用ContentProvider.openFileDescriptor()來(lái)訪問(wèn)DownloadManager公開文件
APK sinature schme v2
-
隱式廣播的限制
-
ACTION_NEW_PICTURE
和ACTION_NEW_VIDEO
隱式廣播無(wú)法接受和發(fā)出 -
CONNECTIVITY_ACTION
靜態(tài)注冊(cè)廣播無(wú)法收到,動(dòng)態(tài)廣播可以收到 - 對(duì)于
CONNECTIVITY_CHANGE
廣播酸员,ConnectvityManager
提供其他更健壯的API蜒车,如NetworkRequest
.
-
-
增加的Dozen模式
AndroidN 對(duì)AndroidM的Dozen模式進(jìn)一步增強(qiáng),降低進(jìn)入Dozen模式的條件幔嗦,AndroidM中的條件是不插電屏幕熄滅靜置一段時(shí)間酿愧,AndroidN中去掉靜置的條件。另一方面Dozen模式分為兩個(gè)階段邀泉,當(dāng)設(shè)備切斷電源嬉挡,屏幕熄滅一段時(shí)間就會(huì)進(jìn)入第一階段,切斷網(wǎng)絡(luò)連接汇恤,推遲任務(wù)和同步棘伴;如果再靜置一段時(shí)間進(jìn)入第二階段,增加對(duì)維持喚醒(PowerManagerc.WakeLock)定時(shí)任務(wù)(AlarmMager)Gps和WiFi掃描的限制屁置。- 在Android6.0中AlarmManager中增加兩個(gè)方法setAllowWhiledle()和setExactAndAllowWhiledle()通過(guò)這兩個(gè)方法可使得Alarm在Dozen模式下運(yùn)行焊夸,另外使用這方法時(shí),應(yīng)用每9分鐘只能喚醒一次alarm蓝角。
- 給應(yīng)用添加權(quán)限
REQUEST_IGNORE_BATTERY_OPTIMIZATIONS
,并使用ACTION_REQUEST_IGNORE_BATTERY_OPTIMIZATIONS
,系統(tǒng)會(huì)彈出設(shè)置窗口,用戶可以直接將該應(yīng)用添加到白名單中.
Intent intent = new Intent(Settings.ACTION_REQUEST_IGNORE_BATTERY_OPTIMIZATIONS); intent.setData(Uri.parse("package:com.showdy.dozen")); startActivity(intent);
Android8.xx
在Android 8.0之前阱穗,如果應(yīng)用在運(yùn)行時(shí)請(qǐng)求某個(gè)權(quán)限并且被授予,系統(tǒng)會(huì)錯(cuò)誤地將屬于同一權(quán)限組并且在清單中注冊(cè)的其他權(quán)限也一并授予該應(yīng)用使鹅。對(duì)于Android8.0的應(yīng)用揪阶,此行為已被糾正。系統(tǒng)只會(huì)授予應(yīng)用明確請(qǐng)求的權(quán)限患朱。然而鲁僚,一旦用戶為應(yīng)用授予某個(gè)權(quán)限,則所有后續(xù)對(duì)該權(quán)限組中權(quán)限的請(qǐng)求都將被自動(dòng)批準(zhǔn)裁厅,而不會(huì)提示用戶
-
PHONE權(quán)限組新增兩個(gè)權(quán)限
-
ANSWER_PHONE_CALLS
:權(quán)限運(yùn)行應(yīng)用處理呼入電話 -
READ_PHONE_NUMBERS
:權(quán)限允許應(yīng)用讀取設(shè)備中存儲(chǔ)電話號(hào)碼
-
Notifications
適配
方便管理通知行為和設(shè)置推出了一個(gè)新的概念:渠道和組冰沙,它允許你為要顯示的每種通知類型創(chuàng)建自定義的類別。安裝APK
Android 8.0去除“允許未知來(lái)源”選項(xiàng)执虹,需手動(dòng)確認(rèn)拓挥。如果我們的App具備安裝App的功能,那么AndroidManifest文件需要包含REQUEST_INSTALL_PACKAGES權(quán)限袋励,未聲明此權(quán)限的應(yīng)用將無(wú)法安裝其他應(yīng)用侥啤。我們可以選擇使用当叭。Settings.ACTION_MANAGE_UNKNOWN_APP_SOURCES這個(gè)action將用戶引導(dǎo)至安裝未知應(yīng)用權(quán)限界面,同時(shí)也可以使用 packageManager.canRequestPackageInstalls()查詢此權(quán)限的狀態(tài)盖灸。提醒窗口
WindowManager.LayoutParams
的type設(shè)置為TYPE_SYSTEM_OVERLAY
在4.4到6.0之前蚁鳖,google沒(méi)有提供方法讓我們用于判斷懸浮窗權(quán)限,同時(shí)也沒(méi)有跳轉(zhuǎn)到設(shè)置界面進(jìn)行開啟的方法赁炎,因?yàn)榇藱?quán)限是默認(rèn)開啟的才睹,但是有一些產(chǎn)商會(huì)修改它,所以在使用之前最好進(jìn)行判斷甘邀,以免使用時(shí)出現(xiàn)崩潰琅攘,判斷方法是用反射的方式獲取出是否開啟了懸浮窗權(quán)限。在6.0以及以后的版本中松邪,google為我們提供了判斷方法和跳轉(zhuǎn)界面的方法坞琴,直接使用Settings.canDrawOverlays(context)
就可以判斷是否開啟了懸浮窗權(quán)限,沒(méi)有開啟可以跳轉(zhuǎn)到設(shè)置界面讓用戶開啟逗抑。
需要配置的權(quán)限:
<uses-permission android:name="android.permission.SYSTEM_ALERT_WINDOW"/>
<uses-permission android:name="android.permission.SYSTEM_OVERLAY_WINDOW" />
Android9.xx
-
Android9通過(guò)下列變更簡(jiǎn)化通知渠道設(shè)置
屏蔽渠道組:現(xiàn)在剧辐,用戶可以針對(duì)某個(gè)應(yīng)用在通知設(shè)置中屏蔽整個(gè)渠道組。您可以使用 isBlocked()函數(shù)確定何時(shí)屏蔽一個(gè)渠道組邮府,從而不會(huì)向該組中的渠道發(fā)送任何通知荧关。此外,您的應(yīng)用可以使用全新的 getNotificationChannelGroup()函數(shù)查詢當(dāng)前渠道組設(shè)置褂傀。
全新的廣播 Intent類型:現(xiàn)在忍啤,當(dāng)通知渠道和渠道組的屏蔽狀態(tài)發(fā)生變更時(shí),Android 系統(tǒng)將發(fā)送廣播 Intent仙辟。 擁有已屏蔽的渠道或渠道組的應(yīng)用可以偵聽這些 Intent 并做出相應(yīng)的回應(yīng)同波。 有關(guān)這些 Intent 操作和 extra 的更多信息,請(qǐng)參閱 NotificationManager 參考中更新的常量列表叠国。 有關(guān)響應(yīng)廣播 Intent 的信息未檩,請(qǐng)參閱廣播。
NotificationManager.Policy有3種新的“請(qǐng)勿打擾”優(yōu)先級(jí)類別:
PRIORITY_CATEGORY_ALARMS優(yōu)先處理警報(bào)粟焊。
PRIORITY_CATEGORY_MEDIA優(yōu)先處理媒體源的聲音冤狡,如媒體和語(yǔ)音導(dǎo)航。
PRIORITY_CATEGORY_SYSTEM優(yōu)先處理系統(tǒng)聲音项棠。NotificationManager.Policy還有7種新的“請(qǐng)勿打擾”常量悲雳,可以用來(lái)抑制視覺中斷:
SUPPRESSED_EFFECT_FULL_SCREEN_INTENT防止通知啟動(dòng)全屏 Activity。
SUPPRESSED_EFFECT_LIGHTS屏蔽通知燈沾乘。
SUPPRESSED_EFFECT_PEEK防止通知短暫進(jìn)入視圖(“滑出”)怜奖。
SUPPRESSED_EFFECT_STATUS_BAR防止通知顯示在支持狀態(tài)欄的設(shè)備的狀態(tài)欄中浑测。
SUPPRESSED_EFFECT_BADGE在支持標(biāo)志的設(shè)備上屏蔽標(biāo)志翅阵。
SUPPRESSED_EFFECT_AMBIENT在支持微光顯示的設(shè)備上屏蔽通知歪玲。
SUPPRESSED_EFFECT_NOTIFICATION_LIST防止通知顯示在支持列表視圖(如通知欄或鎖屏)的設(shè)備的列表視圖中。
限制訪問(wèn)通話記錄
Android 9 引入CALL_LOG
權(quán)限組并將READ_CALL_LOG
掷匠、WRITE_CALL_LOG
和PROCESS_OUTGOING_CALLS
權(quán)限移入該組滥崩。 在之前的 Android 版本中,這些權(quán)限位于 PHONE 權(quán)限組讹语。
如果應(yīng)用需要訪問(wèn)通話記錄或者需要處理去電钙皮,則您必須向 CALL_LOG權(quán)限組明確請(qǐng)求這些權(quán)限。 否則會(huì)發(fā)生SecurityException
-
限制訪問(wèn)電話號(hào)碼
- 在未首先獲得
READ_CALL_LOG
權(quán)限的情況下顽决,除了應(yīng)用的用例需要的其他權(quán)限之外短条,運(yùn)行于 Android 9 上的應(yīng)用無(wú)法讀取電話號(hào)碼或手機(jī)狀態(tài)。與來(lái)電和去電關(guān)聯(lián)的電話號(hào)碼可在手機(jī)狀態(tài)廣播(比如來(lái)電和去電的手機(jī)狀態(tài)廣播)中看到才菠,并可通過(guò)PhoneStateListener
類訪問(wèn)茸时。 但是,如果沒(méi)有READ_CALL_LOG
權(quán)限赋访,則PHONE_STATE_CHANGED
廣播和PhoneStateListener
提供的電話號(hào)碼字段為空可都。 - 要從手機(jī)狀態(tài)中讀取電話號(hào)碼,請(qǐng)根據(jù)您的用例更新應(yīng)用以請(qǐng)求必要的權(quán)限:
要通過(guò)PHONE_STATE
Intent操作讀取電話號(hào)碼蚓耽,同時(shí)需要READ_CALL_LOG
權(quán)限和READ_PHONE_STATE
權(quán)限渠牲。
要從onCallStateChanged()
中讀取電話號(hào)碼,只需要READ_CALL_LOG
權(quán)限步悠。 不需要READ_PHONE_STATE
權(quán)限签杈。
- 在未首先獲得
劉海屏適配
對(duì)使用非SDK接口的限制和適配策略
Build.SERIAL 始終設(shè)置為 "UNKNOWN" 以保護(hù)用戶的隱私。
如果您的應(yīng)用需要訪問(wèn)設(shè)備的硬件序列號(hào)鼎兽,您應(yīng)改為請(qǐng)求 READ_PHONE_STATE權(quán)限芹壕,然后調(diào)用 getSerial()。-
電話信息現(xiàn)在依賴設(shè)備位置設(shè)置
如果用戶在運(yùn)行 Android 9的設(shè)備上停用設(shè)備定位接奈,則以下函數(shù)不提供結(jié)果:- TelephonyManager.getAllCellInfo()
- TelephonyManager.listen()
- TelephonyManager.getCellLocation()
- TelephonyManager.getNeighboringCellInfo()