Cocos2d-x 之使用 Jni
来源:互联网 发布:完美世界 游戏 知乎 编辑:程序博客网 时间:2024/05/21 18:35
Jni 技术
Android 里面有个 jni.h 封装了 java 代码与原生代码交互的功能,cocos2dx 在cocos/platform/android/jni下面有个jniHelper 类是对 jni 的再次封装,使用 jniHelper 能很容易地实现 c++ 代码与 java 互调。
C++ 调 Java
- Android 端没什么特别要做的,只需要把函数定义好就行,函数分静态和实例两种。
- Cocos 端要注意的东西就比较多,
首先要引入相关的库,这里需要 jni.h 和 jniHelper.h 两个库,但其实 jniHelper.h 里面已经包含 jni.h 了,所以只需要包含 jniHelper.h 就行。jniHelper.h 位于
#if (CC_TARGET_PLATFORM==CC_PLATFORM_ANDROID)#include <platform/android/jni/JniHelper.h>#endif
然后就是调 android 方法了,同样要加上平台判断预处理。
- 声明jni方法结构体
JniMethodInfo jm;
- 查找方法是否存在
静态方法 bool b=JniHelper::getStaticMethodInfo(jm,"完整类名“,”方法名“,”(函数参数)返回值“);实例方法 bool b=JniHelper::getStaticMethodInfo(jm,"完整类名”,“方法名”,“(函数参数)返回值”);
完整类名是指包含完整的包名,比如 org/cocos2dx/cpp/AppActivity。
函数参数及返回值指的是类型,要写 jni 里面的类型,关于 c++ 数据类型与 jni 的对应关系,请自行上网查。
- 调用方法
根据返回值不同调用不同的函数 - 返回整型静态方法
jint jRes = jm.env->CallStaticIntMethod(jm.classID, jm.methodID, 函数参数);
- 无返回值实例方法
jm.env->CallVoidMethod(类实例, jm.methodID);
- 类实例通过调用静态方法来获得
jobject jIns = jm.env->CallStaticObjectMethod(jm.classID, jm.methodID);
Java 调 C++
- Android 声明原生函数,只声明不用实现,实现放在 C++ 端。
public [static] native 返回值 方法名(参数);
Cocos 端实现原生函数
不仅参数和返回值要和 Android 端定义的一样,函数名也有要求,函数名格式 Java_包1_包2_类名_原生函数名。比如类 Foo 有个原生函数叫 test,所在包是 org/cocos2dx/cpp,则 cocos 端实现的函数叫 Java_org_cocos2dx_cpp_Foo_testAndroid端直接调该函数。
静态方法
// Java端public class AppActivity extends Cocos2dxActivity { /** * c++调java函数 * 静态方法 */ public static int nativeCallJava(String name, String filter) { String fullName=name+"."+filter; javaCallNative(fullName); return 110; } /** * java调c++原生函数 * 静态方法 */ public static native void javaCallNative(String packageName);}
// C++端#if CC_TARGET_PLATFORM==CC_PLATFORM_ANDROID //声明jni结构体 JniMethodInfo jm; //查找java静态方法 bool b = JniHelper::getStaticMethodInfo(jm, "org/cocos2dx/cpp/AppActivity", "nativeCallJava", "(Ljava/lang/String;Ljava/lang/String;)I"); if (b) { //定义java字符串变量 jstring jTitle = jm.env->NewStringUTF("sound/bg"); jstring jText = jm.env->NewStringUTF("mp3"); //调用java静态方法 jint jRes = jm.env->CallStaticIntMethod(jm.classID, jm.methodID, jTitle, jText); //资源回收 jm.env->DeleteLocalRef(jTitle); jm.env->DeleteLocalRef(jText); //取得java方法返回值 char name[16]; sprintf(name, "return code:%d", jRes); this->addChild(m_tip_text); m_tip_text->setVisible(true); m_tip_text->setString(name); }#endif#if CC_TARGET_PLATFORM==CC_PLATFORM_ANDROIDextern "C"{ /** * java调原生函数 */ void Java_org_cocos2dx_cpp_AppActivity_javaCallNative(JNIEnv* env, jobject thiz, jstring name) { JniMethodInfo jm; const char* cName = jm.env->GetStringUTFChars(name, NULL); SimpleAudioEngine::getInstance()->playBackgroundMusic(cName); SimpleAudioEngine::getInstance()->setBackgroundMusicVolume(100); env->ReleaseStringUTFChars(name, cName); }}#endif
实例方法
//Java端package org.cocos2dx.cpp;public class Foo{ /** * c++调java函数 * 静态方法 * 获取类实例 */ private static Foo _ins; public static Object getInstance() { if (_ins == null) { _ins = new Foo(); } return _ins; } /** * c++调java函数 * 非静态方法 */ public int nativeCallJava() { javaCallNative(); return 111; } /** * java调c++原生函数 * 非静态方法 */ public native void javaCallNative();}
//C++端#if CC_TARGET_PLATFORM==CC_PLATFORM_ANDROID //声明jni结构体 JniMethodInfo jm; //声明java类实例 jobject jIns; //先调用静态方法获得类实例 if (JniHelper::getStaticMethodInfo(jm, "org/cocos2dx/cpp/Foo", "getInstance", "()Ljava/lang/Object;")) { jIns = jm.env->CallStaticObjectMethod(jm.classID, jm.methodID); if (!jIns) { m_tip_text->setString("ins is null"); return; } } //查找非静态方法 bool b = JniHelper::getMethodInfo(jm, "org/cocos2dx/cpp/Foo", "nativeCallJava", "()I"); if (b) { //调用java非静态方法 jint jRes = jm.env->CallIntMethod(jIns, jm.methodID); jm.env->CallVoidMethod(jIns, jm.methodID); //取得java方法返回值 char name[16]; sprintf(name, "return code:%d", jRes); m_tip_text->setString(name); }#endif#if CC_TARGET_PLATFORM==CC_PLATFORM_ANDROIDextern "C"{ /** * java调原生函数 */ void Java_org_cocos2dx_cpp_Foo_javaCallNative(JNIEnv* env, jobject thiz) { SimpleAudioEngine::getInstance()->stopBackgroundMusic(); }}#endif
阅读全文
1 0
- Cocos2d-x 之使用 Jni
- Cocos2d-x JNI使用--震动
- cocos2d-x之jni使用(对接Android各种sdk)
- cocos2d-x Jni调用
- cocos2d-x admob jni
- cocos2d-x学习之二:cocos2d-x之CCUserDefault使用
- cocos2d-x 使用JNI从Java调C++
- cocos2d-x 使用JNI从Java调C++
- cocos2d-x 使用JNI从Java调C++
- cocos2d-x中使用JNI的调用JAVA方法
- Cocos2d-x游戏开发之随机数使用
- cocos2d-x之texturepacker的使用
- Cocos2d-x 之声音模块的使用
- Cocos2d-x游戏开发之音效使用
- cocos2d-x 之美术字bmfont工具使用
- Cocos2d-x之LayerMultiplex的使用
- cocos2d-x 入门之初次使用
- Cocos2d-x之lambda表达式的使用
- 前端表单验证常用的15个JS正则表达式
- “人工智能2.0”的来龙去脉与人工智能发展规划
- Cent OS 安装MySQL-Service警告:... DSA/SHA1 Signature, 密钥 ID 5072e1f5: NOKEY ...
- 进程和线程关系及区别
- JSP基本语法
- Cocos2d-x 之使用 Jni
- 1039: n个数求和
- CSDN博客迁移至Hexo之同步CSDN博文到本地MD文件
- 编写sql语句一些关键词的注意事项
- (转载)深入理解java异常处理机制
- 关于CentOS安装完成的一些基本设置技巧
- CSU
- 全局变量的存储类型
- 字符设备驱动高级篇1——新接口介绍