Changing activity using a JNI call or using Openfeint crashes applications

I have a huge problem when I want to change the activity of my Android application by calling JNI from my C ++ code. The application uses cocos2d-x for rendering. The specific situation is that I want to open OpenFeint-Dashboard in Java using this very small function:

void launchOpenFeintDashboard() {
    Dashboard.open();
}

Then this function is called from C ++ using a simple JNI-Call:

void
OFWrapper::launchDashboard() {
// init openfeint
CCLog("CPP Init OpenFeint Dashboard");

CCDirector::sharedDirector()->pause();

jmethodID javamethod = JNIManager::env()->GetMethodID(JNIManager::mainActivity(), "launchOpenFeintDashboard", "()V");
if (javamethod == 0)
    return;
JNIManager::env()->CallVoidMethod( JNIManager::mainActivityObj(), javamethod );

CCLog("CPP Init OpenFeint Dashboard done");
}

The implementation of the JNIManager class is also very simple and basic:

#include "JNIManager.h"
#include <cstdlib>

static JNIEnv* sJavaEnvironment = NULL;
static jobject sMainActivityObject = NULL;
static jclass  sMainActivity = NULL;


extern "C" {
    JNIEXPORT void JNICALL Java_net_plazz_mainzelapp_mainzelapp_sendJavaEnvironment(JNIEnv* env, jobject obj);
};

// this function is called from JAVA at startup to get the env
JNIEXPORT void JNICALL Java_net_plazz_mainzelapp_mainzelapp_sendJavaEnvironment(JNIEnv* env, jobject obj)
{
sJavaEnvironment = env;
sMainActivityObject = obj;
sMainActivity = JNIManager::env()->GetObjectClass(obj);
}



JNIEnv* 
JNIManager::env() 
{
return sJavaEnvironment;
}

jobject 
JNIManager::mainActivityObj() 
{
return sMainActivityObject;
}

jclass 
JNIManager::mainActivity() 
{
return sMainActivity;
}

From my point of view, cocos2d-x has some circular problems when changing activity with a JNI call, because I also get App-Crash when changing Activity to any of my own actions.

, OpenFeint Achievement JNI-, App-Crash, Activity:

void updateAchievementProgress( final String achievementIdStr, final String progressStr ) {
    Log.v("CALLBACK", "updateAchievementProgress (tid:" + Thread.currentThread().getId() + ")");

    float x = Float.valueOf(progressStr).floatValue();
    final Achievement a = new Achievement(achievementIdStr);
    a.updateProgression(x, new Achievement.UpdateProgressionCB() {
        @Override
        public void onSuccess(boolean b) {
            Log.e("In Achievement", "UpdateProgression");
            a.notifyAll();
        }

        @Override
        public void onFailure(String exceptionMessage) {
            Log.e("In Achievement", "Unlock failed");
            a.notifyAll();
        }
    });
    Log.v("CALLBACK", "updateAchievementProgress done (tid:" + Thread.currentThread().getId() + ")");
}

, , Android Cocos2d-x - ( Achievement) Activity NDK ( NDKr7, NDKr5).

, , Java, JNI !

, - , - , . , Cocos2d-x.

.

+5
2

Dalvik, @Goz : JNIEnv - JNI, . Java, JNIEnv , (, ). , , .

( ), JNIEnv , . :

JavaVM *jvm;
env->GetJavaVM(&jvm);

, JNIEnv, :

JNIEnv *env;
jvm->AttachCurrentThread((void **)&env, NULL);

env, ,

jvm->DetachCurrentThread();

/ , Java ( ) Thread, Java.

: , Java. Dalvik, , , .

+5

. , . , nativeOnPause cocos2d-x MessageJNI. CCApplication:: sharedApplication(), CCApplication, .

EDIT: This is a complete edit from the original post, so comments no longer make sense.

+3
source

All Articles