zoukankan      html  css  js  c++  java
  • OpenGL ReverseZ

     https://nlguillemot.wordpress.com/2016/12/07/reversed-z-in-opengl/

    测试代码

    #include<stdio.h>
    #include<conio.h>
    #include<windows.h>
    #include<iostream>
    #include <cassert>
    
    //计算nativeZ
    float NativeZ(double nearv, double farv, double EyePosZ)
    {
        /*
        float a = -(farv + nearv) / (farv - nearv);
        float b = -(2.0 * farv* nearv / (farv - nearv));
        float depthv =  (a *EyePosZ + b) / -EyePosZ;  //模拟除以w值, -zeye的值
        return depthv;*/
    
        float a = -(farv + nearv) / (farv - nearv) *EyePosZ;
        float b = -(2.0 * farv* nearv / (farv - nearv));
        float depthv = (a  + b) / -EyePosZ;  //模拟除以w值, -zeye的值
        return depthv; 
    }
    
    
    float ReverseZ(double nearz, double farz, double EyePosZ)
    {
        float a = nearz / (farz - nearz);
        float b = farz * nearz / (farz- nearz);
    
        float depthv = (a *EyePosZ  + b) / -EyePosZ;  //模拟除以w值, -zeye的值
    
        return depthv;
    }
    
    
    //NativeZ to LinearZ
    float LinearizeDepth(float nearv,float farv,float Nativedepth)
    {
        float a = -(farv + nearv) / (farv - nearv);
        float b = -(2.0 * farv* nearv / (farv - nearv));
    
        //float z = Nativedepth * 2.0 - 1.0; // back to NDC 
        //return (2.0 * nearv * farv) / (farv + nearv - z * (farv - nearv)) ;
    
        float eyeposZ = -b / (a + Nativedepth);
    
        return (-eyeposZ -nearv) /(farv -nearv);
    }
    
    //NativeZ to LinearZ
    float LinearizeDepthold(float nearv, float farv, float Nativedepth)
    {
        float z = Nativedepth * 2.0 - 1.0; // back to NDC 
        return ((2.0 * nearv * farv) / (farv + nearv - z * (farv - nearv)) - nearv) / (farv - nearv);
    }
    
    //自己计算LinearZ,不依赖NativeZ
    float MyLinearCalc(float nearv, float farv, float eyePosZ)
    {
        float zv = -eyePosZ; //Opengl相机空间里 z是负值
    
        float x = (zv -nearv) ;
    
        return x /(farv - nearv);
    }
    
    float ReverseZToLinear(float nearz, float farz, float reversedz)
    {
        float a = nearz / (farz - nearz);
        float b = farz * nearz / (farz - nearz);
    
        float eyeposZ = -b / (a + reversedz);
    
        return eyeposZ ;
    }
    
    
    
    
    
    const float CameraFar = 4000;
    const float CameraNear = 2;
    
    
    int main()
    {
        const int stepN = 400;
        /*
        for (int n = 0; n < stepN; ++n)
        {
            float eyePosZ = -n * (CameraFar -CameraNear) / (float)stepN - CameraNear;
            float nativeZ = NativeZold(CameraNear, CameraFar, eyePosZ);
            float linearv = LinearizeDepthold(CameraNear, CameraFar, nativeZ * 0.50 -0.50);
            float myCalcZ = MyLinearCalcold(CameraNear, CameraFar, eyePosZ);
            
            float newNativeZ = NativeZ(CameraNear, CameraFar, eyePosZ);
            float newLinearZ = LinearizeDepth(CameraNear, CameraFar, nativeZ);
            printf("nativeZ:%f  %f  %f %f  %f  %f 
    ",eyePosZ, nativeZ,newNativeZ, linearv,myCalcZ ,newLinearZ);
        }*/
    
        
        for (unsigned int n = 0; n <= stepN; ++n)
        {
            float oneStep = (CameraFar - CameraNear) / (float)stepN;
            float eyePosZ = -(n * oneStep )- CameraNear;
            float reverseZv = ReverseZ(CameraNear, CameraFar, eyePosZ);
            float nativeZ = NativeZ(CameraNear, CameraFar, eyePosZ) ;
            float eyeposRev = ReverseZToLinear(CameraNear, CameraFar, reverseZv);
            float eyeposNativ = LinearizeDepth(CameraNear, CameraFar, nativeZ);
            float myCalcZ = MyLinearCalc(CameraNear, CameraFar, eyePosZ);
            float lineardepthold = LinearizeDepthold(CameraNear, CameraFar, nativeZ * 0.5f+ 0.5);
            printf("nativeZ:%f  %f  -- %f  %f  %f  %f
    ", eyePosZ,reverseZv,nativeZ,  eyeposNativ,lineardepthold, myCalcZ);
        }
    
        int delay;
        scanf("%d",&delay);
    }

    为了展示,我线性化后的,否则一片漆黑

  • 相关阅读:
    Java-JUC(四):同步容器介绍
    Java-JUC(三):原子性变量与CAS算法
    Java:双向链表反转实现
    Java-JUC(二):Java内存模型可见性、原子性、有序性及volatile具有特性
    Java-JUC(一):volatile引入
    TSQL:判断某较短字符串在较长字符串中出现的次数。
    二叉树的定义与前序、中序、后序遍历
    c#:判断一个数组元素中否有重复元素
    c#:对两个字符串大小比较(不使用c#/java内部的比较函数),按升序排序
    mysql之 OPTIMIZE TABLE整理碎片
  • 原文地址:https://www.cnblogs.com/dragon2012/p/14880373.html
Copyright © 2011-2022 走看看