jni.hpp icon indicating copy to clipboard operation
jni.hpp copied to clipboard

How do I convert a jobject to jni::Object?

Open akshetpandey opened this issue 6 years ago • 2 comments

Considering the following code:

import android.app.Activity;

class NativeClassProxy {
  private long peer;
  private Activity mActivity;

  public void initialize(Activity activity) {
    mActivity = activity;
  }
}
struct Activity { static constexpr auto Name() { return "android/app/Activity"; } };
struct NativeClassProxy { static constexpr auto Name() { return "NativeClassProxy"; } };

NativeClass::NativeClass() {
  auto env = cocos2d::JniHelper::getEnv();
  auto cls = jni::Class<NativeClassProxy>::Find(*env);
  auto constructor = cls.GetConstructor(*env);
  auto object = cls.New(*env, constructor);

  auto initialize = cls.GetMethod<void (jni::Object<Activity>)>(*env, "initialize");

  jobject activity = cocos2d::JniHelper::getActivity();
  object.Call(*env, initialize, activity);
}

Of course, I can't send the activity directly since it expects a jni::Object<Activity>. But how do I convert it into what it expects?

akshetpandey avatar Mar 20 '19 01:03 akshetpandey

I ended up up doing the following and it seems to work. I am not sure if it's leaking memory though.

    auto act = (jni::jobject *)cocos2d::JniHelper::getActivity();
    auto activity = jni::Local<jni::Object<Activity>> {*env, jni::NewLocalRef(*env, act).release()};

akshetpandey avatar Mar 21 '19 03:03 akshetpandey

My solution was similar:

   JNIEXPORT void JNICALL Java_com_ttm_v2_sync_SyncService_init(JNIEnv* env, jobject obj)
   {
         auto instance = jni::Global<jni::Object<SSyncService>>(
            *env, jni::Wrap<jni::jobject*>(env->NewGlobalRef(obj)));
   }

However, IMHO, the NewGlobal and NewLocal methods should offer a convenience for this so I can just do:

auto instance = jni::NewGlobal<jni::Object<SSyncService>>(*env, obj);

rcdailey avatar Oct 04 '19 21:10 rcdailey