牵着老婆满街逛

严以律己,宽以待人. 三思而后行.
GMail/GTalk: yanglinbo#google.com;
MSN/Email: tx7do#yahoo.com.cn;
QQ: 3 0 3 3 9 6 9 2 0 .

VS2015编译Android版Cocos项目所踩的那些坑

微软现在已经越来越变态了,简直万能了.彻底的拥抱了开源.
比如,Windows10下直接把Ubuntu变成了子系统(不是基于虚拟机,基于容器),用起来就跟CMD一样!
比如,VS2015直接支持Android的编译打包.
说实话,就目前来说,VS的学习成本是最低的,虽然现在Android Studio 2.2已经支持了CMake编译NDK原生代码了,但是Gradle,Ant,NDK这些学习成本太高,弄起来也稍微有点复杂,特别是,国内把谷歌墙了的情况下,它又非常的依赖网络.
我用惯了VS,VS+VA真是天生绝配.我要说明的是,我VIM也用得挺溜的,就算是开发linux程序,我编码还是用的VS(VS+Samba+SSH).以前想,如果VS能提供全套服务,那该多好.如今,这个梦想实现了.

我的工程基础来自于这篇文章:Cocos2d-x Visual Studio Android Project
下载下来,然后按照教程里面一二三的做,经过了编译的等待之后,成功的打包出apk,烧到手机上,也毫无问题的运行成功.

这看起来是很完美,但是,它是把cocos引擎代码放在so里面跟游戏代码一起编译的,真要搞起来,编译cocos就要搞死人,这很坑.
很显然,我需要把cocos提取出来编译成单独的一个静态库.a.
我拿so文件稍作修改,改出了一个cocos引擎的静态库工程,然后编译,一切都很顺利,很正常.
然而,编译so项目的时候,幺蛾子出现!
出现无数的undefined referenced错误,通常来说,这都是没有引用静态库导致的未找到实现代码的错误.
可是,问题是我已经引用了所有的.a文件了,然后我纳闷了很久.
突然一激灵:gcc的链接器对ld链接的文件是有顺序要求的!
因为我用VS引用.lib从来没有说有这样的顺序问题.以为它对gcc也一样,然而并没有.
我立马根据依赖关系,调整了引用的顺序.(o゜▽゜)o☆[BINGO!]果然OK了!

我看了apk,比之前那个少了一半的大小,想着静态库的话,动态库是选择性的把代码链接进去,而没用的代码抛去.想着应该没啥问题,于是就兴冲冲的烧进手机,结果懵逼了,crash了!
赶紧的VS开USB真机调试,然后我就懵逼了:jni的入口方法:JNI_OnLoad没有被调用!
难道没有被导出?这不应该吧?只能用nm命令查看下了.
这时候,Windows10的子系统Ubuntu就派上了大大的用场了.我Win+R->bash,启动了Ubuntu,然后输入命令查看:

尼玛,果然!!!
我接着,试着在so里面直接模拟调用了JNI_OnLoad,没问题,调试进去了.a里面的代码块,也就是说,链接进去了,但是,并没有将之导出.哪怕我强制性的设置其可见性,也是没用的:
__attribute__ ((visibility ("default"))) jint JNI_OnLoad(JavaVM *vm, void *reserved)
{
    JniHelper::setJavaVM(vm);

    cocos_android_app_init(JniHelper::getEnv());

    return JNI_VERSION_1_4;
}
我再一次懵逼了.
如果是这样,那么恐怕只有完整的链接到so才能解决问题了.
我在so工程的 链接器->高级 里面找到了"整个存档"这个选项,或许就是它了,我把它设置成:

然后把so工程重编译了,看了下,so的大小这时候跟最早没拆分的版本一样大了.
烧进真机一调试,果然就没问题了.
虽然这当中折腾了我不少时间和精力,但是相对来说,VS不算折腾了.

另外,资源只是放在assets里面,还不够的,还需要在工程里面引用才可以,这点有点坑。

开发环境
VS2015 Update3
cocos2d-x-3.13.
apache-ant-1.9.7
jdk1.8.0_112
android-ndk-r13b

下载
cocos引擎静态库工程文件,请将其解压放置在$COCOS_ROOT()/build下,静态库.a文件生成在$COCOS_ROOT()/lib下:/Files/tx7do/libcocos2d-android.zip
HelloWorld示例工程文件:/Files/tx7do/proj.visualstudio.zip

参考资料
Cocos2d-x Visual Studio Android Project
Linux系统下 连接器ld链接顺序的总结
我所理解的jni与ndk

posted on 2017-01-01 14:40 杨粼波 阅读(3378) 评论(0)  编辑 收藏 引用 所属分类: C++


只有注册用户登录后才能发表评论。
网站导航: 博客园   IT新闻   BlogJava   知识库   博问   管理