132001f49Smrg/* showbuffer.c */
232001f49Smrg
332001f49Smrg
432001f49Smrg/*
532001f49Smrg * Copy the depth buffer to the color buffer as a grayscale image.
632001f49Smrg * Useful for inspecting the depth buffer values.
732001f49Smrg *
832001f49Smrg * This program is in the public domain.
932001f49Smrg *
1032001f49Smrg * Brian Paul   November 4, 1998
1132001f49Smrg */
1232001f49Smrg
1332001f49Smrg
1432001f49Smrg#include <assert.h>
1532001f49Smrg#include <stdlib.h>
1632001f49Smrg#include "gl_wrap.h"
1732001f49Smrg#include "showbuffer.h"
1832001f49Smrg
1932001f49Smrg
2032001f49Smrg
2132001f49Smrg/*
2232001f49Smrg * Copy the depth buffer values into the current color buffer as a
2332001f49Smrg * grayscale image.
2432001f49Smrg * Input:  winWidth, winHeight - size of the window
2532001f49Smrg *         zBlack - the Z value which should map to black (usually 1)
2632001f49Smrg *         zWhite - the Z value which should map to white (usually 0)
2732001f49Smrg */
2832001f49Smrgvoid
2932001f49SmrgShowDepthBuffer( GLsizei winWidth, GLsizei winHeight,
3032001f49Smrg                 GLfloat zBlack, GLfloat zWhite )
3132001f49Smrg{
3232001f49Smrg   GLfloat *depthValues;
3332001f49Smrg
3432001f49Smrg   assert(zBlack >= 0.0);
3532001f49Smrg   assert(zBlack <= 1.0);
3632001f49Smrg   assert(zWhite >= 0.0);
3732001f49Smrg   assert(zWhite <= 1.0);
3832001f49Smrg   assert(zBlack != zWhite);
3932001f49Smrg
4032001f49Smrg   glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
4132001f49Smrg   glPixelStorei(GL_PACK_ALIGNMENT, 1);
4232001f49Smrg
4332001f49Smrg   /* Read depth values */
4432001f49Smrg   depthValues = (GLfloat *) malloc(winWidth * winHeight * sizeof(GLfloat));
4532001f49Smrg   assert(depthValues);
4632001f49Smrg   glReadPixels(0, 0, winWidth, winHeight, GL_DEPTH_COMPONENT,
4732001f49Smrg                GL_FLOAT, depthValues);
4832001f49Smrg
4932001f49Smrg   /* Map Z values from [zBlack, zWhite] to gray levels in [0, 1] */
5032001f49Smrg   /* Not using glPixelTransfer() because it's broke on some systems! */
5132001f49Smrg   if (zBlack != 0.0 || zWhite != 1.0) {
5232001f49Smrg      GLfloat scale = 1.0 / (zWhite - zBlack);
5332001f49Smrg      GLfloat bias = -zBlack * scale;
5432001f49Smrg      int n = winWidth * winHeight;
5532001f49Smrg      int i;
5632001f49Smrg      for (i = 0; i < n; i++)
5732001f49Smrg         depthValues[i] = depthValues[i] * scale + bias;
5832001f49Smrg   }
5932001f49Smrg
6032001f49Smrg   /* save GL state */
6132001f49Smrg   glPushAttrib(GL_CURRENT_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT |
6232001f49Smrg                GL_TRANSFORM_BIT | GL_VIEWPORT_BIT);
6332001f49Smrg
6432001f49Smrg   /* setup raster pos for glDrawPixels */
6532001f49Smrg   glMatrixMode(GL_PROJECTION);
6632001f49Smrg   glPushMatrix();
6732001f49Smrg   glLoadIdentity();
6832001f49Smrg
6932001f49Smrg   glOrtho(0.0, (GLdouble) winWidth, 0.0, (GLdouble) winHeight, -1.0, 1.0);
7032001f49Smrg   glMatrixMode(GL_MODELVIEW);
7132001f49Smrg   glPushMatrix();
7232001f49Smrg   glLoadIdentity();
7332001f49Smrg
7432001f49Smrg   glViewport(0, 0, winWidth, winHeight);
7532001f49Smrg
7632001f49Smrg   glDisable(GL_STENCIL_TEST);
7732001f49Smrg   glDisable(GL_DEPTH_TEST);
7832001f49Smrg   glRasterPos2f(0, 0);
7932001f49Smrg
8032001f49Smrg   glDrawPixels(winWidth, winHeight, GL_LUMINANCE, GL_FLOAT, depthValues);
8132001f49Smrg
8232001f49Smrg   glPopMatrix();
8332001f49Smrg   glMatrixMode(GL_PROJECTION);
8432001f49Smrg   glPopMatrix();
8532001f49Smrg   free(depthValues);
8632001f49Smrg
8732001f49Smrg   glPopAttrib();
8832001f49Smrg}
8932001f49Smrg
9032001f49Smrg
9132001f49Smrg
9232001f49Smrg
9332001f49Smrg/*
9432001f49Smrg * Copy the alpha channel values into the current color buffer as a
9532001f49Smrg * grayscale image.
9632001f49Smrg * Input:  winWidth, winHeight - size of the window
9732001f49Smrg */
9832001f49Smrgvoid
9932001f49SmrgShowAlphaBuffer( GLsizei winWidth, GLsizei winHeight )
10032001f49Smrg{
10132001f49Smrg   GLubyte *alphaValues;
10232001f49Smrg
10332001f49Smrg   glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
10432001f49Smrg   glPixelStorei(GL_PACK_ALIGNMENT, 1);
10532001f49Smrg
10632001f49Smrg   /* Read alpha values */
10732001f49Smrg   alphaValues = (GLubyte *) malloc(winWidth * winHeight * sizeof(GLubyte));
10832001f49Smrg   assert(alphaValues);
10932001f49Smrg   glReadPixels(0, 0, winWidth, winHeight, GL_ALPHA, GL_UNSIGNED_BYTE, alphaValues);
11032001f49Smrg
11132001f49Smrg   /* save GL state */
11232001f49Smrg   glPushAttrib(GL_CURRENT_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL |
11332001f49Smrg                GL_TRANSFORM_BIT | GL_VIEWPORT_BIT);
11432001f49Smrg
11532001f49Smrg   /* setup raster pos for glDrawPixels */
11632001f49Smrg   glMatrixMode(GL_PROJECTION);
11732001f49Smrg   glPushMatrix();
11832001f49Smrg   glLoadIdentity();
11932001f49Smrg
12032001f49Smrg   glOrtho(0.0, (GLdouble) winWidth, 0.0, (GLdouble) winHeight, -1.0, 1.0);
12132001f49Smrg   glMatrixMode(GL_MODELVIEW);
12232001f49Smrg   glPushMatrix();
12332001f49Smrg   glLoadIdentity();
12432001f49Smrg
12532001f49Smrg   glViewport(0, 0, winWidth, winHeight);
12632001f49Smrg
12732001f49Smrg   glDisable(GL_STENCIL_TEST);
12832001f49Smrg   glDisable(GL_DEPTH_TEST);
12932001f49Smrg   glRasterPos2f(0, 0);
13032001f49Smrg
13132001f49Smrg   glDrawPixels(winWidth, winHeight, GL_LUMINANCE, GL_UNSIGNED_BYTE, alphaValues);
13232001f49Smrg
13332001f49Smrg   glPopMatrix();
13432001f49Smrg   glMatrixMode(GL_PROJECTION);
13532001f49Smrg   glPopMatrix();
13632001f49Smrg   free(alphaValues);
13732001f49Smrg
13832001f49Smrg   glPopAttrib();
13932001f49Smrg}
14032001f49Smrg
14132001f49Smrg
14232001f49Smrg
14332001f49Smrg/*
14432001f49Smrg * Copy the stencil buffer values into the current color buffer as a
14532001f49Smrg * grayscale image.
14632001f49Smrg * Input:  winWidth, winHeight - size of the window
14732001f49Smrg *         scale, bias - scale and bias to apply to stencil values for display
14832001f49Smrg */
14932001f49Smrgvoid
15032001f49SmrgShowStencilBuffer( GLsizei winWidth, GLsizei winHeight,
15132001f49Smrg                   GLfloat scale, GLfloat bias )
15232001f49Smrg{
15332001f49Smrg   GLubyte *stencilValues;
15432001f49Smrg
15532001f49Smrg   glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
15632001f49Smrg   glPixelStorei(GL_PACK_ALIGNMENT, 1);
15732001f49Smrg
15832001f49Smrg   /* Read stencil values */
15932001f49Smrg   stencilValues = (GLubyte *) malloc(winWidth * winHeight * sizeof(GLubyte));
16032001f49Smrg   assert(stencilValues);
16132001f49Smrg   glReadPixels(0, 0, winWidth, winHeight, GL_STENCIL_INDEX, GL_UNSIGNED_BYTE, stencilValues);
16232001f49Smrg
16332001f49Smrg   /* save GL state */
16432001f49Smrg   glPushAttrib(GL_CURRENT_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT |
16532001f49Smrg                GL_PIXEL_MODE_BIT | GL_TRANSFORM_BIT | GL_VIEWPORT_BIT);
16632001f49Smrg
16732001f49Smrg   /* setup raster pos for glDrawPixels */
16832001f49Smrg   glMatrixMode(GL_PROJECTION);
16932001f49Smrg   glPushMatrix();
17032001f49Smrg   glLoadIdentity();
17132001f49Smrg
17232001f49Smrg   glOrtho(0.0, (GLdouble) winWidth, 0.0, (GLdouble) winHeight, -1.0, 1.0);
17332001f49Smrg   glMatrixMode(GL_MODELVIEW);
17432001f49Smrg   glPushMatrix();
17532001f49Smrg   glLoadIdentity();
17632001f49Smrg
17732001f49Smrg   glViewport(0, 0, winWidth, winHeight);
17832001f49Smrg
17932001f49Smrg   glDisable(GL_STENCIL_TEST);
18032001f49Smrg   glDisable(GL_DEPTH_TEST);
18132001f49Smrg   glRasterPos2f(0, 0);
18232001f49Smrg
18332001f49Smrg   glPixelTransferf(GL_RED_SCALE, scale);
18432001f49Smrg   glPixelTransferf(GL_RED_BIAS, bias);
18532001f49Smrg   glPixelTransferf(GL_GREEN_SCALE, scale);
18632001f49Smrg   glPixelTransferf(GL_GREEN_BIAS, bias);
18732001f49Smrg   glPixelTransferf(GL_BLUE_SCALE, scale);
18832001f49Smrg   glPixelTransferf(GL_BLUE_BIAS, bias);
18932001f49Smrg
19032001f49Smrg   glDrawPixels(winWidth, winHeight, GL_LUMINANCE, GL_UNSIGNED_BYTE, stencilValues);
19132001f49Smrg
19232001f49Smrg   glPopMatrix();
19332001f49Smrg   glMatrixMode(GL_PROJECTION);
19432001f49Smrg   glPopMatrix();
19532001f49Smrg   free(stencilValues);
19632001f49Smrg
19732001f49Smrg   glPopAttrib();
19832001f49Smrg}
199