Android 8.0自定义锁屏如何屏蔽其他应用锁屏通知及回复功能?
The core issue here is that Android 8.0 (API 26) introduced TYPE_APPLICATION_OVERLAY with a lower window hierarchy than system notifications, which is why your custom lock screen can't block notifications anymore. Notifications will always render above overlay windows of this type. Here's how to fix it:
1. Use the Correct Window Type for Lock Screens
Replace TYPE_APPLICATION_OVERLAY with TYPE_KEYGUARD (for API 26+). This is a system window type specifically designed for lock screens, and it has a higher priority than notifications—so your custom lock screen will properly cover them.
Modified Code Example
public WindowManager winManager; public RelativeLayout wrapperView; WindowManager.LayoutParams localLayoutParams; // Adjust window type and flags for Android 8.0+ if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) { localLayoutParams = new WindowManager.LayoutParams( WindowManager.LayoutParams.TYPE_KEYGUARD, // Use lock screen-specific type WindowManager.LayoutParams.FLAG_LAYOUT_IN_SCREEN | WindowManager.LayoutParams.FLAG_FULLSCREEN | WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED // Show over system lock screen | WindowManager.LayoutParams.FLAG_DISMISS_KEYGUARD // Allow dismissing system lock | WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON, // Keep screen active PixelFormat.TRANSLUCENT); } else { localLayoutParams = new WindowManager.LayoutParams( WindowManager.LayoutParams.TYPE_SYSTEM_ERROR, WindowManager.LayoutParams.FLAG_LAYOUT_IN_SCREEN | WindowManager.LayoutParams.FLAG_FULLSCREEN | WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED | WindowManager.LayoutParams.FLAG_DISMISS_KEYGUARD | WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON, PixelFormat.TRANSLUCENT); } // Note: If this is an Activity, you don't need to add a view via WindowManager // Just set the Activity's window attributes directly getWindow().setAttributes(localLayoutParams); setContentView(R.layout.lock_screen_activity); // If you're using a floating lock screen (not an Activity), use this instead: // this.winManager = ((WindowManager) getApplicationContext().getSystemService(WINDOW_SERVICE)); // this.wrapperView = new RelativeLayout(getBaseContext()); // this.wrapperView.setBackgroundColor(getResources().getColor(R.color.white)); // View.inflate(this, R.layout.lock_screen_activity, this.wrapperView); // this.winManager.addView(this.wrapperView, localLayoutParams);
2. Add Required Permissions
Add these permissions to your AndroidManifest.xml:
<uses-permission android:name="android.permission.SYSTEM_ALERT_WINDOW" /> <uses-permission android:name="android.permission.DISABLE_KEYGUARD" /> <uses-permission android:name="android.permission.ACCESS_NOTIFICATION_POLICY" /> <!-- Optional, for extra control -->
3. Request Dynamic Permissions (Android 6.0+)
For API 23+, you need to prompt the user to enable the "Draw over other apps" permission:
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M && !Settings.canDrawOverlays(this)) { Intent permissionIntent = new Intent(Settings.ACTION_MANAGE_OVERLAY_PERMISSION, Uri.parse("package:" + getPackageName())); startActivityForResult(permissionIntent, 1001); // Handle result in onActivityResult }
4. Optional: Enforce Notification Blocking
To add an extra layer of protection (in case the window type doesn't fully block notifications), use NotificationManager to pause all notifications while your lock screen is active:
NotificationManager notificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE); // When lock screen is shown if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) { notificationManager.setInterruptionFilter(NotificationManager.INTERRUPTION_FILTER_NONE); } // When lock screen is dismissed if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) { notificationManager.setInterruptionFilter(NotificationManager.INTERRUPTION_FILTER_ALL); }
Why Your Original Code Failed
Android 8.0 reworked window hierarchies:
TYPE_APPLICATION_OVERLAYis the lowest-priority system window, so notifications (which use higher-priority windows likeSTATUS_BAR_NOTIFICATION_SHADE) will always appear above it.TYPE_KEYGUARDis part of the lock screen window hierarchy, which the system prioritizes over notifications—ensuring your custom lock screen stays on top.
内容的提问来源于stack exchange,提问作者mrugen patel

