pc8888888 发表于 2021-12-24 17:14

unity5.0 打包出来的apk 为什么闪退?

开篇之前,请先阅读雨松MOMO大神的两篇文章:

[*]Unity3D研究院之打开Activity与调用JAVA代码传递参数(十八)
[*]Unity3D研究院之与Android相互传递消息(十九)
到这里如果你用的是Unity 4.x 的话就可以跳过剩下的所有文字了,教程结束,用Unity5的话请继续往下看:
拜读完两篇大作之后你觉得有雨松MOMO大神光环加身,打开Unity5和简陋的Eclipse准备撸代码,直到你遇到了下面的错误:


WTF! 你重新看了一遍教程确认自己按照教程一步步走下来的,甚至直接用大神的工程来编译也是这个错误,去评论区找也是相关的评论而没有解决方案。
WTFx2! 这时候你才确定遇到了某种坑,这种坑需要自己来填。
看错误是在将classes文件转换成dex文件时,下面这这几个class文件已经存在了:
Uncaught translation error: java.lang.IllegalArgumentException: already added: Lcom/my/test/R;
Uncaught translation error: java.lang.IllegalArgumentException: already added: Lcom/my/test/R$attr;
Uncaught translation error: java.lang.IllegalArgumentException: already added: Lcom/my/test/R$drawable;
Uncaught translation error: java.lang.IllegalArgumentException: already added: Lcom/my/test/R$string;
Uncaught translation error: java.lang.IllegalArgumentException: already added: Lcom/my/test/R$style;我们到Eclipse生成的classes目录(bin\classes)中看一下,发现除了我们自己的 MainActivity 的class,Eclipse还附赠了 BuildConfig和 R 相关的class文件,回忆我们之前是用下面的命令将所有classes打包的,那么错误的原因的很好解释了:Unity打包时会帮我们生成R相关的classes,而这个过程会和Eclipse生成的classes文件相冲突。
“万恶”的打包jar命令: jar -cvf test.jar *问题到了这里就很好解决了,如果要使用jar命令打包,需要删除 BuildConfig 和 R相关的classes再进行打包。其实通过下面的两种方式可以绕过这个问题:

[*]用Eclipse导出jar文件。具体操作是:右键 -> Export -> Java/JAR file -> 勾选src下面的包全部导出jar。这种方法不会导出多余的文件,编译不会就不会报错了,这是推荐方式。
[*]在Eclipse里面改包名为不和包名相同的任意值,例如com.never.mind。这种方法的话Eclipse会将多余的文件生成到com/never/mind目录下面,因为不和最终的包名相同,所以用jar命令打包不会导致冲突。
正确导出的应该的是右边的这个jar:


到了这里你以为问题已经解决了,直到你膝盖又中了一箭。
老大:我们需要在游戏的退出框里加个游戏的icon。
你:好,我去网上找一找。
然后你找到了这样的代码:
AlertDialog.Builder builder = new AlertDialog.Builder(this);
builder.setTitle("退出");
builder.setMessage("是否退出游戏?");
builder.setPositiveButton("確定", new OnClickListener()
{
    @Override
    public void onClick(DialogInterface dialog, int which)
    {
      finish();
    }
});
builder.setNegativeButton("取消", new OnClickListener()
{
    @Override
    public void onClick(DialogInterface dialog, int which)
    {
      dialog.dismiss();
    }
});
builder.setIcon(R.drawable.app_icon);        // 很急很关键

AlertDialog dialog = builder.create();
dialog.setCanceledOnTouchOutside(false);
dialog.show();运行的结果是这样的:


WTFx3! 这张图你是谁?人与机器之间最基本的信任在哪里?
于是我们尝试反编译APK看问题在哪里,发现是Unity5 在最前面自动给我们加了个app_banner:


到了这里我们只能将所有用到R相关的东西全用反射来拿了,方法大概长成下面这个样子:
public static int GetIdFromR(Context context, String the_class, String the_name)
{
    int id = -1;
    try
    {
      String packageName = context.getPackageName();
      Class<?> the_r_class = Class.forName(packageName + ".R$" + the_class);
                  
      id = the_r_class.getField(the_name).getInt(the_r_class);
    }
    catch(Exception e)
    {
      e.printStackTrace();
    }
   
    return id;
}调用的话是这样:
builder.setIcon(GetIdFromR(this, "drawable", "app_icon"));于是,我们见到了久违的弹出框:


最后的最后,我讨厌雨松MOMO叼着奶嘴的头像。
2016.3.17:修改初版完成。
2016.3.18:错别字修改,吐槽添加完毕。
=================== 以下是原答案 ===================
Unity接入Android sdk有两种方式:一是Android插件的形式导入unity(unity5注意package的问题hack即可,具体优雅解决还待细查)。二是unity导出Android工程来做。两种方法都应该是可行的,具体闪退原因看Logcat应该能找出原因,猜测是主启动活动没写全路径。

Doris232 发表于 2021-12-24 17:17

开篇之前,请先阅读雨松MOMO大神的两篇文章:

[*]Unity3D研究院之打开Activity与调用JAVA代码传递参数(十八)
[*]Unity3D研究院之与Android相互传递消息(十九)
到这里如果你用的是Unity 4.x 的话就可以跳过剩下的所有文字了,教程结束,用Unity5的话请继续往下看:
拜读完两篇大作之后你觉得有雨松MOMO大神光环加身,打开Unity5和简陋的Eclipse准备撸代码,直到你遇到了下面的错误:


WTF! 你重新看了一遍教程确认自己按照教程一步步走下来的,甚至直接用大神的工程来编译也是这个错误,去评论区找也是相关的评论而没有解决方案。
WTFx2! 这时候你才确定遇到了某种坑,这种坑需要自己来填。
看错误是在将classes文件转换成dex文件时,下面这这几个class文件已经存在了:
Uncaught translation error: java.lang.IllegalArgumentException: already added: Lcom/my/test/R;
Uncaught translation error: java.lang.IllegalArgumentException: already added: Lcom/my/test/R$attr;
Uncaught translation error: java.lang.IllegalArgumentException: already added: Lcom/my/test/R$drawable;
Uncaught translation error: java.lang.IllegalArgumentException: already added: Lcom/my/test/R$string;
Uncaught translation error: java.lang.IllegalArgumentException: already added: Lcom/my/test/R$style;我们到Eclipse生成的classes目录(bin\classes)中看一下,发现除了我们自己的 MainActivity 的class,Eclipse还附赠了 BuildConfig和 R 相关的class文件,回忆我们之前是用下面的命令将所有classes打包的,那么错误的原因的很好解释了:Unity打包时会帮我们生成R相关的classes,而这个过程会和Eclipse生成的classes文件相冲突。
“万恶”的打包jar命令: jar -cvf test.jar *问题到了这里就很好解决了,如果要使用jar命令打包,需要删除 BuildConfig 和 R相关的classes再进行打包。其实通过下面的两种方式可以绕过这个问题:

[*]用Eclipse导出jar文件。具体操作是:右键 -> Export -> Java/JAR file -> 勾选src下面的包全部导出jar。这种方法不会导出多余的文件,编译不会就不会报错了,这是推荐方式。
[*]在Eclipse里面改包名为不和包名相同的任意值,例如com.never.mind。这种方法的话Eclipse会将多余的文件生成到com/never/mind目录下面,因为不和最终的包名相同,所以用jar命令打包不会导致冲突。
正确导出的应该的是右边的这个jar:


到了这里你以为问题已经解决了,直到你膝盖又中了一箭。
老大:我们需要在游戏的退出框里加个游戏的icon。
你:好,我去网上找一找。
然后你找到了这样的代码:
AlertDialog.Builder builder = new AlertDialog.Builder(this);
builder.setTitle("退出");
builder.setMessage("是否退出游戏?");
builder.setPositiveButton("確定", new OnClickListener()
{
    @Override
    public void onClick(DialogInterface dialog, int which)
    {
      finish();
    }
});
builder.setNegativeButton("取消", new OnClickListener()
{
    @Override
    public void onClick(DialogInterface dialog, int which)
    {
      dialog.dismiss();
    }
});
builder.setIcon(R.drawable.app_icon);        // 很急很关键

AlertDialog dialog = builder.create();
dialog.setCanceledOnTouchOutside(false);
dialog.show();运行的结果是这样的:


WTFx3! 这张图你是谁?人与机器之间最基本的信任在哪里?
于是我们尝试反编译APK看问题在哪里,发现是Unity5 在最前面自动给我们加了个app_banner:


到了这里我们只能将所有用到R相关的东西全用反射来拿了,方法大概长成下面这个样子:
public static int GetIdFromR(Context context, String the_class, String the_name)
{
    int id = -1;
    try
    {
      String packageName = context.getPackageName();
      Class<?> the_r_class = Class.forName(packageName + ".R$" + the_class);
                  
      id = the_r_class.getField(the_name).getInt(the_r_class);
    }
    catch(Exception e)
    {
      e.printStackTrace();
    }
   
    return id;
}调用的话是这样:
builder.setIcon(GetIdFromR(this, "drawable", "app_icon"));于是,我们见到了久违的弹出框:


最后的最后,我讨厌雨松MOMO叼着奶嘴的头像。
2016.3.17:修改初版完成。
2016.3.18:错别字修改,吐槽添加完毕。
=================== 以下是原答案 ===================
Unity接入Android sdk有两种方式:一是Android插件的形式导入unity(unity5注意package的问题hack即可,具体优雅解决还待细查)。二是unity导出Android工程来做。两种方法都应该是可行的,具体闪退原因看Logcat应该能找出原因,猜测是主启动活动没写全路径。

Mecanim 发表于 2021-12-24 17:26

官方说法是 5.0的打包确实存在Bug,在我回答你的时候也就是5.3的时候版本已经稳定了。
页: [1]
查看完整版本: unity5.0 打包出来的apk 为什么闪退?