android 添加jni函数

在android-4.0.4版本中添加:
—————————————

vim frameworks/base/core/java/android/util/Javahello.java

============================================================================
Javahello.java如下:
package android.util;  //这句在生成.h文件之后在加上。
public final class Javahello{
    static {
        System.loadLibrary("javahello");                                //这个javahello是JNI层需要实现的动态库  makefile里的LOCAL_MODULE=libjavahello
    }
    /** @hide */    public static native String native_hello();
    /** @hide */    public static native int native_add(int x,int y);
}
============================================================================

javac Javahello.java  编译出Javahello.class,没有什么用这个文件。
javah Javahello        编译出Javahello.h  JNI的接口函数声明在里面, 一会在JNI层实现接口函数 native_hell()和native_add()。Javahello.h是编译出来的,不需要修改。
============================================================================
Javahello.h如下:
/* DO NOT EDIT THIS FILE - it is machine generated */
#include <jni.h>
/* Header for class Javahello */

#ifndef _Included_Javahello
#define _Included_Javahello
#ifdef __cplusplus
extern "C" {
#endif
/*
 * Class:     Javahello
 * Method:    native_hello
 * Signature: ()Ljava/lang/String;
 */
JNIEXPORT jstring JNICALL Java_Javahello_native_1hello
  (JNIEnv *, jclass);

/*
 * Class:     Javahello
 * Method:    native_add
 * Signature: (II)I
 */
JNIEXPORT jint JNICALL Java_Javahello_native_1add
  (JNIEnv *, jclass, jint, jint);

#ifdef __cplusplus
}
#endif
#endif
============================================================================

mkdir frameworks/base/native_hello/  创建自己JNI层的源码目录
[jiajiandong@jiajiandong android-4.0.4]$ cd frameworks/base/native_hello/
[jiajiandong@jiajiandong native_hello]$ ls
  Android.mk  include  src
[jiajiandong@jiajiandong native_hello]$ tree .
.
|-- Android.mk
|-- include
|   `-- Javahello.h
`-- src
    `-- jni
        `-- native_hello.c


============================================================================
Android.mk如下:   
LOCAL_PATH := $(call my-dir)     获取当前路径
include $(CLEAR_VARS)              清除变量值
LOCAL_MODULE_TAGS := eng    关于编译的等级
LOCAL_SRC_FILES :=      \          源码文件
    src/jni/native_hello.c
LOCAL_C_INCLUDES :=         \    C语言头文件位置
    $(LOCAL_PATH)/include   \
    $(JNI_H_INCLUDE)    \
LOCAL_MODULE := libjavahello    模块名
include $(BUILD_SHARED_LIBRARY)   编译成什么  这个是shared_library,动态链接库
============================================================================
native_hello.c如下:
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <jni.h>
#include <assert.h>
/*
 *  * Class:     Javahello
 *   * Method:    native_hello
 *    * Signature: ()Ljava/lang/String;
 *     */
JNIEXPORT jstring JNICALL Java_Javahello_native_1hello(JNIEnv *env, jclass clazz){
    printf("hello in c native code.\n");
    return (*env)->NewStringUTF(env,"hello world returned.");        //返回一个字符串
}
/*
 *  * Class:     Javahello
 *   * Method:    native_add
 *    * Signature: (II)I
 *     */
JNIEXPORT jint JNICALL Java_Javahello_native_1add(JNIEnv *env, jclass clazz, jint x, jint y){
    return x+y;
}
static JNINativeMethod gMethods[] = {                     //gMethods里的函数会被注册到env的一个泛型队列内
    {"native_hello","()Ljava/lang/String;",(void*)Java_Javahello_native_1hello},
    {"native_add","(II)I",(void*)Java_Javahello_native_1add},                     //注册    (II)I可以在头文件找到
};
static int registerNativeMethods(JNIEnv* env, const char* className,
    JNINativeMethod* gMethods, int numMethods)
{
    jclass clazz;
    clazz = (*env)->FindClass(env, className);
    if (clazz == NULL)
        return JNI_FALSE;
    if ((*env)->RegisterNatives(env, clazz, gMethods, numMethods) < 0)
        return JNI_FALSE;
    return JNI_TRUE;
}
/*
 *  * Register native methods for all classes we know about.
 *   */
static int registerNatives(JNIEnv* env)
{
    if (!registerNativeMethods(env, " android/util/Javahello",                      //这里注册gMethods   类在系统中的位置。
            gMethods, sizeof(gMethods) / sizeof(gMethods[0])))
        return JNI_FALSE;
    return JNI_TRUE;
}
jint JNI_OnLoad(JavaVM* vm, void* reserved)
{
    JNIEnv* env = NULL;
    jint result = -1;
    printf("Entering JNI_OnLoad\n");
    if ((*vm)->GetEnv(vm, (void**) &env, JNI_VERSION_1_4) != JNI_OK)
        goto bail;
    assert(env != NULL);
    if (!registerNatives(env))
        goto bail;
    /* success -- return valid version number */
    result = JNI_VERSION_1_4;
bail:
    printf("Leaving JNI_OnLoad (result=0x%x)\n", result);
    return result;
}
============================================================================

然后编译。
之后就可以像使用普通的java类一样的使用Javahello类,


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
JNI(Java Native Interface)是一种允许Java代码与本地代码(如C或C++)交互的编程桥梁。在Android Studio中使用JNI可以调用本地代码来实现一些高性能的功能或访问底层系统资源。 要在Android Studio中使用JNI,首先需要创建一个JNI接口文件(.h),该文件将定义Java和本地代码之间的函数接口。然后,使用ndk-build工具或CMake配置来构建本地代码库。 下面是一个简单的步骤来使用JNI: 1. 在Android Studio项目中,创建一个名为"jni"的文件夹,并在其中创建一个名为"native-lib.cpp"的C++源文件。 2. 在native-lib.cpp中实现自己的本地函数,可以通过JNI调用这些函数。 ```cpp #include <jni.h> extern "C" JNIEXPORT jstring JNICALL Java_com_example_myapp_MainActivity_getMessageFromJNI(JNIEnv* env, jobject /* this */) { return env->NewStringUTF("Hello from JNI!"); } ``` 3. 在项目的build.gradle文件中,添加NDK配置。 ```groovy android { // ... defaultConfig { // ... externalNativeBuild { cmake { cppFlags "" } } } // ... externalNativeBuild { cmake { path "CMakeLists.txt" } } } ``` 4. 在项目根目录下创建一个名为"CMakeLists.txt"的文件,并设置构建本地代码的相关设置。 ```cmake cmake_minimum_required(VERSION 3.4.1) add_library(native-lib SHARED native-lib.cpp) find_library(log-lib log) target_link_libraries(native-lib ${log-lib}) ``` 5. 在MainActivity.java中,加载本地库并调用本地函数。 ```java public class MainActivity extends AppCompatActivity { static { System.loadLibrary("native-lib"); } // ... public native String getMessageFromJNI(); // ... @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); // 调用本地函数 String message = getMessageFromJNI(); Log.d("JNI", message); } } ``` 这样就可以在Android Studio中使用JNI来调用本地代码了。需要注意的是,使用JNI需要熟悉C/C++编程,并且需要手动管理Java和本地代码之间的内存和类型转换。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值