three.js: gradientMap GLSL is probably not correct?

Description of the problem

Looking at the gradientmap GLSL

this line

 vec2 coord = vec2( dotNL * 0.5 + 0.5, 0.0 );

this will not actually give a correct gradient. Imagine you have a 2x1 texture.

The correct gradient is here
       |             |
       V             V
+-------------+-------------+
|             |             |
+-------------+-------------+
^                           ^
|                           |
But the code above uses this. That means much of the sampling is outside gradient.

In other words you need to read the gradient from the center of the first texel to the center of the last texel. Past the center on either side is just solid color. The linear interpolation happens between texels which are defined by center points.

The correct code unfortunately requires the width of the gradient texture

 float gradientPos = dotNL * 0.5 + 0.5;
 float sampleLoc = 0.5 + (gradientWidth - 1) * gradientPos;
 vec2 coord = vec2(sampleLoc / gradientWidth, 0.0 );

Does anyone care?

Three.js version
  • Dev
  • r94

About this issue

  • Original URL
  • State: closed
  • Created 6 years ago
  • Comments: 19 (8 by maintainers)

Most upvoted comments

I mean introducing an alternative API for defining gradients.

Sidenote: Apart from defining the amount of tones you could also allow the definition of the respective thresholds (which define when you switch from one tone to the next one).

@WestLangley Sounds interesting, yes. I mean introducing an alternative API for defining gradients.

However, @greggman seems to have issues with the term gradientMap itself. Because in cel shading, you are not rendering real color gradients but single tones.

It’s ridiculous to claim my method is wrong when it’s easy to prove

Um, did you actually read my comments? I did not say your method is wrong. Just inconvenient because of the introduction of an additional uniform which requires the texture’s dimension.

I’ll look into a few weeks. Sorry, I’ve been busy lately.