zoukankan      html  css  js  c++  java
  • Optimize Shader Constant Update in XNA 4.0

     Optimize Shader Constant Update in XNA 4.0

    作者:clayman

    仅供个人学习使用,请勿转载,勿用于任何商业用途。

          虽然xna 4.0删除了SetShaderConstant等一系列方法,让我们不能以最高效的方式更新shader参数,但通过优秀的设计,仍然有很大优化空间。我们的目标有两个:

    1.减少状态改变 --- 这是任何shader constant management系统的首要目标;

    2.减少EffectParameter.SetValue的调用--- reflector可以看到,这是一个非常慢的函数;

     

             如何实现呢?DirectX 10为我们指明了方向,那就是constant buffer(cb)。虽然dx 9下并没有cb,但这并不妨碍我们模拟出类似的机制,要做的不过是稍稍改变编写shader的方式而已:

    float4 PerFrameConstants[n] :register(c0);
    float4 MaterialConstant[m]:register(n);
    float4 InstanceConstant[v] : register(n
    +m);

            不再声明众多独立的uniform变量,而是把他们看做不同类型变量组中的元素,这几乎和dx 10cb的概念一模一样。为了方便编写,可以在shader中,重新组织这些变量,比如:

    static float4*4 viewProj = float4*4(PerFrameConstants[0], PerFrameConstants[1], PerFrameConstants[2], PerFrameConstants[3]);
    static float4*4  worldMatrix = float4*4( InstanceConstant[0], InstanceConstant[1], InstanceConstant[2], InstanceConstant[3]);

    ………………………………

            对应用程序来说,原来众多不同类型的参数,缩减为了非常少的几个数组。所有shader constat的改变都先缓存到数组中,然后一次性提交:

    Vector4[] InstanceConstant;
    InstanceConstant.SetValue(startIndex,elementCount, value);
    //……………set other constant
    EffectParameter.SetValue(InstanceConstant);

            虽然上面的伪代码中InstanceConstant.SetValueEffectParameter.SetValu看起来非常类似,性能却相差很多倍:InstanceConstant.SetValue只是找到特定的数组元素,并为其赋值而已;EffectParameter.SetValue就包括了一系列参数类型验证,从manage codenative code的调用,以及底层DX的函数调用等等。

             当然,性能的提升并不是免费的,改写shader以后,我们需要额外的信息知道某个参数位于哪个数据中的哪几个元素,此外,与dx10一样,cb划分的好坏,对性能有很大影响。

             最后,除性能以外,这样的方法还有一个额外的好处,就是统一了dx9/10的参数更新方式,对那些非xna,同时支持多个dx版本的传统引擎来说,也非常适合,Just Cause 2就是这么做的J

     

    ps:老早就就打算这么干,但犹犹豫豫怕把接口设计的太复杂,今天看了Just Cause2的做法,终于坚定了信心,明天开始改代码-,-

  • 相关阅读:
    hibernate的核心配置
    hibernate的映射配置
    数据库的维护
    索引
    数据库规范化设计
    数据控制DCL
    触发器
    SQL存储过程简介
    Transact-SQL简介
    sysdatabaes表与sysobjects表
  • 原文地址:https://www.cnblogs.com/clayman/p/1787434.html
Copyright © 2011-2022 走看看