Bug Summary

File:scratch/gluex/scan-build-work/hdgeant4/src/G4fixes/G4OpenGLStoredSceneHandler.cc
Location:line 285, column 9
Description:Called C++ object pointer is null

Annotated Source Code

1//
2// ********************************************************************
3// * License and Disclaimer *
4// * *
5// * The Geant4 software is copyright of the Copyright Holders of *
6// * the Geant4 Collaboration. It is provided under the terms and *
7// * conditions of the Geant4 Software License, included in the file *
8// * LICENSE and available at http://cern.ch/geant4/license . These *
9// * include a list of copyright holders. *
10// * *
11// * Neither the authors of this software system, nor their employing *
12// * institutes,nor the agencies providing financial support for this *
13// * work make any representation or warranty, express or implied, *
14// * regarding this software system or assume any liability for its *
15// * use. Please see the license in the file LICENSE and URL above *
16// * for the full disclaimer and the limitation of liability. *
17// * *
18// * This code implementation is the result of the scientific and *
19// * technical work of the GEANT4 collaboration. *
20// * By using, copying, modifying or distributing the software (or *
21// * any work based on the software) you agree to acknowledge its *
22// * use in resulting scientific publications, and indicate your *
23// * acceptance of all terms of the Geant4 Software license. *
24// ********************************************************************
25//
26//
27// $Id: G4OpenGLStoredSceneHandler.cc 87695 2014-12-17 09:35:24Z gcosmo $
28//
29//
30// Andrew Walkden 10th February 1997
31// OpenGL stored scene - creates OpenGL display lists.
32
33#ifdef G4VIS_BUILD_OPENGL_DRIVER1
34
35#include "G4OpenGLStoredSceneHandler.hh"
36
37#include "G4PhysicalVolumeModel.hh"
38#include "G4LogicalVolumeModel.hh"
39#include "G4VPhysicalVolume.hh"
40#include "G4LogicalVolume.hh"
41#include "G4Polyline.hh"
42#include "G4Polymarker.hh"
43#include "G4Text.hh"
44#include "G4Circle.hh"
45#include "G4Square.hh"
46#include "G4Polyhedron.hh"
47#include "G4AttHolder.hh"
48#include "G4OpenGLTransform3D.hh"
49#include "G4OpenGLViewer.hh"
50#include "G4AttHolder.hh"
51
52#include <typeinfo>
53
54G4OpenGLStoredSceneHandler::PO::PO():
55 fDisplayListId(0),
56 fPickName(0),
57 fpG4TextPlus(0),
58 fMarkerOrPolyline(false)
59{}
60
61G4OpenGLStoredSceneHandler::PO::PO(const G4OpenGLStoredSceneHandler::PO& po):
62 fDisplayListId(po.fDisplayListId),
63 fTransform(po.fTransform),
64 fPickName(po.fPickName),
65 fColour(po.fColour),
66 fpG4TextPlus(po.fpG4TextPlus? new G4TextPlus(*po.fpG4TextPlus): 0),
67 fMarkerOrPolyline(po.fMarkerOrPolyline)
68{}
69
70G4OpenGLStoredSceneHandler::PO::PO(G4int id, const G4Transform3D& tr):
71 fDisplayListId(id),
72 fTransform(tr),
73 fPickName(0),
74 fpG4TextPlus(0),
75 fMarkerOrPolyline(false)
76{}
77
78G4OpenGLStoredSceneHandler::PO::~PO()
79{
80 delete fpG4TextPlus;
81}
82
83G4OpenGLStoredSceneHandler::PO& G4OpenGLStoredSceneHandler::PO::operator=
84 (const G4OpenGLStoredSceneHandler::PO& rhs)
85{
86 if (&rhs == this) return *this;
87 fDisplayListId = rhs.fDisplayListId;
88 fTransform = rhs.fTransform;
89 fPickName = rhs.fPickName;
90 fColour = rhs.fColour;
91 fpG4TextPlus = rhs.fpG4TextPlus? new G4TextPlus(*rhs.fpG4TextPlus): 0;
92 fMarkerOrPolyline = rhs.fMarkerOrPolyline;
93 return *this;
94}
95
96G4OpenGLStoredSceneHandler::TO::TO():
97 fDisplayListId(0),
98 fPickName(0),
99 fStartTime(-DBL_MAXstd::numeric_limits<double>::max()),
100 fEndTime(DBL_MAXstd::numeric_limits<double>::max()),
101 fpG4TextPlus(0),
102 fMarkerOrPolyline(false)
103{}
104
105G4OpenGLStoredSceneHandler::TO::TO(const G4OpenGLStoredSceneHandler::TO& to):
106 fDisplayListId(to.fDisplayListId),
107 fTransform(to.fTransform),
108 fPickName(to.fPickName),
109 fStartTime(to.fStartTime),
110 fEndTime(to.fEndTime),
111 fColour(to.fColour),
112 fpG4TextPlus(to.fpG4TextPlus? new G4TextPlus(*to.fpG4TextPlus): 0),
113 fMarkerOrPolyline(to.fMarkerOrPolyline)
114{}
115
116G4OpenGLStoredSceneHandler::TO::TO(G4int id, const G4Transform3D& tr):
117 fDisplayListId(id),
118 fTransform(tr),
119 fPickName(0),
120 fStartTime(-DBL_MAXstd::numeric_limits<double>::max()),
121 fEndTime(DBL_MAXstd::numeric_limits<double>::max()),
122 fpG4TextPlus(0),
123 fMarkerOrPolyline(false)
124{}
125
126G4OpenGLStoredSceneHandler::TO::~TO()
127{
128 delete fpG4TextPlus;
129}
130
131G4OpenGLStoredSceneHandler::TO& G4OpenGLStoredSceneHandler::TO::operator=
132 (const G4OpenGLStoredSceneHandler::TO& rhs)
133{
134 if (&rhs == this) return *this;
135 fDisplayListId = rhs.fDisplayListId;
136 fTransform = rhs.fTransform;
137 fPickName = rhs.fPickName;
138 fStartTime = rhs.fStartTime;
139 fEndTime = rhs.fEndTime;
140 fColour = rhs.fColour;
141 fpG4TextPlus = rhs.fpG4TextPlus? new G4TextPlus(*rhs.fpG4TextPlus): 0;
142 fMarkerOrPolyline = rhs.fMarkerOrPolyline;
143 return *this;
144}
145
146G4OpenGLStoredSceneHandler::G4OpenGLStoredSceneHandler
147(G4VGraphicsSystem& system,
148 const G4String& name):
149G4OpenGLSceneHandler (system, fSceneIdCount++, name),
150fTopPODL (0)
151{}
152
153G4OpenGLStoredSceneHandler::~G4OpenGLStoredSceneHandler ()
154{}
155
156void G4OpenGLStoredSceneHandler::BeginPrimitives
157(const G4Transform3D& objectTransformation)
158{
159 G4OpenGLSceneHandler::BeginPrimitives (objectTransformation);
160 if (fReadyForTransients) glDrawBuffer (GL_FRONT0x0404);
161 // Display list setup moved to AddPrimitivePreamble. See notes there.
162}
163
164void G4OpenGLStoredSceneHandler::EndPrimitives ()
165{
166 // See all primitives immediately... At least soon...
167 ScaledFlush();
168 glDrawBuffer (GL_BACK0x0405);
169 G4OpenGLSceneHandler::EndPrimitives ();
170}
171
172void G4OpenGLStoredSceneHandler::BeginPrimitives2D
173(const G4Transform3D& objectTransformation)
174{
175 G4OpenGLSceneHandler::BeginPrimitives2D(objectTransformation);
176 if (fReadyForTransients) glDrawBuffer (GL_FRONT0x0404);
177}
178
179void G4OpenGLStoredSceneHandler::EndPrimitives2D ()
180{
181 // See all primitives immediately... At least soon...
182 ScaledFlush();
183 glDrawBuffer (GL_BACK0x0405);
184 G4OpenGLSceneHandler::EndPrimitives2D ();
185}
186
187G4bool G4OpenGLStoredSceneHandler::AddPrimitivePreamble(const G4VMarker& visible)
188{
189 return AddPrimitivePreambleInternal(visible, true, false);
190}
191G4bool G4OpenGLStoredSceneHandler::AddPrimitivePreamble(const G4Polyline& visible)
192{
193 return AddPrimitivePreambleInternal(visible, false, true);
194}
195G4bool G4OpenGLStoredSceneHandler::AddPrimitivePreamble(const G4Polyhedron& visible)
196{
197 return AddPrimitivePreambleInternal(visible, false, false);
198}
199
200G4bool G4OpenGLStoredSceneHandler::AddPrimitivePreambleInternal(const G4Visible& visible, bool isMarker, bool isPolyline)
201{
202 const G4Colour& c = GetColour (visible);
203 G4double opacity = c.GetAlpha ();
204
205 G4bool transparency_enabled = true;
206 G4bool isMarkerNotHidden = true;
207 G4OpenGLViewer* pViewer = dynamic_cast<G4OpenGLViewer*>(fpViewer);
1
'pViewer' initialized here
208 if (pViewer) {
2
Assuming 'pViewer' is null
3
Taking false branch
209 transparency_enabled = pViewer->transparency_enabled;
210 isMarkerNotHidden = pViewer->fVP.IsMarkerNotHidden();
211 }
212
213 G4bool isTransparent = opacity < 1.;
214 G4bool isMarkerOrPolyline = isMarker || isPolyline;
215 G4bool treatAsTransparent = transparency_enabled && isTransparent;
216 G4bool treatAsNotHidden = isMarkerNotHidden && isMarkerOrPolyline;
217
218 if (fProcessing2D) glDisable (GL_DEPTH_TEST0x0B71);
4
Taking false branch
219 else {
220 if (isMarkerOrPolyline && isMarkerNotHidden)
221 glDisable (GL_DEPTH_TEST0x0B71);
222 else {glEnable (GL_DEPTH_TEST0x0B71); glDepthFunc (GL_LEQUAL0x0203);}
223 }
224
225 if (fThreePassCapable) {
5
Taking false branch
226
227 // Ensure transparent objects are drawn opaque ones and before
228 // non-hidden markers. The problem of blending/transparency/alpha
229 // is quite a tricky one - see History of opengl-V07-01-01/2/3.
230 if (!(fSecondPassForTransparency || fThirdPassForNonHiddenMarkers)) {
231 // First pass...
232 if (treatAsTransparent) { // Request pass for transparent objects...
233 fSecondPassForTransparencyRequested = true;
234 }
235 if (treatAsNotHidden) { // Request pass for non-hidden markers...
236 fThirdPassForNonHiddenMarkersRequested = true;
237 }
238 // On first pass, transparent objects and non-hidden markers are not drawn...
239 if (treatAsTransparent || treatAsNotHidden) {
240 return false; // No further processing.
241 }
242 }
243
244 // On second pass, only transparent objects are drawn...
245 if (fSecondPassForTransparency) {
246 if (!treatAsTransparent) {
247 return false; // No further processing.
248 }
249 }
250
251 // On third pass, only non-hidden markers are drawn...
252 if (fThirdPassForNonHiddenMarkers) {
253 if (!treatAsNotHidden) {
254 return false; // No further processing.
255
256 }
257 }
258 } // fThreePassCapable
259
260 // Loads G4Atts for picking...
261 G4bool isPicking = false;
262 if (fpViewer->GetViewParameters().IsPicking()) {
6
Taking false branch
263 isPicking = true;
264 glLoadName(++fPickName);
265 G4AttHolder* holder = new G4AttHolder;
266 LoadAtts(visible, holder);
267 fPickMap[fPickName] = holder;
268 }
269
270 // Can we re-use a display list?
271 const G4VSolid* pSolid = 0;
272 G4PhysicalVolumeModel* pPVModel =
273 dynamic_cast<G4PhysicalVolumeModel*>(fpModel);
274 if (fpViewer->GetViewParameters().GetVisAttributesModifiers().size())
7
Taking false branch
275 // Touchables have been modified - don't risk re-using display list.
276 goto end_of_display_list_reuse_test;
277 if (pPVModel) {
8
Assuming 'pPVModel' is non-null
9
Taking true branch
278 // Check that it isn't a G4LogicalVolumeModel (which is a sub-class of
279 // G4PhysicalVolumeModel).
280 G4LogicalVolumeModel* pLVModel =
281 dynamic_cast<G4LogicalVolumeModel*>(pPVModel);
282 if (pLVModel)
10
Assuming 'pLVModel' is null
11
Taking false branch
283 // Logical volume model - don't re-use.
284 goto end_of_display_list_reuse_test;
285 if (pViewer->fVP.IsSection() || pViewer->fVP.IsCutaway())
12
Called C++ object pointer is null
286 // sections and cutaways generate unique views of each model instance
287 goto end_of_display_list_reuse_test;
288 // If part of the geometry hierarchy, i.e., from a
289 // G4PhysicalVolumeModel, check if a display list already exists for
290 // this solid, re-use it if possible. We could be smarter, and
291 // recognise repeated branches of the geometry hierarchy, for
292 // example. But this algorithm should be secure, I think...
293 G4VPhysicalVolume* pPV = pPVModel->GetCurrentPV();
294 if (!pPV)
295 // It's probably a dummy model, e.g., for a user-drawn hit?
296 goto end_of_display_list_reuse_test;
297 G4LogicalVolume* pLV = pPV->GetLogicalVolume();
298 if (!pLV)
299 // Dummy model again?
300 goto end_of_display_list_reuse_test;
301 pSolid = pLV->GetSolid();
302 EAxis axis = kRho;
303 G4VPhysicalVolume* pCurrentPV = pPVModel->GetCurrentPV();
304 if (pCurrentPV -> IsReplicated ()) {
305 G4int nReplicas;
306 G4double width;
307 G4double offset;
308 G4bool consuming;
309 pCurrentPV->GetReplicationData(axis,nReplicas,width,offset,consuming);
310 }
311 // Provided it is not parametrised (because if so, the
312 // solid's parameters might have been changed)...
313 if (!(pCurrentPV -> IsParameterised ()) &&
314 // Provided it is not replicated radially (because if so, the
315 // solid's parameters will have been changed)...
316 !(pCurrentPV -> IsReplicated () && axis == kRho) &&
317 // ...and if the solid has already been rendered...
318 (fSolidMap.find (pSolid) != fSolidMap.end ())) {
319 fDisplayListId = fSolidMap [pSolid];
320 PO po(fDisplayListId,fObjectTransformation);
321 if (isPicking) po.fPickName = fPickName;
322 po.fColour = c;
323 po.fMarkerOrPolyline = isMarkerOrPolyline;
324 fPOList.push_back(po);
325 // No need to test if gl commands are used (result of
326 // ExtraPOProcessing) because we have already decided they will
327 // not, at least not here. Also, pass a dummy G4Visible since
328 // not relevant for G4PhysicalVolumeModel.
329 (void) ExtraPOProcessing(G4Visible(), fPOList.size() - 1);
330 return false; // No further processing.
331 }
332 }
333end_of_display_list_reuse_test:
334
335 // Because of our need to control colour of transients (display by
336 // time fading), display lists may only cover a single primitive.
337 // So display list setup is here.
338
339 if (fMemoryForDisplayLists) {
340 fDisplayListId = glGenLists (1);
341 if (glGetError() == GL_OUT_OF_MEMORY0x0505 ||
342 fDisplayListId > fDisplayListLimit) {
343 G4cout(*G4cout_p) <<
344 "********************* WARNING! ********************"
345 "\n* Display list limit reached in OpenGL."
346 "\n* Continuing drawing WITHOUT STORING. Scene only partially refreshable."
347 "\n* Current limit: " << fDisplayListLimit <<
348 ". Change with \"/vis/ogl/set/displayListLimit\"."
349 "\n***************************************************"
350 << G4endlstd::endl;
351 fMemoryForDisplayLists = false;
352 }
353 }
354
355 if (pSolid) fSolidMap [pSolid] = fDisplayListId;
356
357 if (fMemoryForDisplayLists) {
358 if (fReadyForTransients) {
359 TO to(fDisplayListId, fObjectTransformation);
360 if (isPicking) to.fPickName = fPickName;
361 to.fColour = c;
362 const G4VisAttributes* pVA =
363 fpViewer->GetApplicableVisAttributes(visible.GetVisAttributes());
364 to.fStartTime = pVA->GetStartTime();
365 to.fEndTime = pVA->GetEndTime();
366 to.fMarkerOrPolyline = isMarkerOrPolyline;
367 fTOList.push_back(to);
368 // For transient objects, colour, transformation, are kept in
369 // the TO, so should *not* be in the display list. As mentioned
370 // above, in some cases (display-by-time fading) we need to have
371 // independent control of colour. But for now transform and set
372 // colour for immediate display.
373 glPushMatrix();
374 G4OpenGLTransform3D oglt (fObjectTransformation);
375 glMultMatrixd (oglt.GetGLMatrix ());
376 if (transparency_enabled) {
377 glColor4d(c.GetRed(),c.GetGreen(),c.GetBlue(),c.GetAlpha());
378 } else {
379 glColor3d(c.GetRed(),c.GetGreen(),c.GetBlue());
380 }
381 (void) ExtraTOProcessing(visible, fTOList.size() - 1);
382 // Ignore return value of the above. If this visible does not use
383 // gl commands, a display list is created that is empty and not
384 // used.
385 glNewList (fDisplayListId, GL_COMPILE_AND_EXECUTE0x1301);
386 } else {
387 PO po(fDisplayListId, fObjectTransformation);
388 if (isPicking) po.fPickName = fPickName;
389 po.fColour = c;
390 po.fMarkerOrPolyline = isMarkerOrPolyline;
391 fPOList.push_back(po);
392 // For permanent objects, colour is kept in the PO, so should
393 // *not* be in the display list. This is so that sub-classes
394 // may implement colour modifications according to their own
395 // criteria, e.g., scen tree slider in Qt. But for now set
396 // colour for immediate display.
397 if (transparency_enabled) {
398 glColor4d(c.GetRed(),c.GetGreen(),c.GetBlue(),c.GetAlpha());
399 } else {
400 glColor3d(c.GetRed(),c.GetGreen(),c.GetBlue());
401 }
402 G4bool usesGLCommands = ExtraPOProcessing(visible, fPOList.size() - 1);
403 // Transients are displayed as they come (GL_COMPILE_AND_EXECUTE
404 // above) but persistents are compiled into display lists
405 // (GL_COMPILE only) and then drawn from the display lists with
406 // their fObjectTransformation as stored in fPOList. Thus,
407 // there is no need to do glMultMatrixd here. If
408 // ExtraPOProcessing says the visible object does not use gl
409 // commands, simply return and abandon further processing. It
410 // is assumed that all relevant information is kept in the
411 // POList.
412 if (!usesGLCommands) return false;
413 glNewList (fDisplayListId, GL_COMPILE0x1300);
414 }
415 } else { // Out of memory (or being used when display lists not required).
416 glDrawBuffer (GL_FRONT0x0404);
417 glPushMatrix();
418 G4OpenGLTransform3D oglt (fObjectTransformation);
419 glMultMatrixd (oglt.GetGLMatrix ());
420 if (transparency_enabled) {
421 glColor4d(c.GetRed(),c.GetGreen(),c.GetBlue(),c.GetAlpha());
422 } else {
423 glColor3d(c.GetRed(),c.GetGreen(),c.GetBlue());
424 }
425 }
426
427 if (fProcessing2D) {
428 // Push current 3D world matrices and load identity to define screen
429 // coordinates...
430 glMatrixMode (GL_PROJECTION0x1701);
431 glPushMatrix();
432 glLoadIdentity();
433 if (pViewer) {
434 pViewer->g4GlOrtho (-1., 1., -1., 1., -G4OPENGL_FLT_BIG1.e20, G4OPENGL_FLT_BIG1.e20);
435 }
436 glMatrixMode (GL_MODELVIEW0x1700);
437 glPushMatrix();
438 glLoadIdentity();
439 G4OpenGLTransform3D oglt (fObjectTransformation);
440 glMultMatrixd (oglt.GetGLMatrix ());
441 glDisable (GL_LIGHTING0x0B50);
442 } else {
443 glEnable (GL_LIGHTING0x0B50);
444 }
445
446 return true;
447}
448
449void G4OpenGLStoredSceneHandler::AddPrimitivePostamble()
450{
451 if (fProcessing2D) {
452 // Pop current 3D world matrices back again...
453 glMatrixMode (GL_PROJECTION0x1701);
454 glPopMatrix();
455 glMatrixMode (GL_MODELVIEW0x1700);
456 glPopMatrix();
457 }
458
459 // if ((glGetError() == GL_TABLE_TOO_LARGE) || (glGetError() == GL_OUT_OF_MEMORY)) { // Could close?
460 if (glGetError() == GL_OUT_OF_MEMORY0x0505) { // Could close?
461 G4cerr(*G4cerr_p) <<
462 "ERROR: G4OpenGLStoredSceneHandler::AddPrimitivePostamble: Failure"
463 " to allocate display List for fTopPODL - try OpenGL Immediated mode."
464 << G4endlstd::endl;
465 }
466 if (fMemoryForDisplayLists) {
467 glEndList();
468 if (glGetError() == GL_OUT_OF_MEMORY0x0505) { // Could close?
469 G4cerr(*G4cerr_p) <<
470 "ERROR: G4OpenGLStoredSceneHandler::AddPrimitivePostamble: Failure"
471 " to allocate display List for fTopPODL - try OpenGL Immediated mode."
472 << G4endlstd::endl;
473 }
474 }
475 if (fReadyForTransients || !fMemoryForDisplayLists) {
476 glPopMatrix();
477 }
478}
479
480void G4OpenGLStoredSceneHandler::AddPrimitive (const G4Polyline& polyline)
481{
482 G4bool furtherprocessing = AddPrimitivePreamble(polyline);
483 if (furtherprocessing) {
484 G4OpenGLSceneHandler::AddPrimitive(polyline);
485 AddPrimitivePostamble();
486 }
487}
488
489void G4OpenGLStoredSceneHandler::AddPrimitive (const G4Polymarker& polymarker)
490{
491 G4bool furtherprocessing = AddPrimitivePreamble(polymarker);
492 if (furtherprocessing) {
493 G4OpenGLSceneHandler::AddPrimitive(polymarker);
494 AddPrimitivePostamble();
495 }
496}
497
498void G4OpenGLStoredSceneHandler::AddPrimitive (const G4Text& text)
499{
500 // Note: colour is still handled in
501 // G4OpenGLSceneHandler::AddPrimitive(const G4Text&), so it still
502 // gets into the display list
503 G4bool furtherprocessing = AddPrimitivePreamble(text);
504 if (furtherprocessing) {
505 G4OpenGLSceneHandler::AddPrimitive(text);
506 AddPrimitivePostamble();
507 }
508}
509
510void G4OpenGLStoredSceneHandler::AddPrimitive (const G4Circle& circle)
511{
512 G4bool furtherprocessing = AddPrimitivePreamble(circle);
513 if (furtherprocessing) {
514 G4OpenGLSceneHandler::AddPrimitive(circle);
515 AddPrimitivePostamble();
516 }
517}
518
519void G4OpenGLStoredSceneHandler::AddPrimitive (const G4Square& square)
520{
521 G4bool furtherprocessing = AddPrimitivePreamble(square);
522 if (furtherprocessing) {
523 G4OpenGLSceneHandler::AddPrimitive(square);
524 AddPrimitivePostamble();
525 }
526}
527
528void G4OpenGLStoredSceneHandler::AddPrimitive (const G4Scale& scale)
529{
530 // Let base class split into primitives.
531 G4OpenGLSceneHandler::AddPrimitive(scale);
532}
533
534void G4OpenGLStoredSceneHandler::AddPrimitive (const G4Polyhedron& polyhedron)
535{
536 // Note: colour is still handled in
537 // G4OpenGLSceneHandler::AddPrimitive(const G4Polyhedron&), so it still
538 // gets into the display list
539 G4bool furtherprocessing = AddPrimitivePreamble(polyhedron);
540 if (furtherprocessing) {
541 G4OpenGLSceneHandler::AddPrimitive(polyhedron);
542 AddPrimitivePostamble();
543 }
544}
545
546void G4OpenGLStoredSceneHandler::BeginModeling () {
547 G4VSceneHandler::BeginModeling();
548 /* Debug...
549 fDisplayListId = glGenLists (1);
550 G4cout << "OGL::fDisplayListId (start): " << fDisplayListId << G4endl;
551 */
552}
553
554void G4OpenGLStoredSceneHandler::EndModeling () {
555 // Make a List which calls the other lists.
556 fTopPODL = glGenLists (1);
557 if (glGetError() == GL_OUT_OF_MEMORY0x0505) { // Could pre-allocate?
558 G4cerr(*G4cerr_p) <<
559 "ERROR: G4OpenGLStoredSceneHandler::EndModeling: Failure to allocate"
560 " display List for fTopPODL - try OpenGL Immediated mode."
561 << G4endlstd::endl;
562 } else {
563
564 glNewList (fTopPODL, GL_COMPILE0x1300); {
565 for (size_t i = 0; i < fPOList.size (); i++) {
566 glPushMatrix();
567 G4OpenGLTransform3D oglt (fPOList[i].fTransform);
568 glMultMatrixd (oglt.GetGLMatrix ());
569 if (fpViewer->GetViewParameters().IsPicking())
570 glLoadName(fPOList[i].fPickName);
571 glCallList (fPOList[i].fDisplayListId);
572 glPopMatrix();
573 }
574 }
575 glEndList ();
576
577 if (glGetError() == GL_OUT_OF_MEMORY0x0505) { // Could close?
578 G4cerr(*G4cerr_p) <<
579 "ERROR: G4OpenGLStoredSceneHandler::EndModeling: Failure to allocate"
580 " display List for fTopPODL - try OpenGL Immediated mode."
581 << G4endlstd::endl;
582 }
583 }
584
585 G4VSceneHandler::EndModeling ();
586}
587
588void G4OpenGLStoredSceneHandler::ClearStore () {
589
590 //G4cout << "G4OpenGLStoredSceneHandler::ClearStore" << G4endl;
591
592 G4VSceneHandler::ClearStore (); // Sets need kernel visit, etc.
593
594 // Delete OpenGL permanent display lists.
595 for (size_t i = 0; i < fPOList.size (); i++)
596 glDeleteLists (fPOList[i].fDisplayListId, 1);
597 if (fTopPODL) glDeleteLists (fTopPODL, 1);
598 fTopPODL = 0;
599
600 // Clear other lists, dictionary, etc.
601 fPOList.clear ();
602 fSolidMap.clear ();
603 ClearAndDestroyAtts();
604
605 // ...and clear transient store...
606 for (size_t i = 0; i < fTOList.size (); i++)
607 glDeleteLists(fTOList[i].fDisplayListId, 1);
608 fTOList.clear ();
609
610 fMemoryForDisplayLists = true;
611}
612
613void G4OpenGLStoredSceneHandler::ClearTransientStore ()
614{
615 //G4cout << "G4OpenGLStoredSceneHandler::ClearTransientStore" << G4endl;
616
617 // Delete OpenGL transient display lists and Transient Objects themselves.
618 for (size_t i = 0; i < fTOList.size (); i++)
619 glDeleteLists(fTOList[i].fDisplayListId, 1);
620 fTOList.clear ();
621
622 fMemoryForDisplayLists = true;
623
624 // Redraw the scene ready for the next event.
625 if (fpViewer) {
626 fpViewer -> SetView ();
627 fpViewer -> ClearView ();
628 fpViewer -> DrawView ();
629 }
630}
631
632G4int G4OpenGLStoredSceneHandler::fSceneIdCount = 0;
633
634G4int G4OpenGLStoredSceneHandler::fDisplayListId = 0;
635G4bool G4OpenGLStoredSceneHandler::fMemoryForDisplayLists = true;
636G4int G4OpenGLStoredSceneHandler::fDisplayListLimit = 50000;
637
638#endif