问答 Unity 2017 打包 iOS 版本参数丢失

侑虎科技 · 2020年06月05日 · 1110 次阅读

1) Unity 2017 打包 iOS 版本参数丢失
2) 如何解决相机不渲染的问题
3) Unity 出安卓 APK 超过 2G,无法正常安装运行
4) 在 Shader 中用 if 分支避免纹理采样是否合理
5) Shader 中如何对没有开放在 Property 中的属性,且在 editor 模式下的变量设置初始值


UWA 问答社区:answer.uwa4d.com
UWA QQ 群 2:793972859(原群已满员)


Shader

Q:如图,Unity 5.6.6 版本下打包 iOS 并没出现问题,升级到 2017 后安卓没问题,iOS 打包后不少参数丢失,Shader 表现异常。


丢失的参数和代码中如何使用看不出任何关联,连_Time 这种内置参数也会丢失。目前仅发现使用了 UNITY_INSTANCING_BUFFER_START 定义的参数会较大概率丢失。设置 InstanceStrip 为 KeepAll,打包材质,放入 alwaysinclude 都无法解决该问题。
(2017.4.28 和 2017.4.32 都试过)

A:逐行查看编译后的 metal 代码,发现根源问题是 UNITY_INSTANCING_BUFFER_START 内定义的 Float4。如果与外部定义的 Float4 不连续时,生成的 Buff 大小不正确,甚至会出现参数丢失的可能。修改为 Float4 连续,最后放 Float 后正常。

感谢题主 jiacat@UWA 问答社区提供了回答


Animation

Q:一个比较大的模型在进入场景或者出场景时,由于大部分都在屏幕外面,只有一小部分在屏幕内,Unity 就默认只优化不渲染,但是此操作会导致模型突然闪入或者闪出屏幕,请问一下这个应该怎么解决呢?

A:发现是动画的问题,这个模型是一个动画做的漂浮的物件,美术直接使用的 Legacy CullingType 选了 Base on Renderer,进入屏幕前的动画是没有启动的,改成 Always Animate 就可以正常显示了。

感谢题主好心情@UWA问答社区提供了回答


Build

Q:安卓 APK 包超过 2G 大小,无法安装或者安装后无法启动运行,看 Log 是 Zip 解压问题,这是什么原因?

A:这个是安卓平台限制的,之前我们也遇到了,后面发现安卓应用商店的包都没有超过 2G 的 APK,最大见过 1.98G,超出的资源只能走分包了,热更新进行下载。

感谢田航@UWA问答社区提供了回答


ShaderLab

Q:在 Shader 中用 if 分支避免纹理采样是否合适?

Properties
    {
        _MainTex ("Texture", 2D) = "white" {}
        _MaskTex ("Mask Texture", 2D) = "white" {}
    [ToggleOff] _UseMaskTex("Use Mask Texture", Float) = 0.0
    }

如上我定义一个变量来决定是否采样 Mask 贴图,然后在 frag 中这样:

half4 frag (v2f i) : SV_Target
{
    half4 mainColor = tex2D(_MainTex, i.uv);
    if (_UseMaskTex)
    {
            half4 maskTex = tex2D(_MaskTex, i.uv);                    
                mainColor *= maskTex.r;
    }
        return mainColor;
}

我查了一些资料,大部分都说 Shader 里的动态分支开销很大,然后看到有些朋友说定义在 Properties 里的变量作为 if 的判断条件,属于静态分支,在 GPU 处理同一批像素中可以只走一条分支而不走另外一条分支的开销。

所以我想请问的是,如果我通过一个 Properties 的变量来控制是否采样某张(或某几张)贴图,是否合适。我期望的是当开关关闭时,可以以另一个较小的开销来避免贴图采样的开销。

PS:我知道可以通过变体来控制,但是会增加 Shader 内存,所以想请教一下这个方案是否可行,谢谢。

A1:我记忆中是这样的,GPU 中的 if 分支本身是存在开销的,大概相当于十几条计算指令的开销。但是当一块连续像素(可能移动端 GPU 上的一个 tile)走的是同一个分支的情况下,就不会对另一个分支进行计算。个人猜测如果是从 Properties 传值这样的静态分支,最终的消耗应该就是 if 本身 + 所选的分支开销。所以不只是静态分支,有时使用 if 对分支内大量计算进行优化还是有效的。

Shader 太简单可以试试通过叠 Overdraw 来测试,比如:一个 Shader 用 if 返回颜色,另一个 Shader 采一次图,都使用 Alpha blend 然后在摄像机前叠 100 层去测试性能。
感谢王阳@UWA问答社区提供了回答

A2:个人觉得还是加个 Keyword 的好,让这种选择在 CPU 端来做,就 GPU 而言所有同一个 warp 中的 thread 必须执行相同的指令,如果这些线程在遇到控制流语句时,如果进入不同的分支,那么同一时刻除了正在执行的分支外,其余分支都被阻塞了,也就是说不管你做与不做都在那里耗着,十分影响性能。当然你考虑的变体导致内存问题也有可能,比如你的 Shader 已经存在 1000 个变体了,再加上这个 Keyword 那就有 2000 个变体了,内存的占用是很恐怖的,不过这个时候你的重点应该是怎么去修改你的 Shader,当然如果你这个处理的像素在屏幕上只是很小一部分,其实怎么做都可以。

感谢李星@UWA问答社区提供了回答


Shader

Q:Shader 中如何对没有开放在 Property 中的属性,且在 editor 模式下的变量设置初始值?

例如上图中,需要全局设置默认 fog 颜色。

A:如下图所示:

感谢约定@UWA问答社区提供了回答


今天的分享就到这里。当然,生有涯而知无涯。在漫漫的开发周期中,您看到的这些问题也许都只是冰山一角,我们早已在 UWA 问答网站上准备了更多的技术话题等你一起来探索和分享。欢迎热爱进步的你加入,也许你的方法恰能解别人的燃眉之急;而他山之 “石”,也能攻你之 “玉”。

暂无回复。
需要 登录 后方可回复, 如果你还没有账号请点击这里 注册