math - Glsl mod 与 Hlsl fmod

标签 math opengl directx glsl hlsl

我已经实现了 this question 中描述的螺旋 GLSL 着色器在 HLSL 中,但结果不一样。我认为这是因为 mod GLSL 中的函数,我已经翻译成 fmod在 HLSL 中。我怀疑这个问题只有在 fmod 的输入中有负数时才会发生。功能。

我已经尝试更换对 mod 的调用通过调用我所做的函数来执行 GLSL documentation 中描述的操作它有效:

mod returns the value of x modulo y. This is computed as x - y * floor(x/y).



我使用的工作代码而不是 fmod是:
float mod(float x, float y)
{
  return x - y * floor(x/y)
}

对比 GLSL mod , MSDN says HLSL fmod函数这样做:

The floating-point remainder is calculated such that x = i * y + f, where i is an integer, f has the same sign as x, and the absolute value of f is less than the absolute value of y.



我用过 an HLSL to GLSL converter ,以及 fmod函数翻译为 mod .但是,我不知道我是否可以假设 mod转换为 fmod .

问题
  • GLSL mod有什么区别和 HLSL fmod ?
  • 我如何翻译 MSDN 对 fmod 的神秘描述到伪代码实现?

  • GLSL 着色器
    uniform float time;
    uniform vec2 resolution;
    uniform vec2 aspect;
    
    void main( void ) {
      vec2 position = -aspect.xy + 2.0 * gl_FragCoord.xy / resolution.xy * aspect.xy;
      float angle = 0.0 ;
      float radius = length(position) ;
      if (position.x != 0.0 && position.y != 0.0){
        angle = degrees(atan(position.y,position.x)) ;
      }
      float amod = mod(angle+30.0*time-120.0*log(radius), 30.0) ;
      if (amod<15.0){
        gl_FragColor = vec4( 0.0, 0.0, 0.0, 1.0 );
      } else{
        gl_FragColor = vec4( 1.0, 1.0, 1.0, 1.0 );                    
      }
    }
    

    HLSL 着色器
    struct Psl_VertexShaderInput
    {
        float3 pos : POSITION;
    };
    
    struct Psl_VertexShaderOutput
    {
        float4 pos : POSITION;
    
    };
    
    struct Psl_PixelShaderOutput
    {
        float4 Output0 : COLOR0;
    };
    
    float3 psl_positionOffset;
    float2 psl_dimension;
    
    Psl_VertexShaderOutput Psl_VertexShaderFunction(Psl_VertexShaderInput psl_input)
    {
        Psl_VertexShaderOutput psl_output = (Psl_VertexShaderOutput)0;
    
        psl_output.pos = float4(psl_input.pos + psl_positionOffset, 1);
    
    
        return psl_output;
    }
    
    float time : TIME;
    float2 resolution : DIMENSION;
    
    
    Psl_PixelShaderOutput Psl_PixelShaderFunction(float2 pos : VPOS)
    {
        Psl_PixelShaderOutput psl_output = (Psl_PixelShaderOutput)0;
    
        float2 aspect = float2(resolution.x / resolution.y, 1.0);
        float2 position = -aspect.xy + 2.0 * pos.xy / resolution.xy * aspect.xy;
        float angle = 0.0;
        float radius = length(position);
        if (position.x != 0.0 && position.y != 0.0)
        {
            angle = degrees(atan2(position.y, position.x));
        }
        float amod = fmod((angle + 30.0 * time - 120.0 * log(radius)), 30.0);
        if (amod < 15.0)
        {
            psl_output.Output0 = float4(0.0, 0.0, 0.0, 1.0);
            return psl_output;
        }
    
        else
        {
            psl_output.Output0 = float4(1.0, 1.0, 1.0, 1.0);
            return psl_output;
        }
    
    }
    
    technique Default
    {
        pass P0
        {
            VertexShader = compile vs_3_0 Psl_VertexShaderFunction();
            PixelShader = compile ps_3_0 Psl_PixelShaderFunction();
        }
    }
    

    最佳答案

    正如您所指出的,它们是不同的。 GLSL mod将始终具有与 y 相同的符号而不是 x .否则它是一样的——一个值 f使得 x = i*y + f哪里i是一个整数且 |f| < |y| .如果您正在尝试制作某种重复模式,请使用 GLSL mod通常是你想要的。

    作为比较,HLSL fmod相当于 x - y * trunc(x/y) .当 x/y 时,它们是相同的为正,与 x/y 不同是否定的。

    关于math - Glsl mod 与 Hlsl fmod,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/7610631/

    相关文章:

    c++ - Windows 10 标题栏不工作

    C++ union 数据结构,轻松访问 DWORD 中的位

    c++ - 为什么当我尝试重写指向 Direct3D 设备的 `EndScene` 函数的指针时什么也没有发生?

    java - 包含椭圆的组绕任意轴旋转,如何获取该组上椭圆的 x 和 y 距离变化?

    python - 比较 Python 中的(函数的)求根算法

    python - 评估一阶算术公式

    performance - 替换现有 VAO 中的 VBO

    javascript - 如何在 Javascript 中模拟 Google Sheet 乘法公式的结果?

    opengl - opengl 和 GLSL 有什么区别?

    opengl - GLSL 组件方式相等比较