Draw a line segment in a fragment shader

2019-08-02 15:06发布

I'm struggling to understand the following code, the idea is to draw a simple segment in a fragment shader. I tried to decompose it but I still don't get the ??? line. It would be awesome to have a nice explanation. I couldn't find anything on SO or Google.

float lineSegment(vec2 p, vec2 a, vec2 b) {
    float thickness = 1.0/100.0;

    vec2 pa = p - a;
    vec2 ba = b - a;

    float h = clamp( dot(pa,ba)/dot(ba,ba), 0.0, 1.0 );
    // ????????
    float idk = length(pa - ba*h);

    return smoothstep(0.0, thickness, idk);
}

Original code comes from TheBookOfShaders.

1条回答
等我变得足够好
2楼-- · 2019-08-02 15:44

Assuming the line is defined by the points a, b, and p is the point to evaluate, then pa is the vector that goes from point a to point p and ba the vector from a to b.

Now, dot(ba, ba) is equal to length(ba) ^ 2 and dot(pa,ba) / length(ba) is the projection of the vector pa over your line. Then, dot(pa,ba)/dot(ba,ba) is the projection normalized over the length of your line. That value is clamped between 0 and 1 so your projection will always be in between the point that define your line.

Then on length(pa - ba * h), ba * h is equal to dot(pa,ba) / length(ba) which was the projection of your point over your line, now clamped between points a and b. The subtraction pa - ba * h results in a vector that represents the minimum distance between your line and point p. Using the length of that vector and comparing it against the thickness you can determine whether the point falls inside the line you want to draw.

查看更多
登录 后发表回答