joh*_*nMa 5 c++ java java-native-interface android cocos2d-x
我正在上的cocos2d-X平台的插件项目,我想编写C++封装接口,通过调用Java方法JNI从jarSDK.我知道如何使用JNI来调用静态java方法,但我对java函数中的interface参数感到困惑.我有一个处理回调的cpp函数指针:
typedef void (* MyCallback)(int responseCode, string arg1, set<string> arg2);
Run Code Online (Sandbox Code Playgroud)
我想写一个cpp包装器方法,如:
static void MyCpp::setTags(set<string> tags, MyCallback callback) //it use `JNI` to invoke java method setTags(Context context, Set<String> tags, TagCallback callback).
Run Code Online (Sandbox Code Playgroud)
我想在包装器中调用的java方法是
public static void setTags(Context context, Set<String> tags, TagCallback callback)
Run Code Online (Sandbox Code Playgroud)
并且TagCallback是API用户实现的接口.那么,是否有可能TagCallback最终回调MyCallback函数?换句话说,我可以使用jni将cpp函数指针转换为java接口吗?谢谢你的耐心 .
编辑:setTag如果用户只想使用java,
这里是如何使用:
public static void setTags(context, tags, new TagCallback{
@Override
public void callback(int arg0, String arg1, Set<String> arg2) {
// TODO Auto-generated method stub
}
})
Run Code Online (Sandbox Code Playgroud)
我希望我的SDK用户使用我的cpp包装器方法,如下所示:
void setTagCallback(int responseCode, string arg1, set<string> arg2){
//users handle callback themselves.
}
void someOtherMethodInvokeTheCppWrapperMethod(){
MyCallback callback = setTagCallback;
set<string> tags;
MyCpp::setTags(tags,callback);
}
Run Code Online (Sandbox Code Playgroud)
首先,您需要构建一个可以将本机 C++ 函数指针包装在 TagCallback 兼容基类中的类:
public class NativeTagCallback : TagCallback
{
protected long cppCallbackPtr;
public NativeTagCallback( long callbackPtr )
{
cppCallbackPtr = callbackPtr;
}
public native void NativeCallback( long callbackPtr, int arg0, String arg1, Set<String> arg2 );
public void callback(int arg0, String arg1, Set<String> arg2)
{
NativeCallback( cppCallbackPtr, arg0, arg2, arg2 );
}
}
Run Code Online (Sandbox Code Playgroud)
本机代码定义如下:
extern "C" jvoid Java_com_wrapper_NativeTagCallback_NativeCallback( JNIEnv* pEnv, jobject jCaller, jlong cppCallbackPtr, jint arg0, jstring arg1, jobject arg2 )
{
MyCallback cppCallback = (MyCallback)cppCallbackPtr;
const char* pCString = pEnv->GetStringUTFChars( arg1, 0);
string arg1Str( pCString );
pEnv->ReleaseStringUTFChars( arg1, pCString );
set< string > arg2Set = ConvertJavaSetToCPPSet( arg2 ); // Perform your java to CPP set conversion here.
cppCallbackPtr( (int)arg0, arg1Str, arg2Set );
}
Run Code Online (Sandbox Code Playgroud)
然后,您将创建相关的类并将其从 C++ 传递给您的函数,如下所示:
void MyCpp::setTags(set<string> tags, MyCallback callback)
{
extern __thread JNIEnv* gpEnv;
// Get the setTags function.
jclass jWrapperClass = gpEnv->FindClass( "com/wrapper/cocoswrapper" ); // Insert the correct class name here.
jmethodID jWrapperSetTag = gpEnv->GetStaticMethodID( jWrapperClass, "setTags", "(Landroid/content/Context;Ljava/util/Set;Lcom/wrapper/TagCallback)V;" );
// Get the TagCallback related function
jclass jNativeTagCallbackClass = gpEnv->FindClass( "com/wrapper/NativeTagCallback" );
jclass jNativeTagCallbackConstructor = gpEnv->GetMethodID( jNativeTagCallbackClass, "<init>", "(J)V" );
jobject jNativeTagCallbackObject = gpEnv->NewObject( jNativeTagCallbackClass, jNativeTagCallbackConstructor, (jlong)callback)
// Make function call.
gpEnv->CallStaticVoidMethod( jWrapperClass, jWrapperSetTag, jAndroidContext, tags.GetJNIObject(), jNativeTagCallbackObject );
}
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
3953 次 |
| 最近记录: |