1. 程式人生 > >Android Studio下的NDK開發(三):C中通過JNIEnv訪問Java中的內容

Android Studio下的NDK開發(三):C中通過JNIEnv訪問Java中的內容

1、編寫java native類

直接上程式碼
public class JniUntil {
    public static int a=7;
    public static int b=8;

    public static int sum(int a,int b){
        return a+b;
    }

    public native int askByJni();

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

}


2、生成通過terminal生成.class檔案 

開啟terminal如圖

執行  cd app/src/main/java/com/jnidemo_iii/ 進入到JniUntil.java所在的目錄
然後執行 javac JniUntil.java 可以看到目錄裡多了一個JniUntil.class的檔案

3、通過terminal生成.h標頭檔案

再執行 cd .. cd .. javah com.jnidemo_iii.JniUntil 生成.h檔案,如圖

4、配置CmakeList.txt

將.h標頭檔案拷貝到cpp目錄下,新建com_jnidemo_iii_JniUntil.c檔案,在CmakeLis.txt檔案中加入如下程式碼:


5、編寫c檔案

在com_jnidemo_iii_JniUntil.c中編寫程式碼,如下
#include "com_jnidemo_iii_JniUntil.h"
JNIEXPORT jint JNICALL Java_com_jnidemo_1iii_JniUntil_askByJni
        (JNIEnv * env, jobject obj){
    //獲取JniUntil例項
jclass jniuntil=(*env)->GetObjectClass(env,obj);
    //獲取a的id
    //第一個引數是環境,第二個引數是例項,第三個引數是變數名,第四個引數是簽名
jfieldID a_id=(*env)->GetStaticFieldID(env,jniuntil,"a","I"); //通過a的id獲取a的值 jint a=(*env)->GetStaticIntField(env,jniuntil,a_id); //獲取b的id jfieldID b_id=(*env)->GetStaticFieldID(env,jniuntil,"b","I"); //通過b的id獲取b的值 jint b=(*env)->GetStaticIntField(env,jniuntil,b_id); //獲取函式JniUntil.sum函式id //第一個引數是環境,第二個引數是例項,第三個引數是函式名,第四個引數是簽名 jmethodID id_sum=(*env)->GetStaticMethodID(env,jniuntil,"sum","(II)I"); //呼叫sum函式 //第一個引數是環境,第二個引數是例項,第三個引數是函式的id號,第四、五個引數是是sum()函式的引數 int c=(*env)->CallStaticIntMethod(env,jniuntil,id_sum,a,b); //返回sum函式結果 return c; }

6、通過terminal獲取簽名

執行javap -s -p JniUntil.class  descriptor:之後的就是簽名


7、生成動態連結庫

編譯執行,生成庫檔案,其目錄在如下圖
拷貝到JnilIbs

8、編寫mainActivity測試結果

編輯MainActivity中的程式碼,如下
public class MainActivity extends AppCompatActivity {

    @Override
protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        TextView result=(TextView)findViewById(R.id.result);
        JniUntil until=new JniUntil();
        int a=until.askByJni();
        Log.e("a","");
        result.setText(""+a);
    }
    
}

執行,結果如圖

10、原始碼連結