美文网首页Android-NDK/JNI
AndroidStudio3.0环境,NDK使用CMake编So

AndroidStudio3.0环境,NDK使用CMake编So

作者: 我心若氺 | 来源:发表于2018-01-26 18:16 被阅读264次

    谷歌从AndroidStudio2.2以上就添加了Cmake方式来编译So库,
    这种方式比起原来命令行式的ndk-build方便了不少,
    也不需要Android.mk,Application.mk和JNI文件夹了。

    在下方的谷歌Android官方链接可以看到一个中文NDK的教程。
    https://developer.android.com/studio/projects/add-native-code.html
    而这个链接是谷歌Android官方英文Cmake指南
    https://developer.android.com/ndk/guides/cmake.html
    这俩都要认真上网才能看。

    Using Android Studio 2.2 and higher, you can use the NDK and CMake to compile C and C++ code into a native library. Android Studio then packages your library into your APK using Gradle, the IDE's integrated build system.

    先说一下具体环境,使用的是,Windows10 + AndroidStudio3.0

    新建一个NDK工程

    首先创建一个新项目,选中Include C++ support,因为是NDK项目嘛(见图1)
    然后一路点Next,可以选Empty Activity,Layout文件也不需要,
    因为是为了编So库嘛,不是为了做apk。(见图2,图3)
    最后则要选定C++标准,(比如C++11),异常,RTTI,(见图4)
    就完成了,非常简单。

    图片1.png 图片2.png 图片3.png 图片4.png

    CMake构建

    图片5.png
    工程完成后,先关注下新建好的工程的目录结构,(见图5)
    最主要看两个文件,app目录内的build.gradle和CMakeList.txt
    build.gradle是gradle构建的配置定义文件,这里就不展开讲了,只关注和CMake相关的。
    externalNativeBuild {
        cmake {
            cppFlags "-std=c++11 -frtti -fexceptions"
        }
    }
    
    externalNativeBuild {
        cmake {
            path "CMakeLists.txt"
        }
    }
    

    cppFlags是刚才选择的C++11,rtti和异常
    CMakeList.txt则是接下来重点讲的

    # For more information about using CMake with Android Studio, read the
    # documentation: https://d.android.com/studio/projects/add-native-code.html
    
    # 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.
    set(libs "${CMAKE_SOURCE_DIR}/libs")
    add_library( # Sets the name of the library.
                 native-lib
                 # Sets the library as a shared library.
                 SHARED
                 # Provides a relative path to your source file(s).
                 src/main/cpp/native-lib.cpp )
    # Searches for a specified prebuilt library and stores the path as a
    # variable. Because CMake includes system libraries in the search path by
    # default, you only need to specify the name of the public NDK library
    # you want to add. CMake verifies that the library exists before
    # completing its build.
    
    find_library( # Sets the name of the path variable.
                  log-lib
                  # Specifies the name of the NDK library that
                  # you want CMake to locate.
                  log )
    # Specifies libraries CMake should link to your target library. You
    # can link multiple libraries, such as libraries you define in this
    # build script, prebuilt third-party libraries, or system libraries.
    
    target_link_libraries( # Specifies the target library.
                           native-lib
    
                           # Links the target library to the log library
                           # included in the NDK.
                           ${log-lib} )
    

    cmake_minimum_required(VERSION 3.4.1)用来设置在编译本地库时我们需要的最小的cmake版本,AndroidStudio自动生成,我们几乎不需要自己管。
    以下是几个常用命令:
    set,CMake设置变量,变量在下面就可以使用
    add_library用来设置编译生成的本地库的名字为native-lib,SHARED表示编译生成的是动态链接库(这个概念前面已经提到过了),src/main/cpp/native-lib.cpp表示参与编译的文件的路径,这里面可以写多个文件的路径。
    find_library 是用来添加一些我们在编译我们的本地库的时候需要依赖的一些库,由于cmake已经知道系统库的路径,所以我们这里只是指定使用log库,然后给log库起别名为log-lib便于我们后面引用,此处的log库是我们后面调试时需要用来打log日志的库,是NDK为我们提供的。
    target_link_libraries 是为了关联我们自己的库和一些第三方库或者系统库,这里把我们把自己的库native-lib库和log库关联起来。
    set_target_properties 命令的意思是设置目标的一些属性来改变它们构建的方式。

    常见用法:
    1)设置输出路径
    set(CMAKE_LIBRARY_OUTPUT_DIRECTORY ${PROJECT_SOURCE_DIR}/src/main/libs/${ANDROID_ABI})
    修改So的生成路径至main/libs,与main/cpp同级。

    2)引用第三方库,通过set_target_properties,
    设置IMPORTED_LOCATION,就是被引入So库所在路径。

     add_library(usb-1.0.9
                 SHARED
                 IMPORTED
     )
     set_target_properties(usb-1.0.9
                           PROPERTIES IMPORTED_LOCATION
                          "${libs}/${ANDROID_ABI}/libusb-1.0.9.so")
    

    3)为子目录编译So库文件,
    有的时候,我们并不想把所有代码文件打包成单一个So,那么可以为子目录写一个CMakeList.txt,
    在这个子CMakeList.txt内,add_library,target_link_libraries,
    然后在主CMakeList.txt里加一句add_subdirectory(src/main/cpp/子目录路径),
    这样就会为子目录也生成一个So库文件,
    我们在主CMakeList.txt里可以像引用第三方库一样引用这个子目录了。
    更多:
    对多个So编译,这两篇文章写的很好的。
    分别是子目录多Module编译多个So库文件。我就不赘述了。
    子目录方式:http://blog.csdn.net/b2259909/article/details/58591898
    多Module方式:https://www.jianshu.com/p/4e3c0c20c244

    4)编译Debug版和Release版
    target_link_libraries可以附带debug,optimized的参数
    用法如下:

    target_link_libraries( # Specifies the target library.
                           native-lib
                           debug/optimized
                           # Links the target library to the log library
                           # included in the NDK.
                           ${log-lib} )
    

    target_link_libraries(< target> [item1 [item2 […]]] [[debug|optimized|general] < item>] …)
    这个更多的具体的用法,可以看后面附的CMake命令链接。

    5)CMake引入CpuFeatures库
    在CMakeList.txt里加这两句,然后就可以在target_link_libraries调用cpufeatures了

    include(AndroidNdkModules)
    android_ndk_import_module_cpufeatures()
    
    target_link_libraries( # Specifies the target library.
                           native-lib
                           cpufeatures
                           # Links the target library to the log library
                           # included in the NDK.
                           ${log-lib} )
    

    更进一步学习CMake
    https://www.zybuluo.com/khan-lau/note/254724
    这篇文章很好,翻译了https://cmake.org/cmake-tutorial/,和CMake的80个命令
    CMake的全部命令,官网链接:
    https://cmake.org/cmake/help/latest/manual/cmake-commands.7.html
    CMake的帮助文档,官网链接:
    https://cmake.org/cmake/help/latest/index.html

    最后,编译So库


    点击Make Project,各个ABI的So,就生成在相应的目录内了。

    相关文章

      网友评论

        本文标题:AndroidStudio3.0环境,NDK使用CMake编So

        本文链接:https://www.haomeiwen.com/subject/jauooxtx.html