ECCE @ EIC Software
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
G4UImanager.cc
Go to the documentation of this file. Or view the newest version in sPHENIX GitHub for file G4UImanager.cc
1 //
2 // ********************************************************************
3 // * License and Disclaimer *
4 // * *
5 // * The Geant4 software is copyright of the Copyright Holders of *
6 // * the Geant4 Collaboration. It is provided under the terms and *
7 // * conditions of the Geant4 Software License, included in the file *
8 // * LICENSE and available at http://cern.ch/geant4/license . These *
9 // * include a list of copyright holders. *
10 // * *
11 // * Neither the authors of this software system, nor their employing *
12 // * institutes,nor the agencies providing financial support for this *
13 // * work make any representation or warranty, express or implied, *
14 // * regarding this software system or assume any liability for its *
15 // * use. Please see the license in the file LICENSE and URL above *
16 // * for the full disclaimer and the limitation of liability. *
17 // * *
18 // * This code implementation is the result of the scientific and *
19 // * technical work of the GEANT4 collaboration. *
20 // * By using, copying, modifying or distributing the software (or *
21 // * any work based on the software) you agree to acknowledge its *
22 // * use in resulting scientific publications, and indicate your *
23 // * acceptance of all terms of the Geant4 Software license. *
24 // ********************************************************************
25 //
26 //
27 //
28 //
29 // ---------------------------------------------------------------------
30 
31 #include "G4UImanager.hh"
32 #include "G4UIcommandTree.hh"
33 #include "G4UIcommand.hh"
34 #include "G4UIsession.hh"
35 #include "G4UIbatch.hh"
36 #include "G4UIcontrolMessenger.hh"
37 #include "G4UnitsMessenger.hh"
39 #include "G4ios.hh"
40 #include "G4strstreambuf.hh"
41 #include "G4StateManager.hh"
42 #include "G4UIaliasList.hh"
43 #include "G4Tokenizer.hh"
44 #include "G4MTcoutDestination.hh"
45 #include "G4UIbridge.hh"
46 #include "G4Threading.hh"
47 
48 #include <sstream>
49 #include <fstream>
50 
52 {
53  G4ThreadLocalStatic G4UImanager* _instance = nullptr;
54  return _instance;
55 }
56 
58 {
59  G4ThreadLocalStatic bool _instance = false;
60  return _instance;
61 }
62 
64 {
65  static G4UImanager* _instance = nullptr;
66  return _instance;
67 }
69 
71 
73 {
74  if(!fUImanager())
75  {
77  {
78  fUImanager() = new G4UImanager;
80  }
81  }
82  return fUImanager();
83 }
84 
86 { return fMasterUImanager(); }
87 
90  UImessenger(0), UnitsMessenger(0), CoutMessenger(0),
91  isMaster(false),bridges(0),
92  ignoreCmdNotFound(false), stackCommandsForBroadcast(false),
93  threadID(-1), threadCout(0), lastRC(0)
94 {
95  savedCommand = 0;
96  treeTop = new G4UIcommandTree("/");
98  G4String nullString;
99  savedParameters = nullString;
100  verboseLevel = 0;
101  saveHistory = false;
102  session = nullptr;
103  g4UIWindow = nullptr;
105  pauseAtBeginOfEvent = false;
106  pauseAtEndOfEvent = false;
107  maxHistSize = 20;
108  searchPath="";
109  commandStack = new std::vector<G4String>;
110 }
111 
113 {
117 }
118 
120 {
121  if(bridges)
122  {
123  std::vector<G4UIbridge*>::iterator itr = bridges->begin();
124  for(;itr!=bridges->end();itr++)
125  { delete *itr; }
126  delete bridges;
127  }
128  SetCoutDestination(nullptr);
129  histVec.clear();
130  if(saveHistory) historyFile.close();
131  delete CoutMessenger;
132  delete UnitsMessenger;
133  delete UImessenger;
134  delete treeTop;
135  delete aliasList;
136  fUImanagerHasBeenKilled() = true;
137  fUImanager() = nullptr;
138  if(commandStack)
139  {
140  commandStack->clear();
141  delete commandStack;
142  }
143  if(threadID >= 0)
144  {
145  if(threadCout) delete threadCout;
147  threadID = -1;
148  }
149 }
150 
153 {
156  aliasList = ui.aliasList;
157  g4UIWindow = ui.g4UIWindow;
159  session = ui.session;
160  treeTop = ui.treeTop;
163  CoutMessenger = 0;
167  isMaster = ui.isMaster;
168  bridges = ui.bridges;
172  threadID = ui.threadID;
173  threadCout = ui.threadCout;
174  CreateMessenger();
175 }
176 
178 { return right; }
180 { return (this==&right); }
182 { return (this!=&right); }
183 
185 { doublePrecisionStr = val; }
187 { return doublePrecisionStr; }
188 
190 {
191  G4String theCommand = aCommand;
192  savedCommand = treeTop->FindPath( theCommand );
193  if( savedCommand == nullptr )
194  {
195  G4cerr << "command not found" << G4endl;
196  return G4String();
197  }
198  return savedCommand->GetCurrentValue();
199 }
200 
202 G4int parameterNumber, G4bool reGet)
203 {
204  if(reGet || savedCommand == nullptr)
205  {
206  savedParameters = GetCurrentValues( aCommand );
207  }
208  G4Tokenizer savedToken( savedParameters );
209  G4String token;
210  for(G4int i_thParameter=0;i_thParameter<parameterNumber;i_thParameter++)
211  {
212  token = savedToken();
213  if( token.isNull() ) return G4String();
214  if( token[(size_t)0] == '"' )
215  {
216  token.append(" ");
217  token.append(savedToken("\""));
218  }
219  }
220  return token;
221 }
222 
224 const char * aParameterName, G4bool reGet)
225 {
226  if(reGet || savedCommand == nullptr)
227  {
228  G4String parameterValues = GetCurrentValues( aCommand );
229  }
230  for(size_t i=0;i<savedCommand->GetParameterEntries();++i)
231  {
232  if( aParameterName ==
234  return GetCurrentStringValue(aCommand,i+1,false);
235  }
236  return G4String();
237 }
238 
240 const char * aParameterName, G4bool reGet)
241 {
242  G4String targetParameter =
243  GetCurrentStringValue( aCommand, aParameterName, reGet );
244  G4int value;
245  const char* t = targetParameter;
246  std::istringstream is(t);
247  is >> value;
248  return value;
249 }
250 
252 G4int parameterNumber, G4bool reGet)
253 {
254  G4String targetParameter =
255  GetCurrentStringValue( aCommand, parameterNumber, reGet );
256  G4int value;
257  const char* t = targetParameter;
258  std::istringstream is(t);
259  is >> value;
260  return value;
261 }
262 
264 const char * aParameterName, G4bool reGet)
265 {
266  G4String targetParameter =
267  GetCurrentStringValue( aCommand, aParameterName, reGet );
268  G4double value;
269  const char* t = targetParameter;
270  std::istringstream is(t);
271  is >> value;
272  return value;
273 }
274 
276 G4int parameterNumber, G4bool reGet)
277 {
278  G4String targetParameter =
279  GetCurrentStringValue( aCommand, parameterNumber, reGet );
280  G4double value;
281  const char* t = targetParameter;
282  std::istringstream is(t);
283  is >> value;
284  return value;
285 }
286 
288 {
289  treeTop->AddNewCommand( newCommand );
291  { fMasterUImanager()->AddWorkerCommand(newCommand); }
292 }
293 
295 {
296  treeTop->AddNewCommand( newCommand, true );
297 }
298 
300 {
301  treeTop->RemoveCommand( aCommand );
303  { fMasterUImanager()->RemoveWorkerCommand(aCommand); }
304 }
305 
307 {
308  treeTop->RemoveCommand( aCommand, true );
309 }
310 
311 void G4UImanager::ExecuteMacroFile(const char * fileName)
312 {
313  G4UIsession* batchSession = new G4UIbatch(fileName,session);
314  session = batchSession;
315  lastRC = 0;
316  G4UIsession* previousSession = session->SessionStart();
318  delete session;
319  session = previousSession;
320 }
321 
322 void G4UImanager::LoopS(const char* valueList)
323 {
324  G4String vl = valueList;
325  G4Tokenizer parameterToken(vl);
326  G4String mf = parameterToken();
327  G4String vn = parameterToken();
328  G4String c1 = parameterToken();
329  c1 += " ";
330  c1 += parameterToken();
331  c1 += " ";
332  c1 += parameterToken();
333  const char* t1 = c1;
334  std::istringstream is(t1);
335  G4double d1;
336  G4double d2;
337  G4double d3;
338  is >> d1 >> d2 >> d3;
339  Loop(mf,vn,d1,d2,d3);
340 }
341 
342 void G4UImanager::Loop(const char * macroFile,const char * variableName,
343  G4double initialValue,G4double finalValue,G4double stepSize)
344 {
345  G4String cd;
346  if (stepSize > 0) {
347  for(G4double d=initialValue;d<=finalValue;d+=stepSize)
348  {
349  std::ostringstream os;
350  os << d;
351  cd += os.str();
352  cd += " ";
353  }
354  } else {
355  for(G4double d=initialValue;d>=finalValue;d+=stepSize)
356  {
357  std::ostringstream os;
358  os << d;
359  cd += os.str();
360  cd += " ";
361  }
362  }
363  Foreach(macroFile,variableName,cd);
364 }
365 
366 void G4UImanager::ForeachS(const char* valueList)
367 {
368  G4String vl = valueList;
369  G4Tokenizer parameterToken(vl);
370  G4String mf = parameterToken();
371  G4String vn = parameterToken();
372  G4String c1 = parameterToken();
373  G4String ca;
374  while(!((ca=parameterToken()).isNull()))
375  {
376  c1 += " ";
377  c1 += ca;
378  }
379 
380  G4String aliasValue = c1;
381  if(aliasValue(0)=='"')
382  {
383  G4String strippedValue;
384  if(aliasValue(aliasValue.length()-1)=='"')
385  { strippedValue = aliasValue(1,aliasValue.length()-2); }
386  else
387  { strippedValue = aliasValue(1,aliasValue.length()-1); }
388  aliasValue = strippedValue;
389  }
390 
391 // Foreach(mf,vn,c1);
392  Foreach(mf,vn,aliasValue);
393 }
394 
395 void G4UImanager::Foreach(const char * macroFile,const char * variableName,
396  const char * candidates)
397 {
398  G4String candidatesString = candidates;
399  G4Tokenizer parameterToken( candidatesString );
400  G4String cd;
401  while(!((cd=parameterToken()).isNull()))
402  {
403  G4String vl = variableName;
404  vl += " ";
405  vl += cd;
406  SetAlias(vl);
407  ExecuteMacroFile(FindMacroPath(macroFile));
408  if(lastRC!=0)
409  {
411  ed << "Loop aborted due to a command execution error - "
412  << "error code " << lastRC;
413  G4Exception("G4UImanager::Foreach","UIMAN0201",JustWarning,ed);
414  break;
415  }
416  }
417 }
418 
419 
421 {
422  G4String aCommand = aCmd;
423  G4int ia = aCommand.index("{");
424  G4int iz = aCommand.index("#");
425  while((ia != G4int(std::string::npos))&&((iz==G4int(std::string::npos))||(ia<iz)))
426  {
427  G4int ibx = -1;
428  while(ibx<0)
429  {
430  G4int ib = aCommand.index("}");
431  if( ib == G4int(std::string::npos) )
432  {
433  G4cerr << aCommand << G4endl;
434  for(G4int i=0;i<ia;i++) G4cerr << " ";
435  G4cerr << "^" << G4endl;
436  G4cerr << "Unmatched alias parenthesis -- command ignored" << G4endl;
437  G4String nullStr;
438  return nullStr;
439  }
440  G4String ps = aCommand(ia+1,aCommand.length()-(ia+1));
441  G4int ic = ps.index("{");
442  G4int id = ps.index("}");
443  if(ic!=G4int(std::string::npos) && ic < id)
444  { ia+=ic+1; }
445  else
446  { ibx = ib; }
447  }
448  //--- Here ia represents the position of innermost "{"
449  //--- and ibx represents corresponding "}"
450  G4String subs;
451  if(ia>0) subs = aCommand(0,ia);
452  G4String alis = aCommand(ia+1,ibx-ia-1);
453  G4String rems = aCommand(ibx+1,aCommand.length()-ibx);
454  // G4cout << "<" << subs << "> <" << alis << "> <" << rems << ">" << G4endl;
455  G4String* alVal = aliasList->FindAlias(alis);
456  if(!alVal)
457  {
458  G4cerr << "Alias <" << alis << "> not found -- command ignored" << G4endl;
459  G4String nullStr;
460  return nullStr;
461  }
462  aCommand = subs+(*alVal)+rems;
463  ia = aCommand.index("{");
464  }
465  return aCommand;
466 }
467 
469 {
470  return ApplyCommand(aCmd.data());
471 }
472 
473 #include "G4Threading.hh"
474 
476 {
477  G4String aCommand = SolveAlias(aCmd);
478  if(aCommand.isNull()) return fAliasNotFound;
479  if(verboseLevel) G4cout << aCommand << G4endl;
480  G4String commandString;
481  G4String commandParameter;
482 
483  size_t i = aCommand.index(" ");
484  if( i != std::string::npos )
485  {
486  commandString = aCommand(0,i);
487  commandParameter = aCommand(i+1,aCommand.length()-(i+1));
488  }
489  else
490  {
491  commandString = aCommand;
492  }
493 
494  // remove doubled slash
495  G4int len = commandString.length();
496  G4int ll = 0;
497  G4String a1;
498  G4String a2;
499  while(ll<len-1)
500  {
501  if(commandString(ll,2)=="//")
502  {
503  if(ll==0)
504  { commandString.remove(ll,1); }
505  else
506  {
507  a1 = commandString(0,ll);
508  a2 = commandString(ll+1,len-ll-1);
509  commandString = a1+a2;
510  }
511  len--;
512  }
513  else
514  { ll++; }
515  }
516 
517  if(isMaster&&bridges)
518  {
519  std::vector<G4UIbridge*>::iterator itr = bridges->begin();
520  for(;itr!=bridges->end();itr++)
521  {
522  G4int leng = (*itr)->DirLength();
523  if(commandString(0,leng)==(*itr)->DirName())
524  { return (*itr)->LocalUI()->ApplyCommand(commandString+" "+commandParameter); }
525  }
526  }
527 
528  G4UIcommand * targetCommand = treeTop->FindPath( commandString );
529  if( targetCommand == nullptr )
530  {
532  {
534  { commandStack->push_back(commandString+" "+commandParameter); }
535  return fCommandSucceeded;
536  }
537  else
538  { return fCommandNotFound; }
539  }
540 
541  if(stackCommandsForBroadcast && targetCommand->ToBeBroadcasted())
542  { commandStack->push_back(commandString+" "+commandParameter); }
543 
544  if(!(targetCommand->IsAvailable()))
545  { return fIllegalApplicationState; }
546 
547  if(saveHistory) historyFile << aCommand << G4endl;
548  if( G4int(histVec.size()) >= maxHistSize )
549  { histVec.erase(histVec.begin()); }
550  histVec.push_back(aCommand);
551 
552  targetCommand->ResetFailure();
553  G4int commandFailureCode = targetCommand->DoIt( commandParameter );
554  if(commandFailureCode==0)
555  {
556  G4int additionalFailureCode = targetCommand->IfCommandFailed();
557  if(additionalFailureCode > 0)
558  {
560  msg << targetCommand->GetFailureDescription() << "\n"
561  << "Error code : " << additionalFailureCode;
562  G4Exception("G4UImanager::ApplyCommand","UIMAN0123",
563  JustWarning,msg);
564  commandFailureCode += additionalFailureCode;
565  }
566  }
567  return commandFailureCode;
568 }
569 
570 void G4UImanager::StoreHistory(const char* fileName)
571 { StoreHistory(true,fileName); }
572 
573 void G4UImanager::StoreHistory(G4bool historySwitch,const char* fileName)
574 {
575  if(historySwitch)
576  {
577  if(saveHistory)
578  { historyFile.close(); }
579  historyFile.open((char*)fileName);
580  saveHistory = true;
581  }
582  else
583  {
584  historyFile.close();
585  saveHistory = false;
586  }
587  saveHistory = historySwitch;
588 }
589 
590 void G4UImanager::PauseSession(const char* msg)
591 {
593 }
594 
595 void G4UImanager::ListCommands(const char* direct)
596 {
597  G4UIcommandTree* comTree = FindDirectory(direct);
598  if(comTree)
599  { comTree->List(); }
600  else
601  { G4cout << direct << " is not found." << G4endl; }
602 }
603 
605 {
606  G4String aDirName = dirName;
607  G4String targetDir = aDirName.strip(G4String::both);
608  if( targetDir( targetDir.length()-1 ) != '/' )
609  { targetDir += "/"; }
610  G4UIcommandTree* comTree = treeTop;
611  if( targetDir == "/" )
612  { return comTree; }
613  G4int idx = 1;
614  while( idx < G4int(targetDir.length())-1 )
615  {
616  G4int i = targetDir.index("/",idx);
617  G4String targetDirString = targetDir(0,i+1);
618  comTree = comTree->GetTree(targetDirString);
619  if( comTree == nullptr )
620  { return nullptr; }
621  idx = i+1;
622  }
623  return comTree;
624 }
625 
627 {
628  //G4cout << G4StateManager::GetStateManager()->GetStateString(requestedState) << " <--- " << G4StateManager::GetStateManager()->GetStateString(G4StateManager::GetStateManager()->GetPreviousState()) << G4endl;
630  {
631  if(requestedState==G4State_EventProc &&
633  { PauseSession("BeginOfEvent"); }
634  }
636  {
637  if(requestedState==G4State_GeomClosed &&
638  G4StateManager::GetStateManager()->GetPreviousState()==G4State_EventProc)
639  { PauseSession("EndOfEvent"); }
640  }
641  return true;
642 }
643 
644 //void G4UImanager::Interact()
645 //{
646 // Interact(G4String("G4> "));
647 //}
648 
649 //void G4UImanager::Interact(const char * pC)
650 //{
651 // G4cerr << "G4UImanager::Interact() is out of date and is not used anymore." << G4endl;
652 // G4cerr << "This method will be removed shortly!!!" << G4endl;
653 // G4cerr << "In case of main() use" << G4endl;
654 // G4cerr << " G4UIsession * session = new G4UIterminal;" << G4endl;
655 // G4cerr << " session->SessionStart();" << G4endl;
656 // G4cerr << "In other cases use" << G4endl;
657 // G4cerr << " G4StateManager::GetStateManager()->Pause();" << G4endl;
658 //}
659 
660 
661 
663 {
664  G4coutbuf.SetDestination(value);
665  G4cerrbuf.SetDestination(value);
666 }
667 
668 void G4UImanager::SetAlias(const char * aliasLine)
669 {
670  G4String aLine = aliasLine;
671  G4int i = aLine.index(" ");
672  G4String aliasName = aLine(0,i);
673  G4String aliasValue = aLine(i+1,aLine.length()-(i+1));
674  if(aliasValue(0)=='"')
675  {
676  G4String strippedValue;
677  if(aliasValue(aliasValue.length()-1)=='"')
678  { strippedValue = aliasValue(1,aliasValue.length()-2); }
679  else
680  { strippedValue = aliasValue(1,aliasValue.length()-1); }
681  aliasValue = strippedValue;
682  }
683 
684  aliasList->ChangeAlias(aliasName,aliasValue);
685 }
686 
687 void G4UImanager::RemoveAlias(const char * aliasName)
688 {
689  G4String aL = aliasName;
690  G4String targetAlias = aL.strip(G4String::both);
691  aliasList->RemoveAlias(targetAlias);
692 }
693 
695 {
696  aliasList->List();
697 }
698 
699 void G4UImanager::CreateHTML(const char* dir)
700 {
701  G4UIcommandTree* tr = FindDirectory(dir);
702  if(tr!=0)
703  { tr->CreateHTML(); }
704  else
705  { G4cerr << "Directory <" << dir << "> is not found." << G4endl; }
706 }
707 
709 {
710  searchDirs.clear();
711 
712  size_t idxfirst = 0;
713  size_t idxend = 0;
714  G4String pathstring = "";
715  while( (idxend = searchPath.index(':', idxfirst)) != G4String::npos) {
716  pathstring = searchPath.substr(idxfirst, idxend-idxfirst);
717  if(pathstring.size() != 0) searchDirs.push_back(pathstring);
718  idxfirst = idxend + 1;
719  }
720 
721  pathstring = searchPath.substr(idxfirst, searchPath.size()-idxfirst);
722  if(pathstring.size() != 0) searchDirs.push_back(pathstring);
723 }
724 
725 
727 {
728  G4bool qopen = false;
729  std::ifstream fs;
730  fs.open(fname.c_str(), std::ios::in);
731  if(fs.good()) {
732  fs.close();
733  qopen = true;
734  }
735  return qopen;
736 }
737 
739 {
740  G4String macrofile = fname;
741 
742  for (size_t i = 0; i < searchDirs.size(); i++) {
743  G4String fullpath = searchDirs[i] + "/" + fname;
744  if ( FileFound(fullpath) ) {
745  macrofile = fullpath;
746  break;
747  }
748  }
749 
750  return macrofile;
751 }
752 
753 std::vector<G4String>* G4UImanager::GetCommandStack()
754 {
755  std::vector<G4String>* returnValue = commandStack;
756  commandStack = new std::vector<G4String>;
757  return returnValue;
758 }
759 
761 {
762  if(brg->LocalUI()==this)
763  {
764  G4Exception("G4UImanager::RegisterBridge()","UI7002",FatalException,
765  "G4UIBridge cannot bridge between same object.");
766  }
767  else
768  { bridges->push_back(brg); }
769 }
770 
772 {
773  threadID = tId;
777 }
778 
780 {
787 }
788 
789 void G4UImanager::SetCoutFileName(const G4String& fileN, G4bool ifAppend)
790 {
791  // for sequential mode, ignore this method.
792  if(threadID<0) return;
793 
794  if(fileN == "**Screen**")
795  { threadCout->SetCoutFileName(fileN,ifAppend); }
796  else
797  {
798  std::stringstream fn;
799  fn<<"G4W_"<<threadID<<"_"<<fileN;
800  threadCout->SetCoutFileName(fn.str(),ifAppend);
801  }
802 }
803 
804 void G4UImanager::SetCerrFileName(const G4String& fileN, G4bool ifAppend)
805 {
806  // for sequential mode, ignore this method.
807  if(threadID<0) return;
808 
809  if(fileN == "**Screen**")
810  { threadCout->SetCerrFileName(fileN,ifAppend); }
811  else
812  {
813  std::stringstream fn;
814  fn<<"G4W_"<<threadID<<"_"<<fileN;
815  threadCout->SetCerrFileName(fn.str(),ifAppend);
816  }
817 }
818 
820 {
821  // for sequential mode, ignore this method.
822  if(threadID<0) return;
824 }
825 
827 {
828  // for sequential mode, ignore this method.
829  if(threadID<0) return;
831 }
832 
834 {
835  // for sequential mode, ignore this method.
836  if(threadID<0)
837  {
838  igThreadID = tid;
839  return;
840  }
842 }
843 
845 {
846  // for sequential mode, ignore this method.
847  if(threadID<0) { return; }
849 }
850