想要學習一下在Android Studio中進行JNI的開發,文章挺多的,可是幾乎沒有一個完整的說明的,中間老是有一兩步漏掉。分享技術就應該完整的讓讀者學會,藏着掖着不是君子所爲。對於那些故意含糊過去的,我只想說Navie!html
轉載請註明出處 http://www.cnblogs.com/qiusuo/p/5656625.htmljava
正文android
JNI是JAVA標準平臺中的一個重要功能,它彌補了JAVA的與平臺無關這一重大優勢的不足,在JAVA實現跨平臺的同時,也能與其它語言(如C、C++)的動態庫進行交互,給其它語言發揮優點的機會。app
Android NDK(Native Development Kit )是一套工具集合,容許你用像C/C++語言那樣實現應用程序的一部分。ide
按照通常方法,建立一個Android應用
File - New - New Project工具
package com.example.angel.myapplication; /** * Created by Angel on 2016/7/8. */ public class JniDemo { public native String getJniMessage(); }
#include "com_example_angel_myapplication_JniDemo.h" JNIEXPORT jstring JNICALL Java_com_example_angel_myapplication_JniDemo_getJniMessage (JNIEnv *, jobject) { return (*env)->NewStringUTF(env,"Jni Message: Hello World!"); }
android { sourceSets { main { jniLibs.srcDir 'src/main/jni' } } }
而且自定義so庫的名稱學習
android { ...... defaultConfig { ...... ndk { moduleName 'jnidemo'//自定義名稱 } } }
若是不這麼作的話,生成的庫文件名稱是[lib][module name].sogradle
static { System.loadLibrary("jnidemo"); }
public class MainActivity extends AppCompatActivity { static { System.loadLibrary("jnidemo"); } @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); final JniDemo jniDemo = new JniDemo(); TextView textView = (TextView) findViewById(R.id.text); textView.setText(jniDemo.getHelloWordText()); } }
protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); sContext = getApplicationContext(); } private static Context sContext; public static void showToast() { Toast.makeText(sContext, "此方法由Native方法調用", Toast.LENGTH_SHORT).show(); }
在Native代碼中,使用以下代碼進行調用ui
//找到咱們要調用的方法,注意包名+類名 jclass clazz = (*env)->FindClass(env,"com/example/angel/myapplication/MainActivity"); //獲取某個靜態方法的ID //clazz 是咱們上面找到的類的字節碼文件 //showToast 是clazz類中的方法名 //"()V" 這個表示方法的簽名;()是方法的參數列表;V表示方法的返回類型;V -> void jmethodID id = (*env)->GetStaticMethodID(env,clazz, "showToast","()V"); //最後調用這個方法,CallStaticVoidMethod(clazz,方法ID) (*env)->CallStaticVoidMethod(env,clazz,id);