Android Framework-Launcher-Partner

Partner是什么呢? 嗯 很好,鉴于我贫瘠的文学功底,我借鉴了一下AI的文本。

Partner 机制是一种允许设备制造商(OEM)、运营商或其他合作伙伴通过标准化方式定制和扩展 Android 系统功能的框架。它主要用于在不直接修改 AOSP 核心代码的前提下,实现厂商特定的定制需求,同时保持系统的兼容性和可维护性。

好的,说人话,就是你可以通过覆盖的方式,达到修改Laucher布局的效果。

实现方法

  • 编写一个BroadcastReceiver
java 复制代码
public  class LauncherPartner extends BroadcastReceiver {
    @Override
    public void onReceive(Context context, Intent intent) {

    }
}
  • AndroidMainfest.xml里添加
xml 复制代码
<receiver
            android:name=".LauncherPartner"
            android:exported="true">
            <intent-filter>
                <action android:name="com.android.launcher3.action.PARTNER_CUSTOMIZATION" />
            </intent-filter>
        </receiver>

res/xml包下下构建 partner_default_layout.xml

xml 复制代码
<?xml version="1.0" encoding="utf-8"?>

<favorites  xmlns:launcher="http://schemas.android.com/apk/res-auto">


    <appwidget

        className="com.android.alarmclock.DigitalAppWidgetProvider"
        packageName="com.android.deskclock"
        screen="0"
        spanX="2"
        spanY="2"
        x="3"
        y="0"


        />

    <favorite

        className="com.android.settings.Settings"
        packageName="com.android.settings"
        screen="0"
        spanX="1"
        spanY="1"
        x="4"
        y="4"

        />
    <favorite

        className="com.android.settings.Settings"
        packageName="com.android.settings"
        screen="0"
        spanX="1"
        spanY="1"
        x="4"
        y="3"

        />
    <favorite
        className="com.android.settings.Settings"
        packageName="com.android.settings"
        screen="1"
        spanX="1"
        spanY="1"
        x="3"
        y="2"

        />

    <folder
        screen="0"
        title="test"
        x="0"
        y="3">
        <favorite
            className="com.android.settings.Settings"
            packageName="com.android.settings"/>


        <favorite
            className="com.android.settings.Settings"
            packageName="com.android.settings"/>

        <favorite
            className="com.android.settings.Settings"
            packageName="com.android.settings"/>


        <favorite
            className="com.android.settings.Settings"
            packageName="com.android.settings"/>

    </folder>


    <favorite
        className="com.android.settings.Settings"
        packageName="com.android.settings"
        x="0"
        y="0"
        screen="0"
        container="-101"
       />

    <favorite
        className="com.android.settings.Settings"
        packageName="com.android.settings"
        container="-101"
        screen="1"
        x="1"
        y="0" />

    <favorite
        className="com.android.settings.Settings"
        packageName="com.android.settings"
        container="-101"
        screen="2"
        x="2"
        y="0" />

</favorites>

然后构建apk 或者直接编译到系统中就可以了。

原理解析

Android Framework-Launcher-默认布局的加载 在调用 loadWorkspace方法里

java 复制代码
LauncherSettings.Settings.call(contentResolver,
        LauncherSettings.Settings.METHOD_LOAD_DEFAULT_FAVORITES);

中会执行到 LauncherProviderloadDefaultFavoritesIfNecessary 方法 如果partner 不为null,就会去解析 partner_default_layout.xml。其实就是去匹配符合 actioncom.android.launcher3.action.PARTNER_CUSTOMIZATION的系统apk

java 复制代码
//packages/apps/Launcher3/src/com/android/launcher3/LauncherProvider.java

public static final String RES_PARTNER_DEFAULT_LAYOUT = "partner_default_layout";
loadDefaultFavoritesIfNecessary(){


if (loader == null) {
    final Partner partner = Partner.get(getContext().getPackageManager());
    if (partner != null) {
        int workspaceResId = partner.getXmlResId(RES_PARTNER_DEFAULT_LAYOUT);
        if (workspaceResId != 0) {
            loader = new DefaultLayoutParser(getContext(), widgetHolder,
                    mOpenHelper, partner.getResources(), workspaceResId);
        }
    }
}
}
  • Partner
java 复制代码
private static final String
        ACTION_PARTNER_CUSTOMIZATION = "com.android.launcher3.action.PARTNER_CUSTOMIZATION";
public static Partner get(PackageManager pm) {
    return get(pm, ACTION_PARTNER_CUSTOMIZATION);
}

public static Partner get(PackageManager pm, String action) {
    Pair<String, Resources> apkInfo = findSystemApk(action, pm);
    return apkInfo != null ? new Partner(apkInfo.first, apkInfo.second) : null;
}
相关推荐
邪修king1 小时前
Re:Linux 系统篇(二十九):动静态库Chapter2:动态库深度辨析 —— 核心本质、制作流程、双阶段查找模型与排错指南
android·java·linux·开发语言
Mr YiRan9 小时前
网络请求API监控与网络切换埋点
android·网络
美狐美颜sdk12 小时前
直播APP开发技术栈详解:视频美颜SDK、人脸识别与实时渲染
android·人工智能·音视频·美颜sdk·直播美颜sdk
奈斯先生Vector17 小时前
当模型版本不断变化,RelayRouter 能否帮助 AI 应用摆脱深度绑定
android·java·人工智能·开源·aigc
TimeFine18 小时前
让强模型做“总工”,让高性价比模型写代码
android
又见情义19 小时前
RK3568 Android 13 屏蔽 healthd 电池日志经验分享
android
古法安卓1 天前
Android-Fork 机制详解
android·java·android studio
Android打工仔1 天前
不要在 Data 层随意把 Cold Flow 转换成 Hot Flow
android·架构·kotlin
峥嵘life1 天前
2026免费的 opencode 使用分享:Windows端 + 服务器CLI 实战总结
android·大数据·开发语言
杉氧1 天前
拒绝重复造轮子:我写了一个生产级的 Kotlin 协程与 Flow 工具库(CoroutineKit)
android·kotlin·workflow