简体   繁体   English

金属片段着色器的uv坐标在读取顶点颜色时发生更改

[英]Metal fragment shader uv coordinates change when reading in vertex color

I was playing with applying dithering to a simple colored quad, and found a strange issue. 我在对一个简单的彩色四边形应用抖动处理时发现一个奇怪的问题。 I have a fragment shader which should calculate dithering at some uv and return a dithered color. 我有一个片段着色器,它应该在某些uv计算抖动并返回抖动的颜色。 This works fine on a textured quad, but strangely enough, when I access color data from my inVertex , the uv coordinates change to some bizarre values, and y value seems to be mapped to x axis. 这在带纹理的四边形上可以正常工作,但是奇怪的是,当我从inVertex访问颜色数据时, uv坐标更改为一些奇怪的值,并且y值似乎映射到x轴。 I'll try to illustrate what happens when I change stuff around the fragment shader code. 我将尝试说明在片段着色器代码周围进行更改时发生的情况。

fragment float4 fragment_colored_dithered(ColoredVertex inVertex [[stage_in]],
                                              float2 uv[[point_coord]]) {
        float4 color = inVertex.color;
        uv = (uv/2) + 0.5;
        if (uv.y < 0.67) {
            return float4(uv.y, 0, 0, 1);
        }
        else {
            return color;
        }
    }

Produces the following result: 产生以下结果: 在此处输入图片说明

Where the left side of the image shows my gradient quad, notice that if (uv.y < 0.67) maps to x values in the image 🤔. 在图像左侧显示我的渐变四边形的地方,请注意, if (uv.y < 0.67)映射到图像🤔中的x值。

If I change this fragment shader and nothing else in the code, like so, where I return float4(0, 0, 1, 0) instead of inVertex.color , the uv coordinates are mapped correctly. 如果更改此片段着色器,而不更改代码中的其他内容,例如,在这里我return float4(0, 0, 1, 0) inVertex.color return float4(0, 0, 1, 0)而不是inVertex.color ,则将正确映射uv坐标。

fragment float4 fragment_colored_dithered(ColoredVertex inVertex [[stage_in]],
                                          float2 uv[[point_coord]]) {
    float4 color = inVertex.color;
    uv = (uv/2) + 0.5;
    if (uv.y < 0.67) {
        return float4(uv.y, 0, 0, 1);
    }
    else {
        return float4(0, 0, 1, 0); //return color;
    }
} 

Produces this (correct) result: 产生以下(正确)结果: 在此处输入图片说明

I think I can hack around this problem by applying a 1x1 texture to the gradient and using texture coordinates, but I'd really like to know what is happening here, is this a bug or a feature that I don't understand? 我认为可以通过将1x1纹理应用于渐变并使用纹理坐标来解决此问题,但是我真的很想知道这里发生了什么,这是我不了解的错误还是功能?

Why are you using [[point_coord]] ? 为什么使用[[point_coord]] What do you think it represents? 您认为它代表什么?

Unless you're drawing point primitives, you shouldn't be using that. 除非绘制点图元,否则不应该使用它。 Since you're drawing a "quad", and given the screenshots, I assume you're not drawing point primitives. 由于您正在绘制“四边形”并给出了屏幕截图,因此我假设您没有绘制点图元。

I suspect [[point_coord]] is simply undefined and subject to random-ish behavior when you're drawing triangles. 我怀疑[[point_coord]]只是未定义,在绘制三角形时会受到随机[[point_coord]]影响。 The randomness is apparently affected by the specifics (such as stack layout) of the fragment shader. 随机性显然受片段着色器细节(例如堆栈布局)的影响。

You should either be using [[position]] and scaling by the window size or using an interpolated field within your ColoredVertex struct to carry "texture" coordinates. 您应该使用[[position]]并按窗口大小进行缩放,或者在ColoredVertex结构中使用插值字段来携带“纹理”坐标。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM