首先,让我列出我能找到的最佳结果。jni调用以自定义java接口为参数的java方法
这个回答并不能解决我的问题。让我解释一下我的问题。我想要按如下方式调用NDK。
(1)Java -> (2)CPP -> (3)C (新线程) -> (4)CPP -> (5)Java
代码如下。
(1) Java
请注意,这不是关于如何从C++调用Java的基础问题。我想解决的两个具体问题是如何调用“回调”以及如何调用Java接口实现中的方法。我已经在Obj-C中完成了这个过程,那里很简单直接。
(1)Java -> (2)CPP -> (3)C (新线程) -> (4)CPP -> (5)Java
代码如下。
(1) Java
public interface Callback<T> {
void success(T result);
}
private native void jniUploadAsync(String imagePath, Callback<String> callback);
jniUploadAsync(file.getAbsolutePath(), new Callback<String>() {
@Override
public void success(final String result) {
Log.v("MyClass: result:: ", result);
}
});
(2) CPP
static JavaVM *jvm;
void imageUploadCallback(char *json, void *completionCallback) {
JNIEnv *env;
jint rs = jvm->AttachCurrentThread(&env, NULL);//create JNIEnv from JavaVM
jclass cbClass = env->FindClass("org/winster/test/Callback");
jmethodID method = env->GetMethodID(cbClass, "success", "(Ljava/lang/String;)V");
env->CallVoidMethod(static_cast<jobject>(completionCallback), method, "abcd");
}
void Java_org_winster_test_MyClass_jniUploadAsync(JNIEnv * env, jobject obj, jstring imagePath, jobject completionCallback) {
jint rs = env->GetJavaVM(&jvm); //Cache JavaVM here
CallMyCMethod((char *)filePath, &imageUploadCallback, &completionCallback);
}
(3) C
CallMyCMethod() //please assume that it works. The reason I need void* as the type for completionCallback is because, in ObjC implementation I use this
(4) CPP
//Call comes back to imageUploadCallback()
(5) Java
//I expect this Log.v("MyClass: result:: ", result); to be executed
请注意,这不是关于如何从C++调用Java的基础问题。我想解决的两个具体问题是如何调用“回调”以及如何调用Java接口实现中的方法。我已经在Obj-C中完成了这个过程,那里很简单直接。
imageUploadCallback
中,env
的来源不清楚。很可能需要调用AttachCurrentThread
。 - Michael