標籤:
現在Android Studio已經是1.x版本了,其功能也是越來越完善,個人感覺AS還是蠻好用的,現在也是越來越多的公司轉向使用AS了,使用方便是一個因素,Google官方不在支援eclipse也是一個因素,不管怎麼樣吧,反正就是要轉向使用AS了,正好,前段時間,我所在的公司也要轉向AS。折騰了一段時間後,想想還是寫下這篇文章,分享一下在eclipse轉AS時,NDK編譯的問題。
gradle是多平台的編譯語言,不知道為啥,在android上對ndk的支援一直都不太好,雖然現在簡單的工程是可以正常編譯了,但是如果NDK部分比較複雜的話,那就頭痛了,至少,目前我發現使用gradle構建是沒有辦法編譯靜態庫的。也可能是官方的文檔我沒有看的太詳細,如果有誰知道如何使用gradle編譯NDK的靜態庫,煩請告知,謝謝。
正好,我所開發的程式動態庫的部分比較複雜,多個需求gradle是無法滿足的,剛開始的時候沒有什麼頭緒,到處找解決方案,有找到幾種方法,對比了一下,發現有一種方法基本上是無縫對接,也沒有什麼複雜的操作,所以就用它了,現在把方法貼出來,給有需要的人,避免走彎路。
- local.properties中增加ndk.dir,設定ndk的路徑
- eclipse工程中的jni目錄拷貝到src/main目錄下
- android{}中增加sourceSets.main.jni.srcDirs = [] 和sourceSets.main.jniLibs.srcDir ‘src/main/libs‘
- build.gradle中增加如下代碼
tasks.withType(JavaCompile) { compileTask -> compileTask.dependsOn ndkBuild}task ndkBuild(type: Exec) { workingDir file(‘src/main/jni‘) commandLine getNdkBuildCmd()}task cleanNative(type: Exec){ workingDir file(‘src/main/jni‘) commandLine getNdkBuildCmd(), ‘clean‘}clean.dependsOn cleanNativedef getNdkDir() { if (System.env.ANDROID_NDK_ROOT != null) return System.env.ANDROID_NDK_ROOT Properties properties = new Properties() properties.load(project.rootProject.file(‘local.properties‘).newDataInputStream()) def ndkdir = properties.getProperty(‘ndk.dir‘, null) if (ndkdir == null) throw new GradleException("NDK location not found. Define location with ndk.dir in the local.properties file or with an ANDROID_NDK_ROOT environment variable.") return ndkdir}def getNdkBuildCmd() { def ndkbuild = getNdkDir() + "/ndk-build" ndkbuild += ".cmd" return ndkbuild}
就這麼簡單,搞定。加入這些任務之後,編譯流程變成了,clean操作之前會先執行ndk-build clean任務,編譯動作之前會先執行ndk-build任務,這樣就確保了編譯執行gradle clean的時候回執行ndk-build clean操作,在編譯開始之前執行ndk-build操作,確保所有的動態庫都已經編譯出來,而且在目錄src/main/libs中,然後在編譯apk的時候,直接使用src/main/libs中的動態庫進行打包。
最後執行一下gradle clean build,日誌中我們可以看到ndk-build clean和ndk-build命令都有運行,out目錄下產生的apk中也有相應的動態庫。
2015.12.28
------End------
Android Studio使用eclipse工程編寫的Android.mk檔案