Android16 应用代码新特性
Android16 应用代码新特性
文章目录
- Android16 应用代码新特性
- 一、系统行为强制变更(代码适配差异)
- 1. 全屏布局机制
- 2. 预测返回导航
- 二、权限模型重构(代码声明差异)
- 1. 健康数据权限精细化
- 2. 剪贴板访问权限
- 三、API 接口重大变更(方法 / 类替换)
- 1. 生物识别认证分级
- 2. Nearby Share 传输升级
- 3. 内存管理优化
- 四、AI 与本地模型集成(新增 API)
- 五、广播与事件机制(安全性增强)
- 1. 动态广播导出状态强制声明
- 2. 有序广播废弃
- 六、开发者工具链(依赖与语法变更)
- 1. Jetpack Compose 版本强制升级
- 2. 编译工具要求
- 七、总结:核心差异领域
Android16应用代码对比Android15、14有啥代码差异?
Android 16 相对于 Android 15 和 14,在系统行为、API 接口、权限模型、性能优化等方面存在多处代码级差异,这些差异直接影响应用的兼容性和功能实现。
以下从核心场景对比具体代码变化,有兴趣的看看:
一、系统行为强制变更(代码适配差异)
1. 全屏布局机制
-
Android 14/15:可通过windowOptOutEdgeToEdgeEnforcement
禁用全屏布局:xml
<!-- Android 14/15 可选配置 --> <style name="AppTheme"><item name="windowOptOutEdgeToEdgeEnforcement">true</item> </style>
- Android 16:彻底移除该属性,所有应用默认强制全屏,需显式处理状态栏 / 导航栏遮挡:
kotlin:// Android 16 必须添加的适配代码
val windowInsetsController = ViewCompat.getWindowInsetsController(window.decorView)windowInsetsController?.systemBarsBehavior = WindowInsetsControllerCompat.BEHAVIOR_SHOW_TRANSIENT_BARS_BY_SWIPE// 布局中设置 padding 避免内容被遮挡ViewCompat.setOnApplyWindowInsetsListener(yourView) { view, insets ->val systemBars = insets.getInsets(WindowInsetsCompat.Type.systemBars())view.setPadding(systemBars.left, systemBars.top, systemBars.right, systemBars.bottom)insets}Java:// Android 16 窗口布局适配import androidx.core.view.WindowInsetsControllerCompat;import androidx.core.view.ViewCompat;import androidx.core.graphics.Insets;import androidx.core.view.WindowInsetsCompat;// 配置系统栏行为WindowInsetsControllerCompat windowInsetsController = new WindowInsetsControllerCompat(getWindow(), getWindow().getDecorView());windowInsetsController.setSystemBarsBehavior(WindowInsetsControllerCompat.BEHAVIOR_SHOW_TRANSIENT_BARS_BY_SWIPE
);windowInsetsController.hide(WindowInsetsCompat.Type.systemBars());// 处理布局内边距View rootView = findViewById(R.id.root_view);ViewCompat.setOnApplyWindowInsetsListener(rootView, (view, insets) -> {Insets bars = insets.getInsets(WindowInsetsCompat.Type.systemBars());view.setPadding(bars.left,bars.top,bars.right,bars.bottom);return insets;});
2. 预测返回导航
-
Android 14:仅手势导航支持预测返回,可通过onBackPressed() 兼容:
kotlin // Android 14 旧逻辑 override fun onBackPressed() {super.onBackPressed() // 直接触发返回 }
-
Android 15:扩展至三键导航,但仍支持
onBackPressed()
降级; -
Android 16:完全废弃onBackPressed() 和 KEYCODE_BACK
强制使用新回调:
kotlin: // Android 16 必须使用的新逻辑 onBackPressedDispatcher.addCallback(this, object : OnBackPressedCallback(true) {override fun handleOnBackPressed() {// 处理返回逻辑(如弹窗确认)if (shouldFinish) finish()else isEnabled = false // 交给父级处理} })Java:// Android 16 返回导航import androidx.activity.OnBackPressedCallback;import androidx.lifecycle.LifecycleOwner;getOnBackPressedDispatcher().addCallback((LifecycleOwner) this, new OnBackPressedCallback(true) {@Overridepublic void handleOnBackPressed() {if (canGoBack()) {finish(); // 处理返回} else {showExitDialog(() -> setEnabled(false)); // 禁用回调,让系统处理}}private boolean canGoBack() {// 判断是否可返回的逻辑return false;}private void showExitDialog(Runnable onConfirm) {// 显示退出对话框,确认后调用 onConfirmonConfirm.run();} });
在Android16 demo和手机上测试了一下,onBackPressed()回调还是可以在Activity监听,但是左滑退出没有回调了;
getOnBackPressedDispatcher().addCallback 左滑退出是有回调的,说明之前的onBackPressed()已经废弃了。
二、权限模型重构(代码声明差异)
1. 健康数据权限精细化
-
Android 14/15:通过BODY_SENSORS
统一申请健康传感器权限:
xml <!-- Android 14/15 权限声明 --> <uses-permission android:name="android.permission.BODY_SENSORS" />
-
Android 16:拆分为 12 个细分权限,需按需声明:
xml <!-- Android 16 权限声明 --> <uses-permission android:name="android.permission.READ_HEART_RATE" /> <uses-permission android:name="android.permission.READ_BLOOD_PRESSURE" /> <uses-permission android:name="android.permission.READ_HEALTH_DATA_IN_BACKGROUND" /> <!-- 后台访问需额外声明 -->
代码中请求权限时也需对应调整:
kotlin // Android 16 权限请求 registerForActivityResult(ActivityResultContracts.RequestMultiplePermissions()) { permissions ->if (permissions[Manifest.permission.READ_HEART_RATE] == true) {// 访问心率传感器} }.launch(arrayOf(Manifest.permission.READ_HEART_RATE))Java // Android 16 健康权限请求 import androidx.activity.result.ActivityResultLauncher; import androidx.activity.result.contract.ActivityResultContracts; import android.Manifest; import android.content.pm.PackageManager; // 注册权限请求回调private final ActivityResultLauncher<String[]> requestHealthPermissions =registerForActivityResult(new ActivityResultContracts.RequestMultiplePermissions(), permissions -> {if (permissions.getOrDefault(Manifest.permission.READ_HEART_RATE, false)) {startHeartRateMonitoring();}});// 发起权限请求public void requestHeartRatePermission() {if (checkSelfPermission(Manifest.permission.READ_HEART_RATE) != PackageManager.PERMISSION_GRANTED) {requestHealthPermissions.launch(new String[]{Manifest.permission.READ_HEART_RATE});} else {startHeartRateMonitoring();}}private void startHeartRateMonitoring() {// 开始心率监测}
2. 剪贴板访问权限
-
Android 14/15:访问剪贴板无需特殊权限;
-
Android 16:必须申请READ_CLIPBOARD权限:
xml <!-- Android 16 新增权限 --> <uses-permission android:name="android.permission.READ_CLIPBOARD" />
代码中需先检查权限:
kotlin// Android 16 剪贴板访问逻辑if (ContextCompat.checkSelfPermission(this, Manifest.permission.READ_CLIPBOARD) == PackageManager.PERMISSION_GRANTED) {val clipboard = getSystemService(ClipboardManager::class.java)val text = clipboard.primaryClip?.getItemAt(0)?.text}Java// Android 16 剪贴板访问
import android.content.ClipboardManager;import android.content.pm.PackageManager;
import android.Manifest;import androidx.core.content.ContextCompat;public String getClipboardText() {if (ContextCompat.checkSelfPermission(this, Manifest.permission.READ_CLIPBOARD)!= PackageManager.PERMISSION_GRANTED) {// 未获得权限,请求权限或提示用户return null;}ClipboardManager clipboard = (ClipboardManager) getSystemService(CLIPBOARD_SERVICE);if (clipboard != null && clipboard.getPrimaryClip() != null && clipboard.getPrimaryClip().getItemCount() > 0) {return clipboard.getPrimaryClip().getItemAt(0).getText().toString();}return null;}
三、API 接口重大变更(方法 / 类替换)
1. 生物识别认证分级
-
Android 14/15:通过 BIOMETRIC_STRONG
标识强认证:
kotlin// Android 14/15 生物识别val promptInfo = BiometricPrompt.PromptInfo.Builder().setAllowedAuthenticators(BiometricManager.Authenticators.BIOMETRIC_STRONG).build()
-
Android 16:引入 L1-L3 分级,支付场景强制 L3 级:
kotlin // Android 16 生物识别分级 val promptInfo = BiometricPrompt.PromptInfo.Builder().setAuthenticationLevel(BiometricManager.Authenticators.BIOMETRIC_LEVEL_3) // L3 活体检测.build()Java// Android 16 生物识别分级 import androidx.biometric.BiometricPrompt;import androidx.core.content.ContextCompat; import java.util.concurrent.Executor;private void showBiometricPrompt() {Executor executor = ContextCompat.getMainExecutor(this);BiometricPrompt biometricPrompt = new BiometricPrompt(this, executor,new BiometricPrompt.AuthenticationCallback() {@Overridepublic void onAuthenticationSucceeded(BiometricPrompt.AuthenticationResult result) {super.onAuthenticationSucceeded(result);// 认证成功处理}});BiometricPrompt.PromptInfo promptInfo = new BiometricPrompt.PromptInfo.Builder().setTitle("确认支付")// 设置 L3 级认证(最高安全级).setAllowedAuthenticators(BiometricManager.Authenticators.BIOMETRIC_LEVEL_3).build();biometricPrompt.authenticate(promptInfo); }
2. Nearby Share 传输升级
- Android 14/15:使用旧版 API 单设备传输:
// Android 14/15 传输文件
Nearby.getShareClient(context).send(uri, deviceId).addOnSuccessListener { /* 处理成功 */ }
- Android 16:新增多设备并行传输 API(需 Wi-Fi 7 支持):
kotlin// Android 16 多设备传输val transfer = Nearby.getShareClient(context).createMultiDeviceTransfer(listOf(uri1, uri2), listOf(device1, device2))transfer.start().addOnSuccessListener { /* 处理成功 */ }
3. 内存管理优化
-
Android 14/15:默认 4KB 内存页,无显式配置;
-
Android 16:支持 16KB 内存页,旧应用需兼容:
xml <!-- Android 16 如需保留 4KB 页(不推荐) --> <application android:pageSizeCompat="4k" />
代码中可判断设备支持类型:
kotlin // Android 16 内存页适配 if (Build.VERSION.SDK_INT >= 36) {val pageSize = ActivityManager.getMemoryPageSize()if (pageSize == 16384) { // 16KB// 启用优化逻辑} }Java// Android 16 内存页适配 import android.app.ActivityManager;import android.content.Context; import android.os.Build;import androidx.annotation.RequiresApi;@RequiresApi(api = Build.VERSION_CODES.JAVA16) private void adaptToMemoryPageSize() {ActivityManager activityManager = (ActivityManager) getSystemService(Context.ACTIVITY_SERVICE);int pageSize = activityManager.getMemoryPageSize();if (pageSize == 16384) { // 16KB 内存页// 启用大内存块优化逻辑optimizeForLargePages();} else {// 兼容 4KB 内存页的逻辑compatibilityWithSmallPages();}}private void optimizeForLargePages() {// 针对 16KB 内存页的优化 }private void compatibilityWithSmallPages() {// 兼容 4KB 内存页的逻辑}
四、AI 与本地模型集成(新增 API)
-
Android 14/15:无系统级本地大模型 API;
-
Android 16:新增 Gemini Nano 本地模型接口:
kotlin// Android 16 调用本地 AI 生成图片描述
val gemini = GeminiSession.getInstance(context)val image = ImageDecoder.decodeBitmap(...)
gemini.generateAltText(image).addOnSuccessListener { altText ->// 用于无障碍标签或图片搜索imageView.contentDescription = altText}Java// Android 16 本地 AI 集成
import android.graphics.Bitmap;import android.net.Uri;import android.os.Build;import androidx.annotation.RequiresApi;import com.google.android.gms.gemini.GeminiSession;import com.google.android.gms.tasks.OnSuccessListener;@RequiresApi(api = Build.VERSION_CODES.JAVA16)private void generateImageDescription(Uri imageUri) {try {// 解码图片Bitmap image = ImageDecoder.decodeBitmap(ImageDecoder.createSource(getContentResolver(), imageUri));// 获取 Gemini 实例GeminiSession gemini = GeminiSession.getInstance(getApplicationContext());// 生成图片描述gemini.generateAltText(image).addOnSuccessListener(altText -> {// 设置无障碍描述ImageView imageView = findViewById(R.id.image_view);imageView.setContentDescription(altText);});} catch (Exception e) {e.printStackTrace();}}
五、广播与事件机制(安全性增强)
1. 动态广播导出状态强制声明
-
Android 14:动态注册广播未指定导出状态时默认导出,无报错;
-
Android 15:未指定时抛出警告;
-
Android 16:未指定时直接抛出 IllegalArgumentException,必须显式声明:
kotlin // Android 16 动态广播注册(必须指定导出状态) registerReceiver(myReceiver,IntentFilter("com.example.ACTION"),Context.RECEIVER_EXPORTED // 或 RECEIVER_NOT_EXPORTED )Java// Android 16 动态广播注册 import android.content.BroadcastReceiver;import android.content.IntentFilter; import android.content.Context;private void registerMyReceiver() {BroadcastReceiver myReceiver = new MyReceiver();IntentFilter filter = new IntentFilter("com.example.ACTION");// 必须显式指定导出状态registerReceiver(myReceiver,filter,Context.RECEIVER_EXPORTED // 或 Context.RECEIVER_NOT_EXPORTED);}private class MyReceiver extends BroadcastReceiver {@Overridepublic void onReceive(Context context, Intent intent) {// 处理广播}}
2. 有序广播废弃
-
Android 14/15:仍可使用
sendOrderedBroadcast()
; -
Android 16:标记为废弃,建议改用WorkManager:
kotlin// Android 16 替代有序广播的方案
WorkManager.getInstance(context).beginWith(FirstWorker::class.java).then(SecondWorker::class.java) // 按顺序执行.enqueue()Java
/ Android 16 WorkManager 替代有序广播import androidx.work.OneTimeWorkRequest;
import androidx.work.WorkManager;import java.util.Arrays;private void executeOrderedTasks() {// 第一步任务OneTimeWorkRequest firstWork = new OneTimeWorkRequest.Builder(FirstWorker.class).build();// 第二步任务(依赖第一步)OneTimeWorkRequest secondWork = new OneTimeWorkRequest.Builder(SecondWorker.class).build();// 按顺序执行WorkManager.getInstance(this).beginWith(firstWork).then(secondWork).enqueue();}// 定义 Worker 类
import androidx.work.Worker;import androidx.work.WorkerParameters;public class FirstWorker extends Worker {public FirstWorker(Context context, WorkerParameters params) {super(context, params);}@Overridepublic Result doWork() {// 执行第一步任务return Result.success();}}public class SecondWorker extends Worker {public SecondWorker(Context context, WorkerParameters params) {super(context, params);}@Overridepublic Result doWork() {// 执行第二步任务return Result.success();}}
六、开发者工具链(依赖与语法变更)
1. Jetpack Compose 版本强制升级
-
Android 14/15:支持 Compose 1.x/2.x;
-
Android 16:强制使用 Compose 3.0,部分 API 不兼容:
kotlin // Android 14/15 旧列表组件 LazyColumn {items(dataList) { item -> Text(item) } } // Android 16 新列表组件(性能优化)LazyColumnV2 {items(dataList) { item -> Text(item) }}
2. 编译工具要求
-
Android 14/15:最低支持 AGP 7.0;
-
Android 16:最低要求 AGP 8.5,且必须使用 Java 17 编译:
gradle// Android 16 模块级 build.gradle 配置
android {compileSdk 36buildToolsVersion "36.0.0"compileOptions {sourceCompatibility JavaVersion.VERSION_17targetCompatibility JavaVersion.VERSION_17}}
七、总结:核心差异领域
维度 | Android 14/15 状态 | Android 16 变更点 |
---|---|---|
系统行为 | 可禁用全屏、支持旧返回逻辑 | 强制全屏、废弃 onBackPressed() |
权限模型 | 健康数据 / 剪贴板无细分权限 | 权限精细化、新增 READ_CLIPBOARD |
核心 API | 生物识别单级、单设备传输 | 生物识别分级、多设备传输 API |
性能优化 | 4KB 内存页、传统调度 | 16KB 内存页、Project Quantum 引擎 |
AI 集成 | 无系统级本地模型 | 新增 Gemini Nano 接口 |
开发工具 | 支持旧版 Compose/AGP | 强制 Compose 3.0、AGP 8.5、Java 17 |
适配时需重点关注权限声明更新、系统行为强制变更和废弃 API 迁移,
建议结合官方迁移工具(如 Android Studio 的 lint 检查)批量定位代码差异点。
总的来说感觉变更Android16后,需要适配的实际代码很少,
因为很多功能基本没啥用过,比如AI集成,性能优化,生物识别等,都是不常用的;
返回按键那个功能是要适配一下的,毕竟之前的回调方法没用了,要用新的api方法了。
Android16还有另外的差异吗,肯定是有的,比如系统HIDL在Android16不支持了!那咋搞?
要用AIDL。 Android11新增了可以绑定底层的AIDL (C++ 绑定) 功能适配。
这个算是系统代码实现差异;另外说明。
本文的主要内容,算是应用代码功能使用差异。