Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Incorrect implementation of SplitTB, RampTB and Ramp4 node types #1758

Open
HardCoreCodin opened this issue Apr 2, 2024 · 2 comments
Open

Comments

@HardCoreCodin
Copy link

HardCoreCodin commented Apr 2, 2024

Hello, while using 'splittb_float' node in MaterialX Graph Editor I seem to have stumbled on a real issue where the glsl (and OSL code) is incorrect.
Note: I'll prefice this by highlighting that I am well aware of there being different conventions for how UV space is conceptualized in different realtime rendering engines (w.r.t vertical V dimention directional layout), but as you will see, this issue is agnostic to that disctinction and is just based on what the MaterialX specification specifies vs. what the GLSL and OSL implementations are doing.

The speification for the node states:

splittb: a top-bottom split matte, split at a specified V value.

  • valuet (float or colorN or vectorN): the value at the top (V=1) edge
  • valueb (float or colorN or vectorN): the value at the bottom (V=0) edge
  • center (float): a value representing the V-coordinate of the split; all pixels above "center" will be valuet, all pixels below "center" will be valueb. Default is 0.5.
  • texcoord (vector2): the name of a vector2-type node specifying the 2D texture coordinate at which the split position is evaluated. Default is to use the first set of texture coordinates.

So when the input value ('V' in MaterialX spec, texcoord.y in the GLSL and OSL code) is below the 'center' input value, then the output should be the bottom value ('valueb'), otherwise if it is above then the output should be the top value ('valuet').
Given a default 'center' value of 0.5, it means that a texcoord.y value of 0.0 should yield 'valueb' as the output, and a texcoord.y value of 1.0 should yield 'valuet' as the output.

The glsl and OSL code seem to do the opposite:
mix in GLSL (and similarly in OSL) returns the first argument value when the third argument is 0.0.
The third argument here is a call to mx_aastep(center, texcoord.y) which internlly uses smoothstep.
For a default 'center' value of 0.5, a texcoord.y value of 0.0 yields 0.0 so the third argument to mix() is 0.0, meaning the first argument to mix() is returned. texcoord.y being 0.0 is below 'center' of 0.5 so the MaterialX spec states that 'valueb' should be returned, and yet the returned first argument to mix() is 'valuet'.
Similarly, when texcoord.y is 1.0 being above a 'center' value of 0.5 the MaterilX spec states that 'valuet' should be returned, and yet this glsl implementtion returns 'valueb' in this case.

Here is a demonstration of the effect of this using the bundled MaterialX Graph Editor:
Using a simple plane segment mesh with texture coordinates, here is how the values of 'texcoord.y' look:
MaterialX_Graph_Editor_TexcoordY
And here is how splittb behaves with a 'valueb' of 0 and 'valuet' of 1 and a default 'center' of 0.5:
MaterialX_Graph_Editor_SplitTB

UPDATE: The same applies to ramptp node type:

ramptb: a top-to-bottom linear value ramp.

  • valuet (float or colorN or vectorN): the value at the top (V=1) edge
  • valueb (float or colorN or vectorN): the value at the bottom (V=0) edge
  • texcoord (vector2): the name of a vector2-type node specifying the 2D texture coordinate at which the ramp interpolation is evaluated. Default is to use the first set of texture coordinates.
MaterialX_RampTB

UPDATE2: Same happens for ramp4 - a vertical flip.

@HardCoreCodin HardCoreCodin changed the title Incorrect GLSL implementation of SplitTB node Incorrect implementation of SplitTB node Apr 2, 2024
@HardCoreCodin HardCoreCodin changed the title Incorrect implementation of SplitTB node Incorrect implementation of SplitTB and RampTB node types Apr 3, 2024
@HardCoreCodin HardCoreCodin changed the title Incorrect implementation of SplitTB and RampTB node types Incorrect implementation of SplitTB, RampTB and Ramp4 node types Apr 3, 2024
@jstone-lucasfilm
Copy link
Member

This is a great catch as well, thanks @HardCoreCodin. If you have the bandwidth to address the two issues that you caught, feel free to propose PRs for these!

@HardCoreCodin
Copy link
Author

HardCoreCodin commented May 6, 2024

Thank you @jstone-lucasfilm for your consideration. I would not be looking to fix those, as I've only looked at 2 of the backends and am not actually using any of them (I use a different backend). I am using existing graph editors like Material Graph Editor that comes with the library and QuiltiX, as a way of authoring MaterialX node graphs and then importing them into a rendering application. My backend implements the nodes according to the MaterialX spec, so most importantly - I am using these editors to visually validate my implementation against them. Especially the built-in Material Graph Editor that comes with the library, should be considered safe to use as reference point, in my opinion. It gets a bit confusing when my nodes are up to spec and yet my results appear different from what's in the library's editor. As far as I understand, all these editors use the library's backends for code generation so inherit these issues when these backends aren't to spec.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants