[BACK]Return to cliptex_mwin.c CVS log [TXT][DIR] Up to [Development] / performer / src / pguide / libpr / C

File: [Development] / performer / src / pguide / libpr / C / cliptex_mwin.c (download)

Revision 1.1, Tue Nov 21 21:39:39 2000 UTC (16 years, 11 months ago) by flynnt
Branch: MAIN
CVS Tags: HEAD

Initial check-in based on OpenGL Performer 2.4 tree.
-flynnt

/*
 * Copyright 1995, Silicon Graphics, Inc.
 * ALL RIGHTS RESERVED
 *
 * This source code ("Source Code") was originally derived from a
 * code base owned by Silicon Graphics, Inc. ("SGI")
 * 
 * LICENSE: SGI grants the user ("Licensee") permission to reproduce,
 * distribute, and create derivative works from this Source Code,
 * provided that: (1) the user reproduces this entire notice within
 * both source and binary format redistributions and any accompanying
 * materials such as documentation in printed or electronic format;
 * (2) the Source Code is not to be used, or ported or modified for
 * use, except in conjunction with OpenGL Performer; and (3) the
 * names of Silicon Graphics, Inc.  and SGI may not be used in any
 * advertising or publicity relating to the Source Code without the
 * prior written permission of SGI.  No further license or permission
 * may be inferred or deemed or construed to exist with regard to the
 * Source Code or the code base of which it forms a part. All rights
 * not expressly granted are reserved.
 * 
 * This Source Code is provided to Licensee AS IS, without any
 * warranty of any kind, either express, implied, or statutory,
 * including, but not limited to, any warranty that the Source Code
 * will conform to specifications, any implied warranties of
 * merchantability, fitness for a particular purpose, and freedom
 * from infringement, and any warranty that the documentation will
 * conform to the program, or any warranty that the Source Code will
 * be error free.
 * 
 * IN NO EVENT WILL SGI BE LIABLE FOR ANY DAMAGES, INCLUDING, BUT NOT
 * LIMITED TO DIRECT, INDIRECT, SPECIAL OR CONSEQUENTIAL DAMAGES,
 * ARISING OUT OF, RESULTING FROM, OR IN ANY WAY CONNECTED WITH THE
 * SOURCE CODE, WHETHER OR NOT BASED UPON WARRANTY, CONTRACT, TORT OR
 * OTHERWISE, WHETHER OR NOT INJURY WAS SUSTAINED BY PERSONS OR
 * PROPERTY OR OTHERWISE, AND WHETHER OR NOT LOSS WAS SUSTAINED FROM,
 * OR AROSE OUT OF USE OR RESULTS FROM USE OF, OR LACK OF ABILITY TO
 * USE, THE SOURCE CODE.
 * 
 * Contact information:  Silicon Graphics, Inc., 
 * 1600 Amphitheatre Pkwy, Mountain View, CA  94043, 
 * or:  http://www.sgi.com
 *
** This program, cliptex, is a demo/test program for displaying a clip texture.
** it expects a clip texture configuration file as an argument. For information
** on clip texture configuration files, see pfdLoadClipTexture(3).
**
** The performer release has sample clipmap data you can run under
**  data/clipdata. The usual convention for naming clip texture configuration
** files is nameofdata.ct You should check the files for environment variable
** names. They may need to be set in order for the cliptexture config file
** to point to the data.
**
** cliptex shows a birds-eye view of the data, roaming the clip square back
** and forth. You can see the different levels of details as progressivly
** larger blurred torroidal zones around the clip center, which will
** be sharpest.
**
** You may want to use this program as a starting point to writing you
** own libpr-style cliptexture program. It is not as appropriate for
** libpf-style programs.
*/


#include <stdio.h>
#include <stdlib.h>
#include <math.h>
#include <string.h>
#include <strings.h>
#include <Performer/pfdu.h>
#include <Performer/pr.h>
#include <X11/keysym.h>
#include <sys/unistd.h>
#include <sys/types.h>
#include <sys/uio.h>
#include <fcntl.h>

#define ZMIN -.1
#define ZMAX .1
#define XMIN -.1
#define XMAX .1
#define YMIN -.1
#define YMAX .1

#define MAX_WINS 3


int winpos[3][2] = {{0, 0},
		    {256, 0},
		    {512, 0}};


pfClipTexture	*clip[MAX_WINS];
char		*clipfname;
pfWindow        *win[MAX_WINS];

static void 
do_events(Display *dsp, int *timing, int *move)
{
    static uint DTRMode = 0;
    while (XPending(dsp))
    {
	XEvent event;
	
	XNextEvent(dsp, &event);
	switch (event.type) 
	{
	case KeyPress:
	{
	    char buf[100];
	    int rv;
	    KeySym ks;

	    rv = XLookupString(&event.xkey, buf, sizeof(buf), &ks, 0);
	       
	    switch(ks) 
	    {
	    case XK_Escape:
		exit(0);
		break;
	    case XK_g:
	    case XK_G:
		if(*move) /* toggle movement */
		{
		    *move = 0;
		    pfNotify(PFNFY_INFO, PFNFY_PRINT, "Stop Moving");
		}
		else
		{
		    *move = 1;
		    pfNotify(PFNFY_INFO, PFNFY_PRINT, "Start Moving");
		}
		break;
	    case XK_t:
	    case XK_T:
		    if(DTRMode & PF_DTR_TEXLOAD)
		    {
			DTRMode &= ~PF_DTR_TEXLOAD;
			pfNotify(PFNFY_INFO, PFNFY_PRINT,
				 "Texture Download Load Control Disabled");
		    }
		    else
		    {
			DTRMode |=  PF_DTR_TEXLOAD;
			pfNotify(PFNFY_INFO, PFNFY_PRINT,
				 "Texture Download Load Control Enabled");
		    }
		    pfClipTextureDTRMode(clip[0], DTRMode);
		break;
	    case XK_m:
	    case XK_M:
		    if(DTRMode & PF_DTR_MEMLOAD)
		    {
			DTRMode &= ~PF_DTR_MEMLOAD;
			pfNotify(PFNFY_INFO, PFNFY_PRINT,
				 "Memory Download Load Control Disabled");
		    }
		    else
		    {
			DTRMode |=  PF_DTR_MEMLOAD;
			pfNotify(PFNFY_INFO, PFNFY_PRINT,
				 "Memory Download Load Control Enabled");
		    }
		    pfClipTextureDTRMode(clip[0], DTRMode);
		break;
	    case XK_r:
	    case XK_R:
		    /* toggle read queue sorting bit */
		    if(DTRMode & PF_DTR_READSORT)
		    {
			DTRMode &= ~PF_DTR_READSORT;
			pfNotify(PFNFY_INFO, PFNFY_PRINT,
				 "Read Queue Sorting Disabled");
		    }
		    else
		    {
			DTRMode |=  PF_DTR_READSORT;
			pfNotify(PFNFY_INFO, PFNFY_PRINT,
				 "Read Queue Sorting Enabled");
		    }
		    pfClipTextureDTRMode(clip[0], DTRMode);
		break;
	    case XK_s:
	    case XK_S: /* toggle performance statistics */
		*timing = !(*timing);
		if(*timing)
		    pfNotify(PFNFY_INFO, PFNFY_PRINT,
			     "Performance Timing Enabled");
		else
		    pfNotify(PFNFY_INFO, PFNFY_PRINT,
			     "Performance Timing Disabled");
		break;
	    case XK_d:
	    case XK_D: /* delete cliptexture */
		if(clip[0])
		{
		    int i;
		    pfNotify(PFNFY_INFO, PFNFY_PRINT,
			     "Deleting Clip Texture");
		    pfDelete(clip[0]);
		    for(i = 0; i < MAX_WINS; i++)
		    {
			clip[i] = 0;
			pfSelectWin(win[i]);
			pfDisable(PFEN_TEXTURE);
		    }
		}
		break;
	    case XK_l:
	    case XK_L: /* load cliptexture */
		if(!clip[0])
		{
		    int i;
		    int centerS, centerT;
		    int vSize;
		    pfNotify(PFNFY_INFO, PFNFY_PRINT,
			     "Loading Clip Texture");
		    pfSelectWin(win[0]);
		    clip[0] = pfdLoadClipTexture(clipfname);
		    pfGetClipTextureVirtualSize(clip[0], &vSize, NULL, NULL);
		    centerS = centerT = vSize/2;
		    pfEnable(PFEN_TEXTURE);
		    pfClipTextureCenter(clip[0], centerS, centerT, 0);
		    pfApplyClipTexture(clip[0]);
		    for(i = 1; i < MAX_WINS; i++)
		    {
			pfSelectWin(win[i]);
			pfApplyClipTexture(clip[0]); /* all ctxs share texid */
			clip[i] = pfNewClipTexture(pfGetArena(NULL));
			pfClipTextureMaster(clip[i], clip[0]);
			pfEnable(PFEN_TEXTURE);
		    }
		}
		break;
	    }/* key switch */
	}
	}/* dev switch */
    } /* while events */
}


int main(int argc, char **argv)
{
    static int		centerS, centerT;
    char		winname[256];
    Display             *dsp;
    Window              xwin;
    pfTexEnv 		*tev; 	
    pfFrustum 		*frust;
    pfLight		*light;
    pfLightModel 	*lm;
    pfGeoSet	       	*geom;   
    pfMaterial 		*mat;
    pfDispList		*draw_quad, *increment_position;
    int 		i;
    int			quit = 0;
    int			vSize,cSize,nTiles,tSize,maxLoadSize,cacheS,cacheT;
    pfVec3		*coords;
    pfVec3		*norms;
    pfVec2		*tcoords;
    int                 move = 1;
    int                 timing = FALSE;
    double              time = 0.;

    if(argc == 1) {
	fprintf(stderr, "Usage: %s cliptexture_config_file\n", argv[0]);
	return -1;
    }

    clipfname = strdup(argv[1]);

    pfNotifyLevel(PFNFY_INFO);
    pfInit();
    pfInitArenas();
    pfInitState(NULL);
    pfInitClock(0.0);


    /* Setup viewing frustum */
    frust = pfNewFrust(NULL);
    pfMakeSimpleFrust(frust, 45.0f);
    pfFrustNearFar(frust, 1.0f, 100.0f);

    /* Setup Texture Environment */
    tev = pfNewTEnv(NULL);


    for(i = 0; i < MAX_WINS; i++) {
	win[i]=pfNewWin(NULL);
	pfWinOriginSize(win[i], winpos[i][0], winpos[i][1], 768, 768);
	(void)sprintf(winname, "Performer Roam %d", i);
	pfWinName(win[i], winname);
	pfWinType(win[i], PFWIN_TYPE_X);
#if 0 /* use to do multiple screens */
	pfWinScreen(win[i], i);
#endif
	pfOpenWin(win[i]);
	pfInitGfx();
	pfApplyFrust(frust);

	pfAntialias(PFAA_ON);  
	pfCullFace(PFCF_OFF);
	pfTranslate(0.0,0.0,-4.0);
    }
    pfDelete(frust);

    dsp = pfGetCurWSConnection();
    xwin = pfGetWinWSWindow(win[0]);
    XSelectInput(dsp, xwin, KeyPressMask);
    
    pfFilePath(".:/usr/share/Performer/data:/usr/demos/data/textures");
    
    geom = pfNewGSet(NULL); 

    coords = (pfVec3 *)pfMalloc(sizeof(pfVec3) * 3 * 4, pfGetArena(NULL));
    norms = (pfVec3 *)pfMalloc(sizeof(pfVec3) * 3 * 1, pfGetArena(NULL));
    tcoords = (pfVec2 *)pfMalloc(sizeof(pfVec3) * 2 * 4, pfGetArena(NULL));

    pfSetVec3(coords[0], XMIN, YMIN, ZMAX);
    pfSetVec3(coords[1], XMAX, YMIN, ZMAX);
    pfSetVec3(coords[2], XMAX, YMAX, ZMAX);
    pfSetVec3(coords[3], XMIN, YMAX, ZMAX);

    pfSetVec3(norms[0], 0., 1., 0.);

    pfSetVec2(tcoords[0], 0., 0.);
    pfSetVec2(tcoords[1], 1., 0.);
    pfSetVec2(tcoords[2], 1., 1.);
    pfSetVec2(tcoords[3], 0., 1.);


    pfGSetAttr(geom, PFGS_COORD3, PFGS_PER_VERTEX, coords, NULL);
    pfGSetAttr(geom, PFGS_TEXCOORD2, PFGS_PER_VERTEX, tcoords, NULL);
    pfGSetAttr(geom, PFGS_NORMAL3, PFGS_PER_PRIM, norms, NULL);
                           
    pfGSetPrimType(geom, PFGS_QUADS);
    pfGSetNumPrims(geom, 1);

    /* Setup Clipped Textures */

    clip[0] = pfdLoadClipTexture(clipfname);
    if(!clip[0]) {
	fprintf(stderr, 
		"%s pfdLoadClipTexture failed; "
		"please check configuration file\n",
		argv[0]);
	return -1;
    }
    cSize = pfGetClipTextureClipSize(clip[0]);
    pfGetClipTextureVirtualSize(clip[0], &vSize, NULL, NULL);
    centerS = centerT = vSize/2;

    /* Set center and apply master first */
    pfSelectWin(win[0]);
    pfClipTextureCenter(clip[0], centerS, centerT, 0);
    pfApplyClipTexture(clip[0]);
    pfEnable(PFEN_TEXTURE);
    pfApplyTEnv(tev);

    /* Create Slave clip textures, attaching them to master */

    for(i = 1; i < MAX_WINS; i++)
    {
	pfSelectWin(win[i]);
	pfApplyClipTexture(clip[0]); /* so all contexts share same texid */
	clip[i] = pfNewClipTexture(pfGetArena(NULL));
	pfClipTextureMaster(clip[i], clip[0]);
	pfEnable(PFEN_TEXTURE);
	pfApplyTEnv(tev);
    }


    /* XXX the following is temporary initialization constraint */
    /* The Initial Center Position must be such that all of the tiles */
    /* Are able to have non clamped origins - ie each tile must have */
    /* implied origin >= 0 based on initial center */
  

    while(!quit)
    {
	int		offS,offT, offR;
	int		tSizeS,tSizeT,tSizeR,ncomps;
	uint		*img;
	pfMatrix	tmat;
	static pfVec4	clr = {0.1f, 0.0f, 0.4f, 1.0f};

	for(i = 0; i < MAX_WINS; i++) {
	    pfSelectWin(win[i]);
	    pfClear(PFCL_COLOR | PFCL_DEPTH, clr);
	}
	
		/* READ IN NEW CLIP CENTER */
	{
	    static int signS = 1;
	    static int signT = 1;
#define LSIZE 8
	centerS += LSIZE * signS * move;
	centerT += LSIZE * signT * move;
	if (centerS >= vSize-cSize/2)
	    signS = -1;
	if (centerS <= 0)
	    signS = 1;
	if (centerT >= vSize-cSize/2)
	    signT = -1;
	if (centerT <= 0)
	    signT = 1;
	}


	/* Update center and apply cliptexture - actually perform subloads */
	if(clip[0])
	{
	    for(i = 0; i < MAX_WINS; i++) 
	    {
		pfSelectWin(win[i]);
		pfClipTextureCenter(clip[i], centerS, centerT, 0);
		pfApplyClipTexture(clip[i]);
	    }
	}
	/* Draw the textured geometry */
	for(i = 0; i < MAX_WINS; i++) {
	    if(clip[0]) /* geometry treats master cliptexture as texture */
		pfApplyTex((pfTexture *)clip[0]);
	    pfSelectWin(win[i]);
	    pfPushMatrix();
	    pfScale(10.0,10.0,10.0);
	    pfDrawGSet(geom);
	    pfPopMatrix();
	    pfSwapWinBuffers(win[i]);
	}
	do_events(dsp, &timing, &move);
    }
    exit(0);
}