最近使用AndroidStudio的最新ndk编译方式cMake来编译底层cpp文件,因为以前没有接触过cMake语法,先附上官方学习文档地址:https://developer.android.com/ndk/guides/cmake.html,以及友情中文翻译网址:https://www.zybuluo.com/khan-lau/note/254724;html
底层c文件一大堆,以下图所示java
问题一:android
其中native-lib.cpp是提供对外接口的,因此对其余文件的依赖都写在了该文件中,接下来直接编译吗?no,那样你会获得编译错误,在native-lib.cpp中找不到其余c文件里边的函数。因此是cMake编译的时候没有把那些c文件编译进去,这样要去CMakeLists.txt中去添加文件了。c++
未修改以前的CMakeLists.txt文件内容是这样的:ide
# Sets the minimum version of CMake required to build the native library. cmake_minimum_required(VERSION 3.4.1) # Creates and names a library, sets it as either STATIC # or SHARED, and provides the relative paths to its source code. # You can define multiple libraries, and CMake builds them for you. # Gradle automatically packages shared libraries with your APK. add_library( # Sets the name of the library. native-lib # Sets the library as a shared library. SHARED EXCLUDE_FROM_ALL # Provides a relative path to your source file(s). src/main/cpp/native-lib.cpp )
学习CMake的官方文档能够知道,其中的add_library()正是设置生成包的地方,这里只有native-lib.cpp一个文件,理论上应该要包括其余那些的,那么加上其余那几个文件就行了吧?是能够这样,可是那么多文件,未免也太长了吧,固然CMake确定预料到这种问题了,因此咱们能够get一个新技能,使用aux_source_directory(),在源文件位置添加文件列表,而不是单个文件,get修改以后的文件内容以下:函数
# Sets the minimum version of CMake required to build the native library. cmake_minimum_required(VERSION 3.4.1) # Creates and names a library, sets it as either STATIC # or SHARED, and provides the relative paths to its source code. # You can define multiple libraries, and CMake builds them for you. # Gradle automatically packages shared libraries with your APK. aux_source_directory(src/main/cpp SRC_LIST) add_library( # Sets the name of the library. native-lib # Sets the library as a shared library. SHARED EXCLUDE_FROM_ALL # Provides a relative path to your source file(s). #src/main/cpp/native-lib.cpp ${SRC_LIST} )
这样子改完须要Synchronize同步一下,这样就能够从新编译了。学习
问题二:ui
在编译经过以后,运行调用底层代码,结果程序崩溃了,提示java.lang.UnsatisfiedLinkError: Native method not found: ***;好吧,没有找到这个底层方法?但是明明已经生成了,仔细观察上图代码结构能够发现,因为AndroidStudio自动生成的底层文件是.cpp的,也就是使用了c++的语法规则,而其余的底层文件都是.c的使用的c语言规则,他们二者之间仍是有区别的,如今须要在cpp文件中调用c文件,那么要在cpp文件中作些修改,首先头文件包含c的是相同的,不一样点是在使用c文件中的函数上方,加一行 extern "C" 便可。这样从新编译运行,一切正常!spa