默认锁屏壁纸无效问题

news/2024/10/30 18:19:52/

Android O默认锁屏壁纸无效

我们设置android默认壁纸的时候,会替换对应的资源文件,但是android O之后只能配置系统壁纸,锁屏壁纸设置为透明或设置与系统壁纸一样,如果我们要像之前一样单独配置锁屏壁纸需要修改WallpaperManager.关于Android O后面为什么不能设置锁屏壁纸,源码有下面的解释:

frameowrks/base/core/java/android/app/WallpaperManager.java

 public static InputStream openDefaultWallpaper(Context context, @SetWallpaperFlags int which) {final String whichProp;final int defaultResId;if (which == FLAG_LOCK) {/* Factory-default lock wallpapers are not yet supportedwhichProp = PROP_LOCK_WALLPAPER;defaultResId = com.android.internal.R.drawable.default_lock_wallpaper;*/return null;} else {whichProp = PROP_WALLPAPER;defaultResId = com.android.internal.R.drawable.default_wallpaper;}........return null;}

openDefaultWallpaper方法有一个参数which,它只会有两种类型FLAG_LOCK,FLAG_SYSTEM,分别代表这锁屏壁纸和桌面壁纸(桌面壁纸在SysemUI应用里面).但是源码这里有一个注解"Factory-default lock wallpapers are not yet supported",说明官方不支持设置默认锁屏壁纸,经过发现,默认锁屏就是默认桌面的壁纸,default_lock_wallpaper;是无效.

如果要实现单独配置锁屏和桌面壁纸,需要修改相关代码,在修改之前需要了解加载流程.

默认壁纸加载相关的类

以展讯8.1为例:
展讯8.1直接把默认壁纸透明话,只显示桌面壁纸.从而省略了加载锁屏壁纸的流程,提高了流畅度.所以我们需要先把这个开关打开.
frameowrks/base/package/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java

private static final boolean ENABLE_LOCKSCREEN_WALLPAPER = SystemProperties.getBoolean("ro.lockwallpaper.enable", true);

加载锁屏和默认壁纸有相关的4个类

modified:   base/core/java/android/app/WallpaperManager.javamodified:   base/packages/SystemUI/src/com/android/systemui/ImageWallpaper.javamodified:   base/packages/SystemUI/src/com/android/systemui/statusbar/phone/LockscreenWallpaper.javamodified:   base/services/core/java/com/android/server/wallpaper/WallpaperManagerService.java
功能类,名所属
桌面壁纸(系统壁纸加载类)ImageWallpaperSystemUI
锁屏壁纸加载类LockscreenWallpaperSystemUI
壁纸加载服务类应用进程端ImageWallpaperframeworks
壁纸加载服务类系统进程端WallpaperManagerServiceframeworks

加载默认壁纸是在"壁纸加载服务类应用进程端"

默认壁纸加载流程

在这里插入图片描述加载默认壁纸是不会调用WallpaperManagerService,只在

在LockscreenWallpaperhe 和ImageWallpaper最终调用getBitmapAsUser如下所示

    public Bitmap getBitmap() {return getBitmapAsUser(mContext.getUserId());}/*** Like {@link #getDrawable()} but returns a Bitmap for the provided user.** @hide*/public Bitmap getBitmapAsUser(int userId) {return sGlobals.peekWallpaperBitmap(mContext, true, FLAG_SYSTEM, userId);}

在getBitmapAsUser只会传入FLAG_SYSTEM,见:peekWallpaperBitmap(mContext, true, FLAG_SYSTEM, userId);所以要在加载锁屏壁纸这个逻辑要修改(后面修改)

然后进入peekWallpaperBitmap,代码如下

        public Bitmap peekWallpaperBitmap(Context context, boolean returnDefault,@SetWallpaperFlags int which, int userId) {....if (returnDefault) {Bitmap defaultWallpaper = mDefaultWallpaper;if (defaultWallpaper == null) {
;defaultWallpaper = getDefaultWallpaper(context, which);synchronized (this) {mDefaultLockWallpaper = defaultWallpaper;}}return defaultWallpaper;}return null;}

这个只有一个mDefaultLockWallpaper,所以在保存的时候只会保存一个,因为要想锁屏壁纸和系统壁纸都有效,必须分别加载,这里也要修改.(后面修改)

最后到openDefaultWallpaper方法

    public static InputStream openDefaultWallpaper(Context context, @SetWallpaperFlags int which) {....if (which == FLAG_LOCK) {/* Factory-default lock wallpapers are not yet supported*/whichProp = PROP_LOCK_WALLPAPER;defaultResId = com.android.internal.R.drawable.default_lock_wallpaper;return null;*/} else {whichProp = PROP_WALLPAPER;defaultResId = com.android.internal.R.drawable.default_wallpaper;}final String path = SystemProperties.get(whichProp);if (!TextUtils.isEmpty(path)) {final File file = new File(path);if (file.exists()) {try {return new FileInputStream(file);} catch (IOException e) {// Ignored, fall back to platform default below}}}try {return context.getResources().openRawResource(defaultResId);} catch (NotFoundException e) {// no default defined for this device; this is not a failure}return null;}

which == FLAG_LOCK已经被注解了,需要去掉注解,去掉retrun null;(后面修改)

增加配置默认锁屏壁纸功能

step 1 :打开锁屏壁纸加载开关

SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java
打开加载锁屏壁纸开关

-    private static final boolean ENABLE_LOCKSCREEN_WALLPAPER = SystemProperties.getBoolean("ro.lockwallpaper.enable", true);
+    private static final boolean ENABLE_LOCKSCREEN_WALLPAPER = true;
step 2 :修改加载锁屏壁纸方式,使得加载与系统壁纸区分

SystemUI/src/com/android/systemui/statusbar/phone/LockscreenWallpaper.java
修改LockscreenWallpaper加载方式
在这里插入图片描述

  1. 需要注释掉加载系统壁纸的代码,因为这里是加载锁屏壁纸
  2. 注意selectedUser有时候会null,我们只需要mCurrentUserId,selectedUser.getIdentifier()返回本身就是mCurrentUserId
  3. getLockBitmapAsUser方法是后面添加WallpaperManager中的.
step 3 : wallpaperManager加载锁屏壁纸

base/core/java/android/app/WallpaperManager.java

在这里插入图片描述
上面方法是原来的加载的方法,现在只做系统壁纸加载,后面添加的方法做锁屏壁纸加载

修改:WallpaperManager内部类Globals的方法peekWallpaperBitmap

在这里插入图片描述
在这里插入图片描述这样就能保存锁屏和系统两种不同的默认壁纸了

修改:WallpaperManager内部类Globals的方法openDefaultWallpaper

在这里插入图片描述

按照如上修改,系统就能分别配置锁屏和默认壁纸了

修改的patch

其他平台和android版本修改应该大同小异

下面是3个文件的修改patch

diff --git a/base/core/java/android/app/WallpaperManager.java b/base/core/java/android/app/WallpaperManager.java
index 8a375cd44..2cb77e88d 100644
--- a/base/core/java/android/app/WallpaperManager.java
+++ b/base/core/java/android/app/WallpaperManager.java
@@ -284,6 +284,7 @@ public class WallpaperManager {private Bitmap mCachedWallpaper;private int mCachedWallpaperUserId;private Bitmap mDefaultWallpaper;
+        private Bitmap mDefaultLockWallpaper;private Handler mMainLooperHandler;Globals(Looper looper) {
@@ -393,6 +394,7 @@ public class WallpaperManager {public Bitmap peekWallpaperBitmap(Context context, boolean returnDefault,@SetWallpaperFlags int which, int userId) {
+if (mService != null) {try {if (!mService.isWallpaperSupported(context.getOpPackageName())) {
@@ -427,11 +429,15 @@ public class WallpaperManager {}}if (returnDefault) {
-                Bitmap defaultWallpaper = mDefaultWallpaper;
+                Bitmap defaultWallpaper = (which == FLAG_LOCK) ? mDefaultLockWallpaper : mDefaultWallpaper;if (defaultWallpaper == null) {defaultWallpaper = getDefaultWallpaper(context, which);synchronized (this) {
-                        mDefaultWallpaper = defaultWallpaper;
+                        if(which == FLAG_LOCK) {
+                            mDefaultLockWallpaper = defaultWallpaper;
+                        } else {
+                            mDefaultWallpaper = defaultWallpaper;
+                        }}}return defaultWallpaper;
@@ -831,6 +837,17 @@ public class WallpaperManager {return sGlobals.peekWallpaperBitmap(mContext, true, FLAG_SYSTEM, userId);}+    /**
+     * Like {@link #getDrawable()} but returns a Bitmap for the provided user.
+     *
+     * @hide
+     */
+    public Bitmap getLockBitmapAsUser(int userId) {
+        Log.i("wangcan","wallpapseManager-getLockBitmapAsUser FLAG_LOCK");
+        return sGlobals.peekWallpaperBitmap(mContext, true, FLAG_LOCK, userId);
+    }
+
+/*** Get an open, readable file descriptor to the given wallpaper image file.* The caller is responsible for closing the file descriptor when done ingesting the file.
@@ -1829,11 +1846,10 @@ public class WallpaperManager {final String whichProp;final int defaultResId;if (which == FLAG_LOCK) {
-            /* Factory-default lock wallpapers are not yet supported
+            /* Factory-default lock wallpapers are not yet supported*/whichProp = PROP_LOCK_WALLPAPER;defaultResId = com.android.internal.R.drawable.default_lock_wallpaper;
-            */
-            return null;
+            //return null;} else {whichProp = PROP_WALLPAPER;defaultResId = com.android.internal.R.drawable.default_wallpaper;
diff --git a/base/packages/SystemUI/src/com/android/systemui/statusbar/phone/LockscreenWallpaper.java b/base/packages/SystemUI/src/com/android/systemui/statusbar/phone/LockscreenWallpaper.java
index e44a47220..25993c55b 100644
--- a/base/packages/SystemUI/src/com/android/systemui/statusbar/phone/LockscreenWallpaper.java
+++ b/base/packages/SystemUI/src/com/android/systemui/statusbar/phone/LockscreenWallpaper.java
@@ -109,10 +109,10 @@ public class LockscreenWallpaper extends IWallpaperManagerCallback.Stub implemenselectedUser != null ? selectedUser.getIdentifier() : currentUserId;ParcelFileDescriptor fd = mWallpaperManager.getWallpaperFile(WallpaperManager.FLAG_LOCK, lockWallpaperUserId);
-        if (fd == null && mBar.getPowerSaveModeInternal() == PowerManagerEx.MODE_ULTRASAVING) {
-            fd = mWallpaperManager.getWallpaperFile(
-                WallpaperManager.FLAG_SYSTEM, lockWallpaperUserId);
-        }
+        //if (fd == null && mBar.getPowerSaveModeInternal() == PowerManagerEx.MODE_ULTRASAVING) {
+        //    fd = mWallpaperManager.getWallpaperFile(
+        //        WallpaperManager.FLAG_SYSTEM, lockWallpaperUserId);
+        //}if (fd != null) {try {BitmapFactory.Options options = new BitmapFactory.Options();
@@ -128,11 +128,13 @@ public class LockscreenWallpaper extends IWallpaperManagerCallback.Stub implemenif (selectedUser != null) {// Show the selected user's static wallpaper.return LoaderResult.success(
-                        mWallpaperManager.getBitmapAsUser(selectedUser.getIdentifier()));
+                        mWallpaperManager.getLockBitmapAsUser(selectedUser.getIdentifier()));} else {// When there is no selected user, show the system wallpaper
-                return LoaderResult.success(null);
+                //return LoaderResult.success(null);
+                return LoaderResult.success(
+                        mWallpaperManager.getLockBitmapAsUser(mCurrentUserId));}}}
diff --git a/base/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java b/base/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java
index 22d0bed37..b9ee91f84 100644
--- a/base/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java
+++ b/base/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java
@@ -381,7 +381,7 @@ public class StatusBar extends SystemUI implements DemoMode,private static final boolean ONLY_CORE_APPS;/** If true, the lockscreen will show a distinct wallpaper */
-    private static final boolean ENABLE_LOCKSCREEN_WALLPAPER = SystemProperties.getBoolean("ro.lockwallpaper.enable", true);
+    private static final boolean ENABLE_LOCKSCREEN_WALLPAPER = true;/* If true, the device supports freeform window management.* This affects the status bar UI. */

http://www.ppmy.cn/news/252370.html

相关文章

linux mint更改锁屏壁纸

系统是Linux mint。进入/usr/share/backgrounds/linuxmint 目录下,把自己的图片拷到目录下,改变default_background.jpg的软链接指向即可。 ➜ bulletin git:(master) ✗ cd /usr/share/backgrounds/linuxmint➜ linuxmint ls -al total 5836 drwxr-x…

android锁屏壁纸设置,安卓锁屏壁纸怎么换 安卓锁屏壁纸设置教程

最近笔者身边一朋友在手机刷机的情况,不小心将手机刷成了砖,开机无法进入系统,并且进入Recovery模式后,也无法找到刷机选项,后面无奈,只有拿手机去修了,由于手机配置较低,花50元修理…

manjaro修改锁屏壁纸

如果不是用startx启动图形界面,而是在图形化的界面中输入密码启动图形界面.如自带gdm的gnome-manjaro版, 那么你一定会想怎么修改锁屏输入密码界面的背景。这款脚本可轻松完成壁纸替换工作-突然觉得我手动折腾好几小时毫无意义 archibold-官方下载 - sudo mv ./a…

锁屏壁纸开发 Android,Android开发自己的锁屏壁纸

SurfaceView SurfaceHolder MediaPlayer Service BroadcastReceiver KeyguardManager PowerManager 思路:启动一个服务,监听灭屏广播,当收到广播的时候,点亮屏幕,禁用锁屏,调用使用Surface…

Android锁屏壁纸 代码,android 锁屏壁纸和桌面壁纸的设置实现

在flyme系统下面,有个类是可以用来设置桌面壁纸的,叫做WallpaperManager,调用该类的setBitmap(),即可。但是锁屏壁纸的设置却无法直接调用这个类的某些方法。 需要用到反射调用。反射调用可以参考以下两篇文章: 1.通过java反射调用…

windows10如何使用Wallpaper Engine实现动态锁屏壁纸?把WE的壁纸应用到锁屏。

Wallpaper Engine想必大多数人都知道,但是它只能设置桌面壁纸,无法设置锁屏壁纸。 想要设置好看的锁屏壁纸,可能需要下载Microsoft Store中的iSaver,但是我们已经花钱买了WE还要再花一次钱买iSaver吗?而且还比WE贵两块…

Linux I2C 驱动实验

目录 1. Linux I2C 驱动框架简介 1.1 I2C 总线驱动 1.2 I2C 设备驱动 1.3 I2C 设备和驱动匹配过程 2 I.MX6U 的 I2C 适配器驱动分析 3. 实验代码 1. Linux I2C 驱动框架简介 在裸机中,我们通常会有如下四个文件:xxxi2c.h,xxxi2c.c&…

JavaWeb中页面跳转方法的区别 request.getRequestDispatcher() response.sendRedirect()

⛳JavaWeb中页面跳转方法的区别 request.getRequestDispatcher() 和 response.sendRedirect() 都是Java Web 中用于页面跳转的方法,但它们的作用和实现方式有所不同。 🐾1、request.getRequestDispatcher() request.getRequestDispatcher() 方法用于在…