概述

  • Android Studio2.2开始支持使用CMake来构建NDK项目。

工具

  • NDK:这套工具集允许你为 Android使用C和C++代码,并提供众多平台库,让您可以管理原生Activity和访问物理设备组件。

  • CMake:一款外部构建工具,可与Gradle搭配使用来构建原生库。

  • LLDB:一个高性能的调试程序,Android Studio使用它来调试C代码。

  • 可通过SDK Manager来安装以上的工具。

    打开Android Studio,从菜单栏选择Tools -> Android -> SDK Manager。

    点击SDK Tools标签,再选中NDK、CMake和LLDB,最后点击Apply进行下载安装。

创建支持C/C++的新项目

  1. 在向导的Configure your new project部分,选中Include C++ Support复选框。

    导入C++支持
  2. 在向导的Customize C++ Support部分,可自定义C++支持。

    自定义C++支持-w380

    C++ Standard:使用哪种C++标准,默认为Toolchain Default,即使用默认的CMake设置。

    Exceptions Support:启用对C++异常处理的支持。Android Studio会将-fexceptions标志添加到CMake的gradle配置中。

    Runtime Type Information Support:支持RTTI。Android Studio会将-frtti标志添加到CMake的gradle配置中。

  3. 创建项目成功后,可看到项目/app下有一个CMakeLists.txt。它是CMake构建脚本,指定C/C++代码文件的编译。

  4. 同时可看到项目/app/build.gradle中有与CMake相关的gradle配置。

    android {    defaultConfig {        externalNativeBuild {            cmake {                cppFlags "-frtti -fexceptions"            }        }    }        externalNativeBuild {        cmake {            path "CMakeLists.txt"        }    }}

CMake构建脚本

指定CMake的版本号

# Sets the minimum version of CMake required to build your native library.cmake_minimum_required(VERSION 3.4.1)

创建原生库

  • 创建一个动态库,并往其中添加源文件。
add_library( # Sets the name of the library.             nativecode             # Sets the library as a shared library.             SHARED             # Provides a relative path to your source file(s).             src/main/cpp/api.c             src/main/cpp/entrance.c )
  • 创建一个静态库,并往其中添加源文件。
add_library( app-glue             STATIC             ${ANDROID_NDK}/sources/android/native_app_glue/android_native_app_glue.c )

指定头文件的路径

# Specifies a path to native header files.include_directories(src/main/cpp/include/)

添加NDK API

# 此处为引用Android的日志支持库log,并将其路径存为log-lib变量。find_library( # Defines the name of the path variable that stores the              # location of the NDK library.              log-lib              # Specifies the name of the NDK library that              # CMake needs to locate.              log )

关联库

  • 将多个库关联起来。
# Links your native library against one or more other native libraries.target_link_libraries( native-lib app-glue ${log-lib} )

添加其他预构建库

  • 添加一个预构建库与上面为CMake指定要创建原生库类似。区别在于此库已经预先构建,不用添加源文件,而使用IMPORTED标志告知CMake将库导入。
add_library( imported-lib             SHARED             IMPORTED )
  • 指定预构建库的路径。
set_target_properties( # Specifies the target library.                       imported-lib                       # Specifies the parameter you want to define.                       PROPERTIES IMPORTED_LOCATION                       # Provides the path to the library you want to import.                       src/main/cpp/ext/imported-lib/${ANDROID_ABI}/libimported-lib.so )
  • 指定预构建库的头文件的路径。
include_directories( src/main/cpp/ext/imported-lib/include/ )
  • 将预构建库关联到自己创建的原生库上。
target_link_libraries( native-lib app-glue ${log-lib} imported-lib )

Gradle配置

Gradle与原生库关联

android {    externalNativeBuild {        cmake {            path "CMakeLists.txt"        }    }}

指定可选配置

android {    defaultConfig {        externalNativeBuild {            cmake {                // 传递可选参数给CMake                arguments "-DANDROID_PLATFORM=android-8", "-DANDROID_ARM_NEON=TRUE", "-DANDROID_TOOLCHAIN=clang"                // 为C编译器设置可选标志                cFlags "-D_EXAMPLE_C_FLAG1", "-D_EXAMPLE_C_FLAG2"                // 设置标志来支持C++编译器的格式化宏常量。                cppFlags "-frtti -fexceptions", "-D__STDC_FORMAT_MACROS"            }        }    }}
  • 如果你的CMake定义多个原生库,你可以使用targets属性仅为给定ProductFlavor构建和打包这些库中的一部分。
android {    productFlavors {        demo {            externalNativeBuild {                cmake {                    targets "native-lib-demo"                }            }        }    }}

指定ABI

  • 默认情况下,Gradle会针对NDK支持的ABI,将你的原生库构建成一个个支持特定ABI的.so文件,并将它们全部打包到APK中。

  • 可使用android.defaultConfig.ndk.abiFilters来指示Gradle要构建和打包的ABI版本。

android {    defaultConfig {        ndk {            abiFilters 'armeabi', 'armeabi-v7a', 'x86'        }    }}
  • 可使用android.defaultConfig.externalNativeBuild.cmake.abiFilters来单独指示CMake输出的ABI版本。但最终打包进APK的ABI版本还是由ndk.abiFilters决定。
android {    defaultConfig {        externalNativeBuild {            cmake {                abiFilters 'armeabi', 'armeabi-v7a', 'x86'            }        }    }}

CMake的单元测试

  • 使用JUnit在instrumentation testing中(即androidTest目录下)进行单元测试。
@RunWith(AndroidJUnit4.class)public class NDKUtilTest {        @Test    public void test() {        String libName = NDKUtil.getName();        Log.e("NDKUtil", libName);    }}

我的博客

更多相关文章

  1. Android(安卓)Studio配置文件路径修改
  2. Windows下NDK开发环境搭建,Eclipse+ADT+CDT+MINGW+NDK
  3. 三、android编译cmake工程
  4. android操作文件
  5. 修改Android(安卓)Media Scanner的扫描路径
  6. Android(安卓)Studio安装过程中出现Failed to install Intel HAX
  7. Android(安卓)Eclipse导入源码时对自己新增的class文件提示"XXX
  8. 使用Android(安卓)隐藏API和内部 API
  9. Android使用FFmpeg 解码H264并播放(一)

随机推荐

  1. android快速上手(二)android开发环境搭建及
  2. android 多线程
  3. 手把手搭建 android 开发环境||资源打包
  4. 《Android》Lesson15-学段复习
  5. [读书笔记] Android(安卓)Toast 显示时间
  6. Android原生SpeechRecognizer(语音识别)
  7. 【Android】NDK的使用常见问题
  8. TextView属性大全
  9. 从UA类型设备分辨出Android设备类型
  10. xmlns:android和xmlns:mi