Geant4 Cross Reference |
1 // 1 // 2 // ******************************************* 2 // ******************************************************************** 3 // * License and Disclaimer << 3 // * DISCLAIMER * 4 // * 4 // * * 5 // * The Geant4 software is copyright of th << 5 // * The following disclaimer summarizes all the specific disclaimers * 6 // * the Geant4 Collaboration. It is provided << 6 // * of contributors to this software. The specific disclaimers,which * 7 // * conditions of the Geant4 Software License << 7 // * govern, are listed with their locations in: * 8 // * LICENSE and available at http://cern.ch/ << 8 // * http://cern.ch/geant4/license * 9 // * include a list of copyright holders. << 10 // * 9 // * * 11 // * Neither the authors of this software syst 10 // * Neither the authors of this software system, nor their employing * 12 // * institutes,nor the agencies providing fin 11 // * institutes,nor the agencies providing financial support for this * 13 // * work make any representation or warran 12 // * work make any representation or warranty, express or implied, * 14 // * regarding this software system or assum 13 // * regarding this software system or assume any liability for its * 15 // * use. Please see the license in the file << 14 // * use. * 16 // * for the full disclaimer and the limitatio << 17 // * 15 // * * 18 // * This code implementation is the result << 16 // * This code implementation is the intellectual property of the * 19 // * technical work of the GEANT4 collaboratio << 17 // * GEANT4 collaboration. * 20 // * By using, copying, modifying or distri << 18 // * By copying, distributing or modifying the Program (or any work * 21 // * any work based on the software) you ag << 19 // * based on the Program) you indicate your acceptance of this * 22 // * use in resulting scientific publicati << 20 // * statement, and all its terms. * 23 // * acceptance of all terms of the Geant4 Sof << 24 // ******************************************* 21 // ******************************************************************** 25 // 22 // 26 // 23 // >> 24 // $Id: G4OpenGLSceneHandler.cc,v 1.32 2005/04/17 16:08:43 allison Exp $ >> 25 // GEANT4 tag $Name: geant4-07-01-patch-01 $ 27 // 26 // 28 // << 27 // 29 // Andrew Walkden 27th March 1996 28 // Andrew Walkden 27th March 1996 30 // OpenGL stored scene - creates OpenGL displa 29 // OpenGL stored scene - creates OpenGL display lists. 31 // OpenGL immediate scene - draws immediately 30 // OpenGL immediate scene - draws immediately to buffer 32 // (saving space on 31 // (saving space on server). 33 32 >> 33 #ifdef G4VIS_BUILD_OPENGL_DRIVER >> 34 >> 35 // Included here - problems with HP compiler if not before other includes? >> 36 #include "G4NURBS.hh" 34 37 35 # include "G4OpenGLSceneHandler.hh" << 38 // Here follows a special for Mesa, the OpenGL emulator. Does not affect 36 # include "G4OpenGLViewer.hh" << 39 // other OpenGL's, as far as I'm aware. John Allison 18/9/96. 37 # include "G4OpenGLTransform3D.hh" << 40 #define CENTERLINE_CLPP /* CenterLine C++ workaround: */ 38 # include "G4Point3D.hh" << 41 // Also seems to be required for HP's CC and AIX xlC, at least. 39 # include "G4Normal3D.hh" << 42 40 # include "G4Transform3D.hh" << 43 #include "G4OpenGLSceneHandler.hh" 41 # include "G4Polyline.hh" << 44 #include "G4OpenGLViewer.hh" 42 # include "G4Polymarker.hh" << 45 #include "G4OpenGLFontBaseStore.hh" 43 # include "G4Text.hh" << 46 #include "G4OpenGLTransform3D.hh" 44 # include "G4Circle.hh" << 47 #include "G4Point3D.hh" 45 # include "G4Square.hh" << 48 #include "G4Normal3D.hh" 46 # include "G4VMarker.hh" << 49 #include "G4Transform3D.hh" 47 # include "G4Polyhedron.hh" << 50 #include "G4Polyline.hh" 48 # include "G4VisAttributes.hh" << 51 #include "G4Text.hh" 49 # include "G4PhysicalVolumeModel.hh" << 52 #include "G4Circle.hh" 50 # include "G4VPhysicalVolume.hh" << 53 #include "G4Square.hh" 51 # include "G4LogicalVolume.hh" << 54 #include "G4VMarker.hh" 52 # include "G4VSolid.hh" << 55 #include "G4Polyhedron.hh" 53 # include "G4Scene.hh" << 56 #include "G4VisAttributes.hh" 54 # include "G4VisExtent.hh" << 57 #include "G4VPhysicalVolume.hh" 55 # include "G4AttHolder.hh" << 58 #include "G4LogicalVolume.hh" 56 # include "G4PhysicalConstants.hh" << 59 #include "G4VSolid.hh" 57 # include "G4RunManager.hh" << 60 58 # include "G4Run.hh" << 61 G4OpenGLSceneHandler::G4OpenGLSceneHandler (G4VGraphicsSystem& system, 59 # include "G4RunManagerFactory.hh" << 62 G4int id, 60 # include "G4Mesh.hh" << 63 const G4String& name): 61 # include "G4PseudoScene.hh" << 64 G4VSceneHandler (system, id, name) 62 # include "G4VisManager.hh" << 65 {} >> 66 >> 67 G4OpenGLSceneHandler::~G4OpenGLSceneHandler () >> 68 { >> 69 ClearStore (); >> 70 } 63 71 64 const GLubyte G4OpenGLSceneHandler::fStippleMa 72 const GLubyte G4OpenGLSceneHandler::fStippleMaskHashed [128] = { 65 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 73 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 66 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 74 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 67 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 75 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 68 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 76 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 69 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 77 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 70 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 78 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 71 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 79 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 72 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 80 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 73 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 81 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 74 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 82 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 75 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 83 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 76 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 84 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 77 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 85 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 78 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 86 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 79 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 87 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55, 80 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55 88 0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55 81 }; 89 }; 82 90 83 G4OpenGLSceneHandler::G4OpenGLSceneHandler (G4 << 91 //Method for handling G4Polyline objects (from tracking or wireframe). 84 G4 << 85 co << 86 G4VSceneHandler (system, id, name), << 87 fPickName(0), << 88 fThreePassCapable(false), << 89 fSecondPassForTransparencyRequested(false), << 90 fSecondPassForTransparency(false), << 91 fThirdPassForNonHiddenMarkersRequested(false), << 92 fThirdPassForNonHiddenMarkers(false), << 93 fEdgeFlag(true) << 94 { << 95 } << 96 << 97 G4OpenGLSceneHandler::~G4OpenGLSceneHandler () << 98 { << 99 ClearStore (); << 100 } << 101 << 102 void G4OpenGLSceneHandler::ClearAndDestroyAtts << 103 { << 104 std::map<GLuint, G4AttHolder*>::iterator i; << 105 for (i = fPickMap.begin(); i != fPickMap.end << 106 fPickMap.clear(); << 107 } << 108 << 109 G4int G4OpenGLSceneHandler::fEntitiesFlushInte << 110 G4OpenGLSceneHandler::FlushAction << 111 G4OpenGLSceneHandler::fFlushAction = G4OpenGLS << 112 << 113 void G4OpenGLSceneHandler::ScaledFlush() << 114 { << 115 if (fReadyForTransients) { << 116 << 117 // Drawing transients, e.g., trajectories. << 118 << 119 if (!fpScene) { << 120 // No scene - shouldn't happen << 121 glFlush(); << 122 return; << 123 } << 124 // Get event from modeling parameters << 125 if (!fpModel) { << 126 // No model - shouldn't happen << 127 glFlush(); << 128 return; << 129 } << 130 const G4ModelingParameters* modelingParame << 131 fpModel->GetModelingParameters(); << 132 if (!modelingParameters) { << 133 // No modeling parameters - shouldn't ha << 134 glFlush(); << 135 return; << 136 } << 137 const G4Event* thisEvent = modelingParamet << 138 if (!thisEvent) { << 139 // No event, so not in event loop. << 140 if (fFlushAction == endOfEvent) { << 141 fFlushAction = endOfRun; << 142 } else if (fFlushAction == NthEvent) { << 143 fFlushAction = NthPrimitive; << 144 } << 145 } << 146 G4RunManager* runMan = G4RunManagerFactory << 147 if (!runMan) { << 148 // No run manager - shouldn't happen << 149 glFlush(); << 150 return; << 151 } << 152 const G4Run* thisRun = runMan->GetCurrentR << 153 if (!thisRun) { << 154 // No run, so not in event loop. << 155 if (fFlushAction == endOfRun) { << 156 fFlushAction = NthPrimitive; << 157 } else if (fFlushAction == NthEvent) { << 158 fFlushAction = NthPrimitive; << 159 } << 160 } << 161 << 162 switch (fFlushAction) { << 163 case endOfEvent: << 164 // If "/vis/scene/endOfEventAction ref << 165 // end of run anyway, so only scale if << 166 if (!fpScene->GetRefreshAtEndOfEvent() << 167 // But if "/vis/scene/endOfEventActi << 168 // called until end of run, so we ha << 169 // Get event from modeling parameter << 170 G4int thisEventID = thisEvent->GetEv << 171 static G4int lastEventID = 0; << 172 if (thisEventID != lastEventID) { << 173 glFlush(); << 174 lastEventID = thisEventID; << 175 } << 176 } << 177 break; << 178 case endOfRun: << 179 // If "/vis/scene/endOfRunAction refre << 180 // end of run anyway, so only scale if << 181 if (!fpScene->GetRefreshAtEndOfRun()) << 182 // If "/vis/scene/endOfRunAction acc << 183 // so we have to watch for a new run << 184 G4int thisRunID = thisRun->GetRunID( << 185 static G4int lastRunID = 0; << 186 if (thisRunID != lastRunID) { << 187 glFlush(); << 188 lastRunID = thisRunID; << 189 } << 190 } << 191 break; << 192 case eachPrimitive: << 193 // This is equivalent to numeric with << 194 fEntitiesFlushInterval = 1; << 195 [[fallthrough]]; // Fall through to NthPrim << 196 case NthPrimitive: << 197 { // Encapsulate in scope {} brackets to << 198 static G4int primitivesWaitingToBeFlus << 199 primitivesWaitingToBeFlushed++; << 200 if (primitivesWaitingToBeFlushed < fEn << 201 glFlush(); << 202 primitivesWaitingToBeFlushed = 0; << 203 break; << 204 } << 205 case NthEvent: << 206 // If "/vis/scene/endOfEventAction ref << 207 // end of event anyway, so only scale << 208 if (!fpScene->GetRefreshAtEndOfEvent() << 209 G4int thisEventID = thisEvent->GetEv << 210 static G4int lastEventID = 0; << 211 if (thisEventID != lastEventID) { << 212 static G4int eventsWaitingToBeFlus << 213 eventsWaitingToBeFlushed++; << 214 if (eventsWaitingToBeFlushed < fEn << 215 glFlush(); << 216 eventsWaitingToBeFlushed = 0; << 217 lastEventID = thisEventID; << 218 } << 219 } << 220 break; << 221 case never: << 222 break; << 223 default: << 224 break; << 225 } << 226 << 227 } << 228 << 229 else << 230 << 231 { << 232 << 233 // For run duration model drawing (detecto << 234 // Immediate mode: a huge speed up is obta << 235 // Stored mode: no discernable difference << 236 // back buffer and then swapped. << 237 // So eachPrimitive and NthPrimitive make << 238 // endOfRun are treated as "no action", i. << 239 // as happens anyway, when drawing is comp << 240 << 241 switch (fFlushAction) { << 242 case endOfEvent: << 243 break; << 244 case endOfRun: << 245 break; << 246 case eachPrimitive: << 247 // This is equivalent to NthPrimitive << 248 fEntitiesFlushInterval = 1; << 249 [[fallthrough]]; // Fall through to NthPrim << 250 case NthPrimitive: << 251 { // Encapsulate in scope {} brackets to << 252 static G4int primitivesWaitingToBeFlus << 253 primitivesWaitingToBeFlushed++; << 254 if (primitivesWaitingToBeFlushed < fEn << 255 glFlush(); << 256 primitivesWaitingToBeFlushed = 0; << 257 break; << 258 } << 259 case NthEvent: << 260 break; << 261 case never: << 262 break; << 263 default: << 264 break; << 265 } << 266 << 267 } << 268 } << 269 << 270 void G4OpenGLSceneHandler::ProcessScene() << 271 { << 272 fThreePassCapable = true; << 273 << 274 G4VSceneHandler::ProcessScene(); << 275 << 276 // Repeat if required... << 277 if (fSecondPassForTransparencyRequested) { << 278 fSecondPassForTransparency = true; << 279 G4VSceneHandler::ProcessScene(); << 280 fSecondPassForTransparency = false; << 281 fSecondPassForTransparencyRequested = fals << 282 } << 283 << 284 // And again if required... << 285 if (fThirdPassForNonHiddenMarkersRequested) << 286 fThirdPassForNonHiddenMarkers = true; << 287 G4VSceneHandler::ProcessScene(); << 288 fThirdPassForNonHiddenMarkers = false; << 289 fThirdPassForNonHiddenMarkersRequested = f << 290 } << 291 << 292 fThreePassCapable = false; << 293 } << 294 << 295 void G4OpenGLSceneHandler::PreAddSolid << 296 (const G4Transform3D& objectTransformation, << 297 const G4VisAttributes& visAttribs) << 298 { << 299 G4VSceneHandler::PreAddSolid (objectTransfor << 300 } << 301 << 302 void G4OpenGLSceneHandler::BeginPrimitives << 303 (const G4Transform3D& objectTransformation) << 304 { << 305 G4VSceneHandler::BeginPrimitives (objectTran << 306 } << 307 << 308 void G4OpenGLSceneHandler::EndPrimitives () << 309 { << 310 G4VSceneHandler::EndPrimitives (); << 311 } << 312 << 313 void G4OpenGLSceneHandler::BeginPrimitives2D << 314 (const G4Transform3D& objectTransformation) << 315 { << 316 G4VSceneHandler::BeginPrimitives2D (objectTr << 317 } << 318 << 319 void G4OpenGLSceneHandler::EndPrimitives2D () << 320 { << 321 G4VSceneHandler::EndPrimitives2D (); << 322 } << 323 << 324 G4DisplacedSolid* G4OpenGLSceneHandler::Create << 325 { << 326 return G4VSceneHandler::CreateSectionSolid() << 327 // If clipping done in G4OpenGLViewer::SetVi << 328 // return 0; << 329 // Note: if you change this, you must also c << 330 // G4OpenGLStoredViewer::CompareForKernelVis << 331 } << 332 << 333 G4DisplacedSolid* G4OpenGLSceneHandler::Create << 334 { << 335 // return G4VSceneHandler::CreateCutawaySoli << 336 // If cutaway done in G4OpenGLViewer::SetVie << 337 return 0; << 338 // Note: if you change this, you must also c << 339 // G4OpenGLStoredViewer::CompareForKernelVis << 340 } << 341 << 342 void G4OpenGLSceneHandler::AddPrimitive (const 92 void G4OpenGLSceneHandler::AddPrimitive (const G4Polyline& line) 343 { 93 { 344 std::size_t nPoints = line.size (); << 94 G4int nPoints = line.size (); 345 if (nPoints <= 0) return; 95 if (nPoints <= 0) return; 346 96 347 // Note: colour and depth test treated in su << 97 const G4Colour& c = GetColour (line); >> 98 glColor3d (c.GetRed (), c.GetGreen (), c.GetBlue ()); 348 99 349 glDisable (GL_LIGHTING); << 100 if (fpViewer -> GetViewParameters ().IsMarkerNotHidden ()) 350 << 101 glDisable (GL_DEPTH_TEST); 351 G4double lineWidth = GetLineWidth(fpVisAttri << 102 else glEnable (GL_DEPTH_TEST); 352 // Need access to method in G4OpenGLViewer. << 353 // work with a virtual base class, so use dy << 354 // test the outcome since viewer is guarante << 355 // G4OpenGLViewer, but test it anyway to kee << 356 G4OpenGLViewer* pGLViewer = dynamic_cast<G4O << 357 if (pGLViewer) pGLViewer->ChangeLineWidth(li << 358 103 359 fEdgeFlag = true; << 104 glDisable (GL_LIGHTING); 360 glBegin (GL_LINE_STRIP); 105 glBegin (GL_LINE_STRIP); 361 // No ned glEdgeFlag for lines : << 106 362 // Boundary and nonboundary edge flags on ve << 107 for (G4int iPoint = 0; iPoint < nPoints; iPoint++) { 363 << 364 // glEdgeFlag (GL_TRUE); << 365 for (std::size_t iPoint = 0; iPoint < nPoint << 366 G4double x, y, z; 108 G4double x, y, z; 367 x = line[iPoint].x(); 109 x = line[iPoint].x(); 368 y = line[iPoint].y(); 110 y = line[iPoint].y(); 369 z = line[iPoint].z(); 111 z = line[iPoint].z(); 370 glVertex3d (x, y, z); 112 glVertex3d (x, y, z); 371 } 113 } 372 glEnd (); 114 glEnd (); 373 } 115 } 374 116 375 void G4OpenGLSceneHandler::AddPrimitive (const << 117 void G4OpenGLSceneHandler::AddPrimitive (const G4Text& text) { 376 { << 118 377 if (polymarker.size() == 0) { << 119 const G4Colour& c = GetColour (text); // Picks up default if none. >> 120 MarkerSizeType sizeType; >> 121 G4double size = GetMarkerSize (text, sizeType); >> 122 G4ThreeVector position (*fpObjectTransformation * text.GetPosition ()); >> 123 G4String textString = text.GetText(); >> 124 >> 125 G4int font_base = G4OpenGLFontBaseStore::GetFontBase(fpViewer,size); >> 126 if (font_base < 0) { >> 127 static G4int callCount = 0; >> 128 ++callCount; >> 129 if (callCount <= 10 || callCount%100 == 0) { >> 130 G4cout << >> 131 "G4OpenGLSceneHandler::AddPrimitive (const G4Text&) call count " >> 132 << callCount << >> 133 "\n No fonts available." >> 134 "\n Called with text \"" >> 135 << text.GetText () >> 136 << "\"\n at " << position >> 137 << ", size " << size >> 138 << ", offsets " << text.GetXOffset () << ", " << text.GetYOffset () >> 139 << ", type " << G4int(sizeType) >> 140 << ", colour " << c >> 141 << G4endl; >> 142 } 378 return; 143 return; 379 } 144 } >> 145 const char* textCString = textString.c_str(); >> 146 glColor3d (c.GetRed (), c.GetGreen (), c.GetBlue ()); >> 147 glDisable (GL_DEPTH_TEST); >> 148 glDisable (GL_LIGHTING); >> 149 >> 150 glRasterPos3f(position.x(),position.y(),position.z()); >> 151 // No action on offset or layout at present. >> 152 glPushAttrib(GL_LIST_BIT); >> 153 glListBase(font_base); >> 154 glCallLists(strlen(textCString), GL_UNSIGNED_BYTE, (GLubyte *)textCString); >> 155 glPopAttrib(); >> 156 } 380 157 381 // Note: colour and depth test treated in su << 158 void G4OpenGLSceneHandler::AddPrimitive (const G4Circle& circle) { >> 159 glEnable (GL_POINT_SMOOTH); >> 160 AddCircleSquare (circle, 24); >> 161 } >> 162 >> 163 void G4OpenGLSceneHandler::AddPrimitive (const G4Square& square) { >> 164 glDisable (GL_POINT_SMOOTH); >> 165 AddCircleSquare (square, 4); >> 166 } 382 167 >> 168 void G4OpenGLSceneHandler::AddCircleSquare >> 169 (const G4VMarker& marker, >> 170 G4int nSides) { >> 171 >> 172 const G4Colour& c = GetColour (marker); >> 173 glColor3d (c.GetRed (), c.GetGreen (), c.GetBlue ()); >> 174 >> 175 if (fpViewer -> GetViewParameters ().IsMarkerNotHidden ()) >> 176 glDisable (GL_DEPTH_TEST); >> 177 else glEnable (GL_DEPTH_TEST); >> 178 383 glDisable (GL_LIGHTING); 179 glDisable (GL_LIGHTING); 384 180 385 MarkerSizeType sizeType; << 181 G4VMarker::FillStyle style = marker.GetFillStyle(); 386 G4double size = GetMarkerSize(polymarker, si << 387 << 388 // Need access to method in G4OpenGLViewer. << 389 // work with a virtual base class, so use dy << 390 // test the outcome since viewer is guarante << 391 // G4OpenGLViewer, but test it anyway to kee << 392 G4OpenGLViewer* pGLViewer = dynamic_cast<G4O << 393 if (!pGLViewer) return; << 394 << 395 if (sizeType == world) { // Size specified << 396 G4double lineWidth = GetLineWidth(fpVisAtt << 397 pGLViewer->ChangeLineWidth(lineWidth); << 398 182 399 G4VMarker::FillStyle style = polymarker.Ge << 183 switch (style) { >> 184 case G4VMarker::noFill: >> 185 glPolygonMode (GL_FRONT_AND_BACK, GL_LINE); >> 186 break; 400 187 401 // G4bool filled = false; Not actually us << 188 case G4VMarker::hashed: 402 static G4bool hashedWarned = false; << 189 /* >> 190 G4cout << "Hashed fill style in G4OpenGLSceneHandler." >> 191 << "\n Not implemented. Using G4VMarker::filled." >> 192 << G4endl; >> 193 */ >> 194 glPolygonMode (GL_FRONT_AND_BACK, GL_FILL); >> 195 glPolygonStipple (fStippleMaskHashed); >> 196 // See also: >> 197 // if (style == G4VMarker::filled || style == G4VMarker::hashed)... >> 198 // (twice) below. >> 199 break; >> 200 >> 201 case G4VMarker::filled: >> 202 glPolygonMode (GL_FRONT_AND_BACK, GL_FILL); >> 203 break; >> 204 >> 205 default: >> 206 G4cout << "Unrecognised fill style in G4OpenGLSceneHandler." >> 207 << "\n Using G4VMarker::filled." >> 208 << G4endl; >> 209 glPolygonMode (GL_FRONT_AND_BACK, GL_FILL); >> 210 break; 403 211 404 switch (style) { << 405 case G4VMarker::noFill: << 406 glPolygonMode (GL_FRONT_AND_BACK, GL_L << 407 glEdgeFlag (GL_TRUE); << 408 //filled = false; << 409 break; << 410 case G4VMarker::hashed: << 411 if (!hashedWarned) { << 412 G4cout << "Hashed fill style in G4Op << 413 << "\n Not implemented. Using G4VM << 414 << G4endl; << 415 hashedWarned = true; << 416 } << 417 // Maybe use << 418 //glPolygonStipple (fStippleMaskHashed << 419 [[fallthrough]]; // Drop through to filled << 420 case G4VMarker::filled: << 421 glPolygonMode (GL_FRONT_AND_BACK, GL_F << 422 //filled = true; << 423 break; << 424 } << 425 } 212 } 426 << 427 // Draw... << 428 if (sizeType == world) { // Size specified << 429 << 430 G4int nSides; << 431 G4double startPhi; << 432 switch (polymarker.GetMarkerType()) { << 433 default: << 434 case G4Polymarker::dots: << 435 size = 1.; << 436 [[fallthrough]]; // Fall through to circles << 437 case G4Polymarker::circles: << 438 nSides = GetNoOfSides(fpVisAttribs); << 439 startPhi = 0.; << 440 break; << 441 case G4Polymarker::squares: << 442 nSides = 4; << 443 startPhi = -pi / 4.; << 444 break; << 445 } << 446 213 447 const G4Vector3D& viewpointDirection = << 214 // A few useful quantities... 448 fpViewer -> GetViewParameters().GetViewp << 215 G4Point3D centre = marker.GetPosition(); 449 const G4Vector3D& up = fpViewer->GetViewPa << 216 G4bool userSpecified = (marker.GetWorldSize() || marker.GetScreenSize()); 450 const G4double dPhi = twopi / nSides; << 217 const G4VMarker& def = fpViewer -> GetViewParameters().GetDefaultMarker(); 451 const G4double radius = size / 2.; << 218 const G4Vector3D& viewpointDirection = 452 G4Vector3D start = radius * (up.cross(view << 219 fpViewer -> GetViewParameters().GetViewpointDirection(); 453 G4double phi; << 220 const G4Vector3D& up = fpViewer->GetViewParameters().GetUpVector(); 454 G4int i; << 221 G4double scale = fpViewer -> GetViewParameters().GetGlobalMarkerScale(); 455 for (size_t iPoint = 0; iPoint < polymarke << 222 G4double size = scale * 456 fEdgeFlag = true; << 223 userSpecified ? marker.GetWorldSize() : def.GetWorldSize(); 457 glBegin (GL_POLYGON); << 224 458 for (i = 0, phi = startPhi; i < nSides; << 225 // Find "size" of marker in world space (but see note below)... 459 G4Vector3D r = start; r.rotate(phi, viewpoin << 226 G4double worldSize; 460 G4Vector3D p = polymarker[iPoint] + r; << 227 if (size) { // Size specified in world coordinates. 461 glVertex3d (p.x(), p.y(), p.z()); << 228 worldSize = size; 462 } << 229 } 463 glEnd (); << 230 else { // Size specified in screen (window) coordinates. 464 } << 231 465 << 232 // Find window coordinates of centre... 466 } else { // Size specified in screen (window << 233 GLdouble modelMatrix[16]; 467 << 234 glGetDoublev (GL_MODELVIEW_MATRIX, modelMatrix); 468 pGLViewer->ChangePointSize(size); << 235 G4double projectionMatrix[16]; 469 << 236 glGetDoublev (GL_PROJECTION_MATRIX, projectionMatrix); 470 //Antialiasing only for circles << 237 GLint viewport[4]; 471 switch (polymarker.GetMarkerType()) { << 238 glGetIntegerv(GL_VIEWPORT,viewport); 472 default: << 239 GLdouble winx, winy, winz; 473 case G4Polymarker::dots: << 240 gluProject(centre.x(), centre.y(), centre.z(), 474 case G4Polymarker::circles: << 241 modelMatrix, projectionMatrix, viewport, 475 glEnable (GL_POINT_SMOOTH); break; << 242 &winx, &winy, &winz); 476 case G4Polymarker::squares: << 243 477 glDisable (GL_POINT_SMOOTH); break; << 244 // Determine ratio window:world... 478 } << 245 const G4Vector3D inScreen = (up.cross(viewpointDirection)).unit(); 479 glBegin (GL_POINTS); << 246 const G4Vector3D p = centre + inScreen; 480 for (size_t iPoint = 0; iPoint < polymarke << 247 GLdouble winDx, winDy, winDz; 481 G4Point3D centre = polymarker[iPoint]; << 248 gluProject(p.x(), p.y(), p.z(), 482 glVertex3d(centre.x(),centre.y(),centre. << 249 modelMatrix, projectionMatrix, viewport, 483 } << 250 &winDx, &winDy, &winDz); 484 glEnd(); << 251 G4double winWorldRatio = std::sqrt(std::pow(winx - winDx, 2) + >> 252 std::pow(winy - winDy, 2)); >> 253 G4double winSize = scale * >> 254 userSpecified ? marker.GetScreenSize() : def.GetScreenSize(); >> 255 worldSize = winSize / winWorldRatio; 485 } 256 } 486 } << 487 257 488 void G4OpenGLSceneHandler::AddPrimitive (const << 258 // Draw... 489 // Pass to specific viewer via virtual funct << 259 DrawXYPolygon (worldSize, centre, nSides); 490 G4OpenGLViewer* pGLViewer = dynamic_cast<G4O << 491 if (pGLViewer) pGLViewer->DrawText(text); << 492 } 260 } 493 261 494 void G4OpenGLSceneHandler::AddPrimitive (const << 262 /*************************************************** 495 G4Polymarker oneCircle(circle); << 263 Note: We have to do it this way round so that when a global 496 oneCircle.push_back(circle.GetPosition()); << 264 transformation is applied, such as with /vis/viewer/set/viewpoint, 497 oneCircle.SetMarkerType(G4Polymarker::circle << 265 the markers follow the world coordinates without having to 498 // Call this AddPrimitive to avoid re-doing << 266 recreate the display lists. The down side is that the markers 499 G4OpenGLSceneHandler::AddPrimitive(oneCircle << 267 rotate. The only way to avoid this is to play with the modelview >> 268 and projection matrices of OpenGL - which I need to think about. >> 269 For future reference, here is the code to draw in window >> 270 coordinates; its down side is that markers do not follow global >> 271 transformations. Some clever stuff is needed. >> 272 >> 273 ... >> 274 // Find window coordinates of centre... >> 275 GLdouble modelMatrix[16]; >> 276 glGetDoublev (GL_MODELVIEW_MATRIX, modelMatrix); >> 277 G4double projectionMatrix[16]; >> 278 glGetDoublev (GL_PROJECTION_MATRIX, projectionMatrix); >> 279 GLint viewport[4]; >> 280 glGetIntegerv(GL_VIEWPORT,viewport); >> 281 GLdouble winx, winy, winz; >> 282 gluProject(centre.x(), centre.y(), centre.z(), >> 283 modelMatrix, projectionMatrix, viewport, >> 284 &winx, &winy, &winz); >> 285 >> 286 // Find window size... >> 287 G4double winSize; >> 288 if (size) { // Size specified in world coordinates. >> 289 // Determine size in window coordinates... >> 290 (Note: improve this by using an inScreen vector as above.) >> 291 GLdouble winx1, winy1, winz1; >> 292 gluProject(centre.x() + size, centre.y() + size, centre.z() + size, >> 293 modelMatrix, projectionMatrix, viewport, >> 294 &winx1, &winy1, &winz1); >> 295 winSize = std::sqrt((std::pow(winx - winx1, 2) + >> 296 std::pow(winy - winy1, 2) + >> 297 std::pow(winz - winz1, 2)) / 3.); >> 298 } >> 299 else { >> 300 winSize = scale * >> 301 userSpecified ? marker.GetScreenSize() : def.GetScreenSize(); >> 302 } >> 303 >> 304 // Prepare to draw in window coordinates... >> 305 glMatrixMode (GL_PROJECTION); >> 306 glPushMatrix(); >> 307 glLoadIdentity(); >> 308 gluOrtho2D(GLdouble(viewport[0]), >> 309 GLdouble(viewport[0] + viewport[2]), >> 310 GLdouble(viewport[1]), >> 311 GLdouble(viewport[1] + viewport[3])); >> 312 glMatrixMode (GL_MODELVIEW); >> 313 glPushMatrix(); >> 314 glLoadIdentity(); >> 315 >> 316 // Draw in window coordinates... >> 317 DrawScreenPolygon (winSize, G4Point3D(winx, winy, winz), nSides); >> 318 >> 319 // Re-instate matrices... >> 320 glMatrixMode (GL_PROJECTION); >> 321 glPopMatrix(); >> 322 glMatrixMode (GL_MODELVIEW); >> 323 glPopMatrix(); >> 324 ... >> 325 } >> 326 >> 327 void G4OpenGLSceneHandler::DrawScreenPolygon >> 328 (G4double size, >> 329 const G4Point3D& centre, >> 330 G4int nSides) { >> 331 glBegin (GL_POLYGON); >> 332 const G4double dPhi = twopi / nSides; >> 333 const G4double r = size / 2.; >> 334 G4double phi; >> 335 G4int i; >> 336 for (i = 0, phi = -dPhi / 2.; i < nSides; i++, phi += dPhi) { >> 337 G4double x, y, z; >> 338 x = centre.x() + r * std::cos(phi); >> 339 y = centre.y() + r * std::sin(phi); >> 340 z = centre.z(); >> 341 glVertex3d (x, y, z); >> 342 } >> 343 glEnd (); 500 } 344 } >> 345 **********************************************/ 501 346 502 void G4OpenGLSceneHandler::AddPrimitive (const << 347 void G4OpenGLSceneHandler::DrawXYPolygon 503 G4Polymarker oneSquare(square); << 348 (G4double size, 504 oneSquare.push_back(square.GetPosition()); << 349 const G4Point3D& centre, 505 oneSquare.SetMarkerType(G4Polymarker::square << 350 G4int nSides) { 506 // Call this AddPrimitive to avoid re-doing << 351 const G4Vector3D& viewpointDirection = 507 G4OpenGLSceneHandler::AddPrimitive(oneSquare << 352 fpViewer -> GetViewParameters().GetViewpointDirection(); >> 353 const G4Vector3D& up = fpViewer->GetViewParameters().GetUpVector(); >> 354 const G4double dPhi = twopi / nSides; >> 355 const G4double radius = size / 2.; >> 356 G4Vector3D start = radius * (up.cross(viewpointDirection)).unit(); >> 357 G4double phi; >> 358 G4int i; >> 359 glBegin (GL_POLYGON); >> 360 for (i = 0, phi = -dPhi / 2.; i < nSides; i++, phi += dPhi) { >> 361 G4Vector3D r = start; r.rotate(phi, viewpointDirection); >> 362 G4Vector3D p = centre + r; >> 363 glVertex3d (p.x(), p.y(), p.z()); >> 364 } >> 365 glEnd (); 508 } 366 } 509 367 510 //Method for handling G4Polyhedron objects for 368 //Method for handling G4Polyhedron objects for drawing solids. 511 void G4OpenGLSceneHandler::AddPrimitive (const 369 void G4OpenGLSceneHandler::AddPrimitive (const G4Polyhedron& polyhedron) { 512 370 513 // Assume all facets are planar convex quadr << 371 //Assume all facets are convex quadrilaterals. 514 // Draw each facet individually << 372 //Draw each G4Facet individually 515 373 516 if (polyhedron.GetNoFacets() == 0) return; 374 if (polyhedron.GetNoFacets() == 0) return; 517 375 518 // Need access to data in G4OpenGLViewer. s << 376 // Get vis attributes - pick up defaults if none. 519 // with a virtual base class, so use dynamic << 377 const G4VisAttributes* pVA = 520 G4OpenGLViewer* pGLViewer = dynamic_cast<G4O << 378 fpViewer -> GetApplicableVisAttributes (polyhedron.GetVisAttributes ()); 521 if (!pGLViewer) return; << 379 522 << 523 // Get view parameters that the user can for 380 // Get view parameters that the user can force through the vis 524 // attributes, thereby over-riding the curre 381 // attributes, thereby over-riding the current view parameter. 525 G4ViewParameters::DrawingStyle drawing_style << 382 G4ViewParameters::DrawingStyle drawing_style = GetDrawingStyle (pVA); 526 << 383 G4bool isAuxEdgeVisible = GetAuxEdgeVisible (pVA); 527 // Note that in stored mode, because this ca << 528 // list, it is the colour _at the time of_ << 529 // even if the colour is changed, for examp << 530 // window, current_colour does not change. << 531 GLfloat* painting_colour; << 532 GLfloat clear_colour[4]; << 533 GLfloat current_colour[4]; << 534 glGetFloatv (GL_CURRENT_COLOR, current_colou << 535 384 536 G4bool isTransparent = false; << 385 //Get colour, etc.. 537 if (current_colour[3] < 1.) { // This objec << 386 const G4Colour& c = pVA -> GetColour (); 538 isTransparent = true; << 387 GLfloat materialColour [4]; 539 } << 388 materialColour [0] = c.GetRed (); 540 << 389 materialColour [1] = c.GetGreen (); 541 if (drawing_style == G4ViewParameters::hlr) << 390 materialColour [2] = c.GetBlue (); 542 // This is the colour used to paint surfac << 391 materialColour [3] = 1.0; 543 glGetFloatv (GL_COLOR_CLEAR_VALUE, clear_c << 392 GLdouble clear_colour[4]; 544 painting_colour = clear_colour; << 393 glGetDoublev (GL_COLOR_CLEAR_VALUE, clear_colour); 545 } else { // drawing_style == G4ViewParamete << 546 painting_colour = current_colour; << 547 } << 548 << 549 G4double lineWidth = GetLineWidth(fpVisAttri << 550 pGLViewer->ChangeLineWidth(lineWidth); << 551 << 552 G4bool isAuxEdgeVisible = GetAuxEdgeVisible << 553 << 554 G4bool clipping = pGLViewer->fVP.IsSection() << 555 << 556 // Lighting disabled unless otherwise reques << 557 glDisable (GL_LIGHTING); << 558 394 559 switch (drawing_style) { 395 switch (drawing_style) { 560 case (G4ViewParameters::hlhsr): 396 case (G4ViewParameters::hlhsr): 561 // Set up as for hidden line removal but p << 397 // Set up as for hidden line removal but paint polygons... 562 case (G4ViewParameters::hlr): 398 case (G4ViewParameters::hlr): 563 glEnable (GL_STENCIL_TEST); 399 glEnable (GL_STENCIL_TEST); 564 // The stencil buffer is cleared in G4Open 400 // The stencil buffer is cleared in G4OpenGLViewer::ClearView. 565 // The procedure below leaves it clear. 401 // The procedure below leaves it clear. 566 glStencilFunc (GL_ALWAYS, 0, 1); 402 glStencilFunc (GL_ALWAYS, 0, 1); 567 glStencilOp (GL_INVERT, GL_INVERT, GL_INVE 403 glStencilOp (GL_INVERT, GL_INVERT, GL_INVERT); 568 glEnable (GL_DEPTH_TEST); 404 glEnable (GL_DEPTH_TEST); 569 glDepthFunc (GL_LEQUAL); << 405 glDepthFunc (GL_LESS); 570 if (isTransparent) { << 406 glEnable (GL_CULL_FACE); 571 // Transparent... << 407 glCullFace (GL_BACK); 572 glColorMaterial(GL_FRONT_AND_BACK, GL_AM << 408 glPolygonMode (GL_FRONT, GL_LINE); 573 glEnable(GL_COLOR_MATERIAL); << 409 glDisable (GL_LIGHTING); 574 //glDisable (GL_CULL_FACE); << 410 glColor3d (c.GetRed (), c.GetGreen (), c.GetBlue ()); 575 glPolygonMode (GL_FRONT_AND_BACK, GL_LIN << 576 } else { << 577 // Opaque... << 578 if (clipping) { << 579 glColorMaterial(GL_FRONT_AND_BACK, GL_ << 580 glEnable(GL_COLOR_MATERIAL); << 581 //glDisable (GL_CULL_FACE); << 582 glPolygonMode (GL_FRONT_AND_BACK, GL_LINE); << 583 } else { << 584 glColorMaterial(GL_FRONT, GL_AMBIENT_A << 585 glEnable(GL_COLOR_MATERIAL); << 586 //glEnable (GL_CULL_FACE); << 587 //glCullFace (GL_BACK); << 588 glPolygonMode (GL_FRONT, GL_LINE); << 589 } << 590 } << 591 break; 411 break; 592 case (G4ViewParameters::hsr): 412 case (G4ViewParameters::hsr): 593 glEnable (GL_DEPTH_TEST); 413 glEnable (GL_DEPTH_TEST); 594 glDepthFunc (GL_LEQUAL); << 414 glDepthFunc (GL_LESS); 595 if (isTransparent) { << 415 glEnable (GL_CULL_FACE); 596 // Transparent... << 416 glCullFace (GL_BACK); 597 glDepthMask (GL_FALSE); // Make depth b << 417 glEnable (GL_LIGHTING); 598 glColorMaterial(GL_FRONT_AND_BACK, GL_AM << 418 glPolygonMode (GL_FRONT, GL_FILL); 599 glEnable(GL_COLOR_MATERIAL); << 419 glMaterialfv (GL_FRONT, GL_AMBIENT_AND_DIFFUSE, materialColour); 600 //glDisable (GL_CULL_FACE); << 420 break; 601 glPolygonMode (GL_FRONT_AND_BACK, GL_FIL << 602 } else { << 603 // Opaque... << 604 glDepthMask (GL_TRUE); // Make depth bu << 605 if (clipping) { << 606 glColorMaterial(GL_FRONT_AND_BACK, GL_ << 607 glEnable(GL_COLOR_MATERIAL); << 608 //glDisable (GL_CULL_FACE); << 609 glPolygonMode (GL_FRONT_AND_BACK, GL_FILL); << 610 } else { << 611 glColorMaterial(GL_FRONT, GL_AMBIENT_A << 612 glEnable(GL_COLOR_MATERIAL); << 613 //glEnable (GL_CULL_FACE); << 614 //glCullFace (GL_BACK); << 615 glPolygonMode (GL_FRONT, GL_FILL); << 616 } << 617 } << 618 if (!fProcessing2D) glEnable (GL_LIGHTING) << 619 break; << 620 case (G4ViewParameters::wireframe): 421 case (G4ViewParameters::wireframe): 621 default: 422 default: >> 423 //glDisable (GL_DEPTH_TEST); 622 glEnable (GL_DEPTH_TEST); 424 glEnable (GL_DEPTH_TEST); 623 glDepthFunc (GL_LEQUAL); //??? was GL_A << 425 glDepthFunc (GL_ALWAYS); 624 //glDisable (GL_CULL_FACE); << 426 glDisable (GL_CULL_FACE); >> 427 glDisable (GL_LIGHTING); 625 glPolygonMode (GL_FRONT_AND_BACK, GL_LINE) 428 glPolygonMode (GL_FRONT_AND_BACK, GL_LINE); >> 429 glColor3d (c.GetRed (), c.GetGreen (), c.GetBlue ()); 626 break; 430 break; 627 } 431 } 628 432 629 //Loop through all the facets... 433 //Loop through all the facets... 630 fEdgeFlag = true; << 631 glBegin (GL_QUADS); 434 glBegin (GL_QUADS); 632 glEdgeFlag (GL_TRUE); << 633 G4bool notLastFace; 435 G4bool notLastFace; 634 do { 436 do { 635 437 636 //First, find vertices, edgeflags and norm << 438 //First, find surface normal and note "not last facet"... 637 G4Point3D vertex[4]; << 439 G4Normal3D SurfaceUnitNormal; 638 G4int edgeFlag[4]; << 440 notLastFace = polyhedron.GetNextUnitNormal (SurfaceUnitNormal); 639 G4Normal3D normals[4]; << 640 G4int nEdges; << 641 notLastFace = polyhedron.GetNextFacet(nEdg << 642 441 643 //Loop through the four edges of each G4Fa 442 //Loop through the four edges of each G4Facet... 644 for(G4int edgeCount = 0; edgeCount < nEdge << 443 G4bool notLastEdge; >> 444 G4Point3D vertex[4]; >> 445 G4int edgeFlag[4]; >> 446 G4int edgeCount = 0; >> 447 glNormal3d(SurfaceUnitNormal.x(), SurfaceUnitNormal.y(), >> 448 SurfaceUnitNormal.z()); >> 449 do { >> 450 notLastEdge = polyhedron.GetNextVertex (vertex[edgeCount], >> 451 edgeFlag[edgeCount]); 645 // Check to see if edge is visible or no 452 // Check to see if edge is visible or not... 646 if (isAuxEdgeVisible) { 453 if (isAuxEdgeVisible) { 647 edgeFlag[edgeCount] = 1; << 454 edgeFlag[edgeCount] = G4int (true); 648 } 455 } 649 if (edgeFlag[edgeCount] > 0) { << 456 if (edgeFlag[edgeCount]) { 650 if (fEdgeFlag != true) { << 457 glEdgeFlag (GL_TRUE); 651 glEdgeFlag (GL_TRUE); << 652 fEdgeFlag = true; << 653 } << 654 } else { 458 } else { 655 if (fEdgeFlag != false) { << 459 glEdgeFlag (GL_FALSE); 656 glEdgeFlag (GL_FALSE); << 657 fEdgeFlag = false; << 658 } << 659 } 460 } 660 glNormal3d (normals[edgeCount].x(), << 661 normals[edgeCount].y(), << 662 normals[edgeCount].z()); << 663 glVertex3d (vertex[edgeCount].x(), 461 glVertex3d (vertex[edgeCount].x(), 664 vertex[edgeCount].y(), 462 vertex[edgeCount].y(), 665 vertex[edgeCount].z()); 463 vertex[edgeCount].z()); 666 } << 464 edgeCount++; 667 << 465 } while (notLastEdge && edgeCount < 4); 668 // HepPolyhedron produces triangles too; i << 466 // HEPPolyhedron produces triangles too; in that case add an extra vertex.. 669 // vertex identical to first... << 467 while (edgeCount < 4) { 670 if (nEdges == 3) { << 468 vertex[edgeCount] = vertex[edgeCount-1]; 671 G4int edgeCount = 3; << 469 edgeFlag[edgeCount] = G4int (false); 672 normals[edgeCount] = normals[0]; << 470 glEdgeFlag (GL_FALSE); 673 vertex[edgeCount] = vertex[0]; << 674 edgeFlag[edgeCount] = -1; << 675 if (fEdgeFlag != false) { << 676 glEdgeFlag (GL_FALSE); << 677 fEdgeFlag = false; << 678 } << 679 << 680 glNormal3d (normals[edgeCount].x(), << 681 normals[edgeCount].y(), << 682 normals[edgeCount].z()); << 683 glVertex3d (vertex[edgeCount].x(), 471 glVertex3d (vertex[edgeCount].x(), 684 vertex[edgeCount].y(), 472 vertex[edgeCount].y(), 685 vertex[edgeCount].z()); 473 vertex[edgeCount].z()); >> 474 edgeCount++; 686 } 475 } 687 // Trap situation where number of edges is 476 // Trap situation where number of edges is > 4... 688 if (nEdges > 4) { << 477 while (notLastEdge) { >> 478 notLastFace = polyhedron.GetNextUnitNormal (SurfaceUnitNormal); >> 479 edgeCount++; >> 480 } >> 481 if (edgeCount > 4) { 689 G4cerr << 482 G4cerr << 690 "G4OpenGLSceneHandler::AddPrimitive(G4Polyhe << 483 "G4OpenGLSceneHandler::AddPrimitive(G4Polyhedron): WARNING"; 691 "\n G4Polyhedron facet with " << nEdges << << 484 if (fpCurrentPV) { >> 485 G4cerr << >> 486 "\n Volume " << fpCurrentPV->GetName() << >> 487 ", Solid " << fpCurrentLV->GetSolid()->GetName() << >> 488 " (" << fpCurrentLV->GetSolid()->GetEntityType(); >> 489 } >> 490 G4cerr<< >> 491 "\n G4Polyhedron facet with " << edgeCount << " edges" << G4endl; 692 } 492 } 693 493 694 << 695 // Do it all over again (twice) for hlr... 494 // Do it all over again (twice) for hlr... 696 if (drawing_style == G4ViewParameters::hl 495 if (drawing_style == G4ViewParameters::hlr || 697 drawing_style == G4ViewParameters::hlhsr) { 496 drawing_style == G4ViewParameters::hlhsr) { 698 497 699 glDisable(GL_COLOR_MATERIAL); // Revert << 700 glEnd (); // Placed here to balance glB 498 glEnd (); // Placed here to balance glBegin above, allowing GL 701 << 499 // state changes below, then glBegin again. Avoids 702 // state changes below, then glBegin aga << 703 // having glBegin/End pairs *inside* loop 500 // having glBegin/End pairs *inside* loop in the more 704 // usual case of no hidden line removal. 501 // usual case of no hidden line removal. 705 502 706 // Lighting disabled unless otherwise re << 707 glDisable (GL_LIGHTING); << 708 << 709 // Draw through stencil... 503 // Draw through stencil... 710 glStencilFunc (GL_EQUAL, 0, 1); 504 glStencilFunc (GL_EQUAL, 0, 1); 711 glStencilOp (GL_KEEP, GL_KEEP, GL_KEEP); 505 glStencilOp (GL_KEEP, GL_KEEP, GL_KEEP); 712 if (drawing_style == G4ViewParameters::h << 506 glPolygonMode (GL_FRONT, GL_FILL); 713 if (!fProcessing2D) glEnable (GL_LIGHTING); << 507 if (drawing_style == G4ViewParameters::hlhsr) glEnable (GL_LIGHTING); 714 } << 508 glBegin (GL_QUADS); 715 glEnable (GL_DEPTH_TEST); << 716 glDepthFunc (GL_LEQUAL); << 717 if (isTransparent) { << 718 // Transparent... << 719 glDepthMask (GL_FALSE); // Make depth buffe << 720 //glDisable (GL_CULL_FACE); << 721 glPolygonMode (GL_FRONT_AND_BACK, GL_FILL); << 722 } else { << 723 // Opaque... << 724 glDepthMask (GL_TRUE); // Make depth buffer << 725 if (clipping) { << 726 //glDisable (GL_CULL_FACE); << 727 glPolygonMode (GL_FRONT_AND_BACK, GL_FILL) << 728 } else { << 729 //glEnable (GL_CULL_FACE); << 730 //glCullFace (GL_BACK); << 731 glPolygonMode (GL_FRONT, GL_FILL); << 732 } << 733 } << 734 if (drawing_style == G4ViewParameters:: 509 if (drawing_style == G4ViewParameters::hlr) { 735 if (isTransparent) { << 510 glColor4dv (clear_colour); 736 // Transparent - don't paint... << 511 } else { // drawing_style == G4ViewParameters::hlhsr 737 goto end_of_drawing_through_stencil; << 512 glMaterialfv (GL_FRONT, GL_AMBIENT_AND_DIFFUSE, materialColour); 738 } << 739 } 513 } 740 if (isTransparent) { << 514 glNormal3d(SurfaceUnitNormal.x(), SurfaceUnitNormal.y(), 741 // Transparent... << 515 SurfaceUnitNormal.z()); 742 glMaterialfv (GL_FRONT_AND_BACK, GL_AMBIENT_ << 743 } else { << 744 // Opaque... << 745 glMaterialfv (GL_FRONT, GL_AMBIENT_AND_DIFFU << 746 } << 747 glColor4fv (painting_colour); << 748 glBegin (GL_QUADS); << 749 glEdgeFlag (GL_TRUE); << 750 fEdgeFlag = true; << 751 << 752 for (int edgeCount = 0; edgeCount < 4; + 516 for (int edgeCount = 0; edgeCount < 4; ++edgeCount) { 753 if (edgeFlag[edgeCount] > 0) { << 517 if (edgeFlag[edgeCount]) { 754 if (fEdgeFlag != true) { << 518 glEdgeFlag (GL_TRUE); 755 glEdgeFlag (GL_TRUE); << 519 } else { 756 fEdgeFlag = true; << 520 glEdgeFlag (GL_FALSE); 757 } << 521 } 758 } else { << 522 glVertex3d (vertex[edgeCount].x(), 759 if (fEdgeFlag != false) { << 523 vertex[edgeCount].y(), 760 glEdgeFlag (GL_FALSE); << 524 vertex[edgeCount].z()); 761 fEdgeFlag = false; << 762 } << 763 } << 764 glNormal3d (normals[edgeCount].x(), << 765 normals[edgeCount].y(), << 766 normals[edgeCount].z()); << 767 glVertex3d (vertex[edgeCount].x(), << 768 vertex[edgeCount].y(), << 769 vertex[edgeCount].z()); << 770 } 525 } 771 glEnd (); 526 glEnd (); 772 end_of_drawing_through_stencil: << 527 glDisable (GL_LIGHTING); 773 528 774 // and once more to reset the stencil bi 529 // and once more to reset the stencil bits... 775 glStencilFunc (GL_ALWAYS, 0, 1); 530 glStencilFunc (GL_ALWAYS, 0, 1); 776 glStencilOp (GL_INVERT, GL_INVERT, GL_IN 531 glStencilOp (GL_INVERT, GL_INVERT, GL_INVERT); 777 glDepthFunc (GL_LEQUAL); // to make sur 532 glDepthFunc (GL_LEQUAL); // to make sure line gets drawn. 778 if (isTransparent) { << 533 glPolygonMode (GL_FRONT, GL_LINE); 779 // Transparent... << 534 glColor3d (c.GetRed (), c.GetGreen (), c.GetBlue ()); 780 //glDisable (GL_CULL_FACE); << 781 glPolygonMode (GL_FRONT_AND_BACK, GL_LINE); << 782 } else { << 783 // Opaque... << 784 if (clipping) { << 785 //glDisable (GL_CULL_FACE); << 786 glPolygonMode (GL_FRONT_AND_BACK, GL_LINE) << 787 } else { << 788 //glEnable (GL_CULL_FACE); << 789 //glCullFace (GL_BACK); << 790 glPolygonMode (GL_FRONT, GL_LINE); << 791 } << 792 } << 793 glDisable (GL_LIGHTING); << 794 glColor4fv (current_colour); << 795 fEdgeFlag = true; << 796 glBegin (GL_QUADS); 535 glBegin (GL_QUADS); 797 glEdgeFlag (GL_TRUE); << 798 fEdgeFlag = true; << 799 for (int edgeCount = 0; edgeCount < 4; + 536 for (int edgeCount = 0; edgeCount < 4; ++edgeCount) { 800 if (edgeFlag[edgeCount] > 0) { << 537 if (edgeFlag[edgeCount]) { 801 if (fEdgeFlag != true) { << 538 glEdgeFlag (GL_TRUE); 802 glEdgeFlag (GL_TRUE); << 539 } else { 803 fEdgeFlag = true; << 540 glEdgeFlag (GL_FALSE); 804 } << 541 } 805 } else { << 542 glVertex3d (vertex[edgeCount].x(), 806 if (fEdgeFlag != false) { << 543 vertex[edgeCount].y(), 807 glEdgeFlag (GL_FALSE); << 544 vertex[edgeCount].z()); 808 fEdgeFlag = false; << 809 } << 810 } << 811 glNormal3d (normals[edgeCount].x(), << 812 normals[edgeCount].y(), << 813 normals[edgeCount].z()); << 814 glVertex3d (vertex[edgeCount].x(), << 815 vertex[edgeCount].y(), << 816 vertex[edgeCount].z()); << 817 } 545 } 818 glEnd (); 546 glEnd (); 819 << 547 glDepthFunc (GL_LESS); // Revert for next quadrilateral. 820 glDepthFunc (GL_LEQUAL); // Revert for << 548 glBegin (GL_QUADS); // Ready for next quadrilateral. GL 821 fEdgeFlag = true; << 549 // says it ignores incomplete 822 glBegin (GL_QUADS); // Ready for ne << 550 // quadrilaterals, so final empty 823 glEdgeFlag (GL_TRUE); << 551 // glBegin/End sequence should be OK. 824 fEdgeFlag = true; << 825 // says it ignores incomplete << 826 // quadrilaterals, so final empty << 827 // glBegin/End sequence should be OK. << 828 } 552 } 829 } while (notLastFace); 553 } while (notLastFace); 830 554 831 glEnd (); 555 glEnd (); 832 glDisable (GL_STENCIL_TEST); // Revert to d << 556 glDisable (GL_STENCIL_TEST); 833 glDepthMask (GL_TRUE); // Revert to d << 834 glDisable (GL_LIGHTING); // Revert to d << 835 } 557 } 836 558 837 void G4OpenGLSceneHandler::AddCompound(const G << 559 //Method for handling G4NURBS objects for drawing solids. 838 G4VSceneHandler::AddCompound(traj); // For << 560 //Knots and Ctrl Pnts MUST be arrays of GLfloats. 839 } << 561 void G4OpenGLSceneHandler::AddPrimitive (const G4NURBS& nurb) { >> 562 >> 563 GLUnurbsObj *gl_nurb; >> 564 gl_nurb = gluNewNurbsRenderer (); >> 565 >> 566 GLfloat *u_knot_array, *u_knot_array_ptr; >> 567 u_knot_array = u_knot_array_ptr = new GLfloat [nurb.GetnbrKnots(G4NURBS::U)]; >> 568 G4NURBS::KnotsIterator u_iterator (nurb, G4NURBS::U); >> 569 while (u_iterator.pick (u_knot_array_ptr++)); >> 570 >> 571 GLfloat *v_knot_array, *v_knot_array_ptr; >> 572 v_knot_array = v_knot_array_ptr = new GLfloat [nurb.GetnbrKnots(G4NURBS::V)]; >> 573 G4NURBS::KnotsIterator v_iterator (nurb, G4NURBS::V); >> 574 while (v_iterator.pick (v_knot_array_ptr++)); >> 575 >> 576 GLfloat *ctrl_pnt_array, *ctrl_pnt_array_ptr; >> 577 ctrl_pnt_array = ctrl_pnt_array_ptr = >> 578 new GLfloat [nurb.GettotalnbrCtrlPts () * G4NURBS::NofC]; >> 579 G4NURBS::CtrlPtsCoordsIterator c_p_iterator (nurb); >> 580 while (c_p_iterator.pick (ctrl_pnt_array_ptr++)); >> 581 >> 582 // Get vis attributes - pick up defaults if none. >> 583 const G4VisAttributes* pVA = >> 584 fpViewer -> GetApplicableVisAttributes (nurb.GetVisAttributes ()); 840 585 841 void G4OpenGLSceneHandler::AddCompound(const G << 586 // Get view parameters that the user can force through the vis 842 G4VSceneHandler::AddCompound(hit); // For n << 587 // attributes, thereby over-riding the current view parameter. 843 } << 588 G4ViewParameters::DrawingStyle drawing_style = GetDrawingStyle (pVA); >> 589 //G4bool isAuxEdgeVisible = GetAuxEdgeVisible (pVA); >> 590 >> 591 //Get colour, etc.. >> 592 const G4Colour& c = pVA -> GetColour (); 844 593 845 void G4OpenGLSceneHandler::AddCompound(const G << 594 switch (drawing_style) { 846 G4VSceneHandler::AddCompound(digi); // For << 595 847 } << 596 case (G4ViewParameters::hlhsr): >> 597 // G4cout << "Hidden line removal not implememented in G4OpenGL.\n" >> 598 // << "Using hidden surface removal." << G4endl; >> 599 case (G4ViewParameters::hsr): >> 600 { >> 601 glEnable (GL_LIGHTING); >> 602 glEnable (GL_DEPTH_TEST); >> 603 glEnable (GL_AUTO_NORMAL); >> 604 glEnable (GL_NORMALIZE); >> 605 gluNurbsProperty (gl_nurb, GLU_DISPLAY_MODE, GLU_FILL); >> 606 gluNurbsProperty (gl_nurb, GLU_SAMPLING_TOLERANCE, 50.0); >> 607 GLfloat materialColour [4]; >> 608 materialColour [0] = c.GetRed (); >> 609 materialColour [1] = c.GetGreen (); >> 610 materialColour [2] = c.GetBlue (); >> 611 materialColour [3] = 1.0; >> 612 glMaterialfv (GL_FRONT, GL_AMBIENT_AND_DIFFUSE, materialColour); >> 613 break; >> 614 } >> 615 case (G4ViewParameters::hlr): >> 616 // G4cout << "Hidden line removal not implememented in G4OpenGL.\n" >> 617 // << "Using wireframe." << G4endl; >> 618 case (G4ViewParameters::wireframe): >> 619 default: >> 620 glDisable (GL_LIGHTING); >> 621 // glDisable (GL_DEPTH_TEST); >> 622 glEnable (GL_DEPTH_TEST); >> 623 glDisable (GL_AUTO_NORMAL); >> 624 glDisable (GL_NORMALIZE); >> 625 gluNurbsProperty (gl_nurb, GLU_DISPLAY_MODE, GLU_OUTLINE_POLYGON); >> 626 gluNurbsProperty (gl_nurb, GLU_SAMPLING_TOLERANCE, 50.0); >> 627 glColor3d (c.GetRed (), c.GetGreen (), c.GetBlue ()); >> 628 break; >> 629 } 848 630 849 void G4OpenGLSceneHandler::AddCompound(const G << 631 gluBeginSurface (gl_nurb); 850 G4VSceneHandler::AddCompound(hits); // For << 632 G4int u_stride = 4; >> 633 G4int v_stride = nurb.GetnbrCtrlPts(G4NURBS::U) * 4; >> 634 >> 635 gluNurbsSurface (gl_nurb, >> 636 nurb.GetnbrKnots (G4NURBS::U), (GLfloat*)u_knot_array, >> 637 nurb.GetnbrKnots (G4NURBS::V), (GLfloat*)v_knot_array, >> 638 u_stride, >> 639 v_stride, >> 640 ctrl_pnt_array, >> 641 nurb.GetUorder (), >> 642 nurb.GetVorder (), >> 643 GL_MAP2_VERTEX_4); >> 644 >> 645 gluEndSurface (gl_nurb); >> 646 >> 647 delete [] u_knot_array; // These should be allocated with smart allocators >> 648 delete [] v_knot_array; // to avoid memory explosion. >> 649 delete [] ctrl_pnt_array; >> 650 >> 651 gluDeleteNurbsRenderer (gl_nurb); 851 } 652 } 852 653 853 void G4OpenGLSceneHandler::AddCompound(const G << 654 void G4OpenGLSceneHandler::AddCompound(const G4VTrajectory& traj) { 854 G4VSceneHandler::AddCompound(hits); // For << 655 G4VSceneHandler::AddCompound(traj); // For now. 855 } 656 } 856 657 857 void G4OpenGLSceneHandler::AddCompound(const G << 658 void G4OpenGLSceneHandler::AddCompound(const G4VHit& hit) { 858 StandardSpecialMeshRendering(mesh); << 659 G4VSceneHandler::AddCompound(hit); // For now. 859 } 660 } >> 661 >> 662 #endif 860 663