textureLod + textureQueryLod == texture?

Hi,

Are there two set of operations supposed to produce the same visual result, even with anisotropic filtering enable?

Color = textureLod(Diffuse, is_In.Texcoord * 16, textureQueryLod(Diffuse, is_In.Texcoord * 16).x);

Color = texture(Diffuse, is_In.Texcoord * 16);

Thanks!

The benefit of not having aniso in core :wink:

I wouldn’t expect these two to behave the same with aniso > 1.
‘textureLod’ is supposed to sample from specific lod, it logically sets partial derivatives to 0, so i cant see how it can do any anisotropic filtering.

Then again, i dont think anything definite is possible to dig out from specs.

textureQueryLod is actually not the problem and generate LOD value that looks correct even with anisotropic filtering. If I use own textureQueryLod I wrote myself for anisotropic filtering, I have a coherence result. However, ‘textureLod’ seems to introduce aliasing artefacts as if the pixel footprint was too small.

This is happening on AMD, I need to check on NVIDIA…

The issue i mentioned is: query lod ‘flattens’ its input data to just one float. You cant do anisotropic filtering with just a single float (lod) and texcoord from which no derivatives are computed - theres just not enough data.

If you still see exact same results then i would consider this a bug. This is assuming ‘texture’ is using anisotropic filtering and you have data that causes it to look different then normal case.

Are there two set of operations supposed to produce the same visual result, even with anisotropic filtering enable?

No. The textureLod function explicitly sets the derivatives to zero. So anisotropic filtering has no information to go on.

Oo

Why setting the derivative to 0? Why not computing the derivative when anisotropic filtering is enable? That just doesn’t make any sense to me… but yes it’s apparently what it does :stuck_out_tongue:

Why not computing the derivative when anisotropic filtering is enable?

Because that’s what it’s for. It is for fetching directly from a specific mipmap level (or levels, when doing filtering). It would seem silly to compute derivatives just for anisotropic filtering, while ignoring the use of those derivatives in computing which mipmaps to use.

Anisotropic filtering affects the selected mipmap. Therefore, it doesn’t make sense to use any anisotropic filtering if the selected mipmap isn’t also being computed by the algorithm. The results would not be reasonable.

This is also why textureGrad exists.

Anisotropic filtering is useful without mipmaps. Just stretch a 2D image.

Anisotropic filtering is useful without mipmaps.

Useful is a strong word. It can be used, but it is far more efficient with mipmaps. Also, since he’s using textureLod, mipmaps are kinda required.

That doesn’t seems silly to me. If for anisotropic filtering we need to compute the derivative, then compute the derivative when the anisotropic filtering is used. If it is useless for trilinear filtering, then don’t compute it.

The lod level is computed from the derivates, so it is necessary whether you use anisotropic filtering or not.

The difference between the first and second commands is that the first one ignores anisotropy and the .y component of the textureQueryLod, so that you get only bilinear interpolation.

That doesn’t seems silly to me. If for anisotropic filtering we need to compute the derivative, then compute the derivative when the anisotropic filtering is used. If it is useless for trilinear filtering, then don’t compute it.

textureLod is used to select a specific LOD from the texture. That’s the purpose of the function. It’s like accessing an array; if you ask for the 3.4 LOD, you should not get information from LOD 2. You asked for a specific location and LOD; anisotropic filtering would interfere with that.

You are wrong and there is no interference. textureQueryLod would compute a different lod if the sampler has anisotropic filtering set.

The derivatives are used to determine the direction of the pixel footprint and its size, how this has to do with the LOD? The mipmaps can be anything but if there are anything we will either have 1/ aliasing or 2/ blurry filtering.

Moreover, textureLod takes a float and can linearly interpolate between 2 mipmaps, how this is like accessing an array?

The difference between textureQueryLod().x and textureQueryLod().y is only that the sampler parameters (lod bias, lod min, lod max) are taken into account with .x and not .y.

The only issue with decoupling texture with textureQueryLod and textureLod is that some operations must be done twice, like computing the derivatives.

There isn’t any technical limitation here the real question is more either this is useful or not? It makes a lot of sense to use the build-in textureQueryLod() to take advantage of the dedicated hardware to compute the LOD. However, only corner cases will take advantage of using a user-defined textureQueryLod() and the build-in textureLod(). I indeed up on that case checking the behaviours of my textureQueryLod function but my goal is to write a sampling function.

In the end there is one absolute case to do this: hardware that don’t support textureQueryLod. In the end people would say use textureGrad if you don’t have textureQueryLod.

The derivatives are used to determine the direction of the pixel footprint and its size, how this has to do with the LOD?

Because anisotropic filtering can fetch from many LODs. Not just the two nearest. It depends on the sample area in texture space, as approximated by the gradients. Therefore, incorporating anisotropy into textureLod would violate the entire point of the function: to select from one (or two+interpolation) specific LOD.

There isn’t any technical limitation

Exactly; the question is what should the API do.

There should be a function that fetches from a specific LOD. If gradients were involved in that fetching, then anisotropic filtering could change the specific LOD in question. And therefore, it would not be a function that fetches from a specific LOD.

You’re looking at this from the perspective of wanting to use textureQueryLod and textureLod together to emulate the functioning of texture. I’m telling you that textureLod is the wrong tool for that task.

I’m not saying that there shouldn’t be a textureLodGrad or something. I’m saying that textureLod has a specific purpose and functionality which is useful. And it does not and should not provide the features you need, because it provides other features that other people need.

I just hope nobody from Khronos reads this. They could go ahead and push for textureLodGradProjOffset and family :wink:

One thing this problem shows though, is that its not the best idea to have universally supported features outside of specification.

One thing this problem shows though, is that its not the best idea to have universally supported features outside of specification.

Why? This has nothing to do aniso not being part of core. The textureLod documentation specifically states that the gradients are 0. Even if aniso were core, textureLod would effectively turn it off.

It could. It doesn’t have to. Extensions amend the specification, so aniso could effectively override the workings of any GLSL functions. It predates GLSL though, so how it affects it isn’t really well defined.

And even though derivatives are set to zero, aniso could still work by means of magic - as its currently defined.

This topic was automatically closed 183 days after the last reply. New replies are no longer allowed.