Android编译应用的 C 和 C++ 代码主要可以使用NDK-Build和CMake两种方式来进行,NDK-Build是基于Make构建系统来构建项目的,个人比较倾向于使用CMake的方式来构建,下面主要从CMake的方式进行说明
CMake可以和Gradle配合使用,也可以单独使用命令行的方式进行构建,我们这边主要研究Gradle是如何给我们设置这些版本信息的
NDK版本
NDK版本默认是根据你配置的Android Gradle插件版本(AGP)来选择的,
buildscript {
ext.kotlin_version = "1.5.0"
repositories {
google()
mavenCentral()
}
dependencies {
classpath "com.android.tools.build:gradle:4.2.1"
classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version"
// NOTE: Do not place your application dependencies here; they belong
// in the individual module build.gradle files
}
}
比如这个边配置的是4.2.1
classpath “com.android.tools.build:gradle:4.2.1”
下表说明了各个版本使用的NDK默认版本情况
Android Studio/Gradle 插件版本 | 为 AGP 版本指定的默认 NDK 版本 |
4.2 | 21.4.7075529 |
4.1 | 21.1.6352462 |
4.0 | 21.0.6113669 |
3.6 | 20.0.5594570 |
3.5以前 | 未指定默认版本,会选择最新下载的NDK版本 |
如果你需要修改默认的NDK版本,可以在模块的 build.gradle 文件中使用 android.ndkVersion 属性指定相应的版本,如下所示
android {
ndkVersion "major.minor.build" // e.g., ndkVersion "21.1.6352462"
}
或者可以通过在 Android Studio 项目根目录下的 local.properties 文件中,使用 ndk.dir 属性:
ndk.dir = /Users/ndkPath/ndk21 // Point to your own NDK
注意,该设置在不同AGP的版本下,还有着不同的一些设置方法,大家可以参考:
https://developer.android.google.cn/studio/projects/configure-agp-ndk?language=agp3-6#agp-version
CMake版本
AndroidStudio的SDK Manager中管理了3个版本的CMake,分别是
默认情况下,如果不进行设定CMake的版本,那么使用的是3.10.2的版本进行的构建,如果想要使用其他的CMake版本,则在模块的 build.gradle 文件中添加以下内容
android {
...
externalNativeBuild {
cmake {
...
version "cmake-version"
}
}
}
cmake-version 可以定义为3.18.1或是3.6.0,那么如果我们想要设置除了SDK Manager管理的这三个版本以外的版本行不行呢?
答案是可行的,我们来尝试一下,随便写一个版本号,注意,这边我们使用的AGP的版本先使用4.2
android {
...
externalNativeBuild {
cmake {
...
version "3.12.0"
}
}
}
同步一下Gradle,发现报错了,我们看一下错误信息
> Configure project :app
CMake '3.12.0' was not found in SDK, PATH, or by cmake.dir property.
- CMake '3.20.3' found in PATH did not satisfy requested version.
- CMake '3.10.2' found in SDK did not satisfy requested version.
- CMake '3.18.1' found in SDK did not satisfy requested version.
- CMake '3.6.0' found in SDK did not satisfy requested version.
CMake '3.12.0' was not found in SDK, PATH, or by cmake.dir property.
- CMake '3.20.3' found in PATH did not satisfy requested version.
- CMake '3.10.2' found in SDK did not satisfy requested version.
- CMake '3.18.1' found in SDK did not satisfy requested version.
- CMake '3.6.0' found in SDK did not satisfy requested version.
No valid CMake executable was found.
No valid CMake executable was found.
BUILD SUCCESSFUL in 3s
这边可以很明显的发现,Gradle会从SDK, PATH以及cmake.dir里去找你配置的版本,只要有一个地方找到了,就会使用,都没找到就会报错,我们分别来看看这几个地方
SDK
查找Android SDK路径下的cmake文件夹下对应的版本,如下
这边的文件夹名称对应的就是版本名称,这边的3.6.4111459,3.18.1,3.10.2.4988404就是sdkmanager管理的cmake版本
如需使用3.6.4111459,则在version中填写3.6.0即可
这边其他的一些版本是从cmake官网下载的https://cmake.org/download/,这边的版本也是可以让Gradle找到的,
如我这边cmake-3.14.7-win64-x64,如果我需要使用该版本,我只需要在version中填写3.14.7即可找到这个版本,
并且,你可以自己修改文件夹名称,
如3.14.0,我可以修改成3.14.1,相应的version中也填写3.14.1,也是可以找到的,当然其实他还是使用的3.14.0的版本进行的构建
PATH
查找环境变量中PATH中的value配置的cmake版本,如下,PATH中配置了CMake环境变量,我这边配置的是3.20.3的,所以在version中填写3.20.3,能够正确找到
cmake.dir
将其添加到项目的 local.properties 文件中,如下所示
# If you set this property, Gradle no longer uses PATH to find CMake.
cmake.dir=E\:\\ndk\\3.15.0
AGP版本的不同行为
上面提到的都是在AGP版本4.2的行为,在4.1,会有所不同,如下
dependencies {
classpath "com.android.tools.build:gradle:4.1.0"
classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version"
// NOTE: Do not place your application dependencies here; they belong
// in the individual module build.gradle files
}
CMake '3.14.7' was not found in PATH or by cmake.dir property.
- CMake '3.15.0' found from cmake.dir did not match requested version '3.14.7'.
- CMake '3.10.2' found in SDK did not match requested version '3.14.7'.
- CMake '3.18.1' found in SDK did not match requested version '3.14.7'.
- CMake '3.6.0' found in SDK did not match requested version '3.14.7'.
- CMake '3.20.3' found in PATH did not match requested version '3.14.7'.
可以看到,如果将Gradle版本修改为4.1.0,则其是不会找到我们自己放在SDK.cmake目录下的版本的
Ninja版本
默认情况下,如果是使用SDK Manager管理的那三个CMake版本,则不需要配置任何Ninja相关的配置,默认的Cmake已经包含了ninja的可执行程序
而如果是使用我们自行下载的CMake,则需要进行手动配置,有以下方式配置
手动放入ninja可执行程序
把ninja的可执行程序放入你使用的cmake的bin目录下即可,就和上面的默认情况一样的位置就行
通过环境变量配置
在PATH里面配置ninja可执行文件的路径即可,如果配置了cmake的环境变量在PATH中,可以直接将可执行文件丢到该配置中即可
通过Gradle配置进行配置
可以在模块的build.gradle中添加如下配置
defaultConfig {
........
externalNativeBuild {
cmake {
arguments("-DCMAKE_MAKE_PROGRAM=C:/Program Files/CMake/bin/ninja.exe")
}
}
}
这样就指定了ninja的版本了
另外,如果手动放入了ninja可执行程序,则会优先使用该ninja的版本进行构建,没有的话,会使用环境变量里面配置的ninja,再没有那就会报错了,
CMake Error: CMake was unable to find a build program corresponding to "Ninja". CMAKE_MAKE_PROGRAM is not set. You probably need to select a different build tool.
Configuring incomplete, errors occurred!
See also "C:/Users/Administrator/AndroidStudioProjects/NativeEvalDemo/app/.cxx/cmake/debug/x86/CMakeFiles/CMakeOutput.log".
当然,如果是进行了gradle配置,则会使用你配置的版本