Android 21+ 如何编程切换静音模式与DND模式?
Android 21+ 切换静音、DND及混合状态的实现方案
核心问题说明
Android 21(Lollipop)引入Do Not Disturb(DND)模式后,AudioManager.RINGER_MODE_SILENT的行为发生了变化:部分设备或系统版本中,设置该模式会自动触发DND,而非单纯的仅关闭铃声、保留通知音的静音状态。
权限准备
首先在AndroidManifest.xml中添加必要权限:
<!-- 控制铃声模式基础权限 --> <uses-permission android:name="android.permission.MODIFY_AUDIO_SETTINGS" /> <!-- Android 23+ 控制DND模式需额外权限 --> <uses-permission android:name="android.permission.ACCESS_NOTIFICATION_POLICY" />
Android 23+ 需动态请求DND权限:
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) { val notificationManager = getSystemService(Context.NOTIFICATION_SERVICE) as NotificationManager if (!notificationManager.isNotificationPolicyAccessGranted) { startActivity(Intent(Settings.ACTION_NOTIFICATION_POLICY_ACCESS_SETTINGS)) } }
各状态的具体实现
1. 单纯静音模式(仅关铃声,不触发DND)
Android 21+ 无直接API设置单纯静音,可通过调整铃声音量为0、关闭DND实现:
val audioManager = getSystemService(Context.AUDIO_SERVICE) as AudioManager // 将铃声音量设为0 audioManager.setStreamVolume(AudioManager.STREAM_RING, 0, 0) // 关闭DND模式 if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) { val notificationManager = getSystemService(Context.NOTIFICATION_SERVICE) as NotificationManager notificationManager.setInterruptionFilter(NotificationManager.INTERRUPTION_FILTER_ALL) }
2. 开启DND模式(完全静音,屏蔽所有通知/铃声)
通过NotificationManager设置DND过滤规则,配合铃声模式设置:
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) { val notificationManager = getSystemService(Context.NOTIFICATION_SERVICE) as NotificationManager // 设置为完全DND,屏蔽所有打扰 notificationManager.setInterruptionFilter(NotificationManager.INTERRUPTION_FILTER_NONE) } // 同步设置铃声模式为静音(部分设备需此步骤) val audioManager = getSystemService(Context.AUDIO_SERVICE) as AudioManager audioManager.ringerMode = AudioManager.RINGER_MODE_SILENT
3. 静音+DND兼具状态
DND本身已包含静音效果,若需更严格控制,可额外关闭通知音量:
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) { val notificationManager = getSystemService(Context.NOTIFICATION_SERVICE) as NotificationManager notificationManager.setInterruptionFilter(NotificationManager.INTERRUPTION_FILTER_NONE) } val audioManager = getSystemService(Context.AUDIO_SERVICE) as AudioManager // 关闭铃声和通知音量 audioManager.setStreamVolume(AudioManager.STREAM_RING, 0, 0) audioManager.setStreamVolume(AudioManager.STREAM_NOTIFICATION, 0, 0)
4. 恢复正常模式
val audioManager = getSystemService(Context.AUDIO_SERVICE) as AudioManager // 恢复铃声模式为正常 audioManager.ringerMode = AudioManager.RINGER_MODE_NORMAL // 恢复默认音量(可根据需求调整数值) val maxRingVolume = audioManager.getStreamMaxVolume(AudioManager.STREAM_RING) audioManager.setStreamVolume(AudioManager.STREAM_RING, maxRingVolume / 2, 0) // 关闭DND if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) { val notificationManager = getSystemService(Context.NOTIFICATION_SERVICE) as NotificationManager notificationManager.setInterruptionFilter(NotificationManager.INTERRUPTION_FILTER_ALL) }
关键注意事项
- 设备兼容性:小米、华为等厂商对DND和静音模式的实现存在差异,部分设备需额外适配系统自带设置逻辑。
- 权限限制:Android 12+ 对DND权限管控更严格,动态请求后需用户手动授权才能生效。
内容的提问来源于stack exchange,提问作者Sir Codesalot
相关产品推荐
相关产品推荐

