Import Geant4 11.1.0.beta source tree
This commit is contained in:
@@ -32,8 +32,6 @@
|
||||
#include <tools/forit>
|
||||
#include <tools/tokenize>
|
||||
|
||||
#include <tools/xml/xml_style> //it uses expat.
|
||||
|
||||
G4PlotterManager& G4PlotterManager::GetInstance () {
|
||||
static G4PlotterManager s_instance;
|
||||
return s_instance;
|
||||
|
||||
@@ -145,7 +145,7 @@ G4bool G4Scene::AddWorldIfEmpty (G4bool warn) {
|
||||
if (successful) {
|
||||
if (warn) {
|
||||
G4cout <<
|
||||
"G4Scene::AddWorldIfEmpty: The scene was empty of run-duration models."
|
||||
"G4Scene::AddWorldIfEmpty: The scene had no extent."
|
||||
"\n \"world\" has been added.";
|
||||
G4cout << G4endl;
|
||||
}
|
||||
@@ -196,6 +196,7 @@ G4bool G4Scene::AddEndOfEventModel (G4VModel* pModel, G4bool warn) {
|
||||
return false;
|
||||
}
|
||||
fEndOfEventModelList.push_back (Model(pModel));
|
||||
CalculateExtent ();
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -216,6 +217,7 @@ G4bool G4Scene::AddEndOfRunModel (G4VModel* pModel, G4bool warn) {
|
||||
return false;
|
||||
}
|
||||
fEndOfRunModelList.push_back (pModel);
|
||||
CalculateExtent ();
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
@@ -64,6 +64,7 @@
|
||||
#include "G4Ellipsoid.hh"
|
||||
#include "G4Polycone.hh"
|
||||
#include "G4Polyhedra.hh"
|
||||
#include "G4Tet.hh"
|
||||
#include "G4DisplacedSolid.hh"
|
||||
#include "G4LogicalVolume.hh"
|
||||
#include "G4PhysicalVolumeModel.hh"
|
||||
@@ -425,24 +426,28 @@ void G4VSceneHandler::AddCompound (const G4THitsMap<G4StatDouble>& hits) {
|
||||
|
||||
void G4VSceneHandler::AddCompound(const G4Mesh& mesh)
|
||||
{
|
||||
G4ExceptionDescription ed;
|
||||
ed << "There has been an attempt to draw a mesh (a nested parameterisation),"
|
||||
"\nbut it is not implemented by the current graphics driver. Here we simply"
|
||||
"\ndraw the container, \"" << mesh.GetContainerVolume()->GetName() << "\".";
|
||||
G4Exception("G4VSceneHandler::AddCompound(const G4Mesh&)",
|
||||
"visman0107", JustWarning, ed);
|
||||
|
||||
G4cerr <<
|
||||
"There has been an attempt to draw a mesh with option \""
|
||||
<< fpViewer->GetViewParameters().GetSpecialMeshRenderingOption()
|
||||
<< "\":\n" << mesh
|
||||
<< "but it is not of a recognised type or is not implemented"
|
||||
"\nby the current graphics driver. Instead we draw its"
|
||||
"\ncontainer \"" << mesh.GetContainerVolume()->GetName() << "\"."
|
||||
<< G4endl;
|
||||
const auto& pv = mesh.GetContainerVolume();
|
||||
const auto& lv = pv->GetLogicalVolume();
|
||||
const auto& solid = lv->GetSolid();
|
||||
const auto& transform = mesh.GetTransform();
|
||||
// Make sure container is visible
|
||||
G4VisAttributes tmpVisAtts; // Visible, white, not forced.
|
||||
const auto& saveVisAtts = lv->GetVisAttributes();
|
||||
auto tmpVisAtts = *saveVisAtts;
|
||||
tmpVisAtts.SetVisibility(true);
|
||||
auto colour = saveVisAtts->GetColour();
|
||||
colour.SetAlpha(1.);
|
||||
tmpVisAtts.SetColour(colour);
|
||||
if (saveVisAtts) {
|
||||
tmpVisAtts = *saveVisAtts;
|
||||
tmpVisAtts.SetVisibility(true);
|
||||
auto colour = saveVisAtts->GetColour();
|
||||
colour.SetAlpha(1.);
|
||||
tmpVisAtts.SetColour(colour);
|
||||
}
|
||||
// Draw container
|
||||
PreAddSolid(transform,tmpVisAtts);
|
||||
solid->DescribeYourselfTo(*this);
|
||||
@@ -1147,3 +1152,687 @@ std::ostream& operator << (std::ostream& os, const G4VSceneHandler& sh) {
|
||||
|
||||
return os;
|
||||
}
|
||||
|
||||
void G4VSceneHandler::PseudoSceneFor3DRectMeshPositions::AddSolid(const G4Box&) {
|
||||
if (fpPVModel->GetCurrentDepth() == fDepth) { // Leaf-level cells only
|
||||
const auto& material = fpPVModel->GetCurrentLV()->GetMaterial();
|
||||
const auto& name = material->GetName();
|
||||
const auto* pVisAtts = fpPVModel->GetCurrentLV()->GetVisAttributes();
|
||||
// Get position in world coordinates
|
||||
// As a parameterisation the box is transformed by the current transformation
|
||||
// and its centre, originally by definition at (0,0,0), is now translated.
|
||||
const G4ThreeVector& position = fpCurrentObjectTransformation->getTranslation();
|
||||
fPositionByMaterial.insert(std::make_pair(material,position));
|
||||
if (fNameAndVisAttsByMaterial.find(material) == fNameAndVisAttsByMaterial.end())
|
||||
// Store name and vis attributes of first encounter with this material
|
||||
fNameAndVisAttsByMaterial[material] = NameAndVisAtts(name,*pVisAtts);
|
||||
}
|
||||
}
|
||||
|
||||
void G4VSceneHandler::PseudoSceneForTetVertices::AddSolid(const G4VSolid& solid) {
|
||||
if (fpPVModel->GetCurrentDepth() == fDepth) { // Leaf-level cells only
|
||||
// Need to know it's a tet !!!! or implement G4VSceneHandler::AddSolid (const G4Tet&) !!!!
|
||||
try {
|
||||
const G4Tet& tet = dynamic_cast<const G4Tet&>(solid);
|
||||
const auto& material = fpPVModel->GetCurrentLV()->GetMaterial();
|
||||
const auto& name = material->GetName();
|
||||
const auto* pVisAtts = fpPVModel->GetCurrentLV()->GetVisAttributes();
|
||||
// Transform into world coordinates if necessary
|
||||
if (fpCurrentObjectTransformation->xx() == 1. &&
|
||||
fpCurrentObjectTransformation->yy() == 1. &&
|
||||
fpCurrentObjectTransformation->zz() == 1.) { // No transformation necessary
|
||||
const auto& vertices = tet.GetVertices();
|
||||
fVerticesByMaterial.insert(std::make_pair(material,vertices));
|
||||
} else {
|
||||
auto vertices = tet.GetVertices();
|
||||
for (auto&& vertex: vertices) {
|
||||
vertex = G4Point3D(vertex).transform(*fpCurrentObjectTransformation);
|
||||
}
|
||||
fVerticesByMaterial.insert(std::make_pair(material,vertices));
|
||||
}
|
||||
if (fNameAndVisAttsByMaterial.find(material) == fNameAndVisAttsByMaterial.end())
|
||||
// Store name and vis attributes of first encounter with this material
|
||||
fNameAndVisAttsByMaterial[material] = NameAndVisAtts(name,*pVisAtts);
|
||||
}
|
||||
catch (const std::bad_cast&) {
|
||||
G4ExceptionDescription ed;
|
||||
ed << "Called for a mesh that is not a tetrahedron mesh: " << solid.GetName();
|
||||
G4Exception("PseudoSceneForTetVertices","visman0108",JustWarning,ed);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void G4VSceneHandler::StandardSpecialMeshRendering(const G4Mesh& mesh)
|
||||
// Standard way of special mesh rendering.
|
||||
// MySceneHandler::AddCompound(const G4Mesh& mesh) may use this if
|
||||
// appropriate or implement its own special mesh rendereing.
|
||||
{
|
||||
G4bool implemented = false;
|
||||
switch (mesh.GetMeshType()) {
|
||||
case G4Mesh::rectangle: [[fallthrough]];
|
||||
case G4Mesh::nested3DRectangular:
|
||||
switch (fpViewer->GetViewParameters().GetSpecialMeshRenderingOption()) {
|
||||
case G4ViewParameters::meshAsDots:
|
||||
Draw3DRectMeshAsDots(mesh); // Rectangular 3-deep mesh as dots
|
||||
implemented = true;
|
||||
break;
|
||||
case G4ViewParameters::meshAsSurfaces:
|
||||
Draw3DRectMeshAsSurfaces(mesh); // Rectangular 3-deep mesh as surfaces
|
||||
implemented = true;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case G4Mesh::tetrahedron:
|
||||
switch (fpViewer->GetViewParameters().GetSpecialMeshRenderingOption()) {
|
||||
case G4ViewParameters::meshAsDots:
|
||||
DrawTetMeshAsDots(mesh); // Tetrahedron mesh as dots
|
||||
implemented = true;
|
||||
break;
|
||||
case G4ViewParameters::meshAsSurfaces:
|
||||
DrawTetMeshAsSurfaces(mesh); // Tetrahedron mesh as surfaces
|
||||
implemented = true;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case G4Mesh::cylinder: [[fallthrough]];
|
||||
case G4Mesh::sphere: [[fallthrough]];
|
||||
case G4Mesh::invalid: break;
|
||||
}
|
||||
if (!implemented) {
|
||||
G4VSceneHandler::AddCompound(mesh); // Base class function - just print warning
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
void G4VSceneHandler::Draw3DRectMeshAsDots(const G4Mesh& mesh)
|
||||
// For a rectangular 3-D mesh, draw as coloured dots by colour and material,
|
||||
// one dot randomly placed in each visible mesh cell.
|
||||
{
|
||||
// Check
|
||||
if (mesh.GetMeshType() != G4Mesh::rectangle &&
|
||||
mesh.GetMeshType() != G4Mesh::nested3DRectangular) {
|
||||
G4ExceptionDescription ed;
|
||||
ed << "Called with a mesh that is not rectangular:" << mesh;
|
||||
G4Exception("G4VSceneHandler::Draw3DRectMeshAsDots","visman0108",JustWarning,ed);
|
||||
return;
|
||||
}
|
||||
|
||||
static G4bool firstPrint = true;
|
||||
const auto& verbosity = G4VisManager::GetVerbosity();
|
||||
G4bool print = firstPrint && verbosity >= G4VisManager::errors;
|
||||
if (print) {
|
||||
G4cout
|
||||
<< "Special case drawing of 3D rectangular G4VNestedParameterisation as dots:"
|
||||
<< '\n' << mesh
|
||||
<< G4endl;
|
||||
}
|
||||
|
||||
const auto& container = mesh.GetContainerVolume();
|
||||
|
||||
// This map is static so that once filled it stays filled.
|
||||
static std::map<G4String,std::map<const G4Material*,G4Polymarker>> dotsByMaterialAndMesh;
|
||||
auto& dotsByMaterial = dotsByMaterialAndMesh[mesh.GetContainerVolume()->GetName()];
|
||||
|
||||
// Fill map if not already filled
|
||||
if (dotsByMaterial.empty()) {
|
||||
|
||||
// Get positions and material one cell at a time (using PseudoSceneFor3DRectMeshPositions).
|
||||
// The pseudo scene allows a "private" descent into the parameterisation.
|
||||
// Instantiate a temporary G4PhysicalVolumeModel
|
||||
G4ModelingParameters tmpMP;
|
||||
tmpMP.SetCulling(true); // This avoids drawing transparent...
|
||||
tmpMP.SetCullingInvisible(true); // ... or invisble volumes.
|
||||
const G4bool useFullExtent = true; // To avoid calculating the extent
|
||||
G4PhysicalVolumeModel tmpPVModel
|
||||
(container,
|
||||
G4PhysicalVolumeModel::UNLIMITED,
|
||||
G4Transform3D(), // so that positions are in local coordinates
|
||||
&tmpMP,
|
||||
useFullExtent);
|
||||
// Accumulate information in temporary maps by material
|
||||
std::multimap<const G4Material*,const G4ThreeVector> positionByMaterial;
|
||||
std::map<const G4Material*,G4VSceneHandler::NameAndVisAtts> nameAndVisAttsByMaterial;
|
||||
// Instantiate the pseudo scene
|
||||
PseudoSceneFor3DRectMeshPositions pseudoScene
|
||||
(&tmpPVModel,mesh.GetMeshDepth(),positionByMaterial,nameAndVisAttsByMaterial);
|
||||
// Make private descent into the parameterisation
|
||||
tmpPVModel.DescribeYourselfTo(pseudoScene);
|
||||
// Now we have a map of positions by material.
|
||||
// Also a map of name and colour by material.
|
||||
|
||||
const auto& prms = mesh.GetThreeDRectParameters();
|
||||
const auto& halfX = prms.fHalfX;
|
||||
const auto& halfY = prms.fHalfY;
|
||||
const auto& halfZ = prms.fHalfZ;
|
||||
|
||||
// Fill the permanent (static) map of dots by material
|
||||
G4int nDotsTotal = 0;
|
||||
for (const auto& entry: nameAndVisAttsByMaterial) {
|
||||
G4int nDots = 0;
|
||||
const auto& material = entry.first;
|
||||
const auto& nameAndVisAtts = nameAndVisAttsByMaterial[material];
|
||||
const auto& name = nameAndVisAtts.fName;
|
||||
const auto& visAtts = nameAndVisAtts.fVisAtts;
|
||||
G4Polymarker dots;
|
||||
dots.SetInfo(name);
|
||||
dots.SetVisAttributes(visAtts);
|
||||
dots.SetMarkerType(G4Polymarker::dots);
|
||||
dots.SetSize(G4VMarker::screen,1.);
|
||||
// Enter empty polymarker into the map
|
||||
dotsByMaterial[material] = dots;
|
||||
// Now fill it in situ
|
||||
auto& dotsInMap = dotsByMaterial[material];
|
||||
const auto& range = positionByMaterial.equal_range(material);
|
||||
for (auto posByMat = range.first; posByMat != range.second; ++posByMat) {
|
||||
const G4double x = posByMat->second.getX() + (2.*G4UniformRand()-1.)*halfX;
|
||||
const G4double y = posByMat->second.getY() + (2.*G4UniformRand()-1.)*halfY;
|
||||
const G4double z = posByMat->second.getZ() + (2.*G4UniformRand()-1.)*halfZ;
|
||||
dotsInMap.push_back(G4ThreeVector(x,y,z));
|
||||
++nDots;
|
||||
}
|
||||
|
||||
if (print) {
|
||||
G4cout
|
||||
<< std::setw(30) << std::left << name.substr(0,30) << std::right
|
||||
<< ": " << std::setw(7) << nDots << " dots"
|
||||
<< ": colour " << std::fixed << std::setprecision(2)
|
||||
<< visAtts.GetColour() << std::defaultfloat
|
||||
<< G4endl;
|
||||
}
|
||||
|
||||
nDotsTotal += nDots;
|
||||
}
|
||||
|
||||
if (print) {
|
||||
G4cout << "Total number of dots: " << nDotsTotal << G4endl;
|
||||
}
|
||||
}
|
||||
|
||||
// Some subsequent expressions apply only to G4PhysicalVolumeModel
|
||||
auto pPVModel = dynamic_cast<G4PhysicalVolumeModel*>(fpModel);
|
||||
|
||||
G4String parameterisationName;
|
||||
if (pPVModel) {
|
||||
parameterisationName = pPVModel->GetFullPVPath().back().GetPhysicalVolume()->GetName();
|
||||
}
|
||||
|
||||
// Draw the dots by material
|
||||
// Ensure they are "hidden", i.e., use the z-buffer as non-marker primitives do
|
||||
auto keepVP = fpViewer->GetViewParameters();
|
||||
auto vp = fpViewer->GetViewParameters();
|
||||
vp.SetMarkerHidden();
|
||||
fpViewer->SetViewParameters(vp);
|
||||
// Now we transform to world coordinates
|
||||
BeginPrimitives (mesh.GetTransform());
|
||||
for (const auto& entry: dotsByMaterial) {
|
||||
const auto& dots = entry.second;
|
||||
// The current "leaf" node in the PVPath is the parameterisation. Here it has
|
||||
// been converted into polymarkers by material. So...temporarily...change
|
||||
// its name to that of the material (whose name has been stored in Info)
|
||||
// so that its appearance in the scene tree of, e.g., G4OpenGLQtViewer, has
|
||||
// an appropriate name and its visibility and colour may be changed.
|
||||
if (pPVModel) {
|
||||
const auto& fullPVPath = pPVModel->GetFullPVPath();
|
||||
auto leafPV = fullPVPath.back().GetPhysicalVolume();
|
||||
leafPV->SetName(dots.GetInfo());
|
||||
}
|
||||
// Add dots to the scene
|
||||
AddPrimitive(dots);
|
||||
}
|
||||
EndPrimitives ();
|
||||
// Restore view parameters
|
||||
fpViewer->SetViewParameters(keepVP);
|
||||
// Restore parameterisation name
|
||||
if (pPVModel) {
|
||||
pPVModel->GetFullPVPath().back().GetPhysicalVolume()->SetName(parameterisationName);
|
||||
}
|
||||
|
||||
firstPrint = false;
|
||||
return;
|
||||
}
|
||||
|
||||
void G4VSceneHandler::Draw3DRectMeshAsSurfaces(const G4Mesh& mesh)
|
||||
// For a rectangular 3-D mesh, draw as surfaces by colour and material
|
||||
// with inner shared faces removed.
|
||||
{
|
||||
// Check
|
||||
if (mesh.GetMeshType() != G4Mesh::rectangle &&
|
||||
mesh.GetMeshType() != G4Mesh::nested3DRectangular) {
|
||||
G4ExceptionDescription ed;
|
||||
ed << "Called with a mesh that is not rectangular:" << mesh;
|
||||
G4Exception("G4VSceneHandler::Draw3DRectMeshAsSurfaces","visman0108",JustWarning,ed);
|
||||
return;
|
||||
}
|
||||
|
||||
static G4bool firstPrint = true;
|
||||
const auto& verbosity = G4VisManager::GetVerbosity();
|
||||
G4bool print = firstPrint && verbosity >= G4VisManager::errors;
|
||||
if (print) {
|
||||
G4cout
|
||||
<< "Special case drawing of 3D rectangular G4VNestedParameterisation as surfaces:"
|
||||
<< '\n' << mesh
|
||||
<< G4endl;
|
||||
}
|
||||
|
||||
const auto& container = mesh.GetContainerVolume();
|
||||
|
||||
// This map is static so that once filled it stays filled.
|
||||
static std::map<G4String,std::map<const G4Material*,G4Polyhedron>> boxesByMaterialAndMesh;
|
||||
auto& boxesByMaterial = boxesByMaterialAndMesh[mesh.GetContainerVolume()->GetName()];
|
||||
|
||||
// Fill map if not already filled
|
||||
if (boxesByMaterial.empty()) {
|
||||
|
||||
// Get positions and material one cell at a time (using PseudoSceneFor3DRectMeshPositions).
|
||||
// The pseudo scene allows a "private" descent into the parameterisation.
|
||||
// Instantiate a temporary G4PhysicalVolumeModel
|
||||
G4ModelingParameters tmpMP;
|
||||
tmpMP.SetCulling(true); // This avoids drawing transparent...
|
||||
tmpMP.SetCullingInvisible(true); // ... or invisble volumes.
|
||||
const G4bool useFullExtent = true; // To avoid calculating the extent
|
||||
G4PhysicalVolumeModel tmpPVModel
|
||||
(container,
|
||||
G4PhysicalVolumeModel::UNLIMITED,
|
||||
G4Transform3D(), // so that positions are in local coordinates
|
||||
&tmpMP,
|
||||
useFullExtent);
|
||||
// Accumulate information in temporary maps by material
|
||||
std::multimap<const G4Material*,const G4ThreeVector> positionByMaterial;
|
||||
std::map<const G4Material*,G4VSceneHandler::NameAndVisAtts> nameAndVisAttsByMaterial;
|
||||
// Instantiate the pseudo scene
|
||||
PseudoSceneFor3DRectMeshPositions pseudoScene
|
||||
(&tmpPVModel,mesh.GetMeshDepth(),positionByMaterial,nameAndVisAttsByMaterial);
|
||||
// Make private descent into the parameterisation
|
||||
tmpPVModel.DescribeYourselfTo(pseudoScene);
|
||||
// Now we have a map of positions by material.
|
||||
// Also a map of name and colour by material.
|
||||
|
||||
const auto& prms = mesh.GetThreeDRectParameters();
|
||||
const auto& sizeX = 2.*prms.fHalfX;
|
||||
const auto& sizeY = 2.*prms.fHalfY;
|
||||
const auto& sizeZ = 2.*prms.fHalfZ;
|
||||
|
||||
// Fill the permanent (static) map of boxes by material
|
||||
G4int nBoxesTotal = 0, nFacetsTotal = 0;
|
||||
for (const auto& entry: nameAndVisAttsByMaterial) {
|
||||
G4int nBoxes = 0;
|
||||
const auto& material = entry.first;
|
||||
const auto& nameAndVisAtts = nameAndVisAttsByMaterial[material];
|
||||
const auto& name = nameAndVisAtts.fName;
|
||||
const auto& visAtts = nameAndVisAtts.fVisAtts;
|
||||
// Transfer positions into a vector ready for creating polyhedral surface
|
||||
std::vector<G4ThreeVector> positionsForPolyhedron;
|
||||
const auto& range = positionByMaterial.equal_range(material);
|
||||
for (auto posByMat = range.first; posByMat != range.second; ++posByMat) {
|
||||
const auto& position = posByMat->second;
|
||||
positionsForPolyhedron.push_back(position);
|
||||
++nBoxes;
|
||||
}
|
||||
// The polyhedron will be in local coordinates
|
||||
// Add an empty place-holder to the map and get a reference to it
|
||||
auto& polyhedron = boxesByMaterial[material];
|
||||
// Replace with the desired polyhedron (uses efficient "move assignment")
|
||||
polyhedron = G4PolyhedronBoxMesh(sizeX,sizeY,sizeZ,positionsForPolyhedron);
|
||||
polyhedron.SetVisAttributes(visAtts);
|
||||
polyhedron.SetInfo(name);
|
||||
|
||||
if (print) {
|
||||
G4cout
|
||||
<< std::setw(30) << std::left << name.substr(0,30) << std::right
|
||||
<< ": " << std::setw(7) << nBoxes << " boxes"
|
||||
<< " (" << std::setw(7) << 6*nBoxes << " faces)"
|
||||
<< ": reduced to " << std::setw(7) << polyhedron.GetNoFacets() << " facets ("
|
||||
<< std::setw(2) << std::fixed << std::setprecision(2) << 100*polyhedron.GetNoFacets()/(6*nBoxes)
|
||||
<< "%): colour " << std::fixed << std::setprecision(2)
|
||||
<< visAtts.GetColour() << std::defaultfloat
|
||||
<< G4endl;
|
||||
}
|
||||
|
||||
nBoxesTotal += nBoxes;
|
||||
nFacetsTotal += polyhedron.GetNoFacets();
|
||||
}
|
||||
|
||||
if (print) {
|
||||
G4cout << "Total number of boxes: " << nBoxesTotal << " (" << 6*nBoxesTotal << " faces)"
|
||||
<< ": reduced to " << nFacetsTotal << " facets ("
|
||||
<< std::setw(2) << std::fixed << std::setprecision(2) << 100*nFacetsTotal/(6*nBoxesTotal) << "%)"
|
||||
<< G4endl;
|
||||
}
|
||||
}
|
||||
|
||||
// Some subsequent expressions apply only to G4PhysicalVolumeModel
|
||||
auto pPVModel = dynamic_cast<G4PhysicalVolumeModel*>(fpModel);
|
||||
|
||||
G4String parameterisationName;
|
||||
if (pPVModel) {
|
||||
parameterisationName = pPVModel->GetFullPVPath().back().GetPhysicalVolume()->GetName();
|
||||
}
|
||||
|
||||
// Draw the boxes by material
|
||||
// Now we transform to world coordinates
|
||||
BeginPrimitives (mesh.GetTransform());
|
||||
for (const auto& entry: boxesByMaterial) {
|
||||
const auto& poly = entry.second;
|
||||
// The current "leaf" node in the PVPath is the parameterisation. Here it has
|
||||
// been converted into polyhedra by material. So...temporarily...change
|
||||
// its name to that of the material (whose name has been stored in Info)
|
||||
// so that its appearance in the scene tree of, e.g., G4OpenGLQtViewer, has
|
||||
// an appropriate name and its visibility and colour may be changed.
|
||||
if (pPVModel) {
|
||||
const auto& fullPVPath = pPVModel->GetFullPVPath();
|
||||
auto leafPV = fullPVPath.back().GetPhysicalVolume();
|
||||
leafPV->SetName(poly.GetInfo());
|
||||
}
|
||||
AddPrimitive(poly);
|
||||
}
|
||||
EndPrimitives ();
|
||||
// Restore parameterisation name
|
||||
if (pPVModel) {
|
||||
pPVModel->GetFullPVPath().back().GetPhysicalVolume()->SetName(parameterisationName);
|
||||
}
|
||||
|
||||
firstPrint = false;
|
||||
return;
|
||||
}
|
||||
|
||||
void G4VSceneHandler::DrawTetMeshAsDots(const G4Mesh& mesh)
|
||||
// For a tetrahedron mesh, draw as coloured dots by colour and material,
|
||||
// one dot randomly placed in each visible mesh cell.
|
||||
{
|
||||
// Check
|
||||
if (mesh.GetMeshType() != G4Mesh::tetrahedron) {
|
||||
G4ExceptionDescription ed;
|
||||
ed << "Called with mesh that is not a tetrahedron mesh:" << mesh;
|
||||
G4Exception("G4VSceneHandler::DrawTetMeshAsDots","visman0108",JustWarning,ed);
|
||||
return;
|
||||
}
|
||||
|
||||
static G4bool firstPrint = true;
|
||||
const auto& verbosity = G4VisManager::GetVerbosity();
|
||||
G4bool print = firstPrint && verbosity >= G4VisManager::errors;
|
||||
|
||||
if (print) {
|
||||
G4cout
|
||||
<< "Special case drawing of tetrahedron mesh as dots"
|
||||
<< '\n' << mesh
|
||||
<< G4endl;
|
||||
}
|
||||
|
||||
const auto& container = mesh.GetContainerVolume();
|
||||
|
||||
// This map is static so that once filled it stays filled.
|
||||
static std::map<G4String,std::map<const G4Material*,G4Polymarker>> dotsByMaterialAndMesh;
|
||||
auto& dotsByMaterial = dotsByMaterialAndMesh[mesh.GetContainerVolume()->GetName()];
|
||||
|
||||
// Fill map if not already filled
|
||||
if (dotsByMaterial.empty()) {
|
||||
|
||||
// Get vertices and colour one cell at a time (using PseudoSceneForTetVertices).
|
||||
// The pseudo scene allows a "private" descent into the parameterisation.
|
||||
// Instantiate a temporary G4PhysicalVolumeModel
|
||||
G4ModelingParameters tmpMP;
|
||||
tmpMP.SetCulling(true); // This avoids drawing transparent...
|
||||
tmpMP.SetCullingInvisible(true); // ... or invisble volumes.
|
||||
const G4bool useFullExtent = true; // To avoid calculating the extent
|
||||
G4PhysicalVolumeModel tmpPVModel
|
||||
(container,
|
||||
G4PhysicalVolumeModel::UNLIMITED,
|
||||
G4Transform3D(), // so that positions are in local coordinates
|
||||
&tmpMP,
|
||||
useFullExtent);
|
||||
// Accumulate information in temporary maps by material
|
||||
std::multimap<const G4Material*,std::vector<G4ThreeVector>> verticesByMaterial;
|
||||
std::map<const G4Material*,G4VSceneHandler::NameAndVisAtts> nameAndVisAttsByMaterial;
|
||||
// Instantiate a pseudo scene
|
||||
PseudoSceneForTetVertices pseudoScene
|
||||
(&tmpPVModel,mesh.GetMeshDepth(),verticesByMaterial,nameAndVisAttsByMaterial);
|
||||
// Make private descent into the parameterisation
|
||||
tmpPVModel.DescribeYourselfTo(pseudoScene);
|
||||
// Now we have a map of vertices by material.
|
||||
// Also a map of name and colour by material.
|
||||
|
||||
// Fill the permanent (static) map of dots by material
|
||||
G4int nDotsTotal = 0;
|
||||
for (const auto& entry: nameAndVisAttsByMaterial) {
|
||||
G4int nDots = 0;
|
||||
const auto& material = entry.first;
|
||||
const auto& nameAndVisAtts = nameAndVisAttsByMaterial[material];
|
||||
const auto& name = nameAndVisAtts.fName;
|
||||
const auto& visAtts = nameAndVisAtts.fVisAtts;
|
||||
G4Polymarker dots;
|
||||
dots.SetVisAttributes(visAtts);
|
||||
dots.SetMarkerType(G4Polymarker::dots);
|
||||
dots.SetSize(G4VMarker::screen,1.);
|
||||
dots.SetInfo(name);
|
||||
// Enter empty polymarker into the map
|
||||
dotsByMaterial[material] = dots;
|
||||
// Now fill it in situ
|
||||
auto& dotsInMap = dotsByMaterial[material];
|
||||
const auto& range = verticesByMaterial.equal_range(material);
|
||||
for (auto vByMat = range.first; vByMat != range.second; ++vByMat) {
|
||||
const std::vector<G4ThreeVector>& vertices = vByMat->second;
|
||||
// Calculate extent/bounding box
|
||||
G4double xmin, xmax, ymin, ymax, zmin, zmax;
|
||||
xmin = ymin = zmin = DBL_MAX;
|
||||
xmax = ymax = zmax = -DBL_MAX;
|
||||
for (const auto& vertex: vertices) {
|
||||
if (xmin > vertex.x()) xmin = vertex.x();
|
||||
if (ymin > vertex.y()) ymin = vertex.y();
|
||||
if (zmin > vertex.z()) zmin = vertex.z();
|
||||
if (xmax < vertex.x()) xmax = vertex.x();
|
||||
if (ymax < vertex.y()) ymax = vertex.y();
|
||||
if (zmax < vertex.z()) zmax = vertex.z();
|
||||
}
|
||||
// Place dot at random in the extent/bounding box. Yes, I know this will
|
||||
// be bigger than the tetrahedron, so sometimes the position will be outside
|
||||
// the tetrahedron, but it will still give a reasonable visual representation.
|
||||
// If you have a smart algorithm for generating a random point in a
|
||||
// tetrahedron, please let us know.
|
||||
const G4double x = xmin + G4UniformRand()*(xmax - xmin);
|
||||
const G4double y = ymin + G4UniformRand()*(ymax - ymin);
|
||||
const G4double z = zmin + G4UniformRand()*(zmax - zmin);
|
||||
dotsInMap.push_back(G4ThreeVector(x,y,z));
|
||||
++nDots;
|
||||
}
|
||||
|
||||
if (print) {
|
||||
G4cout
|
||||
<< std::setw(30) << std::left << name.substr(0,30) << std::right
|
||||
<< ": " << std::setw(7) << nDots << " dots"
|
||||
<< ": colour " << std::fixed << std::setprecision(2)
|
||||
<< visAtts.GetColour() << std::defaultfloat
|
||||
<< G4endl;
|
||||
}
|
||||
|
||||
nDotsTotal += nDots;
|
||||
}
|
||||
|
||||
if (print) {
|
||||
G4cout << "Total number of dots: " << nDotsTotal << G4endl;
|
||||
}
|
||||
}
|
||||
|
||||
// Some subsequent expressions apply only to G4PhysicalVolumeModel
|
||||
auto pPVModel = dynamic_cast<G4PhysicalVolumeModel*>(fpModel);
|
||||
|
||||
G4String parameterisationName;
|
||||
if (pPVModel) {
|
||||
parameterisationName = pPVModel->GetFullPVPath().back().GetPhysicalVolume()->GetName();
|
||||
}
|
||||
|
||||
// Draw the dots by material
|
||||
// Ensure they are "hidden", i.e., use the z-buffer as non-marker primitives do
|
||||
auto keepVP = fpViewer->GetViewParameters();
|
||||
auto vp = fpViewer->GetViewParameters();
|
||||
vp.SetMarkerHidden();
|
||||
fpViewer->SetViewParameters(vp);
|
||||
|
||||
// Now we transform to world coordinates
|
||||
BeginPrimitives (mesh.GetTransform());
|
||||
for (const auto& entry: dotsByMaterial) {
|
||||
const auto& dots = entry.second;
|
||||
// The current "leaf" node in the PVPath is the parameterisation. Here it has
|
||||
// been converted into polymarkers by material. So...temporarily...change
|
||||
// its name to that of the material (whose name has been stored in Info)
|
||||
// so that its appearance in the scene tree of, e.g., G4OpenGLQtViewer, has
|
||||
// an appropriate name and its visibility and colour may be changed.
|
||||
if (pPVModel) {
|
||||
const auto& fullPVPath = pPVModel->GetFullPVPath();
|
||||
auto leafPV = fullPVPath.back().GetPhysicalVolume();
|
||||
leafPV->SetName(dots.GetInfo());
|
||||
}
|
||||
AddPrimitive(dots);
|
||||
}
|
||||
EndPrimitives ();
|
||||
|
||||
// Restore view parameters
|
||||
fpViewer->SetViewParameters(keepVP);
|
||||
// Restore parameterisation name
|
||||
if (pPVModel) {
|
||||
pPVModel->GetFullPVPath().back().GetPhysicalVolume()->SetName(parameterisationName);
|
||||
}
|
||||
|
||||
firstPrint = false;
|
||||
return;
|
||||
}
|
||||
|
||||
void G4VSceneHandler::DrawTetMeshAsSurfaces(const G4Mesh& mesh)
|
||||
// For a tetrahedron mesh, draw as surfaces by colour and material
|
||||
// with inner shared faces removed.
|
||||
{
|
||||
// Check
|
||||
if (mesh.GetMeshType() != G4Mesh::tetrahedron) {
|
||||
G4ExceptionDescription ed;
|
||||
ed << "Called with mesh that is not a tetrahedron mesh:" << mesh;
|
||||
G4Exception("G4VSceneHandler::DrawTetMeshAsSurfaces","visman0108",JustWarning,ed);
|
||||
return;
|
||||
}
|
||||
|
||||
static G4bool firstPrint = true;
|
||||
const auto& verbosity = G4VisManager::GetVerbosity();
|
||||
G4bool print = firstPrint && verbosity >= G4VisManager::errors;
|
||||
|
||||
if (print) {
|
||||
G4cout
|
||||
<< "Special case drawing of tetrahedron mesh as surfaces"
|
||||
<< '\n' << mesh
|
||||
<< G4endl;
|
||||
}
|
||||
|
||||
const auto& container = mesh.GetContainerVolume();
|
||||
|
||||
// This map is static so that once filled it stays filled.
|
||||
static std::map<G4String,std::map<const G4Material*,G4Polyhedron>> surfacesByMaterialAndMesh;
|
||||
auto& surfacesByMaterial = surfacesByMaterialAndMesh[mesh.GetContainerVolume()->GetName()];
|
||||
|
||||
// Fill map if not already filled
|
||||
if (surfacesByMaterial.empty()) {
|
||||
|
||||
// Get vertices and colour one cell at a time (using PseudoSceneForTetVertices).
|
||||
// The pseudo scene allows a "private" descent into the parameterisation.
|
||||
// Instantiate a temporary G4PhysicalVolumeModel
|
||||
G4ModelingParameters tmpMP;
|
||||
tmpMP.SetCulling(true); // This avoids drawing transparent...
|
||||
tmpMP.SetCullingInvisible(true); // ... or invisble volumes.
|
||||
const G4bool useFullExtent = true; // To avoid calculating the extent
|
||||
G4PhysicalVolumeModel tmpPVModel
|
||||
(container,
|
||||
G4PhysicalVolumeModel::UNLIMITED,
|
||||
G4Transform3D(), // so that positions are in local coordinates
|
||||
&tmpMP,
|
||||
useFullExtent);
|
||||
// Accumulate information in temporary maps by material
|
||||
std::multimap<const G4Material*,std::vector<G4ThreeVector>> verticesByMaterial;
|
||||
std::map<const G4Material*,G4VSceneHandler::NameAndVisAtts> nameAndVisAttsByMaterial;
|
||||
// Instantiate a pseudo scene
|
||||
PseudoSceneForTetVertices pseudoScene
|
||||
(&tmpPVModel,mesh.GetMeshDepth(),verticesByMaterial,nameAndVisAttsByMaterial);
|
||||
// Make private descent into the parameterisation
|
||||
tmpPVModel.DescribeYourselfTo(pseudoScene);
|
||||
// Now we have a map of vertices by material.
|
||||
// Also a map of name and colour by material.
|
||||
|
||||
// Fill the permanent (static) map of surfaces by material
|
||||
G4int nTetsTotal = 0, nFacetsTotal = 0;
|
||||
for (const auto& entry: nameAndVisAttsByMaterial) {
|
||||
G4int nTets = 0;
|
||||
const auto& material = entry.first;
|
||||
const auto& nameAndVisAtts = nameAndVisAttsByMaterial[material];
|
||||
const auto& name = nameAndVisAtts.fName;
|
||||
const auto& visAtts = nameAndVisAtts.fVisAtts;
|
||||
// Transfer vertices into a vector ready for creating polyhedral surface
|
||||
std::vector<G4ThreeVector> verticesForPolyhedron;
|
||||
const auto& range = verticesByMaterial.equal_range(material);
|
||||
for (auto vByMat = range.first; vByMat != range.second; ++vByMat) {
|
||||
const std::vector<G4ThreeVector>& vertices = vByMat->second;
|
||||
for (const auto& vertex: vertices)
|
||||
verticesForPolyhedron.push_back(vertex);
|
||||
++nTets;
|
||||
}
|
||||
// The polyhedron will be in local coordinates
|
||||
// Add an empty place-holder to the map and get a reference to it
|
||||
auto& polyhedron = surfacesByMaterial[material];
|
||||
// Replace with the desired polyhedron (uses efficient "move assignment")
|
||||
polyhedron = G4PolyhedronTetMesh(verticesForPolyhedron);
|
||||
polyhedron.SetVisAttributes(visAtts);
|
||||
polyhedron.SetInfo(name);
|
||||
|
||||
if (print) {
|
||||
G4cout
|
||||
<< std::setw(30) << std::left << name.substr(0,30) << std::right
|
||||
<< ": " << std::setw(7) << nTets << " tetrahedra"
|
||||
<< " (" << std::setw(7) << 4*nTets << " faces)"
|
||||
<< ": reduced to " << std::setw(7) << polyhedron.GetNoFacets() << " facets ("
|
||||
<< std::setw(2) << std::fixed << std::setprecision(2) << 100*polyhedron.GetNoFacets()/(4*nTets)
|
||||
<< "%): colour " << std::fixed << std::setprecision(2)
|
||||
<< visAtts.GetColour() << std::defaultfloat
|
||||
<< G4endl;
|
||||
}
|
||||
|
||||
nTetsTotal += nTets;
|
||||
nFacetsTotal += polyhedron.GetNoFacets();
|
||||
}
|
||||
|
||||
if (print) {
|
||||
G4cout << "Total number of tetrahedra: " << nTetsTotal << " (" << 4*nTetsTotal << " faces)"
|
||||
<< ": reduced to " << nFacetsTotal << " facets ("
|
||||
<< std::setw(2) << std::fixed << std::setprecision(2) << 100*nFacetsTotal/(4*nTetsTotal) << "%)"
|
||||
<< G4endl;
|
||||
}
|
||||
}
|
||||
|
||||
// Some subsequent expressions apply only to G4PhysicalVolumeModel
|
||||
auto pPVModel = dynamic_cast<G4PhysicalVolumeModel*>(fpModel);
|
||||
|
||||
G4String parameterisationName;
|
||||
if (pPVModel) {
|
||||
parameterisationName = pPVModel->GetFullPVPath().back().GetPhysicalVolume()->GetName();
|
||||
}
|
||||
|
||||
// Draw the surfaces by material
|
||||
// Now we transform to world coordinates
|
||||
BeginPrimitives (mesh.GetTransform());
|
||||
for (const auto& entry: surfacesByMaterial) {
|
||||
const auto& poly = entry.second;
|
||||
// The current "leaf" node in the PVPath is the parameterisation. Here it has
|
||||
// been converted into polyhedra by material. So...temporarily...change
|
||||
// its name to that of the material (whose name has been stored in Info)
|
||||
// so that its appearance in the scene tree of, e.g., G4OpenGLQtViewer, has
|
||||
// an appropriate name and its visibility and colour may be changed.
|
||||
if (pPVModel) {
|
||||
const auto& fullPVPath = pPVModel->GetFullPVPath();
|
||||
auto leafPV = fullPVPath.back().GetPhysicalVolume();
|
||||
leafPV->SetName(poly.GetInfo());
|
||||
}
|
||||
AddPrimitive(poly);
|
||||
}
|
||||
EndPrimitives ();
|
||||
|
||||
// Restore parameterisation name
|
||||
if (pPVModel) {
|
||||
pPVModel->GetFullPVPath().back().GetPhysicalVolume()->SetName(parameterisationName);
|
||||
}
|
||||
|
||||
firstPrint = false;
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -31,6 +31,8 @@
|
||||
|
||||
#include "G4VViewer.hh"
|
||||
|
||||
#include "G4Timer.hh"
|
||||
|
||||
#include "G4ios.hh"
|
||||
#include <sstream>
|
||||
|
||||
@@ -111,9 +113,13 @@ void G4VViewer::ProcessView ()
|
||||
if (fNeedKernelVisit) {
|
||||
// Reset flag. This must be done before ProcessScene to prevent
|
||||
// recursive calls when recomputing transients...
|
||||
G4Timer timer;
|
||||
timer.Start();
|
||||
fNeedKernelVisit = false;
|
||||
fSceneHandler.ClearStore ();
|
||||
fSceneHandler.ProcessScene ();
|
||||
timer.Stop();
|
||||
fKernelVisitElapsedTimeSeconds = timer.GetRealElapsed();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -36,6 +36,9 @@
|
||||
#include <sstream>
|
||||
#include <cctype>
|
||||
|
||||
#include "G4PhysicalVolumeModel.hh"
|
||||
#include "G4LogicalVolume.hh"
|
||||
|
||||
G4int G4VVisCommand::fCurrentArrow3DLineSegmentsPerCircle = 6;
|
||||
G4Colour G4VVisCommand::fCurrentColour = G4Colour::White();
|
||||
G4Colour G4VVisCommand::fCurrentTextColour = G4Colour::Blue();
|
||||
@@ -49,7 +52,7 @@ G4PhysicalVolumeModel::TouchableProperties G4VVisCommand::fCurrentTouch
|
||||
G4VisExtent G4VVisCommand::fCurrentExtentForField;
|
||||
std::vector<G4PhysicalVolumesSearchScene::Findings> G4VVisCommand::fCurrrentPVFindingsForField;
|
||||
G4bool G4VVisCommand::fThereWasAViewer = false;
|
||||
G4ViewParameters G4VVisCommand::fVPExistingViewer;
|
||||
G4ViewParameters G4VVisCommand::fExistingVP;
|
||||
|
||||
G4VVisCommand::G4VVisCommand () {}
|
||||
|
||||
@@ -323,7 +326,7 @@ void G4VVisCommand::InterpolateToNewView
|
||||
viewVector.push_back(oldVP);
|
||||
viewVector.push_back(newVP);
|
||||
viewVector.push_back(newVP);
|
||||
|
||||
|
||||
InterpolateViews
|
||||
(currentViewer,
|
||||
viewVector,
|
||||
@@ -332,6 +335,62 @@ void G4VVisCommand::InterpolateToNewView
|
||||
exportString);
|
||||
}
|
||||
|
||||
void G4VVisCommand::Twinkle
|
||||
// Twinkles the touchables in paths
|
||||
// /vis/viewer/centreOn to see its effect
|
||||
(G4VViewer* currentViewer,
|
||||
const G4ViewParameters& baseVP,
|
||||
const std::vector<std::vector<G4PhysicalVolumeModel::G4PhysicalVolumeNodeID>>& paths)
|
||||
{
|
||||
// Copy view parameters to temporary variables ready for adding VisAttributes Modifiers (VAMs)
|
||||
auto loVP = baseVP; // For black and solid VAMs
|
||||
auto hiVP = baseVP; // For white and solid VAMs
|
||||
|
||||
// Modify them with vis attribute modifiers (VAMs)
|
||||
for (const auto& path: paths) {
|
||||
const auto& touchable = path.back().GetPhysicalVolume();
|
||||
auto loVisAtts
|
||||
= *(currentViewer->GetApplicableVisAttributes
|
||||
(touchable->GetLogicalVolume()->GetVisAttributes()));
|
||||
auto hiVisAtts = loVisAtts;
|
||||
loVisAtts.SetColour(G4Colour::Black());
|
||||
loVisAtts.SetForceSolid();
|
||||
hiVisAtts.SetColour(G4Colour::White());
|
||||
hiVisAtts.SetForceSolid();
|
||||
auto pvNameCopyNoPath
|
||||
= G4PhysicalVolumeModel::GetPVNameCopyNoPath(path);
|
||||
|
||||
auto loVAMColour = G4ModelingParameters::VisAttributesModifier
|
||||
(loVisAtts, G4ModelingParameters::VASColour, pvNameCopyNoPath);
|
||||
loVP.AddVisAttributesModifier(loVAMColour);
|
||||
auto loVAMStyle = G4ModelingParameters::VisAttributesModifier
|
||||
(loVisAtts, G4ModelingParameters::VASForceSolid, pvNameCopyNoPath);
|
||||
loVP.AddVisAttributesModifier(loVAMStyle);
|
||||
|
||||
auto hiVAMColour = G4ModelingParameters::VisAttributesModifier
|
||||
(hiVisAtts, G4ModelingParameters::VASColour, pvNameCopyNoPath);
|
||||
hiVP.AddVisAttributesModifier(hiVAMColour);
|
||||
auto hiVAMStyle = G4ModelingParameters::VisAttributesModifier
|
||||
(hiVisAtts, G4ModelingParameters::VASForceSolid, pvNameCopyNoPath);
|
||||
hiVP.AddVisAttributesModifier(hiVAMStyle);
|
||||
}
|
||||
|
||||
// Twinkle
|
||||
std::vector<G4ViewParameters> viewVector;
|
||||
viewVector.push_back(loVP);
|
||||
viewVector.push_back(hiVP);
|
||||
viewVector.push_back(loVP);
|
||||
viewVector.push_back(hiVP);
|
||||
viewVector.push_back(loVP);
|
||||
viewVector.push_back(hiVP);
|
||||
viewVector.push_back(loVP);
|
||||
viewVector.push_back(hiVP);
|
||||
viewVector.push_back(loVP);
|
||||
viewVector.push_back(hiVP);
|
||||
// Just 5 interpolation points for a reasonable twinkle rate
|
||||
InterpolateViews(currentViewer,viewVector,5);
|
||||
}
|
||||
|
||||
void G4VVisCommand::CopyGuidanceFrom
|
||||
(const G4UIcommand* fromCmd, G4UIcommand* toCmd, G4int startLine)
|
||||
{
|
||||
@@ -371,17 +430,6 @@ void G4VVisCommand::DrawExtent(const G4VisExtent& extent)
|
||||
}
|
||||
}
|
||||
|
||||
void G4VVisCommand::CopyMostViewParameters
|
||||
(G4ViewParameters& target, const G4ViewParameters& from)
|
||||
{
|
||||
// Copy view parameters except for autoRefresh and background...
|
||||
auto targetAutoRefresh = target.IsAutoRefresh();
|
||||
auto targetBackground = target.GetBackgroundColour();
|
||||
target = from;
|
||||
target.SetAutoRefresh(targetAutoRefresh);
|
||||
target.SetBackgroundColour(targetBackground);
|
||||
}
|
||||
|
||||
void G4VVisCommand::CopyCameraParameters
|
||||
(G4ViewParameters& target, const G4ViewParameters& from)
|
||||
{
|
||||
|
||||
@@ -101,7 +101,8 @@ G4ViewParameters::G4ViewParameters ():
|
||||
fDisplayLightFrontRed(0.),
|
||||
fDisplayLightFrontGreen(1.),
|
||||
fDisplayLightFrontBlue(0.),
|
||||
fSpecialMeshRendering(false)
|
||||
fSpecialMeshRendering(false),
|
||||
fSpecialMeshRenderingOption(meshAsDots)
|
||||
{
|
||||
// Pick up default no of sides from G4Polyhedron.
|
||||
// Note that this parameter is variously called:
|
||||
@@ -459,6 +460,9 @@ G4String G4ViewParameters::DrawingStyleCommands() const
|
||||
oss << "false";
|
||||
}
|
||||
|
||||
oss << "\n/vis/viewer/set/specialMeshRenderingOption "
|
||||
<< fSpecialMeshRenderingOption;
|
||||
|
||||
oss << "\n/vis/viewer/set/specialMeshVolumes";
|
||||
for (const auto& volume : fSpecialMeshVolumes) {
|
||||
oss << ' ' << volume.GetName() << ' ' << volume.GetCopyNo();
|
||||
@@ -868,20 +872,32 @@ void G4ViewParameters::PrintDifferences (const G4ViewParameters& v) const {
|
||||
}
|
||||
|
||||
std::ostream& operator <<
|
||||
(std::ostream& os, const G4ViewParameters::DrawingStyle& style)
|
||||
(std::ostream& os, G4ViewParameters::DrawingStyle style)
|
||||
{
|
||||
switch (style) {
|
||||
case G4ViewParameters::wireframe:
|
||||
os << "wireframe"; break;
|
||||
case G4ViewParameters::hlr:
|
||||
os << "hlr - hidden lines removed"; break;
|
||||
case G4ViewParameters::hsr:
|
||||
os << "hsr - hidden surfaces removed"; break;
|
||||
case G4ViewParameters::hlhsr:
|
||||
os << "hlhsr - hidden line, hidden surface removed"; break;
|
||||
case G4ViewParameters::cloud:
|
||||
os << "cloud - draw volume as a cloud of dots"; break;
|
||||
default: os << "unrecognised"; break;
|
||||
case G4ViewParameters::wireframe:
|
||||
os << "wireframe"; break;
|
||||
case G4ViewParameters::hlr:
|
||||
os << "hlr - hidden lines removed"; break;
|
||||
case G4ViewParameters::hsr:
|
||||
os << "hsr - hidden surfaces removed"; break;
|
||||
case G4ViewParameters::hlhsr:
|
||||
os << "hlhsr - hidden line, hidden surface removed"; break;
|
||||
case G4ViewParameters::cloud:
|
||||
os << "cloud - draw volume as a cloud of dots"; break;
|
||||
default: os << "unrecognised"; break;
|
||||
}
|
||||
return os;
|
||||
}
|
||||
|
||||
std::ostream& operator <<
|
||||
(std::ostream& os, G4ViewParameters::SMROption option)
|
||||
{
|
||||
switch (option) {
|
||||
case G4ViewParameters::meshAsDots:
|
||||
os << "dots"; break;
|
||||
case G4ViewParameters::meshAsSurfaces:
|
||||
os << "surfaces"; break;
|
||||
}
|
||||
return os;
|
||||
}
|
||||
@@ -1063,19 +1079,19 @@ std::ostream& operator << (std::ostream& os, const G4ViewParameters& v) {
|
||||
<< ' ' << v.fDisplayLightFrontGreen << ' ' << v.fDisplayLightFrontBlue;
|
||||
}
|
||||
|
||||
os << "\n Special Mesh Rendering: ";
|
||||
os << "\n Special Mesh Rendering";
|
||||
if (v.fSpecialMeshRendering) {
|
||||
os << "on: ";
|
||||
os << " requested with option \"" << v.fSpecialMeshRenderingOption;
|
||||
os << "\" for ";
|
||||
if (v.fSpecialMeshVolumes.empty()) {
|
||||
os << "all meshes";
|
||||
os << "any mesh";
|
||||
} else {
|
||||
os << "selected meshes";
|
||||
for (const auto& vol: v.fSpecialMeshVolumes) {
|
||||
os << "\n " << vol.GetName() << ':' << vol.GetCopyNo();
|
||||
}
|
||||
}
|
||||
} else os << "off";
|
||||
|
||||
} else os << ": off";
|
||||
return os;
|
||||
}
|
||||
|
||||
@@ -1121,7 +1137,8 @@ G4bool G4ViewParameters::operator != (const G4ViewParameters& v) const {
|
||||
(fBackgroundColour != v.fBackgroundColour) ||
|
||||
(fPicking != v.fPicking) ||
|
||||
(fRotationStyle != v.fRotationStyle) ||
|
||||
(fSpecialMeshRendering != v.fSpecialMeshRendering)
|
||||
(fSpecialMeshRendering != v.fSpecialMeshRendering) ||
|
||||
(fSpecialMeshRenderingOption != v.fSpecialMeshRenderingOption)
|
||||
)
|
||||
return true;
|
||||
|
||||
@@ -1189,29 +1206,36 @@ G4bool G4ViewParameters::operator != (const G4ViewParameters& v) const {
|
||||
return false;
|
||||
}
|
||||
|
||||
void G4ViewParameters::SetXGeometryString (const G4String& geomStringArg)
|
||||
void G4ViewParameters::SetXGeometryString (const G4String& geomString)
|
||||
{
|
||||
G4int x = 0, y = 0;
|
||||
unsigned int w = 0, h = 0;
|
||||
G4String geomString = geomStringArg;
|
||||
// Parse windowSizeHintString for backwards compatibility...
|
||||
const G4String delimiters("xX+-");
|
||||
G4String::size_type i = geomString.find_first_of(delimiters);
|
||||
if (i == G4String::npos) { // Does not contain "xX+-". Assume single number
|
||||
if (i == G4String::npos) {
|
||||
// Does not contain "xX+-".
|
||||
// Is it a single number?
|
||||
std::istringstream iss(geomString);
|
||||
G4int size;
|
||||
iss >> size;
|
||||
if (!iss) {
|
||||
size = 600;
|
||||
G4cout << "Unrecognised windowSizeHint string: \""
|
||||
<< geomString
|
||||
<< "\". Asuuming " << size << G4endl;
|
||||
if (iss) {
|
||||
// It is a number
|
||||
fWindowSizeHintX = size;
|
||||
fWindowSizeHintY = size;
|
||||
}
|
||||
// Accept other or all defaults (in G4ViewParameters constructor)
|
||||
// Reconstruct a geometry string coherent with the above
|
||||
char signX, signY;
|
||||
if (fWindowLocationHintXNegative) signX = '-'; else signX ='+';
|
||||
if (fWindowLocationHintYNegative) signY = '-'; else signY ='+';
|
||||
std::ostringstream oss;
|
||||
oss << size << 'x' << size;
|
||||
geomString = oss.str();
|
||||
oss << fWindowSizeHintX << 'x' << fWindowSizeHintY
|
||||
<< signX << fWindowLocationHintX << signY << fWindowLocationHintY;
|
||||
fXGeometryString = oss.str();
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
// Assume it's a parseable X geometry string
|
||||
G4int x = 0, y = 0;
|
||||
unsigned int w = 0, h = 0;
|
||||
fGeometryMask = ParseGeometry( geomString, &x, &y, &w, &h );
|
||||
|
||||
// Handle special case :
|
||||
|
||||
@@ -72,6 +72,31 @@ void G4VisCommandAbortReviewKeptEvents::SetNewValue (G4UIcommand*,
|
||||
G4cout << "Type \"continue\" to complete the abort." << G4endl;
|
||||
}
|
||||
|
||||
////////////// /vis/abortReviewPlots /////////////////////////////
|
||||
|
||||
G4VisCommandAbortReviewPlots::G4VisCommandAbortReviewPlots () {
|
||||
G4bool omitable;
|
||||
|
||||
fpCommand = new G4UIcmdWithABool("/vis/abortReviewPlots", this);
|
||||
fpCommand -> SetGuidance("Abort review of plots.");
|
||||
fpCommand -> SetParameterName("abort", omitable=true);
|
||||
fpCommand -> SetDefaultValue(true);
|
||||
}
|
||||
|
||||
G4VisCommandAbortReviewPlots::~G4VisCommandAbortReviewPlots () {
|
||||
delete fpCommand;
|
||||
}
|
||||
|
||||
G4String G4VisCommandAbortReviewPlots::GetCurrentValue (G4UIcommand*) {
|
||||
return G4String();
|
||||
}
|
||||
|
||||
void G4VisCommandAbortReviewPlots::SetNewValue (G4UIcommand*,
|
||||
G4String newValue) {
|
||||
fpVisManager->SetAbortReviewPlots(G4UIcommand::ConvertToBool(newValue));
|
||||
G4cout << "Type \"continue\" to complete the abort." << G4endl;
|
||||
}
|
||||
|
||||
////////////// /vis/drawOnlyToBeKeptEvents /////////////////////////////
|
||||
|
||||
G4VisCommandDrawOnlyToBeKeptEvents::G4VisCommandDrawOnlyToBeKeptEvents ()
|
||||
@@ -319,9 +344,9 @@ void G4VisCommandReviewKeptEvents::SetNewValue (G4UIcommand*, G4String newValue)
|
||||
}
|
||||
|
||||
G4UImanager* UImanager = G4UImanager::GetUIpointer();
|
||||
G4int keepVerbose = UImanager->GetVerboseLevel();
|
||||
G4int keepControlVerbose = UImanager->GetVerboseLevel();
|
||||
G4int newVerbose(0);
|
||||
if (keepVerbose >= 2 || verbosity >= G4VisManager::confirmations)
|
||||
if (keepControlVerbose >= 2 || verbosity >= G4VisManager::confirmations)
|
||||
newVerbose = 2;
|
||||
UImanager->SetVerboseLevel(newVerbose);
|
||||
|
||||
@@ -401,7 +426,129 @@ void G4VisCommandReviewKeptEvents::SetNewValue (G4UIcommand*, G4String newValue)
|
||||
|
||||
if (keepConcreteInstance) fpVisManager->Enable();
|
||||
else fpVisManager->Disable();
|
||||
UImanager->SetVerboseLevel(keepVerbose);
|
||||
UImanager->SetVerboseLevel(keepControlVerbose);
|
||||
}
|
||||
|
||||
////////////// /vis/reviewPlots ///////////////////////////////////////
|
||||
|
||||
G4VisCommandReviewPlots::G4VisCommandReviewPlots ()
|
||||
{
|
||||
fpCommand = new G4UIcmdWithoutParameter("/vis/reviewPlots", this);
|
||||
fpCommand -> SetGuidance("Review plots.");
|
||||
fpCommand -> SetGuidance
|
||||
("Each plot is drawn, one by one, to the current viewer. After each"
|
||||
"\nplot the session is paused. The user may issue any allowed command."
|
||||
"\nThen enter \"cont[inue]\" to continue to the next plot."
|
||||
"\nUseful commands might be:"
|
||||
"\n \"/vis/tsg/export\" to get hard copy."
|
||||
"\n \"/vis/abortReviewPlots\", then \"cont[inue]\", to abort.");
|
||||
}
|
||||
|
||||
G4VisCommandReviewPlots::~G4VisCommandReviewPlots ()
|
||||
{
|
||||
delete fpCommand;
|
||||
}
|
||||
|
||||
G4String G4VisCommandReviewPlots::GetCurrentValue (G4UIcommand*)
|
||||
{
|
||||
return "";
|
||||
}
|
||||
|
||||
#include <tools/histo/h1d>
|
||||
#include <tools/histo/h2d>
|
||||
|
||||
namespace {
|
||||
template <typename HT> // tools::histo::h1d, etc
|
||||
G4bool ReviewPlots(const G4String& plotType) { // h1, etc.
|
||||
auto visManager = G4VisManager::GetInstance();
|
||||
auto ui = G4UImanager::GetUIpointer();
|
||||
auto session = ui->GetSession();
|
||||
G4bool aborting = false;
|
||||
auto keepControlVerbose = ui->GetVerboseLevel();
|
||||
ui->SetVerboseLevel(0);
|
||||
auto status = ui->ApplyCommand("/analysis/" + plotType + "/getVector");
|
||||
ui->SetVerboseLevel(keepControlVerbose);
|
||||
if(status==G4UIcommandStatus::fCommandSucceeded) {
|
||||
G4String hexString = ui->GetCurrentValues(G4String("/analysis/" + plotType + "/getVector"));
|
||||
if(hexString.size()) {
|
||||
void* ptr;
|
||||
std::istringstream is(hexString);
|
||||
is >> ptr;
|
||||
auto _v = (const std::vector<HT*>*)ptr;
|
||||
auto _n = _v->size();
|
||||
for (size_t i = 0; i < _n; ++i) {
|
||||
// Draw then pause session...
|
||||
std::ostringstream oss;
|
||||
oss << "/vis/plot " << plotType << ' ' << i;
|
||||
ui->ApplyCommand(oss.str());
|
||||
session->PauseSessionStart("EndOfEvent");
|
||||
if (visManager->GetAbortReviewPlots()) {
|
||||
aborting = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
return aborting;
|
||||
}
|
||||
}
|
||||
|
||||
void G4VisCommandReviewPlots::SetNewValue (G4UIcommand*, G4String)
|
||||
{
|
||||
if (fpVisManager->GetReviewingPlots()) {
|
||||
G4cout <<
|
||||
"\"/vis/reviewPlots\" not allowed within an already started review."
|
||||
"\n No action taken."
|
||||
<< G4endl;
|
||||
return;
|
||||
}
|
||||
|
||||
auto verbosity = fpVisManager->GetVerbosity();
|
||||
|
||||
auto currentViewer = fpVisManager->GetCurrentViewer();
|
||||
if (!currentViewer) {
|
||||
if (verbosity >= G4VisManager::errors) {
|
||||
G4cerr <<
|
||||
"ERROR: No current viewer - \"/vis/viewer/list\" to see possibilities."
|
||||
<< G4endl;
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
if (currentViewer->GetName().find("TOOLSSG") == std::string::npos) {
|
||||
G4cerr <<
|
||||
"WARNING: Current viewer not able to draw plots."
|
||||
"\n Try \"/vis/open TSG\", then \"/vis/reviewPlots\" again."
|
||||
<< G4endl;
|
||||
return;
|
||||
}
|
||||
|
||||
G4Scene* pScene = fpVisManager->GetCurrentScene();
|
||||
if (!pScene) {
|
||||
if (verbosity >= G4VisManager::errors) {
|
||||
G4cerr << "ERROR: No current scene. Please create one." << G4endl;
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
auto ui = G4UImanager::GetUIpointer();
|
||||
|
||||
auto keepControlVerbose = ui->GetVerboseLevel();
|
||||
ui->SetVerboseLevel(0);
|
||||
auto keepVisVerbose = fpVisManager->GetVerbosity();
|
||||
fpVisManager->SetVerboseLevel(G4VisManager::errors);
|
||||
auto keepEnable = fpVisManager->IsEnabled();
|
||||
fpVisManager->Enable();
|
||||
fpVisManager->SetReviewingPlots(true);
|
||||
|
||||
if (ReviewPlots<tools::histo::h1d>("h1")) goto finish; // Aborting?
|
||||
if (ReviewPlots<tools::histo::h2d>("h2")) goto finish; // Aborting?
|
||||
|
||||
finish:
|
||||
fpVisManager->SetReviewingPlots(false);
|
||||
if (!keepEnable) fpVisManager->Disable();
|
||||
fpVisManager->SetVerboseLevel(keepVisVerbose);
|
||||
ui->SetVerboseLevel(keepControlVerbose);
|
||||
}
|
||||
|
||||
////////////// /vis/verbose ///////////////////////////////////////
|
||||
|
||||
@@ -342,17 +342,22 @@ G4VisCommandOpen::G4VisCommandOpen() {
|
||||
G4bool omitable;
|
||||
fpCommand = new G4UIcommand("/vis/open", this);
|
||||
fpCommand->SetGuidance
|
||||
("Creates a scene handler ready for drawing.");
|
||||
("Creates a scene handler and viewer ready for drawing.");
|
||||
fpCommand->SetGuidance
|
||||
("The scene handler becomes current (the name is auto-generated).");
|
||||
("The scene handler and viewer names are auto-generated.");
|
||||
// Pick up guidance from /vis/viewer/create
|
||||
const G4UIcommandTree* tree = G4UImanager::GetUIpointer()->GetTree();
|
||||
const G4UIcommand* viewerCreateCmd = tree->FindPath("/vis/viewer/create");
|
||||
CopyGuidanceFrom(viewerCreateCmd,fpCommand,2);
|
||||
G4UIparameter* parameter;
|
||||
parameter = new G4UIparameter("graphics-system-name", 's', omitable = false);
|
||||
parameter = new G4UIparameter("graphics-system-name", 's', omitable = true);
|
||||
parameter->SetCurrentAsDefault(true);
|
||||
fpCommand->SetParameter(parameter);
|
||||
parameter = new G4UIparameter("window-size-hint", 's', omitable = true);
|
||||
parameter->SetGuidance
|
||||
("integer (pixels) for square window placed by window manager or"
|
||||
" X-Windows-type geometry string, e.g. 600x600-100+100");
|
||||
parameter->SetDefaultValue("600");
|
||||
parameter->SetDefaultValue("none");
|
||||
fpCommand->SetParameter(parameter);
|
||||
}
|
||||
|
||||
@@ -360,6 +365,19 @@ G4VisCommandOpen::~G4VisCommandOpen() {
|
||||
delete fpCommand;
|
||||
}
|
||||
|
||||
G4String G4VisCommandOpen::GetCurrentValue(G4UIcommand*)
|
||||
{
|
||||
G4String graphicsSystemName;
|
||||
auto graphicsSystem = fpVisManager->GetCurrentGraphicsSystem();
|
||||
if (graphicsSystem) {
|
||||
graphicsSystemName = graphicsSystem->GetName ();
|
||||
}
|
||||
else {
|
||||
graphicsSystemName = "none";
|
||||
}
|
||||
return graphicsSystemName;
|
||||
}
|
||||
|
||||
void G4VisCommandOpen::SetNewValue (G4UIcommand* command, G4String newValue)
|
||||
{
|
||||
G4String systemName, windowSizeHint;
|
||||
@@ -390,26 +408,80 @@ void G4VisCommandOpen::SetNewValue (G4UIcommand* command, G4String newValue)
|
||||
|
||||
finish:
|
||||
if (errorCode) {
|
||||
std::set<G4String> candidates;
|
||||
for (const auto gs: fpVisManager -> GetAvailableGraphicsSystems()) {
|
||||
// Just list nicknames, but exclude FALLBACK nicknames
|
||||
for (const auto& nickname: gs->GetNicknames()) {
|
||||
if (!G4StrUtil::contains(nickname, "FALLBACK")) {
|
||||
candidates.insert(nickname);
|
||||
}
|
||||
}
|
||||
}
|
||||
G4ExceptionDescription ed;
|
||||
ed << "Invoked command has failed - see above. Available graphics systems are (short names):\n ";
|
||||
for (const auto& candidate: candidates) {
|
||||
ed << ' ' << candidate;
|
||||
};
|
||||
ed << "Invoked command has failed - see above. Available graphics systems are:\n ";
|
||||
fpVisManager->PrintAvailableGraphicsSystems(G4VisManager::warnings,ed);
|
||||
command->CommandFailed(errorCode,ed);
|
||||
}
|
||||
|
||||
UImanager->SetVerboseLevel(keepVerbose);
|
||||
}
|
||||
|
||||
////////////// /vis/plot ///////////////////////////////////////
|
||||
|
||||
G4VisCommandPlot::G4VisCommandPlot ()
|
||||
{
|
||||
G4bool omitable;
|
||||
G4UIparameter* parameter;
|
||||
|
||||
fpCommand = new G4UIcommand("/vis/plot", this);
|
||||
fpCommand -> SetGuidance("Draws plots.");
|
||||
parameter = new G4UIparameter ("type", 's', omitable = false);
|
||||
parameter -> SetParameterCandidates("h1 h2");
|
||||
fpCommand -> SetParameter (parameter);
|
||||
parameter = new G4UIparameter ("id", 'i', omitable = false);
|
||||
fpCommand -> SetParameter (parameter);
|
||||
}
|
||||
|
||||
G4VisCommandPlot::~G4VisCommandPlot ()
|
||||
{
|
||||
delete fpCommand;
|
||||
}
|
||||
|
||||
G4String G4VisCommandPlot::GetCurrentValue (G4UIcommand*)
|
||||
{
|
||||
return "";
|
||||
}
|
||||
|
||||
void G4VisCommandPlot::SetNewValue (G4UIcommand*, G4String newValue)
|
||||
{
|
||||
auto currentViewer = fpVisManager->GetCurrentViewer();
|
||||
if (currentViewer->GetName().find("TOOLSSG") == std::string::npos) {
|
||||
G4cerr <<
|
||||
"WARNING: Current viewer not able to draw plots."
|
||||
"\n Try \"/vis/open TSG\", then \"/vis/plot " << newValue << "\" again."
|
||||
<< G4endl;
|
||||
return;
|
||||
}
|
||||
|
||||
G4String type, id;
|
||||
std::istringstream is (newValue);
|
||||
is >> type >> id;
|
||||
|
||||
auto keepEnable = fpVisManager->IsEnabled();
|
||||
|
||||
auto ui = G4UImanager::GetUIpointer();
|
||||
ui->ApplyCommand("/vis/enable");
|
||||
ui->ApplyCommand("/vis/viewer/resetCameraParameters");
|
||||
ui->ApplyCommand("/vis/scene/create");
|
||||
ui->ApplyCommand("/vis/scene/endOfEventAction accumulate 0"); // Don't keep events
|
||||
static G4int plotterID = 0;
|
||||
std::ostringstream ossPlotter;
|
||||
ossPlotter << "plotter-" << plotterID++;
|
||||
const G4String& plotterName = ossPlotter.str();
|
||||
ui->ApplyCommand("/vis/plotter/create " + plotterName);
|
||||
ui->ApplyCommand("/vis/scene/add/plotter " + plotterName);
|
||||
ui->ApplyCommand("/vis/plotter/add/" + type + ' ' + id + ' ' + plotterName);
|
||||
ui->ApplyCommand("/vis/sceneHandler/attach");
|
||||
|
||||
if (!keepEnable) {
|
||||
fpVisManager->Disable();
|
||||
G4cerr <<
|
||||
"WARNING: drawing was enabled for plotting but is now restored to disabled mode."
|
||||
<< G4endl;
|
||||
}
|
||||
}
|
||||
|
||||
////////////// /vis/specify ///////////////////////////////////////
|
||||
|
||||
G4VisCommandSpecify::G4VisCommandSpecify() {
|
||||
|
||||
@@ -348,9 +348,9 @@ void G4VisCommandSceneAddAxes::SetNewValue (G4UIcommand*, G4String newValue) {
|
||||
|
||||
// Consult scene for arrow width...
|
||||
G4double arrowWidth =
|
||||
0.005 * fCurrentLineWidth * sceneExtent.GetExtentRadius();
|
||||
// ...but limit it to length/50.
|
||||
if (arrowWidth > length/50.) arrowWidth = length/50.;
|
||||
0.05 * fCurrentLineWidth * sceneExtent.GetExtentRadius();
|
||||
// ...but limit it to length/30.
|
||||
if (arrowWidth > length/30.) arrowWidth = length/30.;
|
||||
|
||||
G4VModel* model = new G4AxesModel
|
||||
(x0, y0, z0, length, arrowWidth, colourString, newValue,
|
||||
@@ -3077,7 +3077,7 @@ G4VisCommandSceneAddVolume::G4VisCommandSceneAddVolume () {
|
||||
parameter = new G4UIparameter ("depth-of-descent", 'i', omitable = true);
|
||||
parameter -> SetGuidance
|
||||
("Depth of descent of geometry hierarchy. Default = unlimited depth.");
|
||||
parameter -> SetDefaultValue (G4Scene::UNLIMITED);
|
||||
parameter -> SetDefaultValue (G4PhysicalVolumeModel::UNLIMITED);
|
||||
fpCommand -> SetParameter (parameter);
|
||||
parameter = new G4UIparameter ("clip-volume-type", 's', omitable = true);
|
||||
parameter -> SetParameterCandidates("none box -box *box");
|
||||
@@ -3259,12 +3259,11 @@ void G4VisCommandSceneAddVolume::SetNewValue (G4UIcommand*,
|
||||
G4ModelingParameters mp; // Default - no culling.
|
||||
G4PhysicalVolumeModel searchModel
|
||||
(*iterWorld,
|
||||
G4PhysicalVolumeModel::UNLIMITED,
|
||||
requestedDepthOfDescent,
|
||||
G4Transform3D(),
|
||||
&mp,
|
||||
useFullExtent);
|
||||
G4PhysicalVolumesSearchScene searchScene
|
||||
(&searchModel, name, copyNo, requestedDepthOfDescent);
|
||||
G4PhysicalVolumesSearchScene searchScene(&searchModel, name, copyNo);
|
||||
searchModel.DescribeYourselfTo (searchScene); // Initiate search.
|
||||
for (const auto& findings: searchScene.GetFindings()) {
|
||||
findingsVector.push_back(findings);
|
||||
@@ -3357,14 +3356,16 @@ void G4VisCommandSceneAddPlotter::SetNewValue (G4UIcommand*, G4String newValue)
|
||||
}
|
||||
|
||||
G4Plotter& _plotter = G4PlotterManager::GetInstance().GetPlotter(newValue);
|
||||
|
||||
G4VModel* model = new G4PlotterModel(_plotter);
|
||||
G4VModel* model = new G4PlotterModel(_plotter,newValue);
|
||||
|
||||
const G4String& currentSceneName = pScene -> GetName ();
|
||||
G4bool successful = pScene -> AddRunDurationModel (model, warn);
|
||||
G4bool successful = pScene -> AddEndOfRunModel(model, warn);
|
||||
if (successful) {
|
||||
if (verbosity >= G4VisManager::confirmations) {
|
||||
G4cout << "Arrow has been added to scene \"" << currentSceneName << "\"." << G4endl;
|
||||
G4cout
|
||||
<< "Plotter \"" << model->GetCurrentDescription()
|
||||
<< "\" has been added to scene \"" << currentSceneName << "\"."
|
||||
<< G4endl;
|
||||
}
|
||||
}
|
||||
else G4VisCommandsSceneAddUnsuccessful(verbosity);
|
||||
|
||||
@@ -243,16 +243,6 @@ void G4VisCommandSceneHandlerCreate::SetNewValue (G4UIcommand* command,
|
||||
}
|
||||
if (!found) {
|
||||
// Shouldn't happen, since graphicsSystem should be a candidate
|
||||
// Use set to get alphabetical order
|
||||
std::set<G4String> candidates;
|
||||
for (const auto gs: fpVisManager -> GetAvailableGraphicsSystems()) {
|
||||
// Just list nicknames, but exclude FALLBACK nicknames
|
||||
for (const auto& nickname: gs->GetNicknames()) {
|
||||
if (!G4StrUtil::contains(nickname, "FALLBACK")) {
|
||||
candidates.insert(nickname);
|
||||
}
|
||||
}
|
||||
}
|
||||
G4ExceptionDescription ed;
|
||||
ed <<
|
||||
"ERROR: G4VisCommandSceneHandlerCreate::SetNewValue:"
|
||||
@@ -260,9 +250,7 @@ void G4VisCommandSceneHandlerCreate::SetNewValue (G4UIcommand* command,
|
||||
<< graphicsSystem
|
||||
<< "\" requested."
|
||||
<< "\n Candidates are:";
|
||||
for (const auto& candidate: candidates) {
|
||||
ed << ' ' << candidate;
|
||||
};
|
||||
fpVisManager->PrintAvailableGraphicsSystems(verbosity,ed);
|
||||
command->CommandFailed(ed);
|
||||
return;
|
||||
}
|
||||
@@ -337,7 +325,7 @@ void G4VisCommandSceneHandlerCreate::SetNewValue (G4UIcommand* command,
|
||||
// If there is an existing viewer, store its view parameters
|
||||
if (fpVisManager->GetCurrentViewer()) {
|
||||
fThereWasAViewer = true;
|
||||
fVPExistingViewer = fpVisManager->GetCurrentViewer()->GetViewParameters();
|
||||
fExistingVP = fpVisManager->GetCurrentViewer()->GetViewParameters();
|
||||
}
|
||||
|
||||
// Set current graphics system in preparation for
|
||||
|
||||
@@ -209,7 +209,8 @@ G4VisCommandSetLineWidth::G4VisCommandSetLineWidth ()
|
||||
G4bool omitable;
|
||||
fpCommand = new G4UIcmdWithADouble("/vis/set/lineWidth", this);
|
||||
fpCommand->SetGuidance
|
||||
("Defines line width for future \"/vis/scene/add/\" commands.");
|
||||
("Defines line width for future \"/vis/scene/add/\" commands."
|
||||
"\nSee \"/vis/viewer/set/lineWidth\" for more information.");
|
||||
fpCommand->SetParameterName ("lineWidth", omitable = true);
|
||||
fpCommand->SetDefaultValue (1.);
|
||||
fpCommand->SetRange("lineWidth >= 1.");
|
||||
@@ -231,11 +232,12 @@ void G4VisCommandSetLineWidth::SetNewValue (G4UIcommand*, G4String newValue)
|
||||
|
||||
fCurrentLineWidth = fpCommand->GetNewDoubleValue(newValue);
|
||||
|
||||
if (verbosity >= G4VisManager::confirmations) {
|
||||
if (verbosity >= G4VisManager::warnings) {
|
||||
G4cout <<
|
||||
"Line width for future \"/vis/scene/add/\" commands has been set to "
|
||||
<< fCurrentLineWidth
|
||||
<< G4endl;
|
||||
"Line width for *future* \"/vis/scene/add/\" commands has been set to "
|
||||
<< fCurrentLineWidth <<
|
||||
"\nSee \"/vis/viewer/set/lineWidth\" for more information."
|
||||
<< G4endl;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -59,10 +59,14 @@ G4VisCommandsTouchable::G4VisCommandsTouchable()
|
||||
// Pick up additional guidance from /vis/viewer/centreAndZoomInOn
|
||||
CopyGuidanceFrom(fpCommandCentreAndZoomInOn,fpCommandCentreOn,1);
|
||||
|
||||
fpCommandDraw = new G4UIcmdWithoutParameter("/vis/touchable/draw",this);
|
||||
fpCommandDraw = new G4UIcmdWithABool("/vis/touchable/draw",this);
|
||||
fpCommandDraw->SetGuidance("Draw touchable.");
|
||||
fpCommandDraw->SetGuidance
|
||||
("If parameter == true, also draw extent as a white wireframe box.");
|
||||
// Pick up additional guidance from /vis/viewer/centreAndZoomInOn
|
||||
CopyGuidanceFrom(fpCommandCentreAndZoomInOn,fpCommandDraw,1);
|
||||
fpCommandDraw->SetParameterName("extent", omitable = true);
|
||||
fpCommandDraw->SetDefaultValue(false);
|
||||
|
||||
fpCommandDump = new G4UIcmdWithoutParameter("/vis/touchable/dump",this);
|
||||
fpCommandDump->SetGuidance("Dump touchable attributes.");
|
||||
@@ -185,7 +189,10 @@ void G4VisCommandsTouchable::SetNewValue
|
||||
}
|
||||
|
||||
if (command == fpCommandCentreOn || command == fpCommandCentreAndZoomInOn) {
|
||||
|
||||
|
||||
// For twinkling...
|
||||
std::vector<std::vector<G4PhysicalVolumeModel::G4PhysicalVolumeNodeID>> touchables;
|
||||
|
||||
G4PhysicalVolumeModel::TouchableProperties properties =
|
||||
G4TouchableUtils::FindTouchableProperties(fCurrentTouchableProperties.fTouchablePath);
|
||||
if (properties.fpTouchablePV) {
|
||||
@@ -198,17 +205,18 @@ void G4VisCommandsTouchable::SetNewValue
|
||||
nullptr, // Modelling parameters (not used)
|
||||
true, // use full extent (prevents calculating own extent, which crashes)
|
||||
properties.fTouchableBaseFullPVPath);
|
||||
touchables.push_back(properties.fTouchableFullPVPath); // Only one in this case
|
||||
// Use a temporary scene in order to find vis extent
|
||||
G4Scene tempScene("Centre Scene");
|
||||
G4bool successful = tempScene.AddRunDurationModel(&tempPVModel,warn);
|
||||
if (successful) {
|
||||
if (verbosity >= G4VisManager::confirmations) {
|
||||
G4cout
|
||||
<< "Touchable " << fCurrentTouchableProperties.fTouchablePath
|
||||
<< ",\n has been added to temporary scene \"" << tempScene.GetName() << "\"."
|
||||
<< G4endl;
|
||||
}
|
||||
if (!successful) return;
|
||||
if (verbosity >= G4VisManager::parameters) {
|
||||
G4cout
|
||||
<< "Touchable " << fCurrentTouchableProperties.fTouchablePath
|
||||
<< ",\n has been added to temporary scene \"" << tempScene.GetName() << "\"."
|
||||
<< G4endl;
|
||||
}
|
||||
|
||||
const G4VisExtent& newExtent = tempScene.GetExtent();
|
||||
const G4ThreeVector& newTargetPoint = newExtent.GetExtentCentre();
|
||||
G4ViewParameters saveVP = currentViewer->GetViewParameters();
|
||||
@@ -222,8 +230,15 @@ void G4VisCommandsTouchable::SetNewValue
|
||||
// Change the target point
|
||||
const G4Point3D& standardTargetPoint = currentScene->GetStandardTargetPoint();
|
||||
newVP.SetCurrentTargetPoint(newTargetPoint - standardTargetPoint);
|
||||
|
||||
// Interpolate
|
||||
InterpolateToNewView(currentViewer, saveVP, newVP);
|
||||
auto keepVerbose = fpVisManager->GetVerbosity();
|
||||
fpVisManager->SetVerboseLevel(G4VisManager::errors);
|
||||
if (newVP != saveVP) InterpolateToNewView(currentViewer, saveVP, newVP);
|
||||
// ...and twinkle
|
||||
Twinkle(currentViewer,newVP,touchables);
|
||||
fpVisManager->SetVerboseLevel(keepVerbose);
|
||||
|
||||
if (verbosity >= G4VisManager::confirmations) {
|
||||
G4cout
|
||||
<< "Viewer \"" << currentViewer->GetName()
|
||||
@@ -238,6 +253,7 @@ void G4VisCommandsTouchable::SetNewValue
|
||||
} else {
|
||||
G4cout << "Touchable not found." << G4endl;
|
||||
}
|
||||
|
||||
return;
|
||||
|
||||
} else if (command == fpCommandDraw) {
|
||||
@@ -267,10 +283,23 @@ void G4VisCommandsTouchable::SetNewValue
|
||||
UImanager->SetVerboseLevel(keepVerbose);
|
||||
|
||||
if (successful) {
|
||||
if (fpCommandDraw->GetNewBoolValue(newValue)) {
|
||||
const auto& extent = pvModel->GetExtent();
|
||||
const G4double halfX = (extent.GetXmax()-extent.GetXmin())/2.;
|
||||
const G4double halfY = (extent.GetYmax()-extent.GetYmin())/2.;
|
||||
const G4double halfZ = (extent.GetZmax()-extent.GetZmin())/2.;
|
||||
G4Box extentBox("extent",halfX,halfY,halfZ);
|
||||
G4VisAttributes extentVA;
|
||||
extentVA.SetForceWireframe();
|
||||
fpVisManager->Draw(extentBox,extentVA,G4Translate3D(extent.GetExtentCentre()));
|
||||
}
|
||||
if (verbosity >= G4VisManager::confirmations) {
|
||||
G4cout << "\"" << properties.fpTouchablePV->GetName()
|
||||
<< "\", copy no. " << properties.fCopyNo << " drawn"
|
||||
<< G4endl;
|
||||
<< "\", copy no. " << properties.fCopyNo << " drawn";
|
||||
if (fpCommandDraw->GetNewBoolValue(newValue)) {
|
||||
G4cout << " with extent box";
|
||||
}
|
||||
G4cout << '.' << G4endl;
|
||||
}
|
||||
} else {
|
||||
G4VisCommandsSceneAddUnsuccessful(verbosity);
|
||||
@@ -298,8 +327,9 @@ void G4VisCommandsTouchable::SetNewValue
|
||||
std::vector<G4AttValue>* attValues = tempPVModel.CreateCurrentAttValues();
|
||||
G4cout << G4AttCheck(attValues,attDefs);
|
||||
delete attValues;
|
||||
G4Polyhedron* polyhedron =
|
||||
properties.fpTouchablePV->GetLogicalVolume()->GetSolid()->GetPolyhedron();
|
||||
const auto lv = properties.fpTouchablePV->GetLogicalVolume();
|
||||
const auto polyhedron = lv->GetSolid()->GetPolyhedron();
|
||||
polyhedron->SetVisAttributes(lv->GetVisAttributes());
|
||||
G4cout << "\nLocal polyhedron coordinates:\n" << *polyhedron;
|
||||
const G4Transform3D& transform = tempPVModel.GetCurrentTransform();
|
||||
polyhedron->Transform(transform);
|
||||
|
||||
@@ -234,8 +234,12 @@ void G4VisCommandViewerCentreOn::SetNewValue (G4UIcommand* command, G4String new
|
||||
return;
|
||||
}
|
||||
|
||||
// A vector of found paths so that we can highlight (twinkle) the found volume(s).
|
||||
std::vector<std::vector<G4PhysicalVolumeModel::G4PhysicalVolumeNodeID>> foundPaths;
|
||||
|
||||
// Use a temporary scene in order to find vis extent
|
||||
G4Scene tempScene("Centre Scene");
|
||||
G4bool successfullyAdded = true;
|
||||
for (const auto& findings: findingsVector) {
|
||||
// To handle paramaterisations we have to set the copy number
|
||||
findings.fpFoundPV->SetCopyNo(findings.fFoundPVCopyNo);
|
||||
@@ -250,29 +254,33 @@ void G4VisCommandViewerCentreOn::SetNewValue (G4UIcommand* command, G4String new
|
||||
true, // Use full extent
|
||||
findings.fFoundBasePVPath);
|
||||
// ...and add it to the scene.
|
||||
G4bool successful = tempScene.AddRunDurationModel(tempPVModel,warn);
|
||||
if (successful) {
|
||||
if (verbosity >= G4VisManager::confirmations) {
|
||||
G4cout << "\"" << findings.fpFoundPV->GetName()
|
||||
<< "\", copy no. " << findings.fFoundPVCopyNo
|
||||
<< ",\n found in searched volume \""
|
||||
<< findings.fpSearchPV->GetName()
|
||||
<< "\" at depth " << findings.fFoundDepth
|
||||
<< ",\n base path: \"" << findings.fFoundBasePVPath
|
||||
<< ",\n has been added to temporary scene \"" << tempScene.GetName() << "\"."
|
||||
<< G4endl;
|
||||
}
|
||||
auto successful = tempScene.AddRunDurationModel(tempPVModel,warn);
|
||||
if (!successful) {
|
||||
successfullyAdded = false;
|
||||
continue;
|
||||
}
|
||||
if (verbosity >= G4VisManager::parameters) {
|
||||
G4cout << "\"" << findings.fpFoundPV->GetName()
|
||||
<< "\", copy no. " << findings.fFoundPVCopyNo
|
||||
<< ",\n found in searched volume \""
|
||||
<< findings.fpSearchPV->GetName()
|
||||
<< "\" at depth " << findings.fFoundDepth
|
||||
<< ",\n base path: \"" << findings.fFoundBasePVPath
|
||||
<< ",\n has been added to temporary scene \"" << tempScene.GetName() << "\"."
|
||||
<< G4endl;
|
||||
}
|
||||
foundPaths.push_back(findings.fFoundFullPVPath);
|
||||
}
|
||||
// Delete temporary physical volume models
|
||||
for (const auto& sceneModel: tempScene.GetRunDurationModelList()) {
|
||||
delete sceneModel.fpModel;
|
||||
}
|
||||
|
||||
if (!successfullyAdded) return;
|
||||
|
||||
// Relevant results
|
||||
const G4VisExtent& newExtent = tempScene.GetExtent();
|
||||
const G4ThreeVector& newTargetPoint = newExtent.GetExtentCentre();
|
||||
|
||||
|
||||
G4Scene* currentScene = currentViewer->GetSceneHandler()->GetScene();
|
||||
G4ViewParameters saveVP = currentViewer->GetViewParameters();
|
||||
G4ViewParameters newVP = saveVP;
|
||||
@@ -285,8 +293,17 @@ void G4VisCommandViewerCentreOn::SetNewValue (G4UIcommand* command, G4String new
|
||||
// Change the target point
|
||||
const G4Point3D& standardTargetPoint = currentScene->GetStandardTargetPoint();
|
||||
newVP.SetCurrentTargetPoint(newTargetPoint - standardTargetPoint);
|
||||
// Interpolate
|
||||
InterpolateToNewView(currentViewer, saveVP, newVP);
|
||||
|
||||
// If this particular view is simple enough
|
||||
if (currentViewer->GetKernelVisitElapsedTimeSeconds() < 0.1) {
|
||||
// Interpolate
|
||||
auto keepVerbose = fpVisManager->GetVerbosity();
|
||||
fpVisManager->SetVerboseLevel(G4VisManager::errors);
|
||||
if (newVP != saveVP) InterpolateToNewView(currentViewer, saveVP, newVP);
|
||||
// ...and twinkle
|
||||
Twinkle(currentViewer,newVP,foundPaths);
|
||||
fpVisManager->SetVerboseLevel(keepVerbose);
|
||||
}
|
||||
|
||||
if (verbosity >= G4VisManager::confirmations) {
|
||||
G4cout
|
||||
@@ -297,8 +314,8 @@ void G4VisCommandViewerCentreOn::SetNewValue (G4UIcommand* command, G4String new
|
||||
}
|
||||
G4cout << " on physical volume(s) \"" << pvName << '\"'
|
||||
<< G4endl;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
SetViewParameters(currentViewer, newVP);
|
||||
}
|
||||
|
||||
@@ -890,13 +907,35 @@ G4VisCommandViewerCreate::G4VisCommandViewerCreate (): fId (0) {
|
||||
G4bool omitable;
|
||||
fpCommand = new G4UIcommand ("/vis/viewer/create", this);
|
||||
fpCommand -> SetGuidance
|
||||
("Creates a viewer for the specified scene handler.");
|
||||
("Creates a viewer. If the scene handler name is specified, then a"
|
||||
"\nviewer of that scene handler is created. Otherwise, a viewer"
|
||||
"\nof the current scene handler is created.");
|
||||
fpCommand -> SetGuidance
|
||||
("Default scene handler is the current scene handler. Invents a name"
|
||||
"\nif not supplied. (Note: the system adds information to the name"
|
||||
"\nfor identification - only the characters up to the first blank are"
|
||||
"\nused for removing, selecting, etc.) This scene handler and viewer"
|
||||
"\nbecome current.");
|
||||
("If the viewer name is not specified a name is generated from the name"
|
||||
"\nof the scene handler and a serial number.");
|
||||
fpCommand -> SetGuidance("The scene handler and viewer become current.");
|
||||
fpCommand -> SetGuidance
|
||||
("(Note: the system adds the graphics system name to the viewer name"
|
||||
"\nfor identification, but for selecting, copying, etc., only characters"
|
||||
"\nup to the first blank are used. For example, if the viewer name is"
|
||||
"\n\"viewer-0 (G4OpenGLStoredQt)\", it may be referenced by \"viewer-0\","
|
||||
"\nfor example in \"/vis/viewer/select viewer-0\".)");
|
||||
fpCommand -> SetGuidance
|
||||
("Window size and placement hints, e.g. 600x600-100+100 (in pixels):");
|
||||
fpCommand -> SetGuidance
|
||||
("- single number, e.g., \"600\": square window;");
|
||||
fpCommand -> SetGuidance
|
||||
("- two numbers, e.g., \"800x600\": rectangluar window;");
|
||||
fpCommand -> SetGuidance
|
||||
("- two numbers plus placement hint, e.g., \"600x600-100+100\" places window of size"
|
||||
"\n 600x600 100 pixels left and 100 pixels down from top right corner.");
|
||||
fpCommand -> SetGuidance
|
||||
("- If not specified, the default is \"600\", i.e., 600 pixels square, placed"
|
||||
"\n at the window manager's discretion...or picked up from the previous viewer.");
|
||||
fpCommand -> SetGuidance
|
||||
("- This is an X-Windows-type geometry string, see:"
|
||||
"\n https://en.wikibooks.org/wiki/Guide_to_X11/Starting_Programs,"
|
||||
"\n \"Specifying window geometry\".");
|
||||
G4UIparameter* parameter;
|
||||
parameter = new G4UIparameter ("scene-handler", 's', omitable = true);
|
||||
parameter -> SetCurrentAsDefault (true);
|
||||
@@ -905,10 +944,7 @@ G4VisCommandViewerCreate::G4VisCommandViewerCreate (): fId (0) {
|
||||
parameter -> SetCurrentAsDefault (true);
|
||||
fpCommand -> SetParameter (parameter);
|
||||
parameter = new G4UIparameter ("window-size-hint", 's', omitable = true);
|
||||
parameter->SetGuidance
|
||||
("integer (pixels) for square window placed by window manager or"
|
||||
" X-Windows-type geometry string, e.g. 600x600-100+100");
|
||||
parameter->SetDefaultValue("600");
|
||||
parameter -> SetDefaultValue("none");
|
||||
fpCommand -> SetParameter (parameter);
|
||||
}
|
||||
|
||||
@@ -936,17 +972,13 @@ G4String G4VisCommandViewerCreate::GetCurrentValue (G4UIcommand*) {
|
||||
fpVisManager -> GetCurrentSceneHandler ();
|
||||
if (currentSceneHandler) {
|
||||
currentValue = currentSceneHandler -> GetName ();
|
||||
}
|
||||
else {
|
||||
} else {
|
||||
currentValue = "none";
|
||||
}
|
||||
currentValue += ' ';
|
||||
currentValue += '"';
|
||||
currentValue += NextName ();
|
||||
currentValue += '"';
|
||||
|
||||
currentValue += " 600"; // Default number of pixels for window size hint.
|
||||
|
||||
return currentValue;
|
||||
}
|
||||
|
||||
@@ -1032,36 +1064,43 @@ void G4VisCommandViewerCreate::SetNewValue (G4UIcommand* command, G4String newVa
|
||||
}
|
||||
}
|
||||
|
||||
// If there was an existing viewer, use its view parameters
|
||||
if (fThereWasAViewer) {
|
||||
// OK, we're going to use its view parameters below
|
||||
} else {
|
||||
// There wasn't one...but if there now is...
|
||||
if (fpVisManager->GetCurrentViewer()) {
|
||||
fThereWasAViewer = true;
|
||||
fVPExistingViewer = fpVisManager->GetCurrentViewer()->GetViewParameters();
|
||||
// ...and if it's still current...
|
||||
auto existingViewer = fpVisManager->GetCurrentViewer();
|
||||
if (existingViewer) {
|
||||
// ...bring view parameters up to date...
|
||||
fExistingVP = existingViewer->GetViewParameters();
|
||||
}
|
||||
}
|
||||
|
||||
// WindowSizeHint and XGeometryString are picked up from the vis
|
||||
// manager in the G4VViewer constructor. In G4VisManager, after Viewer
|
||||
// creation, we will store theses parameters in G4ViewParameters.
|
||||
if (fThereWasAViewer && windowSizeHintString == "none") {
|
||||
// The user did not specify a window size hint - get from existing VPs
|
||||
windowSizeHintString = fExistingVP.GetXGeometryString();
|
||||
}
|
||||
|
||||
fpVisManager -> CreateViewer (newName,windowSizeHintString);
|
||||
|
||||
// Now we have a new viewer
|
||||
G4VViewer* newViewer = fpVisManager -> GetCurrentViewer ();
|
||||
|
||||
if (newViewer && newViewer -> GetName () == newName) {
|
||||
if (fThereWasAViewer) {
|
||||
G4ViewParameters vp = newViewer->GetViewParameters();
|
||||
CopyMostViewParameters(vp, fVPExistingViewer);
|
||||
fpVisManager->GetCurrentViewer()->SetViewParameters(vp);
|
||||
// Copy view parameters from existing viewer, except for...
|
||||
fExistingVP.SetAutoRefresh(vp.IsAutoRefresh());
|
||||
fExistingVP.SetBackgroundColour(vp.GetBackgroundColour());
|
||||
// ...including window hint paramaters that have been set already above...
|
||||
fExistingVP.SetXGeometryString(vp.GetXGeometryString());
|
||||
vp = fExistingVP;
|
||||
newViewer->SetViewParameters(vp);
|
||||
}
|
||||
if (verbosity >= G4VisManager::confirmations) {
|
||||
G4cout << "New viewer \"" << newName << "\" created." << G4endl;
|
||||
}
|
||||
}
|
||||
else {
|
||||
// Keep for next time...
|
||||
fThereWasAViewer = true;
|
||||
fExistingVP = fpVisManager->GetCurrentViewer()->GetViewParameters();
|
||||
} else {
|
||||
G4ExceptionDescription ed;
|
||||
if (newViewer) {
|
||||
ed << "ERROR: New viewer doesn\'t match!!! Curious!!";
|
||||
@@ -1815,6 +1854,55 @@ void G4VisCommandViewerReset::SetNewValue (G4UIcommand*, G4String newValue) {
|
||||
RefreshIfRequired(viewer);
|
||||
}
|
||||
|
||||
////////////// /vis/viewer/resetCameraParameters ///////////////////////////////////////
|
||||
|
||||
G4VisCommandViewerResetCameraParameters::G4VisCommandViewerResetCameraParameters () {
|
||||
G4bool omitable, currentAsDefault;
|
||||
fpCommand = new G4UIcmdWithAString ("/vis/viewer/resetCameraParameters", this);
|
||||
fpCommand -> SetGuidance ("Resets only the camera parameters.");
|
||||
fpCommand -> SetGuidance
|
||||
("By default, acts on current viewer. \"/vis/viewer/list\""
|
||||
"\nto see possible viewers. Viewer becomes current.");
|
||||
fpCommand -> SetParameterName ("viewer-name",
|
||||
omitable = true,
|
||||
currentAsDefault = true);
|
||||
}
|
||||
|
||||
G4VisCommandViewerResetCameraParameters::~G4VisCommandViewerResetCameraParameters () {
|
||||
delete fpCommand;
|
||||
}
|
||||
|
||||
G4String G4VisCommandViewerResetCameraParameters::GetCurrentValue (G4UIcommand*) {
|
||||
G4VViewer* viewer = fpVisManager -> GetCurrentViewer ();
|
||||
if (viewer) {
|
||||
return viewer -> GetName ();
|
||||
}
|
||||
else {
|
||||
return "none";
|
||||
}
|
||||
}
|
||||
|
||||
void G4VisCommandViewerResetCameraParameters::SetNewValue (G4UIcommand*, G4String newValue) {
|
||||
|
||||
G4VisManager::Verbosity verbosity = fpVisManager->GetVerbosity();
|
||||
|
||||
G4String& resetName = newValue;
|
||||
G4VViewer* viewer = fpVisManager -> GetViewer (resetName);
|
||||
if (!viewer) {
|
||||
if (verbosity >= G4VisManager::errors) {
|
||||
G4cerr << "ERROR: Viewer \"" << resetName
|
||||
<< "\" not found - \"/vis/viewer/list\" to see possibilities."
|
||||
<< G4endl;
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
G4ViewParameters newVP = viewer->GetViewParameters();
|
||||
CopyCameraParameters(newVP,viewer->GetDefaultViewParameters());
|
||||
viewer->SetViewParameters(newVP);
|
||||
RefreshIfRequired(viewer);
|
||||
}
|
||||
|
||||
////////////// /vis/viewer/save ///////////////////////////////////////
|
||||
|
||||
G4VisCommandViewerSave::G4VisCommandViewerSave () {
|
||||
|
||||
@@ -30,6 +30,7 @@
|
||||
#include "G4VisCommandsViewerSet.hh"
|
||||
|
||||
#include "G4UIcommand.hh"
|
||||
#include "G4UIcmdWithoutParameter.hh"
|
||||
#include "G4UIcmdWithAString.hh"
|
||||
#include "G4UIcmdWithABool.hh"
|
||||
#include "G4UIcmdWithAnInteger.hh"
|
||||
@@ -282,6 +283,13 @@ fViewpointVector (G4ThreeVector(0.,0.,1.))
|
||||
fpCommandLineSegments->SetParameterName("line-segments",omitable = true);
|
||||
fpCommandLineSegments->SetDefaultValue(24);
|
||||
|
||||
fpCommandLineWidth = new G4UIcmdWithoutParameter
|
||||
("/vis/viewer/set/lineWidth",this);
|
||||
fpCommandLineWidth->SetGuidance
|
||||
("Use \"/vis/viewer/set/globalLineWidthScale\" instead."
|
||||
"\nFor trajectories use \"/vis/modeling/trajectories/*/default/setLineWidth\"."
|
||||
"\nFor volumes use \"/vis/geometry/set/lineWidth\".");
|
||||
|
||||
fpCommandNumberOfCloudPoints = new G4UIcmdWithAnInteger
|
||||
("/vis/viewer/set/numberOfCloudPoints",this);
|
||||
fpCommandNumberOfCloudPoints->SetGuidance
|
||||
@@ -371,10 +379,18 @@ fViewpointVector (G4ThreeVector(0.,0.,1.))
|
||||
fpCommandSpecialMeshRendering = new G4UIcmdWithABool
|
||||
("/vis/viewer/set/specialMeshRendering",this);
|
||||
fpCommandSpecialMeshRendering -> SetGuidance
|
||||
("Request special rendering of volumes (meshes) that use G4VNestedParameterisation.");
|
||||
("Request special rendering of volumes (meshes) that use G4VParameterisation.");
|
||||
fpCommandSpecialMeshRendering->SetParameterName("render",omitable = true);
|
||||
fpCommandSpecialMeshRendering->SetDefaultValue(true);
|
||||
|
||||
fpCommandSpecialMeshRenderingOption = new G4UIcmdWithAString
|
||||
("/vis/viewer/set/specialMeshRenderingOption",this);
|
||||
fpCommandSpecialMeshRenderingOption->SetGuidance
|
||||
("Set special mesh rendering option - \"dots\" or \"surfaces\".");
|
||||
fpCommandSpecialMeshRenderingOption->SetParameterName ("option",omitable = true);
|
||||
fpCommandSpecialMeshRenderingOption->SetCandidates("dots surfaces");
|
||||
fpCommandSpecialMeshRenderingOption->SetDefaultValue("dots");
|
||||
|
||||
fpCommandSpecialMeshVolumes = new G4UIcommand
|
||||
("/vis/viewer/set/specialMeshVolumes",this);
|
||||
fpCommandSpecialMeshVolumes -> SetGuidance
|
||||
@@ -630,12 +646,14 @@ G4VisCommandsViewerSet::~G4VisCommandsViewerSet() {
|
||||
delete fpCommandTargetPoint;
|
||||
delete fpCommandStyle;
|
||||
delete fpCommandSpecialMeshVolumes;
|
||||
delete fpCommandSpecialMeshRenderingOption;
|
||||
delete fpCommandSpecialMeshRendering;
|
||||
delete fpCommandSectionPlane;
|
||||
delete fpCommandRotationStyle;
|
||||
delete fpCommandProjection;
|
||||
delete fpCommandPicking;
|
||||
delete fpCommandNumberOfCloudPoints;
|
||||
delete fpCommandLineWidth;
|
||||
delete fpCommandLineSegments;
|
||||
delete fpCommandLightsVector;
|
||||
delete fpCommandLightsThetaPhi;
|
||||
@@ -698,7 +716,11 @@ void G4VisCommandsViewerSet::SetNewValue
|
||||
return;
|
||||
}
|
||||
// Copy view parameters except for autoRefresh and background...
|
||||
CopyMostViewParameters(vp, fromViewer->GetViewParameters());
|
||||
auto keepAutoRefresh = vp.IsAutoRefresh();
|
||||
auto keepBackground = vp.GetBackgroundColour();
|
||||
vp = fromViewer->GetViewParameters();
|
||||
vp.SetAutoRefresh(keepAutoRefresh);
|
||||
vp.SetBackgroundColour(keepBackground);
|
||||
// Concatenate any private vis attributes modifiers...
|
||||
const std::vector<G4ModelingParameters::VisAttributesModifier>*
|
||||
privateVAMs = fromViewer->GetPrivateVisAttributesModifiers();
|
||||
@@ -1076,6 +1098,13 @@ void G4VisCommandsViewerSet::SetNewValue
|
||||
}
|
||||
}
|
||||
|
||||
else if (command == fpCommandLineWidth) {
|
||||
if (verbosity >= G4VisManager::errors) {
|
||||
// A do-nothing command
|
||||
G4cerr << command->GetGuidanceLine(0) << G4endl;
|
||||
}
|
||||
}
|
||||
|
||||
else if (command == fpCommandLineSegments) {
|
||||
G4int nSides = G4UIcommand::ConvertToInt(newValue);
|
||||
nSides = vp.SetNoOfSides(nSides);
|
||||
@@ -1222,13 +1251,38 @@ void G4VisCommandsViewerSet::SetNewValue
|
||||
else if (command == fpCommandSpecialMeshRendering) {
|
||||
vp.SetSpecialMeshRendering(G4UIcommand::ConvertToBool(newValue));
|
||||
if (verbosity >= G4VisManager::confirmations) {
|
||||
G4cout << "Special mesh rendering ";
|
||||
if (vp.IsSpecialMeshRendering()) G4cout << "requested.";
|
||||
else G4cout << "inhibited.";
|
||||
G4cout << "Special mesh rendering";
|
||||
if (vp.IsSpecialMeshRendering()) {
|
||||
G4cout << " requested. Current option is \""
|
||||
<< vp.GetSpecialMeshRenderingOption() << "\" for ";
|
||||
if (vp.GetSpecialMeshVolumes().empty()) {
|
||||
G4cout << "any mesh.";
|
||||
} else{
|
||||
G4cout << "selected volumes:";
|
||||
for (const auto& pvNameCopyNo: vp.GetSpecialMeshVolumes()) {
|
||||
G4cout << "\n " << pvNameCopyNo.GetName();
|
||||
if (pvNameCopyNo.GetCopyNo() >= 0) G4cout << ':' << pvNameCopyNo.GetCopyNo();
|
||||
}
|
||||
}
|
||||
}
|
||||
else G4cout << ": off.";
|
||||
G4cout << G4endl;
|
||||
}
|
||||
}
|
||||
|
||||
else if (command == fpCommandSpecialMeshRenderingOption) {
|
||||
G4ViewParameters::SMROption option = G4ViewParameters::meshAsDots;
|
||||
if (newValue == "surfaces") {
|
||||
option = G4ViewParameters::meshAsSurfaces;
|
||||
}
|
||||
vp.SetSpecialMeshRenderingOption(option);
|
||||
if (verbosity >= G4VisManager::confirmations) {
|
||||
G4cout << "Special mesh rendering option set to \""
|
||||
<< vp.GetSpecialMeshRenderingOption() << "\"."
|
||||
<< G4endl;
|
||||
}
|
||||
}
|
||||
|
||||
else if (command == fpCommandSpecialMeshVolumes) {
|
||||
std::vector<G4ModelingParameters::PVNameCopyNo> requestedMeshes;
|
||||
if (newValue.empty()) {
|
||||
|
||||
@@ -95,32 +95,34 @@ G4VisManager* G4VisManager::fpInstance = 0;
|
||||
|
||||
G4VisManager::Verbosity G4VisManager::fVerbosity = G4VisManager::warnings;
|
||||
|
||||
G4VisManager::G4VisManager (const G4String& verbosityString):
|
||||
fVerbose (1),
|
||||
fInitialised (false),
|
||||
fpGraphicsSystem (0),
|
||||
fpScene (0),
|
||||
fpSceneHandler (0),
|
||||
fpViewer (0),
|
||||
fpStateDependent (0),
|
||||
fEventRefreshing (false),
|
||||
fTransientsDrawnThisRun (false),
|
||||
fTransientsDrawnThisEvent (false),
|
||||
fNoOfEventsDrawnThisRun (0),
|
||||
fNKeepRequests (0),
|
||||
fEventKeepingSuspended (false),
|
||||
fDrawEventOnlyIfToBeKept (false),
|
||||
fpRequestedEvent (0),
|
||||
fReviewingKeptEvents (false),
|
||||
fAbortReviewKeptEvents (false),
|
||||
fIsDrawGroup (false),
|
||||
fDrawGroupNestingDepth (0),
|
||||
fIgnoreStateChanges (false)
|
||||
G4VisManager::G4VisManager (const G4String& verbosityString)
|
||||
: fVerbose (1)
|
||||
, fInitialised (false)
|
||||
, fpGraphicsSystem (0)
|
||||
, fpScene (0)
|
||||
, fpSceneHandler (0)
|
||||
, fpViewer (0)
|
||||
, fpStateDependent (0)
|
||||
, fEventRefreshing (false)
|
||||
, fTransientsDrawnThisRun (false)
|
||||
, fTransientsDrawnThisEvent (false)
|
||||
, fNoOfEventsDrawnThisRun (0)
|
||||
, fNKeepRequests (0)
|
||||
, fEventKeepingSuspended (false)
|
||||
, fDrawEventOnlyIfToBeKept (false)
|
||||
, fpRequestedEvent (0)
|
||||
, fReviewingKeptEvents (false)
|
||||
, fAbortReviewKeptEvents (false)
|
||||
, fReviewingPlots (false)
|
||||
, fAbortReviewPlots (false)
|
||||
, fIsDrawGroup (false)
|
||||
, fDrawGroupNestingDepth (0)
|
||||
, fIgnoreStateChanges (false)
|
||||
#ifdef G4MULTITHREADED
|
||||
, fMaxEventQueueSize (100)
|
||||
, fWaitOnEventQueueFull (true)
|
||||
#endif
|
||||
// All other objects use default constructors.
|
||||
// All other objects use default constructors.
|
||||
{
|
||||
fpTrajDrawModelMgr = new G4VisModelManager<G4VTrajectoryModel>("/vis/modeling/trajectories");
|
||||
fpTrajFilterMgr = new G4VisFilterManager<G4VTrajectory>("/vis/filtering/trajectories");
|
||||
@@ -189,8 +191,9 @@ G4VisManager::G4VisManager (const G4String& verbosityString):
|
||||
// ...
|
||||
|
||||
// Make top level command directory...
|
||||
// Vis commands should *not* be broadcast to threads (2nd argument).
|
||||
auto directory = new G4UIdirectory ("/vis/",false);
|
||||
// vis commands should *not* be broadcast to workers
|
||||
G4bool propagateToWorkers;
|
||||
auto directory = new G4UIdirectory ("/vis/",propagateToWorkers=false);
|
||||
directory -> SetGuidance ("Visualization commands.");
|
||||
// Request commands in name order
|
||||
directory -> Sort(); // Ordering propagates to sub-directories
|
||||
@@ -600,6 +603,7 @@ void G4VisManager::RegisterMessengers () {
|
||||
RegisterMessenger(new G4VisCommandViewerRebuild);
|
||||
RegisterMessenger(new G4VisCommandViewerRefresh);
|
||||
RegisterMessenger(new G4VisCommandViewerReset);
|
||||
RegisterMessenger(new G4VisCommandViewerResetCameraParameters);
|
||||
RegisterMessenger(new G4VisCommandViewerSave);
|
||||
RegisterMessenger(new G4VisCommandViewerScale);
|
||||
RegisterMessenger(new G4VisCommandViewerSelect);
|
||||
@@ -623,6 +627,7 @@ void G4VisManager::RegisterMessengers () {
|
||||
// (i.e., commands that invoke other commands) are instantiated here.
|
||||
|
||||
RegisterMessenger(new G4VisCommandAbortReviewKeptEvents);
|
||||
RegisterMessenger(new G4VisCommandAbortReviewPlots);
|
||||
RegisterMessenger(new G4VisCommandDrawOnlyToBeKeptEvents);
|
||||
RegisterMessenger(new G4VisCommandDrawTree);
|
||||
RegisterMessenger(new G4VisCommandDrawView);
|
||||
@@ -631,7 +636,9 @@ void G4VisManager::RegisterMessengers () {
|
||||
RegisterMessenger(new G4VisCommandEnable);
|
||||
RegisterMessenger(new G4VisCommandList);
|
||||
RegisterMessenger(new G4VisCommandOpen);
|
||||
RegisterMessenger(new G4VisCommandPlot);
|
||||
RegisterMessenger(new G4VisCommandReviewKeptEvents);
|
||||
RegisterMessenger(new G4VisCommandReviewPlots);
|
||||
RegisterMessenger(new G4VisCommandSpecify);
|
||||
|
||||
// List manager commands
|
||||
@@ -659,6 +666,60 @@ void G4VisManager::RegisterMessengers () {
|
||||
(fpDigiFilterMgr, fpDigiFilterMgr->Placement()));
|
||||
}
|
||||
|
||||
#include <tools/histo/h1d>
|
||||
#include <tools/histo/h2d>
|
||||
|
||||
namespace {
|
||||
template <typename HT> // tools::histo::h1d, etc
|
||||
G4bool PrintListOfHnPlots(const G4String& plotType) { // h1, etc.
|
||||
auto ui = G4UImanager::GetUIpointer();
|
||||
G4bool thereArePlots = false;
|
||||
auto keepControlVerbose = ui->GetVerboseLevel();
|
||||
ui->SetVerboseLevel(0);
|
||||
auto status = ui->ApplyCommand("/analysis/" + plotType + "/getVector");
|
||||
ui->SetVerboseLevel(keepControlVerbose);
|
||||
if(status==G4UIcommandStatus::fCommandSucceeded) {
|
||||
G4String hexString = ui->GetCurrentValues(G4String("/analysis/" + plotType + "/getVector"));
|
||||
if(hexString.size()) {
|
||||
void* ptr;
|
||||
std::istringstream is(hexString);
|
||||
is >> ptr;
|
||||
auto _v = (const std::vector<HT*>*)ptr;
|
||||
auto _n = _v->size();
|
||||
if (_n > 0) {
|
||||
thereArePlots = true;
|
||||
G4String isare("are"),plural("s");
|
||||
if (_n == 1) {isare = "is"; plural = "";}
|
||||
G4cout <<
|
||||
"There " << isare << ' ' << _n << ' ' << plotType << " histogram" << plural
|
||||
<< G4endl;
|
||||
if (_n <= 5) {
|
||||
for (size_t i = 0; i < _n; ++i) {
|
||||
const auto& _h = (*_v)[i];
|
||||
G4cout
|
||||
<< std::setw(3) << i
|
||||
<< " with " << std::setw(6) << _h->entries() << " entries: "
|
||||
<< _h->get_title() << G4endl;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
return thereArePlots;
|
||||
}
|
||||
void PrintListOfPlots() {
|
||||
G4bool thereArePlots = false;
|
||||
if (PrintListOfHnPlots<tools::histo::h1d>("h1")) thereArePlots = true;
|
||||
if (PrintListOfHnPlots<tools::histo::h2d>("h2")) thereArePlots = true;
|
||||
if (thereArePlots) {
|
||||
G4cout <<
|
||||
"List them with \"/analysis/list\"."
|
||||
"\nView them with \"/vis/plot\" or \"/vis/reviewPlots\"."
|
||||
<< G4endl;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void G4VisManager::Enable() {
|
||||
if (IsValidView ()) {
|
||||
SetConcreteInstance(this);
|
||||
@@ -669,11 +730,18 @@ void G4VisManager::Enable() {
|
||||
G4int nKeptEvents = 0;
|
||||
const G4Run* run = G4RunManager::GetRunManager()->GetCurrentRun();
|
||||
if (run) nKeptEvents = run->GetEventVector()->size();
|
||||
G4String isare("are"),plural("s");
|
||||
if (nKeptEvents == 1) {isare = "is"; plural = "";}
|
||||
G4cout <<
|
||||
"There are " << nKeptEvents << " kept events."
|
||||
"\n \"/vis/reviewKeptEvents\" to review them one by one."
|
||||
"\n \"/vis/viewer/flush\" or \"/vis/viewer/rebuild\" to see them accumulated."
|
||||
"There " << isare << ' ' << nKeptEvents << " kept event" << plural << '.'
|
||||
<< G4endl;
|
||||
if (nKeptEvents > 0) {
|
||||
G4cout <<
|
||||
" \"/vis/reviewKeptEvents\" to review one by one."
|
||||
"\n To see accumulated, \"/vis/enable\", then \"/vis/viewer/flush\" or \"/vis/viewer/rebuild\"."
|
||||
<< G4endl;
|
||||
}
|
||||
PrintListOfPlots();
|
||||
}
|
||||
}
|
||||
else {
|
||||
@@ -1293,14 +1361,26 @@ void G4VisManager::GeometryHasChanged () {
|
||||
|
||||
if (modelList.size () == 0) {
|
||||
if (fVerbosity >= warnings) {
|
||||
G4cout << "WARNING: No models left in this scene \""
|
||||
G4cout << "WARNING: No run-duration models left in this scene \""
|
||||
<< pScene -> GetName ()
|
||||
<< "\"."
|
||||
<< G4endl;
|
||||
}
|
||||
if (pWorld) {
|
||||
if (fVerbosity >= warnings) {
|
||||
G4cout << " Adding current world to \""
|
||||
<< pScene -> GetName ()
|
||||
<< "\"."
|
||||
<< G4endl;
|
||||
}
|
||||
pScene->AddRunDurationModel(new G4PhysicalVolumeModel(pWorld),fVerbosity>=warnings);
|
||||
// (The above includes a re-calculation of the extent.)
|
||||
G4UImanager::GetUIpointer () ->
|
||||
ApplyCommand (G4String("/vis/scene/notifyHandlers " + pScene->GetName()));
|
||||
}
|
||||
}
|
||||
else {
|
||||
pScene->CalculateExtent();
|
||||
pScene->CalculateExtent(); // Recalculate extent
|
||||
G4UImanager::GetUIpointer () ->
|
||||
ApplyCommand (G4String("/vis/scene/notifyHandlers " + pScene->GetName()));
|
||||
}
|
||||
@@ -1620,31 +1700,32 @@ void G4VisManager::SetCurrentViewer (G4VViewer* pViewer) {
|
||||
}
|
||||
}
|
||||
|
||||
void G4VisManager::PrintAvailableGraphicsSystems (Verbosity verbosity) const
|
||||
void G4VisManager::PrintAvailableGraphicsSystems
|
||||
(Verbosity verbosity, std::ostream& out) const
|
||||
{
|
||||
G4cout << "Registered graphics systems are:\n";
|
||||
out << "Registered graphics systems are:\n";
|
||||
if (fAvailableGraphicsSystems.size ()) {
|
||||
for (const auto& gs: fAvailableGraphicsSystems) {
|
||||
const G4String& name = gs->GetName();
|
||||
const std::vector<G4String>& nicknames = gs->GetNicknames();
|
||||
if (verbosity <= warnings) {
|
||||
// Brief output
|
||||
G4cout << " " << name << " (";
|
||||
out << " " << name << " (";
|
||||
for (size_t i = 0; i < nicknames.size(); ++i) {
|
||||
if (i != 0) {
|
||||
G4cout << ", ";
|
||||
out << ", ";
|
||||
}
|
||||
G4cout << nicknames[i];
|
||||
out << nicknames[i];
|
||||
}
|
||||
G4cout << ')';
|
||||
out << ')';
|
||||
} else {
|
||||
// Full output
|
||||
G4cout << *gs;
|
||||
out << *gs;
|
||||
}
|
||||
G4cout << G4endl;
|
||||
out << G4endl;
|
||||
}
|
||||
} else {
|
||||
G4cout << " NONE!!! None registered - yet! Mmmmm!" << G4endl;
|
||||
out << " NONE!!! None registered - yet! Mmmmm!" << G4endl;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1984,12 +2065,6 @@ void G4VisManager::EndOfEvent ()
|
||||
|
||||
if (!GetConcreteInstance()) return;
|
||||
|
||||
// Don't call IsValidView unless there is a scene handler. This
|
||||
// avoids WARNING message at end of event and run when the user has
|
||||
// not instantiated a scene handler, e.g., in batch mode.
|
||||
G4bool valid = fpSceneHandler && IsValidView();
|
||||
if (!valid) return;
|
||||
|
||||
// G4cout << "G4VisManager::EndOfEvent: thread: "
|
||||
// << G4Threading::G4GetThreadId() << G4endl;
|
||||
|
||||
@@ -1999,6 +2074,12 @@ void G4VisManager::EndOfEvent ()
|
||||
// std::this_thread::sleep_for(std::chrono::seconds(5));
|
||||
#endif
|
||||
|
||||
// Don't call IsValidView unless there is a scene handler. This
|
||||
// avoids WARNING message at end of event and run when the user has
|
||||
// not instantiated a scene handler, e.g., in batch mode.
|
||||
G4bool valid = fpSceneHandler && IsValidView();
|
||||
if (!valid) return;
|
||||
|
||||
G4RunManager* runManager = G4RunManagerFactory::GetMasterRunManager();
|
||||
|
||||
const G4Run* currentRun = runManager->GetCurrentRun();
|
||||
@@ -2163,10 +2244,14 @@ void G4VisManager::EndOfEvent ()
|
||||
if (fVerbosity >= warnings) {
|
||||
G4cout <<
|
||||
"WARNING: G4VisManager::EndOfEvent: Automatic event keeping suspended."
|
||||
"\n The number of events exceeds the maximum, "
|
||||
<< maxNumberOfKeptEvents <<
|
||||
", that may be kept by\n the vis manager."
|
||||
<< G4endl;
|
||||
if (maxNumberOfKeptEvents > 0) {
|
||||
G4cout <<
|
||||
"\n The number of events exceeds the maximum, "
|
||||
<< maxNumberOfKeptEvents <<
|
||||
", that may be kept by\n the vis manager."
|
||||
<< G4endl;
|
||||
}
|
||||
}
|
||||
warned = true;
|
||||
}
|
||||
@@ -2181,7 +2266,6 @@ void G4VisManager::EndOfEvent ()
|
||||
eventManager->KeepTheCurrentEvent();
|
||||
fNKeepRequests++;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -2243,7 +2327,7 @@ void G4VisManager::EndOfRun ()
|
||||
G4int nKeptEvents = 0;
|
||||
const std::vector<const G4Event*>* events = currentRun->GetEventVector();
|
||||
if (events) nKeptEvents = events->size();
|
||||
if (fVerbosity >= warnings) {
|
||||
if (fVerbosity >= warnings && nKeptEvents > 0) {
|
||||
G4cout << nKeptEvents;
|
||||
if (nKeptEvents == 1) G4cout << " event has";
|
||||
else G4cout << " events have";
|
||||
@@ -2268,38 +2352,27 @@ void G4VisManager::EndOfRun ()
|
||||
G4cout << G4endl;
|
||||
}
|
||||
G4cout <<
|
||||
" \"/vis/reviewKeptEvents\" to review them one by one."
|
||||
"\n \"/vis/enable\", then \"/vis/viewer/flush\" or \"/vis/viewer/rebuild\" to see them accumulated."
|
||||
" \"/vis/reviewKeptEvents\" to review one by one."
|
||||
"\n To see accumulated, \"/vis/enable\", then \"/vis/viewer/flush\" or \"/vis/viewer/rebuild\"."
|
||||
<< G4endl;
|
||||
}
|
||||
|
||||
// static G4bool warned = false;
|
||||
// if (!valid && fVerbosity >= warnings && !warned) {
|
||||
// G4cout <<
|
||||
// " Only useful if before starting the run:"
|
||||
// "\n a) trajectories are stored (\"/vis/scene/add/trajectories [smooth|rich]\"), or"
|
||||
// "\n b) the Draw method of any hits or digis is implemented."
|
||||
// "\n To view trajectories, hits or digis:"
|
||||
// "\n open a viewer, draw a volume, \"/vis/scene/add/trajectories\""
|
||||
// "\n \"/vis/scene/add/hits\" or \"/vis/scene/add/digitisations\""
|
||||
// "\n and, possibly, \"/vis/viewer/flush\"."
|
||||
// "\n To see all events: \"/vis/scene/endOfEventAction accumulate\"."
|
||||
// "\n (You may need \"/vis/viewer/flush\" or even \"/vis/viewer/rebuild\".)"
|
||||
// "\n To see events individually: \"/vis/reviewKeptEvents\"."
|
||||
// << G4endl;
|
||||
// warned = true;
|
||||
// }
|
||||
if (fVerbosity >= warnings) PrintListOfPlots();
|
||||
|
||||
if (fEventKeepingSuspended && fVerbosity >= warnings) {
|
||||
G4cout <<
|
||||
"WARNING: G4VisManager::EndOfRun: Automatic event keeping was suspended."
|
||||
"\n The number of events in the run exceeded the maximum, "
|
||||
<< fpScene->GetMaxNumberOfKeptEvents() <<
|
||||
", that may be\n kept by the vis manager." <<
|
||||
"\n The number of events kept by the vis manager can be changed with"
|
||||
"\n \"/vis/scene/endOfEventAction accumulate <N>\", where N is the"
|
||||
"\n maximum number you wish to allow. N < 0 means \"unlimited\"."
|
||||
<< G4endl;
|
||||
if (fpScene->GetMaxNumberOfKeptEvents() > 0) {
|
||||
G4cout <<
|
||||
"\n The number of events in the run exceeded the maximum, "
|
||||
<< fpScene->GetMaxNumberOfKeptEvents() <<
|
||||
", that may be\n kept by the vis manager." <<
|
||||
"\n The number of events kept by the vis manager can be changed with"
|
||||
"\n \"/vis/scene/endOfEventAction accumulate <N>\", where N is the"
|
||||
"\n maximum number you wish to allow. N < 0 means \"unlimited\"."
|
||||
<< G4endl;
|
||||
}
|
||||
}
|
||||
|
||||
// Don't call IsValidView unless there is a scene handler. This
|
||||
|
||||
Reference in New Issue
Block a user