先上GitHub参考地址:https://github.com/DroidPluginTeam/DroidPlugin/blob/master/readme_cn.md。
下面直接开始使用。
1. 下载:首先在GitHub下载源码。
2. 导入:解压下载的包,打开Android Studio,新建一个项目,然后导入DroidPlugin\DroidPlugin-master\project\Libraries\DroidPlugin这个Module:
3. 添加依赖:在宿主项目中添加对DroidPlugin的依赖:
修改DroidPlugin的build.gradle中的作者,
4. 接下来开始上代码:
4.1 在自己的Application中初始化插件如下,然后记得在Manifest文件注册:
public class MyApp extends Application{ @Override public void onCreate() { super.onCreate(); PluginHelper.getInstance().applicationOnCreate(getBaseContext()); } @Override protected void attachBaseContext(Context base) { PluginHelper.getInstance().applicationAttachBaseContext(base); super.attachBaseContext(base); } }
private TextView tvTest; private TextView tvResult; private File[] plugins; private Button btnInstall; private Button btnTest; private int a; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); tvTest = (TextView) findViewById(R.id.tv_test); tvResult = (TextView) findViewById(R.id.tv_result); btnTest = (Button) findViewById(R.id.btn_test); btnInstall = (Button) findViewById(R.id.btn_install); //安装apk btnInstall.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { //获取插件,file是插件apk存放的文件夹, File file = new File(Environment.getExternalStorageDirectory(), "/plugin"); plugins = file.listFiles(); //没有插件 if (plugins == null || plugins.length == 0) { Log.d("sss", "插件安装失败==没有找到插件"); return; } //1.先卸载apk,插件apk的包名是“com.plugin”,不管有没有安装,先卸载了再说 try { PluginManager.getInstance().deletePackage("com.plugin", 0); } catch (RemoteException e) { Log.d("sss", "插件卸载失败=="+e.getMessage().toString()); e.printStackTrace(); } for (File apk:plugins ) { if (!apk.getAbsolutePath().contains("apk")){ Log.d("sss", "不是apk文件啊=="+apk.getName()); continue; }
//开始进行插件apk的安装 try { tvTest.setText(apk.getAbsolutePath()); Log.d("sss", "即将安装的apk=="+apk.getAbsolutePath()); //a = PluginManager.getInstance().installPackage(plugins[0].getAbsolutePath(), 0);//安装第一个插件 a =PluginManager.getInstance().installPackage(apk.getAbsolutePath(), PackageManagerCompat.INSTALL_REPLACE_EXISTING); getResult(a); } catch (RemoteException e) { Log.d("sss", "插件安装失败=="+e.getMessage().toString()); e.printStackTrace(); } } } }); //启动APK插件 btnTest.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { try { PackageManager pm = getPackageManager(); Intent intent = pm.getLaunchIntentForPackage("com.plugin"); if (intent == null){ Log.d("sss","intent是空的,没法使用啊"); } intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); startActivity(intent); } catch (Exception e) { e.printStackTrace(); Log.d("sss", "插件启动失败==" + e.toString()); } } }); } private void getResult(int a) { switch (a) { case -1: tvResult.setText("安装或卸载失败"); break; case 1: tvResult.setText("安装或卸载成功"); break; case -110: tvResult.setText("安装程序内部错误"); break; case -2: tvResult.setText("无效的Apk"); break; case 0x00000002: tvResult.setText("安装更新"); break; case -3: tvResult.setText("不支持的ABI"); break; default: tvResult.setText("老天都不知道这是咋了,a=="+a); break; } }
4.3在activity_main.xml中的代码如下:
xml version="1.0" encoding="utf-8"?>5.当你要运用到自己的项目上的时候,还有麻烦,那就是代码混淆:xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" tools:context="com.example.myapplication.MainActivity"> android:id="@+id/tv_test" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_centerInParent="true" android:text="无插件" android:textColor="@android:color/holo_green_dark" android:textSize="22sp" />
-keep class com.morgoo.droidplugin.stub.** { *; } -keep class android.**{ *; }
6。代码混淆后,有可能会出现的问题:
6.1.有可能发生三个警告,然后你安装的时候发现宿主程序就是打不开了
6.2.宿主程序能打开,插件Apk能安装,但是启动的时候找不到Activity了
解决办法:把DroidPlugin的layoutlib.jar去掉,把里面的抽象类Singleton移植到DroidPlugin的android/util目录下(如下图),保持混淆不变,问题解决。
7.附上我做的Demo的下载链接http://download.csdn.net/detail/sxk874890728/9905614。如果有问题,欢迎大家一起讨论问题。