【问题标题】:Create native library in android studio在 android studio 中创建原生库
【发布时间】:2023-03-28 13:00:01
【问题描述】:

我创建了支持 c++ 的 android studio 项目,并安装了本机开发工具包和其他所需工具。如何导入另一个预构建的本机库以包含在 c++ 代码中。我想做这样的事情

我已编辑 cmakelist.txt,如下所示,现在它在 cpp 文件夹下显示共享库。

cmake_minimum_required(VERSION 3.4.1)
set(distribution_DIR ${CMAKE_SOURCE_DIR}/../../../../distribution)
add_library(lib_gmath STATIC IMPORTED)
set_target_properties(lib_gmath PROPERTIES IMPORTED_LOCATION
${distribution_DIR}/gmath/lib/${ANDROID_ABI}/libgmath.a)
add_library(lib_gperf SHARED IMPORTED)
set_target_properties(lib_gperf PROPERTIES IMPORTED_LOCATION
${distribution_DIR}/gperf/lib/${ANDROID_ABI}/libgperf.so)
add_library(lib_ocr SHARED IMPORTED)
set_target_properties(lib_ocr PROPERTIES IMPORTED_LOCATION
${distribution_DIR}/ocr/lib/${ANDROID_ABI}/libLPROCR.so)
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=gnu++11")
add_library(hello-libs SHARED
        hello-libs.cpp)
target_include_directories(hello-libs PRIVATE
                       ${distribution_DIR}/gmath/include
                       ${distribution_DIR}/gperf/include)
target_link_libraries(hello-libs
                  android
                  lib_gmath
                  lib_gperf
                  lib_ocr
                  log)

但我无法在我的 c++ 代码中包含来自该预建库的类。

【问题讨论】:

  • @RichardCritten 我已经读过很多遍了,但我没有明白。它说给模块一个名称,然后编辑模块 android.mk 但我在项目结构中没有看到任何这样的东西。
  • 您在寻找 libLPROCR.so 的暴露 API 吗?
  • @AlexCohn 是的,可能是源代码。
  • 为什么你认为这个库可能对你有用?

标签: android c++ android-ndk ndk-build


【解决方案1】:

这里我应该提到几件事。

  1. 我建议切换到gradle+clang 来构建您的代码。 Android.mk 不知何故变老了,如果您开始新项目,最好使用更新的构建系统。
  2. 确保您的预构建库可以在 android 中使用。如果不是,则需要先构建它。例如,我自己构建了 openssl,因为我找不到合适的预构建库。

如果您使用的是gradle+cmake,这里有一个简单的CMakeLists.txt 文件,用于您的预建库:

cmake_minimum_required(VERSION 3.4.1)

add_library( core-api
             SHARED
             src/main/cpp/mysource.c )

# prebuilt libraries

add_library( crypto-lib
             STATIC
             IMPORTED )

set_target_properties( crypto-lib
                       PROPERTIES IMPORTED_LOCATION
                       ${CMAKE_CURRENT_SOURCE_DIR}/../prebuilt/crypto/${ANDROID_ABI}/lib/libcrypto.a )


include_directories( src/main/cpp/
                     ../prebuilt/crypto/common/include/
                     ../prebuilt/crypto/${ANDROID_ABI}/include/ )

# other libraries

find_library( log-lib
              log )

target_link_libraries( core-api
                       crypto-lib
                       ${log-lib} )

这是一个使用CMakeLists.txtgradle文件:

apply plugin: 'com.android.library'

android {
    compileSdkVersion rootProject.ext.sdkVersion

    defaultConfig {
        minSdkVersion 14
        targetSdkVersion 27

        externalNativeBuild {
            cmake {
                arguments "-DANDROID_TOOLCHAIN=clang", "-DANDROID_STL=c++_static"
                cFlags "-D__STDC_FORMAT_MACROS", "-fno-integrated-as"
            }
        }

        ndk {
            abiFilters "armeabi-v7a", "arm64-v8a", "x86", "x86_64"
        }
    }

    buildTypes {
        release {
            minifyEnabled true
            shrinkResources false
            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
        }

        debug {
            externalNativeBuild {
                cmake {
                    cFlags "-Wall","-DDEBUG"
                }
            }

            debuggable true
        }
    }

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

dependencies {
    implementation fileTree(dir: 'libs', include: ['*.jar'])
}

【讨论】:

  • 我正在使用 gradle+cmake 并编辑了与您类似的 cmakelist.txt。我可以在标记为共享库的 cpp 文件夹下看到预建库。预建库在其他项目中运行良好。但是如何在我的 c++ 代码中使用那个 lib 代码呢?我不能包含文件。我没有包含头文件,但只有 .so 文件。
  • 您确实需要包含标题。如果您导出了C++ 类,则找不到没有头文件的类。如果您确切知道名称,您可能会找到C 出口,但对于C++,您几乎找不到(这将非常困难)。如果您的预建库是共享的,您需要使用add_library(crypto-lib SHARED IMPORTED),我猜其他设置应该类似。
  • 好的,谢谢。我没有包含标题,但只有 .so 文件。如果可以找到该预建库的源代码,我将在网上查找。
猜你喜欢
  • 2022-11-17
  • 2018-06-11
  • 2018-09-10
  • 2023-03-24
  • 1970-01-01
  • 2017-04-14
  • 1970-01-01
  • 1970-01-01
  • 2013-06-30
相关资源
最近更新 更多