00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033 #ifdef G4VIS_BUILD_OPENGL_DRIVER
00034
00035 #include "G4ios.hh"
00036 #include "G4SystemOfUnits.hh"
00037 #include "G4OpenGLViewer.hh"
00038 #include "G4OpenGLSceneHandler.hh"
00039 #include "G4OpenGLTransform3D.hh"
00040 #include "G4OpenGL2PSAction.hh"
00041
00042 #include "G4Scene.hh"
00043 #include "G4VisExtent.hh"
00044 #include "G4LogicalVolume.hh"
00045 #include "G4VSolid.hh"
00046 #include "G4Point3D.hh"
00047 #include "G4Normal3D.hh"
00048 #include "G4Plane3D.hh"
00049 #include "G4AttHolder.hh"
00050 #include "G4AttCheck.hh"
00051 #include "G4Text.hh"
00052
00053
00054 #include "Geant4_gl2ps.h"
00055
00056 #include <sstream>
00057
00058 G4int G4OpenGLViewer::fPrintSizeX = -1;
00059 G4int G4OpenGLViewer::fPrintSizeY = -1;
00060 G4String G4OpenGLViewer::fPrintFilename = "G4OpenGL";
00061 int G4OpenGLViewer::fPrintFilenameIndex = 0;
00062
00063 G4OpenGLViewer::G4OpenGLViewer (G4OpenGLSceneHandler& scene):
00064 G4VViewer (scene, -1),
00065 fPrintColour (true),
00066 fVectoredPs (true),
00067 fOpenGLSceneHandler(scene),
00068 background (G4Colour(0.,0.,0.)),
00069 transparency_enabled (true),
00070 antialiasing_enabled (false),
00071 haloing_enabled (false),
00072 fStartTime(-DBL_MAX),
00073 fEndTime(DBL_MAX),
00074 fFadeFactor(0.),
00075 fDisplayHeadTime(false),
00076 fDisplayHeadTimeX(-0.9),
00077 fDisplayHeadTimeY(-0.9),
00078 fDisplayHeadTimeSize(24.),
00079 fDisplayHeadTimeRed(0.),
00080 fDisplayHeadTimeGreen(1.),
00081 fDisplayHeadTimeBlue(1.),
00082 fDisplayLightFront(false),
00083 fDisplayLightFrontX(0.),
00084 fDisplayLightFrontY(0.),
00085 fDisplayLightFrontZ(0.),
00086 fDisplayLightFrontT(0.),
00087 fDisplayLightFrontRed(0.),
00088 fDisplayLightFrontGreen(1.),
00089 fDisplayLightFrontBlue(0.),
00090 fRot_sens(1.),
00091 fPan_sens(0.01),
00092 fWinSize_x(0),
00093 fWinSize_y(0),
00094 fPointSize (0),
00095 fSizeHasChanged(0),
00096 fGl2psDefaultLineWith(1),
00097 fGl2psDefaultPointSize(2)
00098 {
00099 #ifdef G4DEBUG_VIS_OGL
00100 printf("G4OpenGLViewer:: Creation\n");
00101 #endif
00102
00103 fVP.SetAutoRefresh(true);
00104 fDefaultVP.SetAutoRefresh(true);
00105
00106 fGL2PSAction = new G4OpenGL2PSAction();
00107
00108
00109
00110
00111
00112
00113
00114 }
00115
00116 G4OpenGLViewer::~G4OpenGLViewer ()
00117 {
00118 delete fGL2PSAction;
00119 }
00120
00121 void G4OpenGLViewer::InitializeGLView ()
00122 {
00123 #ifdef G4DEBUG_VIS_OGL
00124 printf("G4OpenGLViewer::InitializeGLView\n");
00125 #endif
00126
00127 fWinSize_x = fVP.GetWindowSizeHintX();
00128 fWinSize_y = fVP.GetWindowSizeHintY();
00129
00130 glClearColor (0.0, 0.0, 0.0, 0.0);
00131 glClearDepth (1.0);
00132 glDisable (GL_LINE_SMOOTH);
00133 glDisable (GL_POLYGON_SMOOTH);
00134
00135
00136 ClearView ();
00137 FinishView ();
00138
00139 glDepthFunc (GL_LEQUAL);
00140 glDepthMask (GL_TRUE);
00141
00142 glEnable (GL_BLEND);
00143 glBlendFunc (GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
00144
00145 #ifdef G4DEBUG_VIS_OGL
00146 printf("G4OpenGLViewer::InitializeGLView END\n");
00147 #endif
00148 }
00149
00150 void G4OpenGLViewer::ClearView () {
00151 #ifdef G4DEBUG_VIS_OGL
00152 printf("G4OpenGLViewer::ClearView\n");
00153 #endif
00154 glClearColor (background.GetRed(),
00155 background.GetGreen(),
00156 background.GetBlue(),
00157 1.);
00158 glClearDepth (1.0);
00159
00160
00161 glClear (GL_COLOR_BUFFER_BIT);
00162 glClear (GL_DEPTH_BUFFER_BIT);
00163 glClear (GL_STENCIL_BUFFER_BIT);
00164 #ifdef G4DEBUG_VIS_OGL
00165 printf("G4OpenGLViewer::ClearView flush\n");
00166 #endif
00167 glFlush ();
00168 }
00169
00170
00171 void G4OpenGLViewer::ResizeWindow(unsigned int aWidth, unsigned int aHeight) {
00172 if ((fWinSize_x != aWidth) || (fWinSize_y != aHeight)) {
00173 fWinSize_x = aWidth;
00174 fWinSize_y = aHeight;
00175 fSizeHasChanged = true;
00176 } else {
00177 fSizeHasChanged = false;
00178 }
00179 }
00180
00187 void G4OpenGLViewer::ResizeGLView()
00188 {
00189 #ifdef G4DEBUG_VIS_OGL
00190 printf("G4OpenGLViewer::ResizeGLView %d %d %#lx\n",fWinSize_x,fWinSize_y,(unsigned long)this);
00191 #endif
00192
00193 GLint dims[2];
00194 dims[0] = 0;
00195 dims[1] = 0;
00196
00197 glGetIntegerv(GL_MAX_VIEWPORT_DIMS, dims);
00198
00199 if ((dims[0] !=0 ) && (dims[1] !=0)) {
00200
00201 if (fWinSize_x > (unsigned)dims[0]) {
00202 G4cerr << "Try to resize view greater than max X viewport dimension. Desired size "<<fWinSize_x <<" is resize to "<< dims[0] << G4endl;
00203 fWinSize_x = dims[0];
00204 }
00205 if (fWinSize_y > (unsigned)dims[1]) {
00206 G4cerr << "Try to resize view greater than max Y viewport dimension. Desired size "<<fWinSize_y <<" is resize to "<< dims[1] << G4endl;
00207 fWinSize_y = dims[1];
00208 }
00209 }
00210
00211 glViewport(0, 0, fWinSize_x,fWinSize_y);
00212
00213
00214 }
00215
00216
00217 void G4OpenGLViewer::SetView () {
00218
00219 if (!fSceneHandler.GetScene()) {
00220 return;
00221 }
00222
00223
00224
00225
00226
00227 GLfloat lightPosition [4];
00228 lightPosition [0] = fVP.GetActualLightpointDirection().x();
00229 lightPosition [1] = fVP.GetActualLightpointDirection().y();
00230 lightPosition [2] = fVP.GetActualLightpointDirection().z();
00231 lightPosition [3] = 0.;
00232
00233 GLfloat ambient [] = { 0.2, 0.2, 0.2, 1.};
00234 GLfloat diffuse [] = { 0.8, 0.8, 0.8, 1.};
00235 glEnable (GL_LIGHT0);
00236 glLightfv (GL_LIGHT0, GL_AMBIENT, ambient);
00237 glLightfv (GL_LIGHT0, GL_DIFFUSE, diffuse);
00238
00239 G4double ratioX = 1;
00240 G4double ratioY = 1;
00241 if (fWinSize_y > fWinSize_x) {
00242 ratioX = ((G4double)fWinSize_y) / ((G4double)fWinSize_x);
00243 }
00244 if (fWinSize_x > fWinSize_y) {
00245 ratioY = ((G4double)fWinSize_x) / ((G4double)fWinSize_y);
00246 }
00247
00248
00249
00250 const G4Point3D targetPoint
00251 = fSceneHandler.GetScene()->GetStandardTargetPoint()
00252 + fVP.GetCurrentTargetPoint ();
00253 G4double radius = fSceneHandler.GetScene()->GetExtent().GetExtentRadius();
00254 if(radius<=0.) radius = 1.;
00255 const G4double cameraDistance = fVP.GetCameraDistance (radius);
00256 const G4Point3D cameraPosition =
00257 targetPoint + cameraDistance * fVP.GetViewpointDirection().unit();
00258 const GLdouble pnear = fVP.GetNearDistance (cameraDistance, radius);
00259 const GLdouble pfar = fVP.GetFarDistance (cameraDistance, pnear, radius);
00260 const GLdouble right = fVP.GetFrontHalfHeight (pnear, radius) * ratioY;
00261 const GLdouble left = -right;
00262 const GLdouble top = fVP.GetFrontHalfHeight (pnear, radius) * ratioX;
00263 const GLdouble bottom = -top;
00264
00265
00266 ResizeGLView();
00267
00268
00269 glMatrixMode (GL_PROJECTION);
00270 glLoadIdentity();
00271
00272 const G4Vector3D scaleFactor = fVP.GetScaleFactor();
00273 glScaled(scaleFactor.x(),scaleFactor.y(),scaleFactor.z());
00274
00275 if (fVP.GetFieldHalfAngle() == 0.) {
00276 glOrtho (left, right, bottom, top, pnear, pfar);
00277 }
00278 else {
00279 glFrustum (left, right, bottom, top, pnear, pfar);
00280 }
00281
00282 glMatrixMode (GL_MODELVIEW);
00283 glLoadIdentity();
00284
00285 const G4Normal3D& upVector = fVP.GetUpVector ();
00286 G4Point3D gltarget;
00287 if (cameraDistance > 1.e-6 * radius) {
00288 gltarget = targetPoint;
00289 }
00290 else {
00291 gltarget = targetPoint - radius * fVP.GetViewpointDirection().unit();
00292 }
00293
00294 const G4Point3D& pCamera = cameraPosition;
00295 gluLookAt (pCamera.x(), pCamera.y(), pCamera.z(),
00296 gltarget.x(), gltarget.y(), gltarget.z(),
00297 upVector.x(), upVector.y(), upVector.z());
00298
00299
00300 glLightfv (GL_LIGHT0, GL_POSITION, lightPosition);
00301
00302
00303
00304
00305
00306
00307
00308 if (false) {
00309 const G4Plane3D& sp = fVP.GetSectionPlane ();
00310 double sArray[4];
00311 sArray[0] = sp.a();
00312 sArray[1] = sp.b();
00313 sArray[2] = sp.c();
00314 sArray[3] = sp.d() + radius * 1.e-05;
00315 glClipPlane (GL_CLIP_PLANE0, sArray);
00316 glEnable (GL_CLIP_PLANE0);
00317 sArray[0] = -sp.a();
00318 sArray[1] = -sp.b();
00319 sArray[2] = -sp.c();
00320 sArray[3] = -sp.d() + radius * 1.e-05;
00321 glClipPlane (GL_CLIP_PLANE1, sArray);
00322 glEnable (GL_CLIP_PLANE1);
00323 } else {
00324 glDisable (GL_CLIP_PLANE0);
00325 glDisable (GL_CLIP_PLANE1);
00326 }
00327
00328
00329
00330
00331
00332 const G4Planes& cutaways = fVP.GetCutawayPlanes();
00333 size_t nPlanes = cutaways.size();
00334 if (fVP.IsCutaway() &&
00335 fVP.GetCutawayMode() == G4ViewParameters::cutawayIntersection &&
00336 nPlanes > 0) {
00337 double a[4];
00338 a[0] = cutaways[0].a();
00339 a[1] = cutaways[0].b();
00340 a[2] = cutaways[0].c();
00341 a[3] = cutaways[0].d();
00342 glClipPlane (GL_CLIP_PLANE2, a);
00343 glEnable (GL_CLIP_PLANE2);
00344 if (nPlanes > 1) {
00345 a[0] = cutaways[1].a();
00346 a[1] = cutaways[1].b();
00347 a[2] = cutaways[1].c();
00348 a[3] = cutaways[1].d();
00349 glClipPlane (GL_CLIP_PLANE3, a);
00350 glEnable (GL_CLIP_PLANE3);
00351 }
00352 if (nPlanes > 2) {
00353 a[0] = cutaways[2].a();
00354 a[1] = cutaways[2].b();
00355 a[2] = cutaways[2].c();
00356 a[3] = cutaways[2].d();
00357 glClipPlane (GL_CLIP_PLANE4, a);
00358 glEnable (GL_CLIP_PLANE4);
00359 }
00360 } else {
00361 glDisable (GL_CLIP_PLANE2);
00362 glDisable (GL_CLIP_PLANE3);
00363 glDisable (GL_CLIP_PLANE4);
00364 }
00365
00366
00367 background = fVP.GetBackgroundColour ();
00368
00369 }
00370
00371
00372
00373 void G4OpenGLViewer::ResetView () {
00374 G4VViewer::ResetView();
00375 fRot_sens = 1;
00376 fPan_sens = 0.01;
00377 }
00378
00379
00380 void G4OpenGLViewer::HaloingFirstPass () {
00381
00382
00383
00384
00385
00386
00387
00388
00389
00390 glColorMask (GL_FALSE, GL_FALSE, GL_FALSE, GL_FALSE);
00391
00392
00393 glDepthMask (GL_TRUE);
00394 glDepthFunc (GL_LESS);
00395 glClearDepth (1.0);
00396
00397
00398 ChangeLineWidth(3.0);
00399
00400 }
00401
00402 void G4OpenGLViewer::HaloingSecondPass () {
00403
00404
00405 glColorMask (GL_TRUE, GL_TRUE, GL_TRUE, GL_TRUE);
00406 glDepthFunc (GL_LEQUAL);
00407 ChangeLineWidth(1.0);
00408
00409 }
00410
00411 void G4OpenGLViewer::Pick(GLdouble x, GLdouble y)
00412 {
00413
00414 const G4int BUFSIZE = 512;
00415 GLuint selectBuffer[BUFSIZE];
00416 glSelectBuffer(BUFSIZE, selectBuffer);
00417 glRenderMode(GL_SELECT);
00418 glInitNames();
00419 glPushName(0);
00420 glMatrixMode(GL_PROJECTION);
00421 G4double currentProjectionMatrix[16];
00422 glGetDoublev(GL_PROJECTION_MATRIX, currentProjectionMatrix);
00423 glPushMatrix();
00424 glLoadIdentity();
00425 GLint viewport[4];
00426 glGetIntegerv(GL_VIEWPORT, viewport);
00427
00428 gluPickMatrix(x, viewport[3] - y, 5., 5., viewport);
00429 glMultMatrixd(currentProjectionMatrix);
00430 glMatrixMode(GL_MODELVIEW);
00431 DrawView();
00432 GLint hits = glRenderMode(GL_RENDER);
00433 if (hits < 0)
00434 G4cout << "Too many hits. Zoom in to reduce overlaps." << G4endl;
00435 else if (hits > 0) {
00436 G4cout << hits << " hit(s)" << G4endl;
00437 GLuint* p = selectBuffer;
00438 for (GLint i = 0; i < hits; ++i) {
00439 GLuint nnames = *p++;
00440
00441
00442
00443
00444
00445
00446 p++;
00447 p++;
00448 for (GLuint j = 0; j < nnames; ++j) {
00449 GLuint name = *p++;
00450 G4cout << "Hit: " << i
00451 << ", Sub-hit: " << j
00452 << ", PickName: " << name << G4endl;
00453 std::map<GLuint, G4AttHolder*>::iterator iter =
00454 fOpenGLSceneHandler.fPickMap.find(name);
00455 if (iter != fOpenGLSceneHandler.fPickMap.end()) {
00456 G4AttHolder* attHolder = iter->second;
00457 if(attHolder && attHolder->GetAttDefs().size()) {
00458 for (size_t iAtt = 0;
00459 iAtt < attHolder->GetAttDefs().size(); ++iAtt) {
00460 G4cout << G4AttCheck(attHolder->GetAttValues()[iAtt],
00461 attHolder->GetAttDefs()[iAtt]);
00462 }
00463 }
00464 }
00465 }
00466 G4cout << G4endl;
00467 }
00468 }
00469 glMatrixMode(GL_PROJECTION);
00470 glPopMatrix();
00471 glMatrixMode(GL_MODELVIEW);
00472 }
00473
00474
00475
00476
00477 GLubyte* G4OpenGLViewer::grabPixels (int inColor, unsigned int width, unsigned int height) {
00478
00479 GLubyte* buffer;
00480 GLint swapbytes, lsbfirst, rowlength;
00481 GLint skiprows, skippixels, alignment;
00482 GLenum format;
00483 int size;
00484
00485 if (inColor) {
00486 format = GL_RGB;
00487 size = width*height*3;
00488 } else {
00489 format = GL_LUMINANCE;
00490 size = width*height*1;
00491 }
00492
00493 buffer = new GLubyte[size];
00494 if (buffer == NULL)
00495 return NULL;
00496
00497 glGetIntegerv (GL_UNPACK_SWAP_BYTES, &swapbytes);
00498 glGetIntegerv (GL_UNPACK_LSB_FIRST, &lsbfirst);
00499 glGetIntegerv (GL_UNPACK_ROW_LENGTH, &rowlength);
00500
00501 glGetIntegerv (GL_UNPACK_SKIP_ROWS, &skiprows);
00502 glGetIntegerv (GL_UNPACK_SKIP_PIXELS, &skippixels);
00503 glGetIntegerv (GL_UNPACK_ALIGNMENT, &alignment);
00504
00505 glPixelStorei (GL_UNPACK_SWAP_BYTES, GL_FALSE);
00506 glPixelStorei (GL_UNPACK_LSB_FIRST, GL_FALSE);
00507 glPixelStorei (GL_UNPACK_ROW_LENGTH, 0);
00508
00509 glPixelStorei (GL_UNPACK_SKIP_ROWS, 0);
00510 glPixelStorei (GL_UNPACK_SKIP_PIXELS, 0);
00511 glPixelStorei (GL_UNPACK_ALIGNMENT, 1);
00512
00513 glReadBuffer(GL_FRONT);
00514 glReadPixels (0, 0, (GLsizei)width, (GLsizei)height, format, GL_UNSIGNED_BYTE, (GLvoid*) buffer);
00515
00516 glPixelStorei (GL_UNPACK_SWAP_BYTES, swapbytes);
00517 glPixelStorei (GL_UNPACK_LSB_FIRST, lsbfirst);
00518 glPixelStorei (GL_UNPACK_ROW_LENGTH, rowlength);
00519
00520 glPixelStorei (GL_UNPACK_SKIP_ROWS, skiprows);
00521 glPixelStorei (GL_UNPACK_SKIP_PIXELS, skippixels);
00522 glPixelStorei (GL_UNPACK_ALIGNMENT, alignment);
00523
00524 return buffer;
00525 }
00526
00527 void G4OpenGLViewer::printEPS() {
00528 bool res;
00529 #ifdef G4DEBUG_VIS_OGL
00530 printf("G4OpenGLViewer::printEPS file:%s Vec:%d Name:%s\n",getRealPrintFilename().c_str(),fVectoredPs,GetName().c_str());
00531 #endif
00532
00533
00534
00535 size_t len = strlen(setlocale(LC_NUMERIC,NULL));
00536 char* oldLocale = (char*)(malloc(len+1));
00537 if(oldLocale!=NULL) strncpy(oldLocale,setlocale(LC_NUMERIC,NULL),len);
00538 setlocale(LC_NUMERIC,"C");
00539
00540 if (fVectoredPs) {
00541 res = printVectoredEPS();
00542 } else {
00543 res = printNonVectoredEPS();
00544 }
00545
00546
00547 if (oldLocale) {
00548 setlocale(LC_NUMERIC,oldLocale);
00549 free(oldLocale);
00550 }
00551
00552 if (res == false) {
00553 G4cerr << "Error while saving file... "<<getRealPrintFilename().c_str()<< G4endl;
00554 } else {
00555 G4cout << "File "<<getRealPrintFilename().c_str()<<" has been saved " << G4endl;
00556 }
00557
00558
00559 if ( fPrintFilenameIndex != -1) {
00560 fPrintFilenameIndex++;
00561 }
00562
00563 #ifdef G4DEBUG_VIS_OGL
00564 printf("G4OpenGLViewer::printEPS END\n");
00565 #endif
00566 }
00567
00568 bool G4OpenGLViewer::printVectoredEPS() {
00569 return printGl2PS();
00570 }
00571
00572 bool G4OpenGLViewer::printNonVectoredEPS () {
00573
00574 int width = getRealPrintSizeX();
00575 int height = getRealPrintSizeY();
00576
00577 #ifdef G4DEBUG_VIS_OGL
00578 printf("G4OpenGLViewer::printNonVectoredEPS file:%s Vec:%d X:%d Y:%d col:%d fWinX:%d fWinY:%d\n",getRealPrintFilename().c_str(),fVectoredPs,width,height,fPrintColour,fWinSize_x,fWinSize_y);
00579 #endif
00580 FILE* fp;
00581 GLubyte* pixels;
00582 GLubyte* curpix;
00583 int components, pos, i;
00584
00585 pixels = grabPixels (fPrintColour, width, height);
00586
00587 if (pixels == NULL) {
00588 G4cerr << "Failed to get pixels from OpenGl viewport" << G4endl;
00589 return false;
00590 }
00591 if (fPrintColour) {
00592 components = 3;
00593 } else {
00594 components = 1;
00595 }
00596 std::string name = getRealPrintFilename();
00597 fp = fopen (name.c_str(), "w");
00598 if (fp == NULL) {
00599 G4cerr << "Can't open filename " << name.c_str() << G4endl;
00600 return false;
00601 }
00602
00603 fprintf (fp, "%%!PS-Adobe-2.0 EPSF-1.2\n");
00604 fprintf (fp, "%%%%Title: %s\n", name.c_str());
00605 fprintf (fp, "%%%%Creator: OpenGL pixmap render output\n");
00606 fprintf (fp, "%%%%BoundingBox: 0 0 %d %d\n", width, height);
00607 fprintf (fp, "%%%%EndComments\n");
00608 fprintf (fp, "gsave\n");
00609 fprintf (fp, "/bwproc {\n");
00610 fprintf (fp, " rgbproc\n");
00611 fprintf (fp, " dup length 3 idiv string 0 3 0 \n");
00612 fprintf (fp, " 5 -1 roll {\n");
00613 fprintf (fp, " add 2 1 roll 1 sub dup 0 eq\n");
00614 fprintf (fp, " { pop 3 idiv 3 -1 roll dup 4 -1 roll dup\n");
00615 fprintf (fp, " 3 1 roll 5 -1 roll } put 1 add 3 0 \n");
00616 fprintf (fp, " { 2 1 roll } ifelse\n");
00617 fprintf (fp, " }forall\n");
00618 fprintf (fp, " pop pop pop\n");
00619 fprintf (fp, "} def\n");
00620 fprintf (fp, "systemdict /colorimage known not {\n");
00621 fprintf (fp, " /colorimage {\n");
00622 fprintf (fp, " pop\n");
00623 fprintf (fp, " pop\n");
00624 fprintf (fp, " /rgbproc exch def\n");
00625 fprintf (fp, " { bwproc } image\n");
00626 fprintf (fp, " } def\n");
00627 fprintf (fp, "} if\n");
00628 fprintf (fp, "/picstr %d string def\n", width * components);
00629 fprintf (fp, "%d %d scale\n", width, height);
00630 fprintf (fp, "%d %d %d\n", width, height, 8);
00631 fprintf (fp, "[%d 0 0 %d 0 0]\n", width, height);
00632 fprintf (fp, "{currentfile picstr readhexstring pop}\n");
00633 fprintf (fp, "false %d\n", components);
00634 fprintf (fp, "colorimage\n");
00635
00636 curpix = (GLubyte*) pixels;
00637 pos = 0;
00638 for (i = width*height*components; i>0; i--) {
00639 fprintf (fp, "%02hx ", (unsigned short)(*(curpix++)));
00640 if (++pos >= 32) {
00641 fprintf (fp, "\n");
00642 pos = 0;
00643 }
00644 }
00645 if (pos)
00646 fprintf (fp, "\n");
00647
00648 fprintf (fp, "grestore\n");
00649 fprintf (fp, "showpage\n");
00650 delete [] pixels;
00651 fclose (fp);
00652
00653
00654
00655
00656
00657 return true;
00658 }
00659
00662 bool G4OpenGLViewer::isGl2psWriting() {
00663
00664 if (!fGL2PSAction) return false;
00665 if (fGL2PSAction->fileWritingEnabled()) {
00666 return true;
00667 }
00668 return false;
00669 }
00670
00671
00672
00673
00674 void G4OpenGLViewer::DrawText(const G4Text& g4text)
00675 {
00676
00677 if (isGl2psWriting()) {
00678
00679 G4VSceneHandler::MarkerSizeType sizeType;
00680 G4double size = fSceneHandler.GetMarkerSize(g4text,sizeType);
00681 G4Point3D position = g4text.GetPosition();
00682
00683 G4String textString = g4text.GetText();
00684 const char* textCString = textString.c_str();
00685
00686 glRasterPos3d(position.x(),position.y(),position.z());
00687 GLint align = GL2PS_TEXT_B;
00688
00689 switch (g4text.GetLayout()) {
00690 case G4Text::left: align = GL2PS_TEXT_BL; break;
00691 case G4Text::centre: align = GL2PS_TEXT_B; break;
00692 case G4Text::right: align = GL2PS_TEXT_BR;
00693 }
00694
00695 gl2psTextOpt(textCString,"Times-Roman",GLshort(size),align,0);
00696
00697 } else {
00698
00699 static G4int callCount = 0;
00700 ++callCount;
00701
00702 if (callCount <= 1) {
00703 G4cout <<
00704 "G4OpenGLViewer::DrawText: Not implemented for \""
00705 << fName <<
00706 "\"\n Called with "
00707 << g4text
00708 << G4endl;
00709 }
00710 }
00711 }
00712
00715 void G4OpenGLViewer::ChangePointSize(G4double size) {
00716
00717 if (isGl2psWriting()) {
00718 fGL2PSAction->setPointSize(int(size));
00719 } else {
00720 glPointSize (size);
00721 }
00722 }
00723
00724
00727 void G4OpenGLViewer::ChangeLineWidth(G4double width) {
00728
00729 if (isGl2psWriting()) {
00730 fGL2PSAction->setLineWidth(int(width));
00731 } else {
00732 glLineWidth (width);
00733 }
00734 }
00735
00736
00737 bool G4OpenGLViewer::printGl2PS() {
00738
00739 int width = getRealPrintSizeX();
00740 int height = getRealPrintSizeY();
00741
00742 if (!fGL2PSAction) return false;
00743
00744 fGL2PSAction->setFileName(getRealPrintFilename().c_str());
00745
00746 int X = fWinSize_x;
00747 int Y = fWinSize_y;
00748
00749 fWinSize_x = width;
00750 fWinSize_y = height;
00751
00752
00753
00754
00755
00756
00757
00758
00759
00760 ResizeGLView();
00761 bool extendBuffer = true;
00762 bool endWriteAction = false;
00763 bool beginWriteAction = true;
00764 while ((extendBuffer) && (! endWriteAction)) {
00765
00766 beginWriteAction = fGL2PSAction->enableFileWriting();
00767 if (beginWriteAction) {
00768
00769
00770
00771
00772 fGL2PSAction->setLineWidth(fGl2psDefaultLineWith);
00773
00774 fGL2PSAction->setPointSize(fGl2psDefaultPointSize);
00775
00776 DrawView ();
00777 endWriteAction = fGL2PSAction->disableFileWriting();
00778 }
00779 if ((! endWriteAction) || (! beginWriteAction)) {
00780 extendBuffer = fGL2PSAction->extendBufferSize();
00781 }
00782 }
00783 fGL2PSAction->resetBufferSizeParameters();
00784
00785 if (!extendBuffer ) {
00786 G4cerr << "gl2ps buffer size is not big enough to print this geometry. Thy to extend it. No output produced"<< G4endl;
00787 }
00788 if (!beginWriteAction ) {
00789 G4cerr << "Error while writing in the file "<<getRealPrintFilename().c_str()<<". Check read/write access No output produced" << G4endl;
00790 }
00791 if (!endWriteAction ) {
00792 G4cerr << "gl2ps error. No output produced" << G4endl;
00793 }
00794 fWinSize_x = X;
00795 fWinSize_y = Y;
00796
00797
00798
00799
00800
00801 return true;
00802 }
00803
00804 unsigned int G4OpenGLViewer::getWinWidth() {
00805 return fWinSize_x;
00806 }
00807
00808 unsigned int G4OpenGLViewer::getWinHeight() {
00809 return fWinSize_y;
00810 }
00811
00812 G4bool G4OpenGLViewer::sizeHasChanged() {
00813 return fSizeHasChanged;
00814 }
00815
00816 G4int G4OpenGLViewer::getRealPrintSizeX() {
00817 if (fPrintSizeX == -1) {
00818 return fWinSize_x;
00819 }
00820 GLint dims[2];
00821 glGetIntegerv(GL_MAX_VIEWPORT_DIMS, dims);
00822
00823
00824 if ((dims[0] !=0 ) && (dims[1] !=0)) {
00825 if (fPrintSizeX > dims[0]){
00826 return dims[0];
00827 }
00828 }
00829 if (fPrintSizeX < -1){
00830 return 0;
00831 }
00832 return fPrintSizeX;
00833 }
00834
00835 G4int G4OpenGLViewer::getRealPrintSizeY() {
00836 if (fPrintSizeY == -1) {
00837 return fWinSize_y;
00838 }
00839 GLint dims[2];
00840 glGetIntegerv(GL_MAX_VIEWPORT_DIMS, dims);
00841
00842
00843 if ((dims[0] !=0 ) && (dims[1] !=0)) {
00844 if (fPrintSizeY > dims[1]){
00845 return dims[1];
00846 }
00847 }
00848 if (fPrintSizeY < -1){
00849 return 0;
00850 }
00851 return fPrintSizeY;
00852 }
00853
00854 void G4OpenGLViewer::setPrintSize(G4int X, G4int Y) {
00855 fPrintSizeX = X;
00856 fPrintSizeY = Y;
00857 }
00858
00859 void G4OpenGLViewer::setPrintFilename(G4String name,G4bool inc) {
00860 if (name != "") {
00861 fPrintFilename = name;
00862 } else {
00863 fPrintFilename = "G4OpenGL";
00864 }
00865 if (inc) {
00866 fPrintFilenameIndex=0;
00867 } else {
00868 fPrintFilenameIndex=-1;
00869 }
00870 }
00871
00872 std::string G4OpenGLViewer::getRealPrintFilename() {
00873 std::string temp = fPrintFilename;
00874 if (fPrintFilenameIndex != -1) {
00875 temp += std::string("_");
00876 std::ostringstream os;
00877 os << fPrintFilenameIndex;
00878 std::string nb_str = os.str();
00879 temp += nb_str;
00880 }
00881 temp += ".eps";
00882 return temp;
00883 }
00884
00885 GLdouble G4OpenGLViewer::getSceneNearWidth()
00886 {
00887 if (!fSceneHandler.GetScene()) {
00888 return 0;
00889 }
00890 const G4Point3D targetPoint
00891 = fSceneHandler.GetScene()->GetStandardTargetPoint()
00892 + fVP.GetCurrentTargetPoint ();
00893 G4double radius = fSceneHandler.GetScene()->GetExtent().GetExtentRadius();
00894 if(radius<=0.) radius = 1.;
00895 const G4double cameraDistance = fVP.GetCameraDistance (radius);
00896 const GLdouble pnear = fVP.GetNearDistance (cameraDistance, radius);
00897 return 2 * fVP.GetFrontHalfHeight (pnear, radius);
00898 }
00899
00900 GLdouble G4OpenGLViewer::getSceneFarWidth()
00901 {
00902 if (!fSceneHandler.GetScene()) {
00903 return 0;
00904 }
00905 const G4Point3D targetPoint
00906 = fSceneHandler.GetScene()->GetStandardTargetPoint()
00907 + fVP.GetCurrentTargetPoint ();
00908 G4double radius = fSceneHandler.GetScene()->GetExtent().GetExtentRadius();
00909 if(radius<=0.) radius = 1.;
00910 const G4double cameraDistance = fVP.GetCameraDistance (radius);
00911 const GLdouble pnear = fVP.GetNearDistance (cameraDistance, radius);
00912 const GLdouble pfar = fVP.GetFarDistance (cameraDistance, pnear, radius);
00913 return 2 * fVP.GetFrontHalfHeight (pfar, radius);
00914 }
00915
00916
00917 GLdouble G4OpenGLViewer::getSceneDepth()
00918 {
00919 if (!fSceneHandler.GetScene()) {
00920 return 0;
00921 }
00922 const G4Point3D targetPoint
00923 = fSceneHandler.GetScene()->GetStandardTargetPoint()
00924 + fVP.GetCurrentTargetPoint ();
00925 G4double radius = fSceneHandler.GetScene()->GetExtent().GetExtentRadius();
00926 if(radius<=0.) radius = 1.;
00927 const G4double cameraDistance = fVP.GetCameraDistance (radius);
00928 const GLdouble pnear = fVP.GetNearDistance (cameraDistance, radius);
00929 return fVP.GetFarDistance (cameraDistance, pnear, radius)- pnear;
00930 }
00931
00932
00933
00934 void G4OpenGLViewer::rotateScene(G4double dx, G4double dy)
00935 {
00936 if (fVP.GetRotationStyle() == G4ViewParameters::freeRotation) {
00937 rotateSceneInViewDirection(dx,dy);
00938 } else {
00939 if( dx != 0) {
00940 rotateSceneThetaPhi(dx,0);
00941 }
00942 if( dy != 0) {
00943 rotateSceneThetaPhi(0,dy);
00944 }
00945 }
00946 }
00947
00948
00949 void G4OpenGLViewer::rotateSceneToggle(G4double dx, G4double dy)
00950 {
00951 if (fVP.GetRotationStyle() != G4ViewParameters::freeRotation) {
00952 rotateSceneInViewDirection(dx,dy);
00953 } else {
00954 if( dx != 0) {
00955 rotateSceneThetaPhi(dx,0);
00956 }
00957 if( dy != 0) {
00958 rotateSceneThetaPhi(0,dy);
00959 }
00960 }
00961 }
00962
00963 void G4OpenGLViewer::rotateSceneThetaPhi(G4double dx, G4double dy)
00964 {
00965 if (!fSceneHandler.GetScene()) {
00966 return;
00967 }
00968
00969 G4Vector3D vp;
00970 G4Vector3D up;
00971
00972 G4Vector3D xprime;
00973 G4Vector3D yprime;
00974 G4Vector3D zprime;
00975
00976 G4double delta_alpha;
00977 G4double delta_theta;
00978
00979 G4Vector3D new_vp;
00980 G4Vector3D new_up;
00981
00982 G4double cosalpha;
00983 G4double sinalpha;
00984
00985 G4Vector3D a1;
00986 G4Vector3D a2;
00987 G4Vector3D delta;
00988 G4Vector3D viewPoint;
00989
00990
00991
00992
00993 vp = fVP.GetViewpointDirection ().unit ();
00994 up = fVP.GetUpVector ().unit ();
00995
00996 yprime = (up.cross(vp)).unit();
00997 zprime = (vp.cross(yprime)).unit();
00998
00999 if (fVP.GetLightsMoveWithCamera()) {
01000 delta_alpha = dy * fRot_sens;
01001 delta_theta = -dx * fRot_sens;
01002 } else {
01003 delta_alpha = -dy * fRot_sens;
01004 delta_theta = dx * fRot_sens;
01005 }
01006
01007 delta_alpha *= deg;
01008 delta_theta *= deg;
01009
01010 new_vp = std::cos(delta_alpha) * vp + std::sin(delta_alpha) * zprime;
01011
01012
01013
01014
01015 if (fVP.GetLightsMoveWithCamera()) {
01016 new_up = (new_vp.cross(yprime)).unit();
01017 if (new_vp.z()*vp.z() <0) {
01018 new_up.set(new_up.x(),-new_up.y(),new_up.z());
01019 }
01020 } else {
01021 new_up = up;
01022 if (new_vp.z()*vp.z() <0) {
01023 new_up.set(new_up.x(),-new_up.y(),new_up.z());
01024 }
01025 }
01026 fVP.SetUpVector(new_up);
01028
01029
01030 cosalpha = new_up.dot (new_vp.unit());
01031 sinalpha = std::sqrt (1. - std::pow (cosalpha, 2));
01032 yprime = (new_up.cross (new_vp.unit())).unit ();
01033 xprime = yprime.cross (new_up);
01034
01035 a1 = sinalpha * xprime;
01036
01037 a2 = sinalpha * (std::cos (delta_theta) * xprime + std::sin (delta_theta) * yprime);
01038
01039 delta = a2 - a1;
01040
01041 viewPoint = new_vp.unit() + delta;
01042
01043 fVP.SetViewAndLights (viewPoint);
01044 }
01045
01046
01047 void G4OpenGLViewer::rotateSceneInViewDirection(G4double dx, G4double dy)
01048 {
01049 if (!fSceneHandler.GetScene()) {
01050 return;
01051 }
01052
01053 G4Vector3D vp;
01054 G4Vector3D up;
01055
01056 G4Vector3D xprime;
01057 G4Vector3D yprime;
01058 G4Vector3D zprime;
01059
01060 G4Vector3D new_vp;
01061 G4Vector3D new_up;
01062
01063 G4Vector3D a1;
01064 G4Vector3D a2;
01065 G4Vector3D delta;
01066 G4Vector3D viewPoint;
01067
01068 dx = dx/100;
01069 dy = dy/100;
01070
01071
01072
01073 #ifdef G4DEBUG_VIS_OGL
01074 printf("G4OpenGLViewer::rotateScene dx:%f dy:%f delta:%f\n",dx,dy, fRot_sens);
01075 #endif
01076
01077 vp = fVP.GetViewpointDirection ().unit();
01078 up = fVP.GetUpVector ().unit();
01079
01080 G4Vector3D zPrimeVector = G4Vector3D(up.y()*vp.z()-up.z()*vp.y(),
01081 up.z()*vp.x()-up.x()*vp.z(),
01082 up.x()*vp.y()-up.y()*vp.x());
01083
01084 viewPoint = vp/fRot_sens + (zPrimeVector*dx - up*dy) ;
01085 new_up = G4Vector3D(viewPoint.y()*zPrimeVector.z()-viewPoint.z()*zPrimeVector.y(),
01086 viewPoint.z()*zPrimeVector.x()-viewPoint.x()*zPrimeVector.z(),
01087 viewPoint.x()*zPrimeVector.y()-viewPoint.y()*zPrimeVector.x());
01088
01089 G4Vector3D new_upUnit = new_up.unit();
01090
01091
01092
01093 fVP.SetUpVector(new_upUnit);
01094 fVP.SetViewAndLights (viewPoint);
01095 }
01096
01097
01098 #endif