版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/u012808234/article/details/82664811
Android 动态替换Icon
Android通过动态替换icon来实现展示不同的icon。
实现方式
1、在清单文件中配置启动的activity的别名activity-alias
类似这样:
<activity
android:name=".ui.SplashActivity"
android:configChanges="orientation|keyboardHidden|screenSize"
android:screenOrientation="portrait"
android:theme="@style/WelcomeContentOverlay">
<!-- <intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>-->
<intent-filter>
<action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.DEFAULT" />
<category android:name="android.intent.category.BROWSABLE" />
<data android:scheme="jixiangrili" />
</intent-filter>
</activity>
<activity-alias
android:enabled="true"
android:label="@string/app_name"
android:icon="@mipmap/jixiang_logo"
android:name=".ui.launcher_main"
android:roundIcon="@mipmap/jixiang_logo"
android:targetActivity=".ui.SplashActivity"
>
<intent-filter >
<action android:name="android.intent.action.MAIN"/>
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity-alias>
<activity-alias
android:enabled="false"
android:label="我试吉祥日历"
android:icon="@drawable/icon_gold_coin"
android:name=".ui.launcher_1"
android:targetActivity=".ui.SplashActivity"
>
<intent-filter >
<action android:name="android.intent.action.MAIN"/>
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity-alias>
<activity-alias
android:enabled="false"
android:label="我试吉祥日历2"
android:icon="@drawable/icon_luopan"
android:name=".ui.launcher_2"
android:targetActivity=".ui.SplashActivity"
>
<intent-filter >
<action android:name="android.intent.action.MAIN"/>
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity-alias>
targetActivity:为要启动的入口Activity
name:别名
2、设置别名以后只要在需要动态替换的时候执行以下方法即可:
//取消掉默认的应用icon
final PackageManager pm = getApplicationContext().getPackageManager();
pm.setComponentEnabledSetting(getComponentName(), PackageManager.COMPONENT_ENABLED_STATE_DISABLED,
PackageManager.DONT_KILL_APP);
//然后执行
pm.setComponentEnabledSetting(new ComponentName(
getBaseContext(),
"com.jixiang.rili.ui.launcher_main"),
PackageManager.COMPONENT_ENABLED_STATE_ENABLED,
PackageManager.DONT_KILL_APP);
“com.jixiang.rili.ui.launcher_main”为别名的全名称(包名+别名name)
下边是一个测试30动态替换一次icon的测试代码。注意别名一定要全路径别名才能生效。
private void changeIcon() {
Thread thread = new Thread(new Runnable() {
@Override
public void run() {
final PackageManager pm = getApplicationContext().getPackageManager();
long last = System.currentTimeMillis();
long detal;
while (true) {
if ((detal = ( System.currentTimeMillis() - last) / 1000) > 30) {
last = System.currentTimeMillis();
//去除旧图标,不去除的话会出现2个App图标
pm.setComponentEnabledSetting(getComponentName(),
PackageManager.COMPONENT_ENABLED_STATE_DISABLED,
PackageManager.DONT_KILL_APP);
int positon = (int) (Math.random()* 3);
CustomLog.e("准备替换icon" + positon);
if (positon == 0) {
//去除旧图标,不去除的话会出现2个App图标
pm.setComponentEnabledSetting(new ComponentName(
getBaseContext(),
"com.jixiang.rili.ui.launcher_1"),
PackageManager.COMPONENT_ENABLED_STATE_DISABLED,
PackageManager.DONT_KILL_APP);
//去除旧图标,不去除的话会出现2个App图标
pm.setComponentEnabledSetting(new ComponentName(
getBaseContext(),
"com.jixiang.rili.ui.launcher_2"),
PackageManager.COMPONENT_ENABLED_STATE_DISABLED,
PackageManager.DONT_KILL_APP);
//显示新图标
pm.setComponentEnabledSetting(new ComponentName(
getBaseContext(),
"com.jixiang.rili.ui.launcher_main"),
PackageManager.COMPONENT_ENABLED_STATE_ENABLED,
PackageManager.DONT_KILL_APP);
} else if (positon == 1) {
//去除旧图标,不去除的话会出现2个App图标
pm.setComponentEnabledSetting(new ComponentName(
getBaseContext(),
"com.jixiang.rili.ui.launcher_2"),
PackageManager.COMPONENT_ENABLED_STATE_DISABLED,
PackageManager.DONT_KILL_APP);
//去除旧图标,不去除的话会出现2个App图标
pm.setComponentEnabledSetting(new ComponentName(
getBaseContext(),
"com.jixiang.rili.ui.launcher_main"),
PackageManager.COMPONENT_ENABLED_STATE_DISABLED,
PackageManager.DONT_KILL_APP);
//显示新图标
pm.setComponentEnabledSetting(new ComponentName(
getBaseContext(),
"com.jixiang.rili.ui.launcher_1"),
PackageManager.COMPONENT_ENABLED_STATE_ENABLED,
PackageManager.DONT_KILL_APP);
} else if (positon == 2) {
//去除旧图标,不去除的话会出现2个App图标
pm.setComponentEnabledSetting(new ComponentName(
getBaseContext(),
"com.jixiang.rili.ui.launcher_main"),
PackageManager.COMPONENT_ENABLED_STATE_DISABLED,
PackageManager.DONT_KILL_APP);
//去除旧图标,不去除的话会出现2个App图标
pm.setComponentEnabledSetting(new ComponentName(
getBaseContext(),
"com.jixiang.rili.ui.launcher_1"),
PackageManager.COMPONENT_ENABLED_STATE_DISABLED,
PackageManager.DONT_KILL_APP);
//显示新图标
pm.setComponentEnabledSetting(new ComponentName(
getBaseContext(),
"com.jixiang.rili.ui.launcher_2"),
PackageManager.COMPONENT_ENABLED_STATE_ENABLED,
PackageManager.DONT_KILL_APP);
}
}
}
}
});
thread.start();
}
注意:
动态替换App icon 中会出现的问题
1、动态替换app icon ,只能替换内置的icon,无法从服务器端获取来更新icon
2、动态替换icon以后,应用内更新的时候必须要切换到原始icon,否则更新安装失败
如果是从第三方应用市场更新的话,会出现无法安装的问题,因为因为无法自动切换到原始icon(替换icon以后最好在一定时间内在还原到默认icon)
3、Android 系统动态替换app icon 会有延迟,在不同的手机系统上刷新icon的时间不一样,大概在10秒左右,在这个时间内点击icon会提示应用未安装
4、测试用三星手机动态替换icon会变换icon显示的位置。
5、频繁替换应用icon耗电严重