JNI开发第一个HellowWorld程序

admin 2022年5月16日09:30:07评论21 views字数 3705阅读12分21秒阅读模式

一、前言

    
      本文将创建一个 HelloWorld 程序,程序功能很简单,就是一个 jni 方法返回" HelloWorld "字符串,然后界面展示。 jni 中涉及动态注册和静态注册,在 实际开发过程中动态注册用的比较多,本工程 采用动态注册方式实现。 Android Studio jni 代码可以通过 ndk 或者 cmake 工具链进行编译。 在本工程中两种方式都进行了配置测试。
    本文中的Demo工程可以作为jni开发过程中最基础的模板。

二、前置准备


     在开发之前请安装好 Android Studio 开发工具,并配置好 cmake ndk 工具。 Android Studio 中 cmake和ndk配置可参考:

安卓ndk开发实战(1)Android Studio 中配置 ndk 和 cmake 工具



三、开发jni程序HelloWorld


      (1)、Android Studio创建工程JNIDemoHelloWorld01的简单Activity应用

      (2)、在工程根目录app/src/main中创建cpp目录保存jni代码

JNI开发第一个HellowWorld程序

(3)、在cpp目录下创建HellWorld.cpp文件已经对应的cmake编译配置、ndk编译配置文件,如下所示:

JNI开发第一个HellowWorld程序

(4)、在工程中的MainActivity中添加native方法,该方法返回字符串。 如下所示:
   
 private  static native String  helloWorld();
(5)、HellWorld.cpp中实现jni方法helloWorld,以下是关键代码:
//jni方法hellWorld对应的逻辑实现static jstring myhelloWorld(JNIEnv *env, jclass cls) {    return env->NewStringUTF("HelloWorld");}//static JNINativeMethod jniHelloWorl[] = {        {                "helloWorld",                "()Ljava/lang/String;",                (void *) myhelloWorld        }};

static bool registerNativeMethods(JNIEnv *env, const char *className, JNINativeMethod *jniMethods, int methods) { jclass clazz = env->FindClass(className); if (clazz == NULL) { return false; }
return env->RegisterNatives(clazz, jniMethods, methods) >= 0;}

//JNI_OnLoad里面完成jni方法的注册JNIEXPORT jint JNICALL JNI_OnLoad(JavaVM *vm, void *reserved) {

int jniMethodSize = sizeof(JNINativeMethod); JNIEnv *env = NULL; if (vm->GetEnv((void **) &env, JNI_VERSION_1_6) != JNI_OK) { return -1; } if (!registerNativeMethods(env, CLASS_NAME, jniHelloWorl, sizeof(jniHelloWorl) / jniMethodSize)) { return -1; } LOGD("JNI Loaded");
return JNI_VERSION_1_6;}

(6)、分别配置Android.mk文件和CMakeLists.txt

     Android.mk文件配置如下:

LOCAL_PATH := $(call my-dir)include $(CLEAR_VARS)LOCAL_MODULE := helloworldLOCAL_CFLAGS += -Wno-error=format-security -fpermissive -O2LOCAL_CFLAGS += -fno-rtti -fno-exceptionsLOCAL_CPPFLAGS += -std=c++11
LOCAL_SRC_FILES := HelloWorld.cpp
LOCAL_LDLIBS := -llog
include $(BUILD_SHARED_LIBRARY)

  CMakeLists.txt配置如下:

cmake_minimum_required(VERSION 3.4.1)project(helloworld)
add_definitions(-std=c++11)
set(${PROJECT_NAME}_SOURCES HelloWorld.cpp )
add_library(${PROJECT_NAME} SHARED ${${PROJECT_NAME}_SOURCES})
target_link_libraries(${PROJECT_NAME} log)


(7)、将Android.mk和CMakeLists.txt加入build.gradle文件

     在实际选择ndk方式还是cmake方式编译的时候,可以在build.gradle中注释掉不需要的编译方式即可。如下是build.gradle的完整内容:

plugins {    id 'com.android.application'}
android { compileSdkVersion 30 buildToolsVersion "30.0.2"
defaultConfig { applicationId "com.android.jnidemo01" minSdkVersion 23 targetSdkVersion 30 versionCode 1 versionName "1.0"
testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
externalNativeBuild {            //cmake编译方式参数配置 cmake { arguments "-DCMAKE_BUILD_TYPE=Release -DDEBUG=1" }            //ndk编译参数配置 ndkBuild { abiFilters 'armeabi-v7a', 'arm64-v8a' } }

}
buildTypes { release { minifyEnabled false proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro' } } compileOptions { sourceCompatibility JavaVersion.VERSION_1_8 targetCompatibility JavaVersion.VERSION_1_8 }    //以下配置比较重要,cmake如果不注释就是使用cmake编译    //ndkBuild如果不注释就是使用ndk方式编译 externalNativeBuild {// cmake {// path file('src/main/cpp/CMakeLists.txt')// } ndkBuild { path file("src/main/cpp/Android.mk") } }}
dependencies {
implementation 'androidx.appcompat:appcompat:1.2.0' implementation 'com.google.android.material:material:1.2.1' implementation 'androidx.constraintlayout:constraintlayout:2.0.4' testImplementation 'junit:junit:4.+' androidTestImplementation 'androidx.test.ext:junit:1.1.2' androidTestImplementation 'androidx.test.espresso:espresso-core:3.3.0'}


(8)、加载helloworld动态库

     在MainActivity类中,加入如下代码完成helloworld动态库的加载

static {    System.loadLibrary("helloworld");}

(9)、调用helloWorld方法测试验证

     本Demo比较简单,直接调用jni方法,然后界面显示返回的字符串。测试关键代码如下:

 textViewShowMsg=(TextView)findViewById(R.id.textViewShowMsg);textViewShowMsg.setText("测试jni返回结果:"+helloWorld());

手机运行结果如下:

JNI开发第一个HellowWorld程序



      如果你需要本文中的Demo工程,请访问如下地址进行下载:

https://gitee.com/ZL007/jnidemo01-hello-world


JNI开发第一个HellowWorld程序  

原文始发于微信公众号(哆啦安全):JNI开发第一个HellowWorld程序

  • 左青龙
  • 微信扫一扫
  • weinxin
  • 右白虎
  • 微信扫一扫
  • weinxin
admin
  • 本文由 发表于 2022年5月16日09:30:07
  • 转载请保留本文链接(CN-SEC中文网:感谢原作者辛苦付出):
                   JNI开发第一个HellowWorld程序http://cn-sec.com/archives/787159.html

发表评论

匿名网友 填写信息