基於外掛程式開發的Android實現流程

來源:互聯網
上載者:User

 

本文記述“柯元旦”Android核心剖析中基於類裝載器的“外掛程式”架構。

外掛程式的概念:

1、外掛程式不能獨立運行,而必須運行於一個宿主程式中,即由宿主程式去調用外掛程式程式。

2、外掛程式一般可以獨安裝。

3、宿主程式中可以管理不同的外掛程式,包括查看外掛程式的數目,禁用或者使用某個外掛程式。

4、宿主程式應該保證外掛程式的向下相容性,即新版本的宿主程式可以運行較老版本的外掛程式。

下面詳細看一下這種架構:

1、宿主程式:

建立Android項目PluginDevAndroid

 

2、外掛程式項目1:Plugin1

3、外掛程式項目2:

4、綜述:

4.1、介面類一般定義在宿主專案中,比如本例中的IPluginDev.java

4.2、外掛程式項目需要應用IPluginDev時,則必須通過一個外部的jar包,並且該jar包是以Library的形式被添加到Plugin項目的build Path,而不是以“外部的”jar方式添加。

4.3、宿主程式想要知道系統中有哪些外掛程式,可以定義一個Action,本例中使用的是如下action。

這樣的話,宿主程式就可以通過PackageManager類的queryIntentActivities函數查詢相關的外掛程式的列表了。

得到了外掛程式的PackageName,就可以訪問外掛程式的資源內容。例如:

 

Resources res = pm.getResourcesForApplication(packageName);int id = 0;id = res.getIdentifier(version, string, packageName);String version = res.getString(id);Log.d(hlwang, MainActivity test version is:+version);
這段代碼中,首先擷取外掛程式的Resource對象,接著得到名稱為version欄位的字串id值,然後再調用getString獲得該變數的值,於是宿主程式就知道外掛程式程式中的資源內容了。

 

 

關鍵代碼:

 

private void test(){Intent intent = new Intent(com.example.plugindevandroid.plugin,null);final PackageManager pm = getPackageManager();final List plugins = pm.queryIntentActivities(intent, 0);for(ResolveInfo r:plugins){ActivityInfo activityInfo = r.activityInfo;String div = System.getProperty(path.separator);String packageName = activityInfo.packageName;String packageName0 = getPackageName();String dexPath = activityInfo.applicationInfo.sourceDir;String dexOutputDir1 = activityInfo.applicationInfo.dataDir;String dexOutputDir2 = getApplicationInfo().dataDir;String libPath = activityInfo.applicationInfo.nativeLibraryDir;Log.d(hlwang, MainActivity test div is:+div+,packageName is:+packageName+,packageName0 is:+packageName0+,dexPath is:+dexPath+,dexOutputDir1 is:+dexOutputDir1+,dexOutputDir2 is:+dexOutputDir2+,libPath is:+libPath);DexClassLoader dexCl = new DexClassLoader(dexPath, dexOutputDir2, libPath, getClassLoader());Log.d(hlwang, MainActivity test clazzName is:+packageName+.PluginVersion);try{Class clazz = dexCl.loadClass(packageName+.PluginVersion);IPluginDev plugin = (IPluginDev) clazz.newInstance();String name = plugin.getName();Log.d(hlwang, MainActivity test name is:+name);Resources res = pm.getResourcesForApplication(packageName);int id = 0;id = res.getIdentifier(version, string, packageName);String version = res.getString(id);Log.d(hlwang, MainActivity test version is:+version);PluginObject p = new PluginObject();p.name = name;p.version = version;Log.d(hlwang, MainActivity test p is:+p);mList.add(p);}catch(Exception e){Log.d(hlwang, MainActivity exception eeeeeeeeeeeee);e.printStackTrace();}}Log.d(hlwang, MainActivity test list size is:+mList.size());setListAdapter(new ArrayAdapter(this,                android.R.layout.simple_list_item_1, mList));}
這段代碼中,首先得到外掛程式的List列表。

 

然後得到外掛程式的packageName,以及外掛程式的dexPath目錄。

再次,得到dexOutputDir目錄。

libPath一般只c/c++使用的庫檔案。

 

DexClassLoader的參數意義:

dexPath:外掛程式apk或者jar包檔案的路徑

dexOutputDir:將目標apk或者jar包解壓的檔案的存放目錄。因為宿主程式只對本應用程式所在的目錄由存取許可權。


運行:

 

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.