本文记录一个Java层与JNI层参数与数据交互的应用程序开发过程,为实现一个功能完整的带Java与JNI的应用程序打下基础。本文假设读者已搭建好Android的Eclipse与NDK开发环境,包括通过ADB连接手机的配置。
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/hello_world" /> 其中的字符串就定义在res文件夹下values文件夹中的strings.xml中。我们对hello_world的值做修改,如下:<?xml version="1.0" encoding="utf-8"?>
<resources>
<string name="app_name">app</string>
<string name="action_settings">Settings</string>
<string name="hello_world">Napolean: Hello Android Application!</string>
</resources> 根据需要,可以将上图中模拟应用界面的左边栏中的控件拖入模拟应用界面上放置,相应地,XML文件中就会有该控件的布局描述。package com.napolean.app;
import android.os.Bundle;
import android.app.Activity;
import android.view.Menu;
public class MainActivity extends Activity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.main, menu);
return true;
}
} 插入手机连接上ADB,或者配置一个Android模拟器,点击运行程序,即可看到应用程序运行并显示我们所修改的字符串。关于手机如何通过ADB连接以及Android模拟器的配置,在此不作展开。package com.napolean.app;
public class NativeInterface {
private native void native_init();
private native void native_exit();
private native byte[] native_process(byte[] in_buffer, int width, int height);
public void NativeInit() {
native_init();
}
public void NativeExit() {
native_exit();
}
public void NativeProcess(byte[] in_buffer, int width, int height)
{
native_process(in_buffer, width, height);
}
static {
System.loadLibrary("NativeInterface");
}
}javah -classpath bin/classes -d jni com.napolean.app.NativeInterface运行命令后,在jni文件夹下就会生成一个名为com_napolean_app_NativeInterface.h的头文件,里面包含有的接口函数如下:
/* DO NOT EDIT THIS FILE - it is machine generated */
#include <jni.h>
/* Header for class com_napolean_app_NativeInterface */
#ifndef _Included_com_napolean_app_NativeInterface
#define _Included_com_napolean_app_NativeInterface
#ifdef __cplusplus
extern "C" {
#endif
/*
* Class: com_napolean_app_NativeInterface
* Method: native_init
* Signature: ()V
*/
JNIEXPORT void JNICALL Java_com_napolean_app_NativeInterface_native_1init
(JNIEnv *, jobject);
/*
* Class: com_napolean_app_NativeInterface
* Method: native_exit
* Signature: ()V
*/
JNIEXPORT void JNICALL Java_com_napolean_app_NativeInterface_native_1exit
(JNIEnv *, jobject);
/*
* Class: com_napolean_app_NativeInterface
* Method: native_process
* Signature: ([BII)[B
*/
JNIEXPORT jbyteArray JNICALL Java_com_napolean_app_NativeInterface_native_1process
(JNIEnv *, jobject, jbyteArray, jint, jint);
#ifdef __cplusplus
}
#endif
#endif
生成这个头文件的目的是免去手动编写JNI层的接口函数,并无其它用途,使用后可删除。在jni文件夹下创建NativeInterface.cpp,将上述头文件中所有内容拷入,经过改造,如下:#include <jni.h>
#include <android/log.h>
#define LOG_TAG "APP"
#define LOGI(...) __android_log_print(ANDROID_LOG_INFO, LOG_TAG, __VA_ARGS__)
#define LOGE(...) __android_log_print(ANDROID_LOG_ERROR, LOG_TAG, __VA_ARGS__)
#ifndef _Included_com_napolean_app_NativeInterface
#define _Included_com_napolean_app_NativeInterface
#ifdef __cplusplus
extern "C" {
#endif
/*
* Class: com_napolean_app_NativeInterface
* Method: native_init
* Signature: ()V
*/
JNIEXPORT void JNICALL Java_com_napolean_app_NativeInterface_native_1init
(JNIEnv *, jobject)
{
LOGI("APP native init.");
}
/*
* Class: com_napolean_app_NativeInterface
* Method: native_exit
* Signature: ()V
*/
JNIEXPORT void JNICALL Java_com_napolean_app_NativeInterface_native_1exit
(JNIEnv *, jobject)
{
LOGI("APP native exit.");
}
/*
* Class: com_napolean_app_NativeInterface
* Method: native_process
* Signature: ([BII)[B
*/
JNIEXPORT jbyteArray JNICALL Java_com_napolean_app_NativeInterface_native_1process
(JNIEnv *, jobject, jbyteArray, jint, jint)
{
LOGI("APP native process.");
}
#ifdef __cplusplus
}
#endif
#endif
上述改造的代码主要是将函数声明改为函数定义,并且添加了打印信息的支持。/home/work/android/android-ndk-r9/platforms/android-18/arch-arm/usr/include/ /home/work/android/android-ndk-r9/sources/cxx-stl/gnu-libstdc++/4.6/include/ /home/work/android/android-ndk-r9/sources/cxx-stl/gnu-libstdc++/4.6/libs/armeabi-v7a/include/ /home/work/android/android-ndk-r9/toolchains/arm-linux-androideabi-4.6/prebuilt/linux-x86/lib/gcc/arm-linux-androideabi/4.6/include/
LOCAL_PATH := $(call my-dir) include $(CLEAR_VARS) LOCAL_MODULE := NativeInterface LOCAL_SRC_FILES := NativeInterface.cpp LOCAL_LDLIBS := -llog include $(BUILD_SHARED_LIBRARY)
package com.napolean.app;
import android.os.Bundle;
import android.app.Activity;
import android.view.Menu;
public class MainActivity extends Activity {
private NativeInterface myJNI;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
byte[] in_buffer = new byte[1920*1080*3/2];
int width = 1920;
int height = 1080;
myJNI = new NativeInterface();
myJNI.NativeInit();
myJNI.NativeProcess(in_buffer, width, height);
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.main, menu);
return true;
}
protected void onDestroy() {
myJNI.NativeExit();
super.onDestroy();
}
}
基于Eclipse的Android JNI层测试应用开发过程记录,布布扣,bubuko.com
基于Eclipse的Android JNI层测试应用开发过程记录
原文:http://blog.csdn.net/cloud_desktop/article/details/30304273