Search Unity

Oblique projection and fog

Discussion in 'Shaders' started by aubergine, Mar 2, 2022.

  1. aubergine

    aubergine

    Joined:
    Sep 12, 2009
    Posts:
    2,878
    Anybody has any idea about how to make an oblique projection w friendly so that the unity builtin fog will work instead of writing custom fog function for reflective surfaces?

    Here is my oblique projection function with a clip plane

    Code (CSharp):
    1.         protected static void SetObliqueMatrix(ref Matrix4x4 mtx, Vector4 plane) {
    2.             Vector4 q;
    3.             q.x = (Sgn(plane.x) + mtx[8]) / mtx[0];
    4.             q.y = (Sgn(plane.y) + mtx[9]) / mtx[5];
    5.             q.z = -1f;
    6.             q.w = (1.0f - mtx[10]) / mtx[14];
    7.             Vector4 c = plane * (2.0f / (Vector4.Dot(plane, q)));
    8.             mtx[2] = c.x;
    9.             mtx[6] = c.y;
    10.             mtx[10] = c.z + 1.0f;
    11.             mtx[14] = c.w;
    12.            
    13.             //mtx[0,0] = mtx[0,0] / mtx[2,3];
    14.             //mtx[1,1] = mtx[1,1] / mtx[2,3];
    15.             //mtx[2,2] = mtx[2,2] / mtx[2,3];
    16.             //mtx[2,3] = mtx[2,3] / mtx[2,3];
    17.         }
    DirectX documents mention that we should divide the above commented lines but while the fog works, the projection is also gets distorted.
     
  2. StaggartCreations

    StaggartCreations

    Joined:
    Feb 18, 2015
    Posts:
    2,260
    Afaik this never worked correctly. Mostly because an oblique projection results in a ridiculous far clipping plane distance (+10k). This jacks the calculated fog factor in the shader, since it's based on clip space z-depth.

    A viable option is to temporarily disable fog before you execute the reflection render, then enabled it back again. The reflective surface would already be fogged, so it usually goes unnoticed.
     
  3. aubergine

    aubergine

    Joined:
    Sep 12, 2009
    Posts:
    2,878
    When you divide, it should be normalized and actually it does if you add mtx[2,3]=1f at the end of the function, but then the projection is distorted. So i thought im doing the division wrong. Here is what directx docs say:



    The viable option you mention is not really viable and when it comes to tricks there are far better options. But i would prefer if this one works.