代码之家  ›  专栏  ›  技术社区  ›  Roi Mulia

与OpenGL mix相当的金属

  •  0
  • Roi Mulia  · 技术社区  · 7 年前

    我在试着理解什么是等价物 mix OpenGL OpenGL 我试图转换的代码:

    float udRoundBox( vec2 p, vec2 b, float r )
    {
        return length(max(abs(p)-b+r,0.0))-r;
    }
    
    void mainImage( out vec4 fragColor, in vec2 fragCoord )
    {
        // setup
        float t = 0.2 + 0.2 * sin(mod(iTime, 2.0 * PI) - 0.5 * PI);
        float iRadius = min(iResolution.x, iResolution.y) * (0.05 + t);
        vec2 halfRes = 0.5 * iResolution.xy;
    
        // compute box
        float b = udRoundBox( fragCoord.xy - halfRes, halfRes, iRadius );
    
        // colorize (red / black )
        vec3 c = mix( vec3(1.0,0.0,0.0), vec3(0.0,0.0,0.0), smoothstep(0.0,1.0,b) );
    
        fragColor = vec4( c, 1.0 );
    } 
    

    到目前为止,我能够转换其中的一部分:

    float udRoundBox( float2 p, float2 b, float r )
    {
        return length(max(abs(p)-b+r,0.0))-r;
    }
    
    float4 cornerRadius(sampler_h src) {
    
        float2 greenCoord = src.coord(); // this is alreay in relative coords; no need to devide by image size
    
        float t = 0.5;
        float iRadius = min(greenCoord.x, greenCoord.y) * (t);
        float2 halfRes = float2(greenCoord.x * 0.5, greenCoord.y * 0.5);
    
        float b = udRoundBox( float2(greenCoord.x - halfRes.x, greenCoord.y - halfRes.y), halfRes, iRadius );
    
        float3 c = mix(float3(1.0,0.0,0.0), float3(0.0,0.0,0.0), smoothstep(0.0,1.0,b) );
    
        return float4(c, 1.0);
    }
    

    但它正在生产绿色屏幕。我试图在视频中实现拐角半径,如下所示:

    enter image description here

    0 回复  |  直到 7 年前
        1
  •  3
  •   Frank Rupprecht    7 年前

    问题是 greenCoord 当前像素 与绝对输入分辨率无关。

    如果您想更换您的 iResolution 使用 src.size() 相反

    destination 参数设置为内核的输入,如下所示:

    float4 cornerRadius(sampler src, destination dest) {
        const float2 destCoord = dest.coord(); // pixel position in the output buffer in absolute coordinates
        const float2 srcSize = src.size();
    
        const float t = 0.5;
        const float radius = min(srcSize.x, srcSize.y) * t;
        const float2 halfRes = 0.5 * srcSize;
    
        const float b = udRoundBox(destCoord - halfRes, halfRes, radius);
    
        const float3 c = mix(float3(1.0,0.0,0.0), float3(0.0,0.0,0.0), smoothstep(0.0,1.0,b) );
    
        return float4(c, 1.0);
    }
    
        2
  •  3
  •   AdaRaider    7 年前

    混合函数是线性插值的一种实现,通常称为Lerp函数。

    例如,如果我有三个值:

    a=0 b=1 和

    我可以调用mix(a,b,t),结果是0.5。这是因为mix函数需要一个起始范围值、一个结束范围值和一个用于插值的因子,所以我得到0.5,介于0和1之间。

    查看文档Metal有一个执行线性插值的mix实现。

    enter image description here