Следующее похоже на работу.Это основано на вышеупомянутом комментарии на следующих примерах C и этой ссылке.
http://urlgrey.net/?p=121
Как говорит ссылка, не создавайте глобальную переменную для env, вместо этого создайте глобальную переменную jvm, а также создайте глобальную ссылку на ваш класс.
Вот как я реализую шаг 1: «1) Первый вызов со стороны java к цели C. Во время этого вызова я хотел бы получить ссылку на объект java.»
Сначала объявите глобальную переменную в заголовочном файле для
1) jvm:
JavaVM *jvm;
2) Класс Java:
jclass smartCallbackClass;
3) JavaОбъект:
jobject smartCallbackObject;
Далее в вызове, который поступает со стороны Java на Objective C, установите значения для этих переменных
1) Для JVM:
(*env)->GetJavaVM(env, &jvm);
2) Для объекта:
smartCallbackObject = (*env)->NewGlobalRef(env, obj);
3) Для класса:
if (smartCallbackClass == NULL) {
jclass localRefCls = (*env)->FindClass(env,"com/studyisland/nativelibs/smart/responsesdk/interfaces/thin/SMARTResponseThinClient");
if (localRefCls == NULL) {
NSLog(@"Unable to create a JNI Java Class reference \n");
}
//Create a global reference for JNI Java class
smartCallbackClass = (*env)->NewGlobalRef(env,localRefCls);
//Delete the local reference as it is no longer needed
(*env)->DeleteLocalRef(env, localRefCls);
//Is the global reference created successfully?
if (smartCallbackClass == NULL) {
NSLog(@"Unable to create JNI Java class reference \n");
return 0;
}
}
Вот ссылка, откуда я получил код для класса
http://java.sun.com/docs/books/jni/html/refs.html
Теперь второй шаг
"2) Позже я хотел бы, чтобы Objective C использовал ссылку, полученную на предыдущем шаге, для вызова методов Java"
Для вызова из Objective C обратно в Java вам необходимо убедиться, что вызов выполняется в том же потоке, которым Java назвала Objective C, поэтому вот код.
-(void)classFailedToStop:(SMARTResponseCallBackEventArg*)anArg{
JNIEnv *env;
int attach = (*jvm)->AttachCurrentThread(jvm, (void**)&env, NULL);
if(attach == 0){
(*jvm)->GetEnv(jvm, (void**)&env, JNI_VERSION_1_4);
jmethodID method = (*env)->GetMethodID(env, smartCallbackClass, "callback_onStopClassFailed", "()V");
(*env)->CallVoidMethod(env, smartCallbackObject, method);
}
(*jvm)->DetachCurrentThread(jvm);
}
Надеюсь, это поможет.