SPModel: plugins/flowHierarchyViewer/visualization.c Source File
VPAC - Computational Software Development
Main | SPModel | StGermain FrameWork |
Main Page | Alphabetical List | Class List | Directories | File List | Class Members | File Members

visualization.c

Go to the documentation of this file.
00001 /*~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
00002 **
00003 ** Copyright (C), 2004, Victorian Partnership for Advanced Computing (VPAC) Ltd, 110 Victoria Street, Melbourne, 3053, Australia.
00004 **
00005 ** Authors:
00006 **  Ogar R. Widjaja, Computational Scientist, VPAC.
00007 **  Raquibul Hassan, Software Engineer, VPAC. (raq@vpac.org)
00008 **  Keith Hsuan, Computational Scientist, VPAC (keith@vpac.org)
00009 **  William F. Appelbe, Director, VPAC. (bill@vpac.org)
00010 **  Stevan M. Quenette, Senior Software Engineer, VPAC. (steve@vpac.org)
00011 **  Patrick D. Sunter, Software Engineer, VPAC. (patrick@vpac.org)
00012 **
00013 ** This file may be distributed under the terms of the VPAC Public License
00014 ** as defined by VPAC of Australia and appearing in the file
00015 ** LICENSE.VPL included in the packaging of this file.
00016 **
00017 ** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
00018 ** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
00019 **
00020 ** $Id: FlowHierarchyViewer.c 72 2004-11-12 01:11:14Z PatrickSunter $
00021 **
00022 **~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/
00023 
00024 #include <mpi.h>
00025 #include <StGermain/StGermain.h>
00026 #include "SPModel/SPModel.h"
00027 
00028 #include "visualization.h"
00029 #include "../faultModel/FaultModel.h"
00030 
00031 #include <math.h>
00032 #include <sys/time.h>
00033 #include <stdio.h>
00034 #include <stdlib.h>
00035 #include <limits.h>
00036 #include <string.h>
00037 #include <assert.h>
00038 
00039 #if defined(__APPLE__) && defined(__MACH__)
00040 #include <OpenGL/gl.h>  // Header File For The OpenGL32 Library
00041 #include <OpenGL/glu.h> // Header File For The GLu32 Library
00042 #else
00043 #include <GL/gl.h>  // Header File For The OpenGL32 Library
00044 #include <GL/glu.h> // Header File For The GLu32 Library
00045 #endif
00046 
00047 
00048 #include <SDL/SDL.h>    
00049 
00050 ExtensionInfo_Index simulationExtensionHandle;
00051 ExtensionInfo_Index faultModelExtensionHandle;
00052 
00053 SPModelSimulationContextExtension *simulationExt = NULL;
00054 SPModelFaultModelContextExtension *faultModel = NULL;
00055 
00056 static int displayOn = 0;
00057 double heightFactor = 2.0f;
00058 
00059 double maxX=0, maxY=0, maxH=0;
00060 double minX=LONG_MAX, minY=LONG_MAX, minH=LONG_MAX;
00061 GLuint selectionBuffer[1024];
00062 float maxIsostaticRebound = 0;
00063 float minIsostaticRebound = 0;
00064 int currentProcessor = 0;
00065 
00066 #define WIDTH 1100
00067 #define HEIGHT 800
00068 #define BPP 16
00069 #define POINT_SIZE 3
00070 #define MY_CIRCLE_LIST 1
00071 
00072 int scaled;
00073 float ratio;
00074 int         oldMouseX;
00075 int         oldMouseY;
00076 GLdouble        xRot = 37.2;
00077 GLdouble        yRot = -36.3;
00078 int         motionOn = 0;
00079 int         zoomOn = 0;
00080 int         oldZoomY = 0;
00081 double      zoomFactor = 9.0f;
00082 int         showReceivers = 0;
00083 int         showFaultBlocks = 0;
00084 int         showFaultModel = 0;
00085 int         selectCatchments = 0;
00086 int         flexureMap = 0;
00087 int         showCatchment = 0;
00088 int         showRegularMesh = 0;
00089 int drawingModeIndex = 0;
00090 int drawingModes[] ={GL_TRIANGLES, GL_LINE_LOOP, GL_POINTS};
00091 int doSelection = 0;
00092 float maxErosion = 0;
00093 float minErosion = 0;
00094 int erosionMap = 0;
00095 float maxSediment = 0;
00096 float minSediment = 0;
00097 int sedimentMap = 0;
00098 
00099 double **normalArray = NULL;
00100 int selectedNode = 1;
00101 
00102 
00103 /* Light related arrays */
00104 GLfloat mat_specular[] = { 1.0, 1.0, 1.0, 1.0 };
00105 GLfloat light_position[] = { 1000.0, 1000.0, 10000.0, 0.0 };
00106 GLfloat diffuseMaterial[4] = { 0.5, 0.5, 0.5, 1.0 };
00107 
00108 void selection(void *context, int x, int y)
00109 {
00110     GLint viewport[4] = {0};
00111     int depth = 0, choose = 0, i = 0;
00112     int selectionHits = 0;
00113     SurfaceMesh *mesh = NULL;
00114 
00115     mesh = ((SPModel_Context*)context)->globalMesh;
00116     glGetIntegerv(GL_VIEWPORT, viewport);
00117     memset ( selectionBuffer, 0, sizeof(selectionBuffer) );
00118     glSelectBuffer(1024, selectionBuffer);
00119 
00120     (void) glRenderMode(GL_SELECT);
00121 
00122     /*  Initializes The Name Stack */
00123     glInitNames();                     
00124 
00125     /* Selects The Projection Matrix */
00126 
00127     glMatrixMode(GL_PROJECTION);
00128     
00129     /* Push The Projection Matrix */
00130     glPushMatrix();                     
00131     glLoadIdentity();
00132 
00133     /* This Creates A Matrix That Will Zoom Up To A Small Portion Of The Screen, Where The Mouse Is */
00134     gluPickMatrix(x, (GLdouble) viewport[3] - y, 5.0f, 5.0f, viewport);
00135 
00136     /* Apply The Perspective Matrix */
00137     gluPerspective( 50.0f, (double)WIDTH/(double)HEIGHT, 0.001f, 1000000.0f );
00138     glMatrixMode(GL_MODELVIEW);
00139         dumpNodes( context );
00140     glMatrixMode(GL_PROJECTION);
00141     glPopMatrix();
00142 
00143     glMatrixMode(GL_MODELVIEW);
00144 
00145     selectionHits = glRenderMode(GL_RENDER);
00146 
00147     choose = selectionBuffer[3];                    /* Make Our Selection The First Object */
00148     depth = selectionBuffer[1];                     /* Store How Far Away It Is */
00149 
00150     for (i = 1; i < selectionHits; i++)             /* Loop Through All The Detected Hits */
00151     {
00152         /* If This Object Is Closer To Us Than The One We Have Selected */
00153         if (selectionBuffer[i*4+1] < (GLuint)depth)
00154         {
00155             choose = selectionBuffer[i*4+3];                    /* Select The Closer Object */
00156             depth = selectionBuffer[i*4+1];                     /* Store How Far Away It Is */
00157         }
00158     }
00159     
00160     printf ("selected node -> %d\n", choose);
00161     selectedNode = choose;
00162     
00163     if( !selectedNode ){
00164         selectedNode = 1;
00165     }
00166 
00167     /*for( i=0; i<3; i++ ){
00168         nodeIndex = visNodes[mesh->vertices[selectedNode][i] - 1];
00169         printf ("node id %d\n", nodeIndex->id);
00170     }*/
00171 }
00172 
00173 void displayCatchments( SPModel_Context *context )
00174 {
00175     SurfaceMesh *mesh = NULL;
00176     int i = 0;
00177     
00178     mesh = context->localMesh;
00179     
00180     for( i=0; i<mesh->numNodes; i++ ){
00181         if( mesh->receiver[i] == mesh->id[i] ){
00182             glColor3f( 1, 0, 0 );
00183             glBegin( GL_POINTS );
00184             glVertex3f( mesh->x[i], mesh->y[i], mesh->h[i]*heightFactor );
00185             glEnd();
00186         }
00187     }
00188 }
00189 
00190 void initializeNodes ( SPModel_Context *SPM_Context )
00191 {
00192     SurfaceMesh *mesh;
00193     int i, j;
00194     double ab[3] = {0};
00195     double ac[3] = {0};
00196     double result[3] = {0};
00197 
00198     mesh = SPM_Context->globalMesh;
00199 
00200     for(i=0; i<mesh->numNodes; i++){
00201         memset( normalArray[i], 0, sizeof(double)*3 );
00202     }
00203     
00204     for(i=0; i<mesh->elementGlobalCount; i++){
00205         ab[0] = mesh->x[mesh->vertices[i][0]-1] - mesh->x[mesh->vertices[i][1]-1];
00206         ab[1] = mesh->y[mesh->vertices[i][0]-1] - mesh->y[mesh->vertices[i][1]-1];
00207         ab[2] = mesh->h[mesh->vertices[i][0]-1] - mesh->h[mesh->vertices[i][1]-1];
00208         
00209         ac[0] = mesh->x[mesh->vertices[i][0]-1] - mesh->x[mesh->vertices[i][2]-1];
00210         ac[1] = mesh->y[mesh->vertices[i][0]-1] - mesh->y[mesh->vertices[i][2]-1];
00211         ac[2] = mesh->h[mesh->vertices[i][0]-1] - mesh->h[mesh->vertices[i][2]-1];
00212 
00213         StGermain_VectorCrossProduct( result, ab, ac );
00214         
00215         for(j=0; j<3; j++){
00216             normalArray[mesh->vertices[i][0]-1][j]+=result[j];
00217             normalArray[mesh->vertices[i][1]-1][j]+=result[j];
00218             normalArray[mesh->vertices[i][2]-1][j]+=result[j];
00219         }
00220     }
00221     
00222     maxIsostaticRebound = -1e32;
00223     minIsostaticRebound = 1e32;
00224     for(i=0; i<mesh->numNodes; i++){
00225         StGermain_VectorNormalise( normalArray[i], 3 );
00226 
00227         if( simulationExt->hisotot[i] > maxIsostaticRebound ){
00228             maxIsostaticRebound = simulationExt->hisotot[i];
00229         }
00230         if( simulationExt->hisotot[i] < minIsostaticRebound ){
00231             minIsostaticRebound = simulationExt->hisotot[i];
00232         }
00233     }
00234     
00235     maxErosion = -1e32;
00236     minErosion = 1e32;
00237     for(i=0; i<mesh->numNodes; i++){
00238 
00239         if( simulationExt->globalErosion[i] > maxErosion ){
00240             maxErosion = simulationExt->globalErosion[i];
00241         }
00242         if( simulationExt->globalErosion[i] < minErosion ){
00243             minErosion = simulationExt->globalErosion[i];
00244         }
00245     }
00246     
00247     maxSediment = -1e32;
00248     minSediment = 1e32;
00249     for(i=0; i<mesh->numNodes; i++){
00250         if( simulationExt->globalSedimentHistory[i] > maxSediment ){
00251             maxSediment = simulationExt->globalSedimentHistory[i];
00252         }
00253         if( simulationExt->globalSedimentHistory[i] < minSediment ){
00254             minSediment = simulationExt->globalSedimentHistory[i];
00255         }
00256     }
00257 }
00258 
00259 void dumpNodes (void *context)
00260 {
00261     colorMap heightColor[3];
00262     colorMap interpolation;
00263     double colorValue = 0;
00264     int i = 0, j = 0, index = 0;
00265     int nodeIndex = 0;
00266     
00267     SPModel_Context *SPM_Context = NULL;
00268     CatchmentList *catchmentList;
00269     int size;
00270     SurfaceMesh *mesh;
00271     int         nodeID = 0;
00272 
00273     SPM_Context = (SPModel_Context *) context;
00274     mesh = SPM_Context->globalMesh;
00275     catchmentList = SPM_Context->catchmentList;
00276     size = SPM_Context->nproc;
00277     scaled = 0;
00278 
00279     initializeNodes( SPM_Context ); 
00280     
00281     clearDepthColor();
00282 
00283     glPushMatrix();
00284         gluLookAt(maxX/2, maxY/2, maxH*100*zoomFactor, maxX/2, maxY/2, -maxH/2, 0, 1, 0);
00285         glTranslated(maxX/2, maxY/2, -maxH/2);
00286         glRotated( xRot, 0.0, 1.0, 0.0 );
00287         glRotated( yRot, 1.0, 0.0, 0.0 );
00288         glTranslated(-maxX/2, -maxY/2, 0.0f);
00289         
00290         if( showRegularMesh ){
00291             goto showRegularMesh;
00292         }
00293         
00294         heightColor[0].height = maxH;
00295         heightColor[0].red = 0.5;
00296         heightColor[0].green = 0.5;
00297         heightColor[0].blue = 0;
00298             
00299         heightColor[1].height = maxH/1.5f;
00300         heightColor[1].red = 0.25;
00301         heightColor[1].green = 0.5;
00302         heightColor[1].blue = 0;
00303             
00304         heightColor[2].height = maxH/3.0f;
00305         heightColor[2].red = 0.05;
00306         heightColor[2].green = 0.3;
00307         heightColor[2].blue = 0;
00308         
00309         if( drawingModes[drawingModeIndex] == GL_TRIANGLES || drawingModes[drawingModeIndex] == GL_LINE_LOOP ){
00310             for(i=0; i<mesh->elementGlobalCount; i++){
00311                 glPushName( i + 1 );
00312                     glBegin(drawingModes[drawingModeIndex]);
00313                         for(j=0; j<3; j++){
00314                             nodeIndex = mesh->vertices[i][j] - 1;
00315 
00316                             if(mesh->h[nodeIndex] > maxH/1.5f) index = 0;
00317                             else if(mesh->h[nodeIndex] > maxH/3.0f) index = 1;
00318                             else index = 2;
00319                     
00320                             memset(&interpolation, 0, sizeof(colorMap));
00321                             if (index == 1){
00322                                 interpolation.red = (maxH-mesh->h[nodeIndex])/maxH*heightColor[0].red + (mesh->h[nodeIndex]-minH)/maxH*heightColor[2].red;
00323                                 interpolation.green = (maxH-mesh->h[nodeIndex])/maxH*heightColor[0].green + (mesh->h[nodeIndex]-minH)/maxH*heightColor[2].green;
00324                                 interpolation.blue = (maxH-mesh->h[nodeIndex])/maxH*heightColor[0].blue + (mesh->h[nodeIndex]-minH)/maxH*heightColor[2].blue;
00325                             }
00326                             if (index == 2){
00327                                 interpolation.red = (maxH-mesh->h[nodeIndex])/maxH*heightColor[0].red + (mesh->h[nodeIndex]-minH)/maxH*heightColor[1].red;
00328                                 interpolation.green = (maxH-mesh->h[nodeIndex])/maxH*heightColor[0].green + (mesh->h[nodeIndex]-minH)/maxH*heightColor[1].green;
00329                                 interpolation.blue = (maxH-mesh->h[nodeIndex])/maxH*heightColor[0].blue + (mesh->h[nodeIndex]-minH)/maxH*heightColor[1].blue;
00330                             }
00331                     
00332                             if (index == 0){
00333                                 interpolation.red = (maxH-mesh->h[nodeIndex])/maxH*heightColor[2].red + (mesh->h[nodeIndex]-minH)/maxH*heightColor[1].red;
00334                                 interpolation.green = (maxH-mesh->h[nodeIndex])/maxH*heightColor[2].green + (mesh->h[nodeIndex]-minH)/maxH*heightColor[1].green;
00335                                 interpolation.blue = (maxH-mesh->h[nodeIndex])/maxH*heightColor[2].blue + (mesh->h[nodeIndex]-minH)/maxH*heightColor[1].blue;
00336                             }
00337                 
00338                             if( flexureMap ){
00339                                 if( simulationExt->hisotot[nodeIndex] > 0.0f ){
00340                                     glColor3f( simulationExt->hisotot[nodeIndex]/maxIsostaticRebound, 0.0, 0.0 );
00341                                 }
00342                                 else{
00343                                     glColor3f( 0.0, simulationExt->hisotot[nodeIndex]/minIsostaticRebound, 0.0 );
00344                                 }
00345                             }
00346                             else if( erosionMap ){
00347                                 if( simulationExt->globalErosion[nodeIndex] >= 0.0f ){
00348                                     glColor3f( simulationExt->globalErosion[nodeIndex]/maxErosion, 0.0, 0.0 );
00349                                 }
00350                                 else{
00351                                     glColor3f( 0.0, simulationExt->globalErosion[nodeIndex]/minErosion, 0.0 );
00352                                 }
00353                             }
00354                             else if( sedimentMap ){
00355                                 if( simulationExt->globalSedimentHistory[nodeIndex] >= 0.0f ){
00356                                     glColor3f( simulationExt->globalSedimentHistory[nodeIndex] / maxSediment, 0.0, 0.0 );
00357                                 }
00358                                 else{
00359                                     glColor3f( 0.0, simulationExt->globalSedimentHistory[nodeIndex]/minSediment, 0.0 );
00360                                 }
00361                             }
00362                             else{
00363                                 glColor3f (mesh->h[nodeIndex]/maxH*heightColor[index].red + interpolation.red, 
00364                                         mesh->h[nodeIndex]/maxH*heightColor[index].green + interpolation.green, 
00365                                         mesh->h[nodeIndex]/maxH*heightColor[index].blue + interpolation.blue);
00366                             
00367                                 glNormal3f(normalArray[nodeIndex][0], 
00368                                         normalArray[nodeIndex][1],
00369                                         normalArray[nodeIndex][2]);
00370                             }
00371                         
00372                     
00373                             glVertex3f(mesh->x[nodeIndex], mesh->y[nodeIndex], heightFactor*mesh->h[nodeIndex]);
00374                         }
00375                     glEnd();
00376                 glPopName();
00377             }
00378         }
00379         else{
00380             glDisable(GL_LIGHTING);
00381             glDisable(GL_LIGHT0);
00382             glColor3f( 0.3, 0.3, 0.3 );
00383             for( i=0; i<mesh->numNodes; i++ ){
00384                 glPushName( mesh->id[i] );
00385                     glBegin( drawingModes[drawingModeIndex] );
00386                         glVertex3f( mesh->x[i], mesh->y[i], mesh->h[i]*heightFactor );
00387                     glEnd();
00388                 glPopName();
00389             }
00390             glEnable(GL_LIGHTING);
00391             glEnable(GL_LIGHT0);
00392         }
00393         
00394         if( showCatchment )
00395             displayCatchments( SPM_Context );
00396         if ( showReceivers ){
00397             for(i=0; i<mesh->numNodes; i++){
00398                 glBegin(GL_LINES);
00399                     colorValue = 0.3f;
00400                     
00401                     if( mesh->processor[i] == currentProcessor ){
00402                         glColor3f( 0.0f, colorValue, colorValue );
00403                     }
00404                     else{
00405                         glColor3f( colorValue, colorValue, 0.0f );
00406                     }
00407                     glVertex3f (mesh->x[i], mesh->y[i], mesh->h[i]*heightFactor);
00408 
00409                     j = mesh->receiver[i];
00410                     if( mesh->processor[j-1] == currentProcessor ){
00411                         glColor3f( 0.0f, colorValue, colorValue );
00412                     }
00413                     else{
00414                         glColor3f( colorValue, colorValue, 0.0f );
00415                     }
00416                     glVertex3f (mesh->x[j-1], mesh->y[j-1], mesh->h[j-1]*heightFactor);
00417                 
00418                 glEnd();
00419                 
00420                 if( mesh->receiver[i] == mesh->id[i] ){
00421                     glPushMatrix();
00422                         glTranslated( mesh->x[i],
00423                             mesh->y[i],
00424                             mesh->h[i]*heightFactor );
00425                         glCallList( MY_CIRCLE_LIST );
00426                     glPopMatrix( );
00427                 }
00428             }
00429         }
00430 
00431         if( doSelection ){
00432             if( drawingModes[drawingModeIndex] == GL_TRIANGLES || drawingModes[drawingModeIndex] == GL_LINE_LOOP ){
00433                 nodeID = mesh->vertices[selectedNode-1][0];
00434         
00435                 glColor3f( 1, 0, 0 );
00436                 glBegin( GL_TRIANGLES );
00437                     for( i=0; i<3; i++ ){
00438                         nodeIndex = mesh->vertices[selectedNode-1][i] - 1;
00439                         glVertex3f(mesh->x[nodeIndex], mesh->y[nodeIndex], heightFactor*mesh->h[nodeIndex]);
00440                     }
00441                 glEnd();
00442             }
00443             else{
00444                 glDisable(GL_LIGHTING);
00445                 glDisable(GL_LIGHT0);
00446                 glPushMatrix();
00447                     glTranslated( mesh->x[selectedNode-1],
00448                         mesh->y[selectedNode-1],
00449                         mesh->h[selectedNode-1]*heightFactor );
00450                     glCallList( MY_CIRCLE_LIST );
00451                 glPopMatrix( );
00452 
00453                 for( i=0; i<mesh->numNeigh[selectedNode-1]; i++ ){
00454                     
00455                         glBegin( GL_POINTS );
00456                             glColor3f( 1, 0, 0 );
00457                             glVertex3f( mesh->x[mesh->nodeNeighbours[selectedNode-1][i]-1],
00458                                 mesh->y[mesh->nodeNeighbours[selectedNode-1][i]-1],
00459                                 mesh->h[mesh->nodeNeighbours[selectedNode-1][i]-1]*heightFactor );
00460                         glEnd();
00461                                 
00462                 }
00463                 glEnable(GL_LIGHTING);
00464                 glEnable(GL_LIGHT0);
00465             }
00466         }
00467         
00468         if( selectCatchments ){
00469             if( drawingModes[drawingModeIndex] == GL_POINTS ){
00470                 int currentNode = selectedNode;
00471                 
00472                 glDisable(GL_LIGHTING);
00473                 glDisable(GL_LIGHT0);
00474                     do{
00475                         
00476                         glBegin( GL_POINTS );
00477                             glColor3f( 1, 0, 0 );
00478                             glVertex3f( mesh->x[currentNode-1],
00479                                         mesh->y[currentNode-1],
00480                                         mesh->h[currentNode-1]*heightFactor );
00481                         glEnd();
00482 
00483                         currentNode = mesh->receiver[currentNode-1];
00484                     }while( mesh->receiver[currentNode-1] != mesh->id[currentNode-1] );
00485                     glBegin( GL_POINTS );
00486                         glColor3f( 1, 0, 0 );
00487                         glVertex3f( mesh->x[currentNode-1],
00488                                     mesh->y[currentNode-1],
00489                                     mesh->h[currentNode-1]*heightFactor );
00490                     glEnd();
00491 
00492                 glEnable(GL_LIGHTING);
00493                 glEnable(GL_LIGHT0);
00494             }
00495         }
00496         
00497         if( showFaultBlocks ){
00498             /*glColor3f( 0.0f, 1.0f, 0.0f );
00499             for( i=0; i<faultBlocks->numFaultBlocks; i++ ){
00500                 for( j=0; j<faultBlocks->numFaultBlockNodes[i]; j++ ){
00501                     glBegin( GL_LINES );
00502                         glVertex3f( mesh->x[faultBlocks->faultBlockNodes[i][j]-1],
00503                                     mesh->y[faultBlocks->faultBlockNodes[i][j]-1],
00504                                     mesh->h[faultBlocks->faultBlockNodes[i][j]-1] + 100.0f );
00505                     glEnd();
00506                     
00507                     glPushMatrix();
00508                         glTranslated( mesh->x[faultBlocks->faultBlockNodes[i][j]-1],
00509                             mesh->y[faultBlocks->faultBlockNodes[i][j]-1],
00510                             maxH );
00511                         glCallList( MY_CIRCLE_LIST );
00512                     glPopMatrix( );
00513                 }
00514             }*/
00515         }
00516 
00517         if( showFaultModel ){
00518             SurfaceMesh *localMesh = SPM_Context->localMesh;
00519             int localIndex = 0;
00520             
00521             for( i=0; i<faultModel->numFaultModel; i++ ){
00522                 for( j=0; j<localMesh->myLoad; j++ ){
00523                     if( faultModel->nodeIndices[i][j] != UNDEFINED ){
00524                         glPushMatrix();
00525                             localIndex = faultModel->nodeIndices[i][j]-1;
00526                             glTranslated( mesh->x[localIndex],
00527                                 mesh->y[localIndex],
00528                                 maxH );
00529                             //glCallList( MY_CIRCLE_LIST );
00530                             glColor3f( 0.0f, faultModel->distFromBoundary[i][j], 0.0f );
00531                             glBegin( GL_POINTS );
00532                                 glVertex3f( 0.0f, 0.0f, 0.0f );
00533                             glEnd();
00534                         glPopMatrix( );
00535                     }
00536                 }
00537             }
00538         }
00539         
00540 showRegularMesh:
00541         if( showRegularMesh ){
00542             SurfaceRegularMesh *regularMesh = SPM_Context->regularMesh;
00543             
00544             for( i=0; i<regularMesh->nx-1; i++ ){
00545                 for( j=0; j<regularMesh->ny-1; j++ ){
00546                     glBegin( GL_LINE_LOOP );
00547                         glVertex3f( regularMesh->regularNodes[i][j].x, regularMesh->regularNodes[i][j].y, maxH );
00548                         glVertex3f( regularMesh->regularNodes[i+1][j].x, regularMesh->regularNodes[i][j].y, maxH );
00549                         glVertex3f( regularMesh->regularNodes[i+1][j].x, regularMesh->regularNodes[i][j+1].y, maxH );
00550                         glVertex3f( regularMesh->regularNodes[i][j].x, regularMesh->regularNodes[i][j+1].y, maxH );
00551                     glEnd();
00552                 }
00553             }
00554 
00555             for( i=0; i<mesh->numNodes; i++ ){
00556                 if( mesh->processor[i] == currentProcessor ){
00557                 
00558                     glPushMatrix();
00559                         glTranslated( mesh->x[i],
00560                             mesh->y[i],
00561                             maxH );
00562                         glCallList( MY_CIRCLE_LIST );
00563                     glPopMatrix( );
00564                 }
00565             }
00566         }
00567         
00568     glPopMatrix();
00569     SDL_GL_SwapBuffers();
00570 }
00571 
00572 void mouseClick( int button, int state, int x, int y ) {
00573     if( button == SDL_BUTTON_LEFT ) {
00574         if( state == SDL_PRESSED ) {
00575             oldMouseX = x;
00576             oldMouseY = y;
00577             motionOn = 1;
00578         }
00579         else if ( state == SDL_RELEASED ) {
00580             motionOn = 0;
00581         }
00582     }
00583     else if( button == SDL_BUTTON_RIGHT ) {
00584         if( state == SDL_PRESSED ) {
00585             zoomOn = 1;
00586             oldZoomY = y;
00587         }
00588         else if ( state == SDL_RELEASED ) {
00589             zoomOn = 0;
00590         }
00591     }
00592 }
00593 
00594 void mouseMotion( int x, int y ) {
00595     if( motionOn ) {
00596         int dx = x - oldMouseX;
00597         int dy = y - oldMouseY;
00598         
00599         xRot += (GLdouble)dx * 0.3;
00600         yRot += (GLdouble)dy * 0.3;
00601         
00602         oldMouseX = x;
00603         oldMouseY = y;
00604     }
00605     if( zoomOn ){
00606         int dy = y - oldZoomY;
00607         
00608         if (zoomFactor+dy*0.03 > 0.0)
00609             zoomFactor += dy*0.03; 
00610         
00611         oldZoomY = y;
00612     }
00613 }
00614 
00615 void windowEvents( void *context ) {
00616     SDL_Event   event;
00617     int quit = 0;
00618     int scaled = 0, i = 0, size = 0;
00619     int *processorLoad = NULL;
00620     SPModel_Context *SPM_Context = NULL;
00621     SurfaceMesh *globalMesh;
00622     _SurfaceMeshDecomp *meshDecomp;
00623     
00624     SPM_Context = (SPModel_Context *) context;
00625     globalMesh = SPM_Context->globalMesh;
00626     meshDecomp = SPM_Context->meshDecomp;
00627     
00628     processorLoad = meshDecomp->processorLoad;
00629     size = SPM_Context->nproc;
00630     
00631     while( !quit ){
00632         if (!scaled) 
00633         {       
00634             for (i=0; i<globalMesh->numNodes; i++)
00635             {
00636                 if ( maxX < globalMesh->x[i] )
00637                    maxX = globalMesh->x[i];
00638 
00639                 if ( maxY < globalMesh->y[i] )
00640                    maxY = globalMesh->y[i];
00641 
00642                 if ( maxH < globalMesh->h[i] )
00643                    maxH = globalMesh->h[i];
00644 
00645 
00646                 if ( minX > globalMesh->x[i] )
00647                    minX = globalMesh->x[i];
00648 
00649                 if ( minY > globalMesh->y[i] )
00650                    minY = globalMesh->y[i];
00651 
00652                 if ( minH > globalMesh->h[i] )
00653                    minH = globalMesh->h[i];
00654             }
00655             scaled = 1;
00656         }
00657 
00658         if( SDL_PollEvent( &event ) ) {
00659             switch( event.type ) {
00660                 case SDL_QUIT:
00661                     quit = 1;
00662                     break;
00663             
00664                 case SDL_KEYDOWN:
00665                     switch( event.key.keysym.sym ) {
00666                         case SDLK_ESCAPE:
00667                             quit = 1;
00668                         break;
00669                     
00670                         case SDLK_o:
00671                             xRot = 0.0;
00672                             yRot = 0.0;
00673                         break;
00674                         
00675                         case SDLK_b:
00676                         {
00677                             showFaultBlocks = !showFaultBlocks;
00678                             showFaultModel = !showFaultModel;
00679                         }
00680                         break;
00681                         
00682                         case SDLK_f:
00683                         {
00684                             flexureMap = !flexureMap; 
00685                             if( flexureMap ){
00686                                 glDisable(GL_LIGHTING);
00687                                 glDisable(GL_LIGHT0);
00688                             }
00689                             else{
00690                                 glEnable(GL_LIGHTING);
00691                                 glEnable(GL_LIGHT0);
00692                             }
00693                         }
00694                         break;
00695     
00696                         case SDLK_e:
00697                             erosionMap = !erosionMap;
00698                         break;
00699                     
00700                         case SDLK_d:
00701                             sedimentMap = !sedimentMap;
00702                         break;
00703     
00704                         case SDLK_r:
00705                             showReceivers = !showReceivers; 
00706                         break;
00707                         
00708                         case SDLK_c:
00709                             showCatchment = !showCatchment; 
00710                         break;
00711 
00712                         case SDLK_t:
00713                             doSelection = 0;
00714                             selectCatchments = !selectCatchments;
00715                         break;
00716                     
00717                         case SDLK_m:
00718                             drawingModeIndex = (drawingModeIndex+1) % 3;
00719                             selectedNode = 1;
00720                         break;
00721 
00722                         case SDLK_s:
00723                             doSelection = !doSelection;
00724                         break;
00725 
00726                         case SDLK_RIGHTBRACKET:
00727                             heightFactor += 3.7f;
00728                         break;
00729                         
00730                         case SDLK_LEFTBRACKET:{
00731                             if( heightFactor - 3.7f > 0.0f )
00732                             heightFactor -= 3.7f;
00733                         }
00734                         break;
00735                         
00736                         case SDLK_p:
00737                             currentProcessor = (currentProcessor + 1) % globalMesh->numProcs;
00738                         break;
00739 
00740                         case SDLK_TAB:
00741                             showRegularMesh = !showRegularMesh;
00742                         break;
00743                         
00744                         default:
00745                         break;
00746                     }
00747                     break;
00748 
00749                 case SDL_MOUSEMOTION:
00750                     mouseMotion( event.motion.x, event.motion.y );
00751                 break;
00752                 
00753                 case SDL_MOUSEBUTTONDOWN:{
00754                     mouseClick( event.button.button, event.button.state, event.button.x, event.button.y );
00755                     if( doSelection || selectCatchments ){
00756                         selection( context, event.button.x, event.button.y );
00757                     }
00758                 }
00759                 break;
00760             
00761                 case SDL_MOUSEBUTTONUP:
00762                     mouseClick( event.button.button, event.button.state, event.button.x, event.button.y );
00763                 break;
00764             
00765                 default:
00766                 break;
00767             }
00768         }
00769         dumpNodes( context );
00770     }
00771 }
00772 
00773 void initializeGL(void)
00774 {
00775     
00776     glShadeModel(GL_SMOOTH);
00777     glClearColor(0.0f, 0.0f, 0.0f, 0.0f);
00778     glClearDepth(1.0f);
00779 
00780     glHint (GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST);
00781     glEnable (GL_NORMALIZE);
00782     glEnable (GL_DEPTH_TEST);
00783     glDepthFunc(GL_LEQUAL);
00784 
00785     glMaterialfv(GL_FRONT, GL_DIFFUSE, diffuseMaterial);
00786     glMaterialfv(GL_FRONT, GL_SPECULAR, mat_specular);
00787     glMaterialf(GL_FRONT, GL_SHININESS, 25.0);
00788     glLightfv(GL_LIGHT0, GL_POSITION, light_position);
00789 
00790     glEnable(GL_LIGHTING);
00791     glEnable(GL_LIGHT0);
00792     
00793     glColorMaterial(GL_FRONT, GL_DIFFUSE);
00794     glEnable(GL_COLOR_MATERIAL);
00795     
00796     glEnable(GL_CULL_FACE);
00797     glCullFace(GL_BACK);
00798     glPointSize( POINT_SIZE );
00799  
00800     glViewport( 0, 0, WIDTH, HEIGHT ); 
00801     glMatrixMode(GL_PROJECTION);
00802     glLoadIdentity();
00803     gluPerspective( 50.0f, (double)WIDTH/(double)HEIGHT, 0.001f, 1000000.0f );
00804     glMatrixMode( GL_MODELVIEW ); 
00805     glLoadIdentity();
00806 
00807 }
00808 
00809 void buildCircle( double radius )
00810 {
00811     GLint i;
00812     GLfloat cosine, sine;
00813 
00814     glNewList(MY_CIRCLE_LIST, GL_COMPILE);
00815         glColor3f( 0.5, 0.5, 0.5 );
00816         glBegin(GL_LINE_LOOP);
00817             for(i=0;i<10;i++){
00818                 cosine=radius*cos(i*2*PI/10.0);
00819                 sine=radius*sin(i*2*PI/10.0);
00820                 glVertex3f(cosine, sine, 0.0);
00821         }
00822         glEnd();
00823     glEndList();
00824 }
00825 
00826 void createGLWindow (SPModel_Context *context)
00827 {
00828 
00829     /* Flags to pass to SDL_SetVideoMode */
00830     int videoFlags;
00831     const SDL_VideoInfo *videoInfo;
00832     SDL_Surface *surface;
00833 
00834 
00835     /* initialize SDL */
00836     if ( SDL_Init( SDL_INIT_VIDEO ) < 0 )
00837     {
00838         fprintf( stderr, "Video initialization failed: %s\n",
00839              SDL_GetError( ) );
00840         exit(0);
00841     }
00842 
00843     /* Fetch the video info */
00844     videoInfo = SDL_GetVideoInfo( );
00845 
00846     if ( !videoInfo )
00847     {
00848         fprintf( stderr, "Video query failed: %s\n",
00849              SDL_GetError( ) );
00850         exit(0);
00851     }
00852 
00853     /* the flags to pass to SDL_SetVideoMode */
00854     videoFlags  = SDL_OPENGL;          /* Enable OpenGL in SDL */
00855     videoFlags |= SDL_GL_DOUBLEBUFFER; /* Enable double buffering */
00856     videoFlags |= SDL_HWPALETTE;       /* Store the palette in hardware */
00857 
00858     /* This checks to see if surfaces can be stored in memory */
00859     if ( videoInfo->hw_available )
00860     videoFlags |= SDL_HWSURFACE;
00861     else
00862     videoFlags |= SDL_SWSURFACE;
00863 
00864     /* This checks if hardware blits can be done */
00865     if ( videoInfo->blit_hw )
00866     videoFlags |= SDL_HWACCEL;
00867 
00868     /* Sets up OpenGL double buffering */
00869     SDL_GL_SetAttribute( SDL_GL_DOUBLEBUFFER, 1 );
00870 
00871     /* get a SDL surface */
00872     surface = SDL_SetVideoMode( WIDTH, HEIGHT, BPP,
00873                 videoFlags );
00874 
00875     /* Verify there is a surface */
00876     if ( !surface )
00877     {
00878         fprintf( stderr,  "Video mode set failed: %s\n", SDL_GetError( ) );
00879         exit(0);
00880     }
00881     initializeGL();
00882     displayOn = 1;
00883 
00884     normalArray = Memory_Alloc_2DArray( double, context->globalMesh->numNodes, 3, "normalArray" );
00885     buildCircle((context->globalMesh->sideX/sqrt(context->globalMesh->numNodes))/3.0f);
00886 
00887     simulationExtensionHandle = ExtensionManager_GetHandle( context->extensionMgr, "Simulation" );
00888     faultModelExtensionHandle = ExtensionManager_GetHandle( context->extensionMgr, "FaultModel" );
00889     
00890     if( faultModelExtensionHandle != -1 ){
00891         faultModel = (SPModelFaultModelContextExtension*)ExtensionManager_Get
00892                     ( context->extensionMgr, context, faultModelExtensionHandle );
00893     }
00894 
00895     if( simulationExtensionHandle != -1 ){
00896         simulationExt = (SPModelSimulationContextExtension*)ExtensionManager_Get
00897                     ( context->extensionMgr, context, simulationExtensionHandle );
00898     }
00899     assert( simulationExt );
00900 }
00901 
00902 void clearDepthColor (void)
00903 {
00904     glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
00905     glClearColor( 0.7, 0.7, 0.7, 1 );
00906 }
00907