由于项目做的越来越大,业务上就产生了要将app模块化的需求,所谓模块化就是将一个app分成不同功能的小模块(插件),当安装程序的时候并不需要将所有模块一次全部安装,用户可以在需要的时候视情况从服务器上更新添加小插件。
android上模块化一直都有人在摸索也出现了不少框架各有优特点,我学习apkplug这个插件化框架。这个框架的特点是
1)插件就是普通apk文件,开发插件跟普通app没有太大区别省去了学习固定api的功夫了。
2)插件apk不用在本地安装,网上比较经典的插件化框架都是通过android:sharedUserId="xxx"的形式将插件与app进行关联,而apkplug不用安装在app进程中运行也算是它的一大特点
3)通过标准OSGI服务实现插件间通讯,我们开发应用时就可以定义自己的通讯接口了,而不必拘泥于固定的接口。
一 环境搭建
从apkplug官网下载其最新的sdk解压出来的文件目录结构为如图1
新建一个主应用工程我取名为myapkplughelloworld,将armeabi,Bundle1.4.0.jar两个文件放入工程的libs文件夹中如图2
配置应用权限到工程的AndroidManifest.xml中
<!-- 插件平台需要的权限! -->
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"></uses-permission>
<uses-permission android:name="android.permission.MOUNT_UNMOUNT_FILESYSTEMS"/>
<uses-permission android:name="android.permission.INTERNET"/>
另外将以下代码加入到<application></application>节点中
<!-- 插件平台需要的配置! -->
<activity
android:name="org.apkplug.app.apkplugActivity"
android:configChanges="orientation|keyboardHidden"
/>
下一步便是调用SDK启动插件了。
这里需要写一个PropertyInstance接口它是apkplug定义的目的是为了插件框架启动时传人一些启动参数,我够出来这个接口的定义如下,具体详细使用可以看apkplug官方提供的文档基本上是模块化的东西
[java]
public inte易做图ce PropertyInstance {
/**
* 框架配置信息获取接口
* 框架将通过该接口从系统获取必要信息
* 可以通过该接口实现框架信息的本地保存
* @param key
* @return
*/
public String getProperty(String key);
/**
* 框架配置信息设置接口
* 框架通过该接口设置其产生的配置信息
* 可以通过该接口实现框架信息的本地保存
* @param key
* @param v
*/
public void setProperty(String key,String v);
/**
* 框架启动时将自动安装该该函数提供的文件
* @return 本地插件绝对路径
*/
public String[] AutoInstall();
/**
* 框架启动时将自动安装并启动该该函数提供的文件
* @return 本地插件绝对路径
*/
public String[] AutoStart();
}
PropertyInstance写好以后便可以调用FrameworkInstance类启动框架了如下代码
[java]
try
{
FrameworkInstance frame=FrameworkFactory.getInstance().start(null,Launcher.this,
MyProperty.getInstance(this.getApplicationContext()));
}catch (Exception ex){
System.err.println("Could not create : " + ex);
//ex.printStackTrace();
StringBuffer buf=new StringBuffer();
buf.append("插件平台启动失败:\n");
buf.append(ex.getMessage());
this.setTitle(buf.toString());
Toast.makeText(this, "插件平台启动失败",
Toast.LENGTH_SHORT).show();
}
如果不出意外插件框架便启动完毕了,通过启动完成后的FrameworkInstance类可以获得框架的第一个内置插件SystemBundle。这个插件很重要它是我们进入框架的一个入口,我们可以通过它调用或启动其他框架的类与activity,下面将列出调用activity的代码
二 编写插件
首先新建一个工程myBundle将SDK包中的OSGI.jar引入到工程(注意这里osgi.jar包不能直接放入libs文件夹中,我们仅引入但不编译否则框架加载插件时会报错,因为包冲突)中如下图
接下来还需要写两个文件,一个是org.osgi.framework.BundleActivator接口,框架启动时将调用我们写的这一个类。另外一个是plugin.xml文档它用于配置插件的启动参数,比如启动的BundleActivator路径,启动的Activity,需要引出的包等。详细可以看官网plugin.xml配置说明http://www.apkplug.com/guide/#39 一下是我写的两个文件代码
[java]
public class SimpleBundle implements BundleActivator
{
private BundleContext mcontext = null;
public void start(BundleContext context) throws Exception
{
System.err.println("你号我是插件,我已经启动了 我的BundleId为:"+context.getBundle().getBundleId());
this.mcontext = context;
}
public void stop(BundleContext context)
{
System.err.println("你号我是插件,我被停止了 我的BundleId为:"+context.getBundle().getBundleId());
}
}
[xml]
<?xml version="1.0" encoding="UTF-8"?>
<plugin-features
Bundle-Name="myBundle"
Bundle-SymbolicName="com.example.mybundle"
Bundle-Version="1.0.0"
date="2013.10.223"
provider-name="插件开发商的名称"
provider-url=""
Bundle-Activator="com.examp
补充:移动开发 , Android ,