GSI Object Oriented Online Offline (Go4)  GO4-5.3.2
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros
TGo4AnalysisObjectManager.cxx
Go to the documentation of this file.
1 // $Id: TGo4AnalysisObjectManager.cxx 1956 2016-11-18 16:46:37Z linev $
2 //-----------------------------------------------------------------------
3 // The GSI Online Offline Object Oriented (Go4) Project
4 // Experiment Data Processing at EE department, GSI
5 //-----------------------------------------------------------------------
6 // Copyright (C) 2000- GSI Helmholtzzentrum f�r Schwerionenforschung GmbH
7 // Planckstr. 1, 64291 Darmstadt, Germany
8 // Contact: http://go4.gsi.de
9 //-----------------------------------------------------------------------
10 // This software can be used under the license agreements as stated
11 // in Go4License.txt file which is part of the distribution.
12 //-----------------------------------------------------------------------
13 
15 
16 #include "Riostream.h"
17 #include "TRegexp.h"
18 #include "TMultiGraph.h"
19 #include "TKey.h"
20 #include "TObjArray.h"
21 #include "TArrayF.h"
22 #include "TFolder.h"
23 #include "TFile.h"
24 #include "TList.h"
25 #include "TThread.h"
26 #include "TMutex.h"
27 
28 #include "TH2.h"
29 #include "TCanvas.h"
30 #include "TCutG.h"
31 #include "TROOT.h"
32 #include "TTree.h"
33 #include "TDataMember.h"
34 #include "TBaseClass.h"
35 
36 #include "TGo4Log.h"
37 #include "TGo4LockGuard.h"
38 #include "TGo4ObjectStatus.h"
39 #include "TGo4BranchStatus.h"
40 #include "TGo4Parameter.h"
41 #include "TGo4Condition.h"
42 #include "TGo4WinCond.h"
43 #include "TGo4PolyCond.h"
44 #include "TGo4HistogramEntry.h"
45 #include "TGo4TreeHistogramEntry.h"
47 #include "TGo4DynamicList.h"
48 #include "TGo4MainTree.h"
50 #include "TGo4HistogramStatus.h"
51 #include "TGo4TreeStructure.h"
52 
53 #include "TGo4EventStore.h"
54 #include "TGo4EventSource.h"
55 #include "TGo4EventProcessor.h"
56 #include "TGo4BackStore.h"
57 
58 #include "TGo4Picture.h"
59 #include "TGo4CompositeEvent.h"
60 #include "TGo4ParameterStatus.h"
61 #include "TGo4MemberStatus.h"
62 #include "TGo4PolyCond.h"
63 #include "TGo4AnalysisImp.h"
64 
65 const char* TGo4AnalysisObjectManager::fgcTOPDYNAMICLIST = "Go4DynamicList";
66 const char* TGo4AnalysisObjectManager::fgcTOPFOLDER = "Go4";
67 const char* TGo4AnalysisObjectManager::fgcHISTFOLDER = "Histograms";
68 const char* TGo4AnalysisObjectManager::fgcDYNFOLDER = "DynamicLists";
69 const char* TGo4AnalysisObjectManager::fgcCONDFOLDER = "Conditions";
70 const char* TGo4AnalysisObjectManager::fgcPARAFOLDER = "Parameters";
71 const char* TGo4AnalysisObjectManager::fgcTREEFOLDER = "Trees";
72 const char* TGo4AnalysisObjectManager::fgcPICTFOLDER = "Pictures";
73 const char* TGo4AnalysisObjectManager::fgcCANVFOLDER = "Canvases";
74 const char* TGo4AnalysisObjectManager::fgcANALYSISFOLDER = "EventObjects";
75 const char* TGo4AnalysisObjectManager::fgcEVENTFOLDER = "Events";
76 const char* TGo4AnalysisObjectManager::fgcSRCFOLDER = "EventSources";
77 const char* TGo4AnalysisObjectManager::fgcSTOREFOLDER = "EventStores";
78 const char* TGo4AnalysisObjectManager::fgcPROCFOLDER = "EventProcessors";
79 const char* TGo4AnalysisObjectManager::fgcUSRFOLDER = "UserObjects";
80 const char* TGo4AnalysisObjectManager::fgcTMPFOLDER = "Go4-tmp";
81 
82 #define fguSUBFOLDERMAXLEN 1024
83 
85  TNamed(name,"The Go4 Analysis Object Manager"),
86  fxGo4Dir(0),fxHistogramDir(0),fxConditionDir(0), fxParameterDir(0),
87  fxDynListDir(0),fxUserDir(0), fxTreeDir(0), fxPictureDir(0), fxCanvasDir(0),
88  fxStoreDir(0), fxSourceDir(0), fxProcessorDir(0), fxEventDir(0),
89  fxAnalysisDir(0), fxTempFolder(0),
90  fxMatchList(0), fxMatchIterator(0),
91  fiDynListCount(0), fiDynListInterval(0),
92  fbCreatedinMake(kFALSE), fbSuppressLoadHistograms(kFALSE)
93 {
94  fxDirMutex = new TMutex(kTRUE);
95  fxGo4Dir = gROOT->GetRootFolder()->AddFolder(fgcTOPFOLDER,"The Go4 Object folder");
96  fxGo4Dir->SetOwner(kTRUE); // top go4 dir owns subfolders
97  gROOT->GetListOfBrowsables()->Add(fxGo4Dir, fxGo4Dir->GetName());
98  fxHistogramDir = fxGo4Dir->AddFolder(fgcHISTFOLDER,"All Histogram objects");
99  fxHistogramDir->SetOwner(kTRUE);
100  fxConditionDir = fxGo4Dir->AddFolder(fgcCONDFOLDER,"All Condition objects");
101  fxConditionDir->SetOwner(kTRUE);
102  fxParameterDir = fxGo4Dir->AddFolder(fgcPARAFOLDER,"All Parameter objects");
103  fxParameterDir->SetOwner(kTRUE);
104  fxDynListDir = fxGo4Dir->AddFolder(fgcDYNFOLDER,"Dynamic List Instances");
105  fxDynListDir->SetOwner(kTRUE);
106  fxTreeDir = fxGo4Dir->AddFolder(fgcTREEFOLDER,"References to trees");
107  fxTreeDir->SetOwner(kFALSE); // tree dir does not own objects,
108  fxPictureDir = fxGo4Dir->AddFolder(fgcPICTFOLDER,"Picture objects");
109  fxPictureDir->SetOwner(kTRUE);
110  fxCanvasDir = fxGo4Dir->AddFolder(fgcCANVFOLDER,"All TCanvases");
111  fxCanvasDir->SetOwner(kTRUE);
112  fxAnalysisDir = fxGo4Dir->AddFolder(fgcANALYSISFOLDER,"Event objects of current analysis");
113  fxAnalysisDir->SetOwner(kTRUE); // owns folders, but not objects in folders
114  fxStoreDir = fxAnalysisDir->AddFolder(fgcSTOREFOLDER,"References to event stores");
115  fxStoreDir->SetOwner(kFALSE); // event classes dir does not own objects,
116  fxSourceDir = fxAnalysisDir->AddFolder(fgcSRCFOLDER,"References to event sources");
117  fxSourceDir->SetOwner(kFALSE); // event classes dir does not own objects,
118  fxProcessorDir = fxAnalysisDir->AddFolder(fgcPROCFOLDER,"References to event processors");
119  fxProcessorDir->SetOwner(kFALSE); // event classes dir does not own objects,
120  fxEventDir = fxAnalysisDir->AddFolder(fgcEVENTFOLDER,"References to event structures");
121  fxEventDir->SetOwner(kFALSE); // event classes dir does not own objects,
122  fxUserDir = fxGo4Dir->AddFolder(fgcUSRFOLDER,"For User Objects");
123 
124  // FIXME: SL, 2.01.2012 why owner flag is disabled here, causes memory leak when destroyed
125  fxGo4Dir->SetOwner(kFALSE);
126 
127  fxTempFolder = gROOT->GetRootFolder()->AddFolder(fgcTMPFOLDER,"The Go4 temporary object folder");
128  fxTempFolder->SetOwner(kFALSE);
129 
130  gROOT->GetListOfCleanups()->Add(this);
131 }
132 
134  TNamed(),
135  fxGo4Dir(0),fxHistogramDir(0),fxConditionDir(0),
136  fxDynListDir(0), fxUserDir(0), fxTreeDir(0), fxPictureDir(0), fxCanvasDir(0),
137  fxStoreDir(0), fxSourceDir(0), fxProcessorDir(0), fxEventDir(0),
138  fxAnalysisDir(0), fxTempFolder(0),
139  fiDynListCount(0), fiDynListInterval(0),
140  fbCreatedinMake(kFALSE), fbSuppressLoadHistograms(kFALSE)
141 {
142  // ctor for streamer only!
143 
144  gROOT->GetListOfCleanups()->Add(this);
145 }
146 
147 
149 {
150  gROOT->GetListOfCleanups()->Remove(this);
151 
152  delete fxMatchIterator;
153  delete fxMatchList;
154  gROOT->GetListOfBrowsables()->Remove(fxGo4Dir);
155  //std::cout <<"Removed all folders from list of browsables" << std::endl;
156 
157  gROOT->GetRootFolder()->Remove(fxTempFolder);
158  gROOT->GetRootFolder()->Remove(fxGo4Dir);
159 
160  // disable canvas clear - does not work for some reasons
161  fxCanvasDir->Clear();
162 
163  fxHistogramDir->Clear();
164  fxConditionDir->Clear();
165  fxParameterDir->Clear();
166  fxDynListDir->Clear();
167  fxUserDir->Clear();
168  fxTreeDir->Clear();
169  fxPictureDir->Clear();
170 
171  fxEventDir->Clear();
172  fxProcessorDir->Clear();
173  fxStoreDir->Clear();
174  fxSourceDir->Clear();
175  fxGo4Dir->Clear();
176  fxTempFolder->Clear();
177 
178  //std::cout <<"Cleared all folders" << std::endl;
179  delete fxTempFolder;
180  //std::cout <<"deleted temporary folder" << std::endl;
181  delete fxGo4Dir;
182  //std::cout <<"deleted top folder" << std::endl;
183 
184  delete fxDirMutex;
185 }
186 
188 {
189  if ((obj!=0) && (obj!=this)) {
190  // remove objects from canvas folder - it may happen that canvas automatically deleted
191  if (fxCanvasDir) fxCanvasDir->RecursiveRemove(obj);
192  }
193 }
194 
195 
196 Bool_t TGo4AnalysisObjectManager::AddObject(TNamed * anything, const char* subfolder, Bool_t replace)
197 {
198  GO4TRACE((11,"TGo4AnalysisObjectManager::AddObject(TNamed *)",__LINE__, __FILE__));
199  // unspecified objects are only allowed to put into userdir
200  return (AddObjectToFolder(anything,fxUserDir,subfolder,replace));
201 }
202 
203 Bool_t TGo4AnalysisObjectManager::RemoveObject(const char * name, Bool_t del)
204 {
205  return RemoveObjectFromFolder(name, fxUserDir, del);
206 }
207 
208 
209 TObject* TGo4AnalysisObjectManager::GetAsTObject(const char * name, const char* folder)
210 {
211  GO4TRACE((11,"TGo4AnalysisObjectManager::GetAsTObject(const char*, const char*)",__LINE__, __FILE__));
212  //
213  TObject* ob(0);
214  TFolder* searchfold(fxGo4Dir);
215  if((folder!=0) && (strcmp(folder,fgcTOPFOLDER)!=0))
216  searchfold = FindSubFolder(fxGo4Dir, folder, kFALSE);
217  if(searchfold) {
218  ob = FindObjectInFolder(searchfold, name);
219  //std::cout << "found object in top folder :" << ob << std::endl;
220  if(ob && ob->InheritsFrom(TTree::Class())) ob=0; // disable sending tree to gui!
221  if(ob && ob->InheritsFrom(TFolder::Class())) ob=0; // disable sending complete folder
222  if(ob && ob->InheritsFrom(TGo4EventElement::Class())) ob=0; // disable events
223  if(ob && ob->InheritsFrom(TGo4EventSource::Class())) ob=0; // disable events
224  if(ob && ob->InheritsFrom(TGo4EventStore::Class())) ob=0; // disable events
225  if(ob && ob->InheritsFrom(TGo4EventProcessor::Class())) ob=0; // disable events
226  }
227  if(ob) {
228  TGo4Analysis::Instance()->Message(0,"AnalysisObjectManager - found object %s of class %s",
229  ob->GetName(), ob->ClassName());
230  } else {
231  TGo4Analysis::Instance()->Message(0,"!!! AnalysisObjectManager - no such object %s !!!",
232  name);
233  }
234  return ob;
235 }
236 
237 
238 
239 TNamed * TGo4AnalysisObjectManager::GetObject(const char * name, const char* folder)
240 {
241  return dynamic_cast<TNamed*> (GetAsTObject(name, folder));
242 }
243 
244 
246 {
247  GO4TRACE((11,"TGo4AnalysisObjectManager::ClearObject(char *)",__LINE__, __FILE__));
248  Bool_t rev=kTRUE;
249  TGo4LockGuard dirguard(fxDirMutex);
250  TObject* ob = fxGo4Dir->FindObjectAny(name);
251  if(ob!=0)
252  {
253  if(ob->InheritsFrom(TFolder::Class()))
254  rev=ClearFolder(dynamic_cast<TFolder*>(ob));
255  else
256  rev=ClearObject(ob);
257  }
258  return rev;
259 }
260 
261 
263 {
264  Bool_t rev=kFALSE;
265  TGo4LockGuard dirguard(fxDirMutex);
266  TObject* ob= fxGo4Dir->FindObjectAny(name);
267  if(ob!=0)
268  {
269  if(ob->InheritsFrom(TFolder::Class()))
270  rev=DeleteFolder(dynamic_cast<TFolder*>(ob));
271  else
272  rev=DeleteObject(ob);
273  }
274  return rev;
275 }
276 
277 Bool_t TGo4AnalysisObjectManager::ProtectObjects(const char* name, const Option_t* flags)
278 {
279  Bool_t rev = kFALSE;
280  TGo4LockGuard dirguard(fxDirMutex);
281  TObject* ob= fxGo4Dir->FindObjectAny(name);
282  if(ob!=0)
283  {
284  if(ob->InheritsFrom(TFolder::Class()))
285  rev=ProtectFolder(dynamic_cast<TFolder*>(ob), flags);
286  else
287  rev=ProtectObject(ob, flags);
288  }
289  return rev;
290 }
291 
293  TGo4CompositeEvent* compevent,
294  Int_t startindex, Int_t* skip,
295  const char* name, const char* title)
296 {
297  GO4TRACE((11,"TGo4AnalysisObjectManager::CreateCompositeBranchFolder(TObjArray*,...)",__LINE__, __FILE__));
298  if (branchlist==0) return 0;
299 
300  if (compevent==0) return CreateBranchFolder(branchlist,name,title);
301 
302  Int_t lastindex=0;
303  if(startindex==1)
304  // top event: scan everything
305  lastindex = startindex + branchlist->GetLast();
306  else
307  // subevent: scan only own members
308  lastindex = startindex + compevent->getNElements();
309 
310  TFolder* subnames=0;
311  TList* nameslist = new TList;
312  TGo4ObjectStatus* state;
313  TObjArray* csubevents = compevent->getListOfComposites();
314 
315  Int_t skippedentries=0;
316  Int_t offset=0;
317  for(Int_t i=startindex; i<lastindex;i++) {
318  //std::cout <<"i+offset="<<i+offset << std::endl;
319  TClass* cl=0;
320  TObject* entry=branchlist->At(i+offset);
321  if((entry!=0) && entry->InheritsFrom(TBranch::Class())) {
322  // found subfolder, process it recursively
323  TBranch* currentbranch= dynamic_cast<TBranch*> (entry);
324  TObjArray* currentbranchlist=0;
325  if (currentbranch!=0) {
326  currentbranchlist=currentbranch->GetListOfBranches();
327  cl=gROOT->GetClass(currentbranch->GetClassName());
328  }
329  if((cl!=0) && cl->InheritsFrom(TGo4CompositeEvent::Class())) {
330  // subevent is also composite event, treat next n branches as subbranches:
331  TGo4CompositeEvent* subevent=0;
332  TString branchname(currentbranch->GetName());
333  Ssiz_t leng = branchname.Length();
334  branchname.Resize(leng-1); // strip dot from branchname
335  //std::cout <<"searching for composite sub event "<< branchname.Data() << std::endl;
336  if(csubevents!=0)
337  subevent = dynamic_cast<TGo4CompositeEvent *>(csubevents->FindObject(branchname.Data()));
338 
339  if((subevent!=0) && subevent->getNElements()>0) {
340  //std::cout <<"found composite subevent "<< subevent->GetName() << std::endl;
341  // found subbranch, add it to folder struct
342 
343  subnames=CreateCompositeBranchFolder(branchlist,
344  subevent,
345  i+offset+1, &skippedentries,
346  subevent->GetName(),
347  subevent->GetTitle());
348  nameslist->AddLast(subnames);
349  offset+=skippedentries;
350  //std::cout <<"skipped:"<<skippedentries<<", i:"<<i << std::endl;
351  //std::cout <<"offset:"<<offset<< std::endl;
352  // now process subbranchlist currentbranchlist of compevent,
353  // add members of this folder to existing folder subnames!
354  TFolder* temp=CreateBranchFolder(currentbranchlist,
355  "dummy",
356  "dummy");
357  subnames->GetListOfFolders()->AddAll(temp->GetListOfFolders());
358  }
359  else
360  {
361  //std::cout <<"composite subevent is basic member..." << std::endl;
362  // subevent not in list, normal operation:
363  //state=new TGo4ObjectStatus(dynamic_cast<TNamed*> (entry) );
364  //nameslist->AddLast(state);
365  if(currentbranchlist!=0)
366  {
367  if(currentbranchlist->IsEmpty())
368  {
369  // subbranchlist is empty, add status object to folder
370  state=new TGo4BranchStatus(currentbranch);
371  nameslist->AddLast(state);
372  }
373  else
374  {
375  subnames=CreateBranchFolder(currentbranchlist,
376  currentbranch->GetName(),
377  currentbranch->GetTitle());
378  nameslist->AddLast(subnames);
379  }
380  } // if(currentbranchlist)
381  } //if(subevent && subevent->getNElements()>0)
382  } // if(cl && cl->InheritsFrom(TGo4CompositeEvent))
383  else
384  {
385  // subevent is not a composite event, normal operation:
386  // state=new TGo4ObjectStatus(dynamic_cast<TNamed*> (entry) );
387  // nameslist->AddLast(state);
388  if(currentbranchlist!=0)
389  {
390  if(currentbranchlist->IsEmpty())
391  {
392  // subbranchlist is empty, add status object to folder
393  state=new TGo4BranchStatus(currentbranch);
394  nameslist->AddLast(state);
395  }
396  else
397  {
398  subnames=CreateBranchFolder(currentbranchlist,
399  currentbranch->GetName(),
400  currentbranch->GetTitle());
401  nameslist->AddLast(subnames);
402  }
403  }
404  //std::cout <<"added entry"<< entry->GetName() << std::endl;
405  }
406  }
407  else
408  {
409  break;
410  // if(entry)
411  // std::cout <<"ERROR: no branch in branchlist, class:"<< entry->ClassName() << std::endl;
412  // else
413  // std::cout << "ZERO entry in branchlist"<< std::endl;
414 
415  } //if(entry->InheritsFrom(TBranch))
416  } // for()
417 
418  *skip=lastindex+offset-startindex;
419  TFolder* fold = fxTempFolder->AddFolder(name,title,nameslist);
420  fold->SetOwner(kTRUE);
421  fxTempFolder->Remove(fold);
422  return fold;
423 }
424 
426 {
427  GO4TRACE((11,"TGo4AnalysisObjectManager::CreateTreeStructure(TTree*)",__LINE__, __FILE__));
428  //
429  TGo4TreeStructure* tstructure=0;
430  if(thetree)
431  {
432  const char* treename=thetree->GetName();
433  const char* treetitle=thetree->GetTitle();
434  TGo4Analysis::Instance()->Message(0,"AnalysisObjectManager - creating structure of tree %s",
435  treename);
436  TObjArray* branchlist=thetree->GetListOfBranches();
437  tstructure= new TGo4TreeStructure(treename);
438  tstructure->fxTopFolder=CreateBranchFolder(branchlist,treename,treetitle, kTRUE);
439  }
440  else {}
441  return tstructure;
442 }
443 
445 {
446  GO4TRACE((11,"TGo4AnalysisObjectManager::CreateTreeStructure(const char *)",__LINE__, __FILE__));
447  TTree* thetree=0;
448  if(fxTreeDir)
449  {
450  thetree=dynamic_cast<TTree*> (fxTreeDir->FindObjectAny(treename));
451  }
452  else
453  {
454  thetree=0;
455  }
456  return (CreateTreeStructure(thetree));
457 }
458 
459 
460 TFolder* TGo4AnalysisObjectManager::CreateMembersFolder(TObject* obj, const char* membrfoldername, TClass* cl)
461 {
462  if(cl==0) return 0;
463  TList* nameslist= new TList;
464 
465  // now process baseclasses of event:
466  TIter biter(cl->GetListOfBases());
467  TObject* bob=0;
468  while((bob=biter()) !=0) {
469  TBaseClass* baseclass = dynamic_cast<TBaseClass*>(bob);
470  if(baseclass==0) continue;
471 
472  // we have a baseclass
473  TClass* bclass=baseclass->GetClassPointer();
474  if(bclass==0) continue;
475 
476  if(!strcmp(bclass->GetName(),"TNamed")) continue; // suppress bases above
477 
478  // recursively find out members of all baseclasses
479  TFolder* subfold = CreateMembersFolder(0, bclass->GetName(), bclass);
480  if(subfold!=0)
481  nameslist->AddLast(subfold);
482  } // while((bob=baseiter->Next()) !=0)
483 
484  TIter miter(cl->GetListOfDataMembers());
485  TObject* nob=0;
486  // scan members of this event class:
487  while((nob=miter()) !=0) {
488  TDataMember* mem = dynamic_cast<TDataMember*>(nob);
489  if((mem==0) || mem->IsaPointer()) continue; // suppress heap aggregates
490  // later, we might scan these recursively
491 
492  TString sbuf;
493 
494  switch(mem->GetArrayDim()) {
495  case 1:
496  sbuf = TString::Format("%s[%d]", mem->GetName(), mem->GetMaxIndex(0));
497  break;
498 
499  case 2:
500  sbuf = TString::Format("%s[%d][%d]", mem->GetName(), mem->GetMaxIndex(0), mem->GetMaxIndex(1));
501  break;
502 
503  default:
504  sbuf = mem->GetName();
505  }
506 
507  TGo4MemberStatus* state = new TGo4MemberStatus(sbuf.Data(), mem->GetFullTypeName());
508  nameslist->AddLast(state);
509  } // while
510 
511  // now process components of composite event
512  if ((obj!=0) && (obj->InheritsFrom(TGo4CompositeEvent::Class()))) {
513 
514  TObjArray* arr =((TGo4CompositeEvent*)obj)->getElements();
515 
516  if (arr!=0)
517  for (Int_t n=0;n<=arr->GetLast();n++) {
518  TGo4EventElement* elem = (TGo4EventElement*) arr->At(n);
519  if (elem==0) continue;
520  TFolder* subfold = CreateMembersFolder(elem, elem->GetName(), elem->IsA());
521  if(subfold!=0)
522  nameslist->AddLast(subfold);
523  }
524  }
525 
526  TFolder* memberfolder = fxTempFolder->AddFolder(membrfoldername, TString("Object of class ") + cl->GetName(), nameslist);
527  fxTempFolder->Remove(memberfolder);
528  memberfolder->SetOwner(kTRUE);
529  return memberfolder;
530 }
531 
532 Bool_t TGo4AnalysisObjectManager::AddHistogram(TH1 * his, const char* subfolder, Bool_t replace)
533 {
534  GO4TRACE((11,"TGo4AnalysisObjectManager::AddHistogram(TH1*)",__LINE__, __FILE__));
535  Bool_t rev = AddObjectToFolder(his,fxHistogramDir,subfolder,replace,kTRUE);
536  // for histograms: add with unique object names within histogramdir
537  // to avoid errors in TTree::Draw()
538  if(rev && his) his->SetDirectory(gROOT); // assign histo to the top dir, no file!
539  return rev;
540 }
541 
542 TH1* TGo4AnalysisObjectManager::MakeTH1(const char* histotype,
543  const char* foldername,
544  const char* histoname,
545  Int_t nbinsx,
546  Axis_t xlow,
547  Axis_t xup,
548  const char* title,
549  const char* xtitle,
550  const char* ytitle) {
551 
552  TString htype(histotype);
553  htype.ToUpper();
554  if (htype.Length()==0) htype = "I";
555  TClass* cl = 0;
556 
557  switch (htype[0]) {
558  case 'C' : cl = TH1C::Class(); break;
559  case 'D' : cl = TH1D::Class(); break;
560  case 'F' : cl = TH1F::Class(); break;
561  case 'I' : cl = TH1I::Class(); break;
562  case 'S' : cl = TH1S::Class(); break;
563  default : cl = TH1I::Class();
564  }
565 
566  TH1* histo = (TH1*) TestObject(fxHistogramDir, foldername, histoname, cl);
567 
568  if (histo) return histo;
569 
570  switch(htype[0]) {
571  case 'C' : histo = new TH1C(histoname, histoname, nbinsx, xlow, xup); break;
572  case 'D' : histo = new TH1D(histoname, histoname, nbinsx, xlow, xup); break;
573  case 'F' : histo = new TH1F(histoname, histoname, nbinsx, xlow, xup); break;
574  case 'I' : histo = new TH1I(histoname, histoname, nbinsx, xlow, xup); break;
575  case 'S' : histo = new TH1S(histoname, histoname, nbinsx, xlow, xup); break;
576  default : histo = new TH1I(histoname, histoname, nbinsx, xlow, xup);
577  }
578 
579  if (title) histo->SetTitle(title);
580  if (xtitle) histo->SetXTitle(xtitle);
581  if (ytitle) histo->SetYTitle(ytitle);
582  AddHistogram(histo, foldername);
583  return histo;
584 }
585 
586 TH2* TGo4AnalysisObjectManager::MakeTH2(const char* histotype,
587  const char* foldername,
588  const char* histoname,
589  Int_t nbinsx,
590  Axis_t xlow,
591  Axis_t xup,
592  Int_t nbinsy,
593  Axis_t ylow,
594  Axis_t yup,
595  const char* title,
596  const char* xtitle,
597  const char* ytitle) {
598  TString htype(histotype);
599  htype.ToUpper();
600  if (htype.Length()==0) htype = "I";
601 
602  TClass* cl = 0;
603 
604  switch (htype[0]) {
605  case 'C' : cl = TH2C::Class(); break;
606  case 'D' : cl = TH2D::Class(); break;
607  case 'F' : cl = TH2F::Class(); break;
608  case 'I' : cl = TH2I::Class(); break;
609  case 'S' : cl = TH2S::Class(); break;
610  default : cl = TH2I::Class();
611  }
612 
613  TH2* histo = (TH2*) TestObject(fxHistogramDir, foldername, histoname, cl);
614 
615  if (histo) return histo;
616 
617  switch(htype[0]) {
618  case 'C' : histo = new TH2C(histoname, histoname, nbinsx, xlow, xup, nbinsy, ylow, yup); break;
619  case 'D' : histo = new TH2D(histoname, histoname, nbinsx, xlow, xup, nbinsy, ylow, yup); break;
620  case 'F' : histo = new TH2F(histoname, histoname, nbinsx, xlow, xup, nbinsy, ylow, yup); break;
621  case 'I' : histo = new TH2I(histoname, histoname, nbinsx, xlow, xup, nbinsy, ylow, yup); break;
622  case 'S' : histo = new TH2S(histoname, histoname, nbinsx, xlow, xup, nbinsy, ylow, yup); break;
623  default : histo = new TH2I(histoname, histoname, nbinsx, xlow, xup, nbinsy, ylow, yup);
624  }
625 
626  if (title) histo->SetTitle(title);
627  if (xtitle) histo->SetXTitle(xtitle);
628  if (ytitle) histo->SetYTitle(ytitle);
629  AddHistogram(histo, foldername);
630  return histo;
631 }
632 
633 TFolder * TGo4AnalysisObjectManager::CreateBranchFolder(TObjArray* branchlist,
634  const char* name,
635  const char* title,
636  Bool_t istopbranch)
637 {
638  GO4TRACE((11,"TGo4AnalysisObjectManager::CreateBranchFolder(TObjArray*)",__LINE__, __FILE__));
639  if (branchlist==0) return 0;
640 
641  TList* nameslist= new TList;
642  TGo4ObjectStatus* state;
643  Int_t cursor=0;
644  TObject* entry = 0;
645  TIter iter(branchlist);
646  while((entry=iter()) !=0) {
647  if(entry->InheritsFrom(TBranch::Class())) {
648  // found subfolder, process it recursively
649  TBranch* subbranch= dynamic_cast<TBranch*> (entry);
650  TObjArray* subbranchlist = subbranch->GetListOfBranches();
651  if(subbranchlist!=0) {
652  if(subbranchlist->IsEmpty()) {
653  // subbranchlist is empty, add status object to folder
654  state=new TGo4BranchStatus(subbranch);
655  nameslist->AddLast(state);
656  } else {
657  // found subbranchlist
658  // test for composite event:
659 
660  TFolder* subnames = 0;
661 
662  TClass* cl = gROOT->GetClass(subbranch->GetClassName());
663  if((cl!=0) && cl->InheritsFrom(TGo4CompositeEvent::Class()) && istopbranch) {
664  // search for composite event of that name in Go4 (only if top level call)
665  TGo4CompositeEvent* cevent=0;
666  TString branchname(subbranch->GetName());
667  Ssiz_t leng = branchname.Length();
668  branchname.Resize(leng-1); // strip dot from branchname
669  //std::cout <<"searching for composite event "<< branchname.Data() << std::endl;
670  cevent = dynamic_cast<TGo4CompositeEvent*> (GetEventStructure(branchname.Data()));
671  if(cevent!=0) {
672  //std::cout <<"found top comp event" << std::endl;
673  Int_t skippedentries=0;
674  // we pass complete top branchlist to method
675  subnames = CreateCompositeBranchFolder(
676  branchlist,cevent,cursor+1,
677  &skippedentries,
678  cevent->GetName(),
679  cevent->GetTitle());
680  // skip comp subelements in iterator:
681  //std::cout <<"top skipped:"<<skippedentries<< std::endl;
682  // now process subbranchlist of top compevent,
683  // add members of this folder to existing folder subnames!
684  TFolder* temp = CreateBranchFolder(subbranchlist, "dummy","dummy");
685  subnames->GetListOfFolders()->AddAll(temp->GetListOfFolders());
686  for(Int_t t=0;t<skippedentries;++t) {
687  iter();
688  cursor++;
689  }
690  } else {
691  //std::cout <<"not found top comp event" << std::endl;
692  subnames=CreateBranchFolder(subbranchlist,
693  subbranch->GetName(),
694  subbranch->GetTitle());
695  }
696  } else {
697  //std::cout <<"no class or not top branch" << std::endl;
698  subnames=CreateBranchFolder(subbranchlist,
699  subbranch->GetName(), subbranch->GetTitle());
700  }
701  nameslist->AddLast(subnames);
702  } // if(subbranchlist->IsEmpty())
703  } else {
704  // no subbranchlist, should not happen...
705  // add status object to folder
706  state=new TGo4BranchStatus(subbranch);
707  nameslist->AddLast(state);
708  } // if(subbranchlist)
709  }
710  cursor++;
711  } // while((entry=iter()) !=0)
712 
713  TFolder* fold = fxTempFolder->AddFolder(name,title,nameslist);
714  fold->SetOwner(kTRUE);
715  fxTempFolder->Remove(fold);
716  return fold;
717 }
718 
719 Bool_t TGo4AnalysisObjectManager::AddTree(TTree* tree, const char* subfolder)
720 {
721  GO4TRACE((11,"TGo4AnalysisObjectManager::AddTree(TTree*, char*)",__LINE__, __FILE__));
722  return (AddObjectToFolder(tree,fxTreeDir,subfolder,kFALSE));
723 }
724 
725 Bool_t TGo4AnalysisObjectManager::RemoveTree(TTree * tree, const char* stepname)
726 {
727  GO4TRACE((11,"TGo4AnalysisObjectManager::RemoveTree(TTree*, const char*)",__LINE__, __FILE__));
728  if (tree==0) return kFALSE;
729 
730  TGo4LockGuard listguard(fxDirMutex);
731  fxTreeDir->Remove(tree);
732  return kTRUE;
733 }
734 
736 {
737  GO4TRACE((11,"TGo4AnalysisObjectManager::GetHistogram(char *)",__LINE__, __FILE__));
738  TH1* rev = dynamic_cast<TH1*> (FindObjectInFolder(fxHistogramDir, name));
739  if(rev==0) rev = dynamic_cast<TH1*> (FindObjectInFolder(fxUserDir, name)); // also check user objects dir
740  return rev;
741 }
742 
743 TTree * TGo4AnalysisObjectManager::GetTree(const char * name)
744 {
745  GO4TRACE((11,"TGo4AnalysisObjectManager::GetTree(char *)",__LINE__, __FILE__));
746  return dynamic_cast<TTree*> (FindObjectInFolder(fxTreeDir, name));
747 }
748 
749 Bool_t TGo4AnalysisObjectManager::RemoveHistogram(const char * name, Bool_t del)
750 {
751  GO4TRACE((11,"TGo4AnalysisObjectManager::RemoveHistogram(char*)",__LINE__, __FILE__));
752  //
753  return RemoveObjectFromFolder(name, fxHistogramDir, del);
754 }
755 
756 
758 {
759  GO4TRACE((11,"TGo4AnalysisObjectManager::AddAnalysisCondition(TGo4Condition *)",__LINE__, __FILE__));
760  return(AddObjectToFolder(con,fxConditionDir,subfolder,kTRUE));
761 }
762 
764  Bool_t counter, TFolder* parent)
765 {
766  GO4TRACE((11,"TGo4AnalysisObjectManager::SetAnalysisCondition(char*, TGo4Condition*, Bool_t)",__LINE__, __FILE__));
767 
768  if(con==0) return kFALSE;
769 
770  TGo4LockGuard listguard(fxDirMutex);
771  Bool_t rev(kFALSE);
772  TFolder* topfolder=0;
773  if(parent)
774  topfolder=parent;
775  else
776  topfolder=fxConditionDir;
777 
778  TObject* searchresult=topfolder->FindObjectAny(name);
779  if(searchresult==0)
780  searchresult=fxUserDir->FindObjectAny(name);
781  // condition may be under user objects folder if not found in topfolder
782  TGo4Condition* oldcon(0);
783  if(searchresult && searchresult->InheritsFrom(TGo4Condition::Class())) {
784  oldcon= dynamic_cast<TGo4Condition *> (searchresult);
785  } else
786  if (searchresult && searchresult->InheritsFrom(TFolder::Class())) {
787  // this is for the case that condition has same name as its folder!
788  TFolder* subf=dynamic_cast<TFolder*>(searchresult);
789  searchresult=subf->FindObjectAny(name);
790  oldcon= dynamic_cast<TGo4Condition *> (searchresult);
791  }
792  if(oldcon!=0) {
793  // update existing condition of given name
794  rev = oldcon->UpdateFrom(con,counter);
795  //std::cout << "++++ Updated condition "<< name<<" from condition "<< con->GetName() << std::endl;
796  //oldcon->PrintCondition(true);
797  } else {
798  // condition not yet exisiting, add external condition
799  TGo4Condition* clonedcon = dynamic_cast<TGo4Condition*>(con->Clone());
800 
801  TGo4PolyCond::CleanupSpecials(); // remove reference to cloned cut
802 
803  const char* separ = strrchr(name, '/');
804  if (separ!=0) {
805  TString fname(name, separ-name);
806  rev=AddObjectToFolder(clonedcon,topfolder,fname.Data(),kTRUE,kFALSE,kFALSE);
807  } else
808  rev=AddObjectToFolder(clonedcon,topfolder,0,kTRUE,kFALSE,kFALSE);
809 
810  }
811  return rev;
812 }
813 
814 TGo4Condition * TGo4AnalysisObjectManager::GetAnalysisCondition(const char * name, const char* cond_cl)
815 {
816  GO4TRACE((11,"TGo4AnalysisObjectManager::GetAnalysisCondition(char*)",__LINE__, __FILE__));
817  TGo4Condition* cond = dynamic_cast<TGo4Condition*> (FindObjectInFolder(fxConditionDir, name));
818  // some users have their conditions rather in user folder...
819  if(cond==0) cond = dynamic_cast<TGo4Condition*> (FindObjectInFolder(fxUserDir, name));
820 
821  if ((cond!=0) && (cond_cl!=0))
822  if(!cond->InheritsFrom(cond_cl)) cond = 0;
823 
824  return cond;
825 }
826 
828  const char* conditionname,
829  Double_t xlow,
830  Double_t xup,
831  const char* bindhistogram,
832  Bool_t invert)
833 {
834  TGo4WinCond* wcond = (TGo4WinCond*)
835  TestObject(fxConditionDir, foldername, conditionname, TGo4WinCond::Class());
836 
837  if (wcond) return wcond;
838 
839  wcond = new TGo4WinCond(conditionname);
840  wcond->SetValues(xlow, xup);
841  if (bindhistogram!=0)
842  wcond->SetHistogram(bindhistogram);
843  if (invert) wcond->Invert(invert);
844  AddAnalysisCondition(wcond, foldername);
845  return wcond;
846 }
847 
849  const char* conditionname,
850  Double_t xlow,
851  Double_t xup,
852  Double_t ylow,
853  Double_t yup,
854  const char* bindhistogram,
855  Bool_t invert)
856 {
857  TGo4WinCond* wcond = (TGo4WinCond*)
858  TestObject(fxConditionDir, foldername, conditionname, TGo4WinCond::Class());
859 
860  if (wcond) return wcond;
861 
862  wcond = new TGo4WinCond(conditionname);
863  wcond->SetValues(xlow, xup, ylow, yup);
864  if (bindhistogram!=0)
865  wcond->SetHistogram(bindhistogram);
866  if (invert) wcond->Invert(invert);
867  AddAnalysisCondition(wcond, foldername);
868  return wcond;
869 }
870 
872  const char* conditionname,
873  Int_t size,
874  Float_t (*points)[2],
875  const char* bindhistogram,
876  Bool_t invert)
877 {
878  TGo4PolyCond* pcond = (TGo4PolyCond*)
879  TestObject(fxConditionDir, foldername, conditionname, TGo4PolyCond::Class());
880 
881  if (pcond) return pcond;
882 
883  TArrayF fullx(size+1), fully(size+1);
884  int numpoints = size;
885 
886  for (int i=0;i<numpoints;i++) {
887  fullx[i] = points[i][0];
888  fully[i] = points[i][1];
889  }
890 
891  // connect first and last points
892  if ((fullx[0]!=fullx[numpoints-1]) || (fully[0]!=fully[numpoints-1])) {
893  fullx[numpoints] = fullx[0];
894  fully[numpoints] = fully[0];
895  numpoints++;
896  }
897 
898  TCutG mycat("initialcut", numpoints, fullx.GetArray(), fully.GetArray());
899  pcond = new TGo4PolyCond(conditionname);
900  pcond->SetValues(&mycat);
901  if (bindhistogram!=0)
902  pcond->SetHistogram(bindhistogram);
903  if (invert) pcond->Invert(invert);
904  AddAnalysisCondition(pcond, foldername);
905  return pcond;
906 }
907 
908 
910 {
911  GO4TRACE((11,"TGo4AnalysisObjectManager::RemoveAnalysisCondition(char*)",__LINE__, __FILE__));
912  return RemoveObjectFromFolder(name, fxConditionDir, kTRUE);
913 }
914 
915 TGo4ObjectStatus * TGo4AnalysisObjectManager::CreateObjectStatus(const char * name, const char* folder)
916 {
917  TNamed* object=GetObject(name, folder);
918  return CreateObjectStatus(object);
919 }
920 
922 {
923  if(obj==0) return 0;
924 
925  if(obj->InheritsFrom(TH1::Class()))
926  return new TGo4HistogramStatus(dynamic_cast<TH1*> (obj),fullinfo);
927 
928  if(obj->InheritsFrom(TGo4Parameter::Class()))
929  return new TGo4ParameterStatus(dynamic_cast<TGo4Parameter*> (obj), fullinfo);
930 
931  return new TGo4ObjectStatus(obj);
932 }
933 
935 {
936  GO4TRACE((11,"TGo4AnalysisObjectManager::CreateNamesList()",__LINE__, __FILE__));
937  TGo4LockGuard listguard(fxDirMutex);
938  TGo4AnalysisObjectNames* namesobject=0;
939  //fxTempFolder->Clear();
940  const char* name = TGo4Analysis::Instance()->GetName();
941  if ((name==0) || (strlen(name)==0)) name = "Go4NamesList";
942  namesobject= new TGo4AnalysisObjectNames(name);
943  namesobject->fxTopFolder=CreateNamesFolder(fxGo4Dir);
944  TGo4PolyCond::CleanupSpecials(); // remove references to cloned TCutG in status
945  return namesobject;
946 }
947 
948 TFolder * TGo4AnalysisObjectManager::CreateNamesFolder(TFolder * objectfolder)
949 {
950  GO4TRACE((11,"TGo4AnalysisObjectManager::CreateNamesFolder(TFolder*)",__LINE__, __FILE__));
951  if (objectfolder==0) return 0;
952 
953  TList* nameslist= new TList;
954  TIter listiter(objectfolder->GetListOfFolders());
955  TObject* entry;
956  while((entry=listiter())!=0) {
957  if(entry->InheritsFrom(TFolder::Class())) {
958  // found subfolder, process it recursively
959  //std::cout <<"##### parsing folder "<< entry->GetName() << std::endl;
960  TFolder* subobj= dynamic_cast<TFolder*> (entry);
961  TFolder* subnames = CreateNamesFolder(subobj);
962  nameslist->AddLast(subnames);
963  } else
964 
965  if (entry->InheritsFrom(TTree::Class())) {
966  // treestructure should be ObjectStatus?
967  TTree* subobj= dynamic_cast<TTree*> (entry);
968  TGo4TreeStructure* treestruct=CreateTreeStructure(subobj);
969  nameslist->AddLast(treestruct);
970  } else
971 
972  if(entry->InheritsFrom(TGo4EventElement::Class())) {
973  TFolder* evfolder = CreateMembersFolder(entry, entry->GetName(), entry->IsA());
974  if (evfolder!=0)
975  nameslist->AddLast(evfolder);
976  } else {
977 
978  TGo4ObjectStatus*state = CreateObjectStatus(entry,kFALSE); // do not use full status info for nameslist
979  if(state!=0)
980  nameslist->AddLast(state);
981  }
982  } // while
983 
984  TFolder* namesfolder = fxTempFolder->AddFolder(objectfolder->GetName(),objectfolder->GetTitle(),nameslist);
985  fxTempFolder->Remove(namesfolder);
986  namesfolder->SetOwner(kTRUE);
987 
988  return namesfolder;
989 }
990 
992 {
993  return fxGo4Dir;
994 }
995 
997 {
998  GO4TRACE((11,"TGo4AnalysisObjectManager::AddEventStore(TGo4EventStore*)",__LINE__, __FILE__));
999  return (AddObjectToFolder(store,fxStoreDir,0,kFALSE));
1000 }
1001 
1003 {
1004  GO4TRACE((11,"TGo4AnalysisObjectManager::RemoveEventStore(TGo4EventStore*)",__LINE__, __FILE__));
1005  Bool_t rev=kFALSE;
1006  if(store)
1007  {
1008  TGo4LockGuard listguard(fxDirMutex);
1009  fxStoreDir->Remove(store);
1010  rev=kTRUE;
1011  }
1012  else
1013  {
1014  rev=kFALSE;
1015  }
1016  return rev;
1017 }
1018 
1020 {
1021  GO4TRACE((11,"TGo4AnalysisObjectManager::AddEventSource(TGo4EventSource*)",__LINE__, __FILE__));
1022  return (AddObjectToFolder(source,fxSourceDir,0,kFALSE));
1023 }
1024 
1026 {
1027  GO4TRACE((11,"TGo4AnalysisObjectManager::RemoveEventSource(TGo4EventSource*)",__LINE__, __FILE__));
1028  Bool_t rev=kFALSE;
1029  if(source)
1030  {
1031  TGo4LockGuard listguard(fxDirMutex);
1032  fxSourceDir->Remove(source);
1033  rev=kTRUE;
1034  }
1035  else
1036  {
1037  rev=kFALSE;
1038  }
1039  return rev;
1040 }
1042 {
1043  GO4TRACE((11,"TGo4AnalysisObjectManager::AddEventProcessor(TGo4EventProcessor*)",__LINE__, __FILE__));
1044  return (AddObjectToFolder(pro,fxProcessorDir,0,kFALSE));
1045 }
1046 
1048 {
1049  GO4TRACE((11,"TGo4AnalysisObjectManager::RemoveEventProcessor(TGo4EventProcessr*)",__LINE__, __FILE__));
1050  Bool_t rev=kFALSE;
1051  if(pro)
1052  {
1053  TGo4LockGuard listguard(fxDirMutex);
1054  fxProcessorDir->Remove(pro);
1055  rev=kTRUE;
1056  }
1057  else
1058  {
1059  rev=kFALSE;
1060  }
1061  return rev;
1062 }
1064 {
1065  GO4TRACE((11,"TGo4AnalysisObjectManager::AddEventStructure(TGo4EventElement*)",__LINE__, __FILE__));
1066  return (AddObjectToFolder(ev,fxEventDir,0,kFALSE));
1067 }
1068 
1070 {
1071  GO4TRACE((11,"TGo4AnalysisObjectManager::RemoveEventStructure(TGo4EventElement*)",__LINE__, __FILE__));
1072  Bool_t rev=kFALSE;
1073  if(ev!=0) {
1074  TGo4LockGuard listguard(fxDirMutex);
1075  fxEventDir->Remove(ev);
1076  // remove pointers to event data from all dynamic lists:
1077  CleanupDynamicLists(ev);
1078  rev=kTRUE;
1079  }
1080  return rev;
1081 }
1082 
1084 {
1085  GO4TRACE((11,"TGo4AnalysisObjectManager::GetEvenStructure(char *)",__LINE__, __FILE__));
1086 
1087  if ((name==0) || (strlen(name)==0)) return 0;
1088 
1089  TString path(name);
1090  TGo4EventElement* curr(0);
1091 
1092  while (path.Length()>0) {
1093  Int_t pos = path.Index("/");
1094  if (pos==0) { path.Remove(0, 1); continue; }
1095 
1096  TString sub = path;
1097  if (pos>0) { sub.Resize(pos); path.Remove(0, pos+1); }
1098  else { path.Clear(); }
1099 
1100  if (curr==0)
1101  curr = dynamic_cast<TGo4EventElement*> (FindObjectInFolder(fxEventDir, sub.Data()));
1102  else {
1103  TGo4EventElement* chld = curr->GetChild(sub.Data());
1104  // this is artefact of folder structures in go4 browser
1105  // event can have subfolder which corresponds to the subevent
1106  // but it also could have subfolder which corresponds to parent class
1107  // in second case just ignore all other artificial subfolders
1108  if ((chld==0) && curr->InheritsFrom(sub.Data())) return curr;
1109  curr = chld;
1110  }
1111 
1112  if (curr==0) return 0;
1113  }
1114 
1115  return curr;
1116 }
1117 
1119 {
1120  if(entry) entry->Reset();
1121  return AddObjectToFolder(entry, fxDynListDir, 0, kTRUE, kFALSE, kFALSE);
1122 }
1123 
1125 {
1126  GO4TRACE((11,"TGo4AnalysisObjectManager::ResetBackStores()",__LINE__, __FILE__));
1127  Bool_t rev=kTRUE;
1128  TIter iter(fxStoreDir->GetListOfFolders());
1129  TObject* entry = 0;
1130  while((entry=iter()) !=0) {
1131  TGo4BackStore* bs= dynamic_cast<TGo4BackStore*>(entry);
1132  if(bs!=0) bs->Reset(clearflag);
1133  } // while
1134  return rev;
1135 }
1136 
1138 {
1139  GO4TRACE((14,"TGo4AnalysisObjectManager::CloseAnalysis()",__LINE__, __FILE__));
1141  fiDynListCount=0;
1142  TGo4Analysis::Instance()->Message(0,"Analysis Object Manager -- Dynamic List was reset.");
1143 }
1144 
1146 {
1147  if(!file) return;
1148  TGo4Analysis::Instance()->Message(0,"Analysis Object Manager -- Saving objects to file %s",file->GetName());
1149  fxGo4Dir->RecursiveRemove(fxTreeDir); // do not save the trees twice!
1150  fxGo4Dir->RecursiveRemove(fxAnalysisDir); // do not save eventclass refs
1152  //fxGo4Dir->Write(0, TObject::kOverwrite);
1155  TDirectory* savdir=gDirectory;
1156  file->cd();
1157  // file->Delete("T*;*"); // remove old contents (get rid of deleted dynamic objects)
1158  // note: we always use RECREATE option on saving now. No need to cleanup old file!
1160  file->Write(0,TObject::kOverwrite); // write all appended objects and subdirs
1161  savdir->cd();
1162  RemoveFromDir(fxGo4Dir,file); // prevent object deletion on closing the file
1164  fxGo4Dir->Add(fxTreeDir);
1165  fxGo4Dir->Add(fxAnalysisDir);
1166 }
1167 Bool_t TGo4AnalysisObjectManager::AddParameter(TGo4Parameter * par, const char* subfolder)
1168 {
1169  GO4TRACE((11,"TGo4AnalysisObjectManager::AddParameter(TGo4Parameter *)",__LINE__, __FILE__));
1170  return (AddObjectToFolder(par,fxParameterDir,subfolder,kTRUE));
1171 }
1172 
1173 Bool_t TGo4AnalysisObjectManager::SetParameter(const char* name, TGo4Parameter * par, TFolder* parent)
1174 {
1175  GO4TRACE((11,"TGo4AnalysisObjectManager::SetParameter(const char*, TGo4Parameter*)",__LINE__, __FILE__));
1176 
1177  if (par==0) return kFALSE;
1178 
1179  Bool_t rev(kFALSE);
1180  TFolder* topfolder = parent ? parent : fxParameterDir;
1181  TGo4Parameter* oldpar= dynamic_cast<TGo4Parameter*> (topfolder->FindObjectAny(name));
1182  if(oldpar!=0) {
1183  // update existing parameter of given name
1184  rev = oldpar->UpdateFrom(par);
1185  TGo4Log::Info("Updated parameter %s from parameter %s", name, par->GetName());
1186  //oldpar->PrintParameter();
1187  } else {
1188  // parameter not yet existing, add external parameter as a copy:
1189  TGo4Parameter* clonedpar=dynamic_cast<TGo4Parameter*>(par->Clone());
1190 
1191  const char* separ = strrchr(name, '/');
1192  if (separ!=0) {
1193  TString fname(name, separ-name);
1194  rev=AddObjectToFolder(clonedpar,topfolder, fname.Data(), kTRUE);
1195  TGo4Log::Info("Added new parameter %s to folder %s/%s", clonedpar->GetName(), topfolder->GetName(), fname.Data());
1196  } else
1197  rev=AddObjectToFolder(clonedpar,topfolder,0,kTRUE);
1198  }
1199  return rev;
1200 }
1201 
1202 Bool_t TGo4AnalysisObjectManager::SetParameterStatus(const char* name, TGo4ParameterStatus* status, TFolder* parent)
1203 {
1204  GO4TRACE((11,"TGo4AnalysisObjectManager::SetParameter(char*, TGo4Parameter*)",__LINE__, __FILE__));
1205 
1206  if (status==0) return kFALSE;
1207 
1208  Bool_t rev (kFALSE);
1209  TFolder* topfolder = (parent!=0) ? parent : fxParameterDir;
1210 
1211  TGo4Parameter* oldpar= dynamic_cast<TGo4Parameter*> (topfolder->FindObjectAny(name));
1212  if(oldpar!=0) {
1213  // update existing parameter of given name
1214  rev = status->UpdateParameterValues(oldpar);
1215  } else {
1216  // parameter not yet existing, add external parameter as a copy:
1217  TGo4Parameter* clonedpar = status->CreateParameter();
1218  // find out destination folder for new parameter from name:
1219 
1220  const char* separ = strrchr(name, '/');
1221  if (separ!=0) {
1222  TString fname(name, separ-name);
1223  rev=AddObjectToFolder(clonedpar,topfolder, fname.Data(), kTRUE);
1224  } else {
1225  rev=AddObjectToFolder(clonedpar,topfolder,0,kTRUE);
1226  }
1227  }
1228  return rev;
1229 }
1230 
1231 TGo4Parameter * TGo4AnalysisObjectManager::GetParameter(const char * name, const char* parameter_class)
1232 {
1233  GO4TRACE((11,"TGo4AnalysisObjectManager::GetParameter(char*)",__LINE__, __FILE__));
1234  TGo4Parameter* rev=dynamic_cast<TGo4Parameter *> (FindObjectInFolder(fxParameterDir,name));
1235  if(rev==0) rev= dynamic_cast<TGo4Parameter *> (FindObjectInFolder(fxUserDir,name));
1236  if ((rev!=0) && (parameter_class!=0))
1237  if (!rev->InheritsFrom(parameter_class)) rev=0;
1238  return rev;
1239 }
1240 
1242 {
1243  GO4TRACE((11,"TGo4AnalysisObjectManager::RemoveParameter(char*)",__LINE__, __FILE__));
1244  return RemoveObjectFromFolder(name, fxParameterDir, kTRUE);
1245 }
1246 
1247 Bool_t TGo4AnalysisObjectManager::AddPicture(TGo4Picture * pic, const char* subfolder)
1248 {
1249  GO4TRACE((11,"TGo4AnalysisObjectManager::AddPicture(TGo4Picture *)",__LINE__, __FILE__));
1250  if(!pic) return kFALSE;
1251 
1252  //pic->LocateObjectsFrom(fxGo4Dir);
1253  return (AddObjectToFolder(pic,fxPictureDir,subfolder,kTRUE));
1254 }
1255 
1256 Bool_t TGo4AnalysisObjectManager::SetPicture(const char* name, TGo4Picture * pic, TFolder* parent)
1257 {
1258  GO4TRACE((11,"TGo4AnalysisObjectManager::SetPicture(char*, TGo4Picture*)",__LINE__, __FILE__));
1259 
1260  if (pic==0) return kFALSE;
1261 
1262  Bool_t rev(kTRUE);
1263  TFolder* topfolder=0;
1264  if(parent)
1265  topfolder=parent;
1266  else
1267  topfolder=fxPictureDir;
1268 
1269  TGo4Picture* oldpic = dynamic_cast<TGo4Picture *> (topfolder->FindObjectAny(name));
1270  if(oldpic!=0) {
1271  // update existing picture of given name
1272  oldpic->UpdateFrom(pic);
1273  // std::cout << "++++ Updated picture "<< name<<" from picture "<< pic->GetName() << std::endl;
1274  } else {
1275  // picture not yet exisiting, add external as a copy:
1276  TGo4Picture* clonedpic = dynamic_cast<TGo4Picture*>(pic->Clone());
1277  // find out destination folder for new pic from name:
1278 
1279  const char* separ = strrchr(name, '/');
1280  if (separ!=0) {
1281  TString fname(name, separ-name);
1282  rev = AddObjectToFolder(clonedpic, topfolder, fname.Data(),kTRUE);
1283  } else
1284  rev = AddObjectToFolder(clonedpic, topfolder, 0, kTRUE);
1285  }
1286  return rev;
1287 }
1288 
1290 {
1291  GO4TRACE((11,"TGo4AnalysisObjectManager::GetPicture(char*)",__LINE__, __FILE__));
1292  TGo4Picture* rev=dynamic_cast<TGo4Picture *> (FindObjectInFolder(fxPictureDir, name));
1293  if(rev==0) rev=dynamic_cast<TGo4Picture *> (FindObjectInFolder(fxUserDir, name));
1294  return rev;
1295 }
1296 
1298 {
1299  GO4TRACE((11,"TGo4AnalysisObjectManager::RemovePicture(char*)",__LINE__, __FILE__));
1300  return RemoveObjectFromFolder(name, fxPictureDir, kTRUE);
1301 }
1302 
1303 Bool_t TGo4AnalysisObjectManager::AddCanvas(TCanvas * can, const char* subfolder)
1304 {
1305  GO4TRACE((11,"TGo4AnalysisObjectManager::AddCanvas(TCanvas *)",__LINE__, __FILE__));
1306 
1307  Bool_t rev = AddObjectToFolder(can,fxCanvasDir,subfolder,kFALSE);
1308 
1309  if (rev && can) can->SetBit(kMustCleanup);
1310 
1311  // do not remove canvas from global list - it has effect on normal ROOT methods
1312 // if(rev && can) gROOT->GetListOfCanvases()->Remove(can);
1313 
1314  return rev;
1315 }
1316 
1317 TCanvas * TGo4AnalysisObjectManager::GetCanvas(const char * name)
1318 {
1319  GO4TRACE((11,"TGo4AnalysisObjectManager::GetPicture(char*)",__LINE__, __FILE__));
1320  TCanvas* rev=dynamic_cast<TCanvas*> (FindObjectInFolder(fxCanvasDir, name));
1321  if(rev==0) rev=dynamic_cast<TCanvas*> (FindObjectInFolder(fxCanvasDir, name));
1322  return rev;
1323 }
1324 
1326 {
1327  GO4TRACE((11,"TGo4AnalysisObjectManager::RemovePicture(char*)",__LINE__, __FILE__));
1328  return RemoveObjectFromFolder(name, fxCanvasDir, kTRUE);
1329 }
1330 
1331 
1333 {
1334  GO4TRACE((11,"TGo4AnalysisObjectManager::LoadObjects(TFile*)",__LINE__, __FILE__));
1335  Bool_t rev=kFALSE;
1336  if(obfile)
1337  {
1338  TObject* ob=obfile->Get(TGo4AnalysisObjectManager::fgcTOPFOLDER);
1339  TFolder* top= dynamic_cast<TFolder*>(ob);
1340  if(top)
1341  {
1342  // kept for backward compatibility: read folder struct directly
1343  //std::cout << "found top go4 folder "<< std::endl;
1344  rev=LoadFolder(top,fxGo4Dir,kFALSE);
1345  }
1346  else
1347  {
1348  // new: convert directory structure of file into folders
1349  //std::cout <<"LoadObjects with Dirscan..." << std::endl;
1350  rev=LoadFolder(obfile,fxGo4Dir,kFALSE);
1351  }
1352  TGo4PolyCond::CleanupSpecials(); // remove references to file cuts
1354  }
1355 
1356  return rev;
1357 }
1358 
1360 {
1362 }
1363 
1365 {
1366  fiDynListCount++;
1367  // normally, all entries are processed eventwise
1368  // except for treehistogramentries
1369  Bool_t processtrees = (fiDynListCount % fiDynListInterval)==0;
1371  if(processtrees) ResetBackStores();
1372 }
1373 
1375 {
1377 }
1378 
1380  const char* histo,
1381  const char* hevx, const char* hmemx,
1382  const char* hevy, const char* hmemy,
1383  const char* hevz, const char* hmemz,
1384  const char* condition,
1385  const char* cevx, const char* cmemx,
1386  const char* cevy, const char* cmemy)
1387 {
1388  if(name==0 || histo==0 || hevx==0 || hmemx==0) return kFALSE;
1389  TGo4HistogramEntry* entry = new TGo4HistogramEntry(name);
1390 
1391  entry->SetHistogramName(histo);
1392 
1393  if ((hevx!=0) && (hmemx!=0)) {
1394  entry->SetHisEventName(0, hevx);
1395  entry->SetHisVarName(0, hmemx);
1396  }
1397 
1398  if ((hevy!=0) && (hmemy!=0)) {
1399  entry->SetHisEventName(1, hevy);
1400  entry->SetHisVarName(1, hmemy);
1401  }
1402 
1403  if ((hevz!=0) && (hmemz!=0)) {
1404  entry->SetHisEventName(2, hevz);
1405  entry->SetHisVarName(2, hmemz);
1406  }
1407 
1408  if((condition!=0) && (cevx!=0) && (cmemx!=0)) {
1409  entry->SetConditionName(condition);
1410  entry->SetConEventName(0, cevx);
1411  entry->SetConVarName(0, cmemx);
1412  if((cevy!=0) && (cmemy!=0)) {
1413  entry->SetConEventName(1, cevy);
1414  entry->SetConVarName(1, cmemy);
1415  }
1416  }
1417 
1418  return AddDynamicEntry(entry);
1419 }
1420 
1421 Bool_t TGo4AnalysisObjectManager::AddTreeHistogram(const char* hisname, const char* treename, const char* varexp, const char* cutexp)
1422 {
1423  GO4TRACE((11,"TGo4AnalysisObjectManager::AddTreeHistogram(char*,...)",__LINE__, __FILE__));
1424  //
1425  Bool_t rev=kFALSE;
1426  TGo4TreeHistogramEntry* tentry =
1427  new TGo4TreeHistogramEntry(hisname, treename, varexp, cutexp);
1428  if(AddDynamicEntry(tentry)) {
1429  TGo4Analysis::Instance()->Message(0,"Analysis added tree histogram %s to dynamic list", tentry->GetName());
1430  rev=kTRUE;
1431  } else {
1432  TGo4Analysis::Instance()->Message(0,"!!! Analysis AddTreeHistogram- ERROR: entry %s already exists !!!", tentry->GetName());
1433  delete tentry;
1434  }
1435  return rev;
1436 }
1437 
1438 
1440 {
1441  return RemoveObjectFromFolder(entryname, fxDynListDir, kTRUE);
1442 }
1443 
1444 
1445 TFolder* TGo4AnalysisObjectManager::FindSubFolder(TFolder* parent, const char* subfolder, Bool_t create)
1446 {
1447  GO4TRACE((11,"TGo4AnalysisObjectManager::FindSubFolder(TFolder*, const char*, Bool_t)",__LINE__, __FILE__));
1448  TGo4LockGuard dirguard(fxDirMutex);
1449  TFolder* result=0;
1450  if(parent==0) return 0;
1451  if(subfolder==0) return parent;
1452  const char* separ = strchr(subfolder,'/'); // find end of first subfolder string
1453  if(separ!=0) {
1454  // we have subfolder of subfolder, process recursively
1455  TString subname(subfolder, separ - subfolder);
1456 
1457  //std::cout <<" fffffff Searching for subfolder "<< subname << std::endl;
1458  TFolder* nextsubfolder = FindSubFolder(parent, subname.Data(), create); // get folder directly under parent
1459  result = FindSubFolder(nextsubfolder, separ+1,create); // search rest of path in this folder
1460  } else {
1461  // only one level of subfolder, find it directly
1462  TIter listiter(parent->GetListOfFolders());
1463  TObject* entry;
1464  while((entry=listiter()) !=0)
1465  if(entry->InheritsFrom(TFolder::Class()))
1466  if(!strcmp(subfolder,entry->GetName())) {
1467  result= dynamic_cast<TFolder*>(entry);
1468  break;
1469  }
1470  if(result==0 && create)
1471  result=parent->AddFolder(subfolder,"UserFolder"); // create new subfolder if not found
1472  } // if (endname!=0)
1473  return result;
1474 }
1475 
1476 
1478  TFolder* fold,
1479  const char* subfolder,
1480  Bool_t replace,
1481  Bool_t uniquename,
1482  Bool_t resetbits)
1483 {
1484  GO4TRACE((11,"TGo4AnalysisObjectManager::AddObjectToFolder(TObject *, TFolder*, const char*, Bool_t)",__LINE__, __FILE__));
1485 
1486  TGo4LockGuard dirguard(fxDirMutex);
1487  if(fold==0) return kFALSE;
1488 
1489  if (ob==0) {
1490  GO4TRACE((12,"TGo4AnalysisObjectManager::AddObjectToFolder - zero object",__LINE__, __FILE__));
1491  return kFALSE;
1492  }
1493 
1494  if(resetbits) {
1495  ob->ResetBit(TGo4Status::kGo4NoReset);
1496  ob->ResetBit(TGo4Status::kGo4CanDelete); // default behavior: allow reset, disable delete
1497  }
1498 
1499  TString subname;
1500  if (subfolder && (strlen(subfolder)!=0)) {
1501  subname = subfolder;
1502  if (subname[subname.Length()-1] == '/')
1503  subname.Resize(subname.Length()-1);
1504  }
1505 
1506  TObject* oldob=0;
1507  if(uniquename) {
1508  // look for object of identical name anywhere in top folder
1509  oldob=fold->FindObjectAny( ob->GetName() );
1510  } else {
1511  TString obname;
1512 
1513  if (subname.Length()>0)
1514  obname = subname + "/" + ob->GetName();
1515  else
1516  obname = ob->GetName();
1517 
1518  // only check for objects that are in given subfolder
1519  oldob = fold->FindObjectAny(obname.Data());
1520  }
1521 
1522  // is object already in folder?
1523  if(oldob) {
1524  //yes, shall we replace? check if pointers are identical first!
1525  if(replace && ob!=oldob) {
1526  // remove old reference before adding new one:
1527  fold->RecursiveRemove(oldob);
1528  CleanupDynamicLists(oldob);
1529 
1530  // std::cout << "Delete object " << oldob << " name = " << oldob->GetName() << " isgpad = " << (oldob == gPad) << std::endl;
1531 
1532  delete oldob;
1533  } else {
1534 
1535  //std::cout << "Find old object " << oldob << " name = " << oldob->GetName() << endl;
1536 
1537  return kFALSE; // do not overwrite old one
1538  }
1539  }
1540 
1541  TFolder* addDir(0);
1542  if(subfolder)
1543  addDir = FindSubFolder(fold, subname, kTRUE);
1544  if(addDir==0) addDir = fold;
1545  // if(subfolder)
1546  addDir->Add(ob);
1547 
1548  return kTRUE;
1549 }
1550 
1551 
1552 Bool_t TGo4AnalysisObjectManager::RemoveObjectFromFolder(const char* fullname, TFolder* fold, Bool_t isDel)
1553 {
1554  GO4TRACE((11,"TGo4AnalysisObjectManager::RemoveObjectFromFolder(const char*, TFolder*, Bool_t)",__LINE__, __FILE__));
1555  //
1556  if(fold==0) return kFALSE;
1557  TGo4LockGuard dirguard(fxDirMutex);
1558  TObject* obj = 0;
1559  Int_t buflen = fguSUBFOLDERMAXLEN;
1560  char buffer[fguSUBFOLDERMAXLEN];
1561  if(fullname) {
1562  strncpy(buffer,fullname,buflen-10);
1563  obj = fold->FindObjectAny(buffer);
1564  }
1565 
1566  if(obj!=0) {
1567  fold->RecursiveRemove(obj);
1568  CleanupDynamicLists(obj);
1569  if (isDel) delete obj;
1570  TGo4Analysis::Instance()->Message(0,"Analysis: removed object %s",buffer);
1571  return kTRUE;
1572  }
1573 
1574  TGo4Analysis::Instance()->Message(0,"!!! Analysis: removing object %s FAILED !!!",buffer);
1575  return kFALSE;
1576 }
1577 
1578 Bool_t TGo4AnalysisObjectManager::LoadFolder(TFolder* source, TFolder* destination, Bool_t replace)
1579 {
1580  if (source==0) return kFALSE;
1581  GO4TRACE((11,"TGo4AnalysisObjectManager::LoadFolder(TFolder*, TFolder*, Bool_t replace)",__LINE__, __FILE__));
1582  TGo4LockGuard dirguard(fxDirMutex);
1583  Bool_t rev=kTRUE;
1584  TIter folderiter(source->GetListOfFolders());
1585  TObject* ob=0;
1586  while(( ob=folderiter() ) !=0)
1587  {
1588  if(ob->InheritsFrom(TFolder::Class()))
1589  {
1590  TFolder* subfolder =dynamic_cast<TFolder*> (ob);
1591  if(subfolder)
1592  {
1593  //std::cout <<"LLLLLL Load folder scanning subfolder "<< subfolder->GetName() << std::endl;
1594  TFolder* subdest=FindSubFolder(destination,subfolder->GetName(), kTRUE);
1595  LoadFolder(subfolder,subdest,replace); // recursively scan all subfolders
1596  }
1597  }
1598  else
1599  {
1600  rev=PutToFolder(ob,destination,replace);
1601  }
1602  } // while(..)
1603  return rev;
1604 }
1605 
1606 Bool_t TGo4AnalysisObjectManager::LoadFolder(TDirectory* source, TFolder* destination, Bool_t replace)
1607 {
1608  GO4TRACE((11,"TGo4AnalysisObjectManager::LoadFolder(TDirectory*, TFolder*, Bool_t replace)",__LINE__, __FILE__));
1609  if(!source || !destination) return kFALSE;
1610  TGo4LockGuard dirguard(fxDirMutex);
1611  Bool_t rev=kTRUE;
1612  TDirectory* savdir=gDirectory;
1613  source->cd(); // this is necessary to let the TKey::ReadObj work!
1614  source->ReadKeys();
1615  TIter keyiter(source->GetListOfKeys());
1616  TObject* keyob=0;
1617  TKey* key=0;
1618  while(( keyob=keyiter() ) !=0)
1619  {
1620  key=dynamic_cast<TKey*>(keyob);
1621  if(key==0)
1622  {
1623  TGo4Analysis::Instance()->Message(3,"Analysis LoadFolder: ZERO key in directory %s",
1624  source->GetName());
1625  return kFALSE;
1626  }
1627  //std::cout <<"Reading key "<<key->GetName() << std::endl;
1628  TObject* ob = key->ReadObj();
1629  if(ob==0)
1630  {
1631  TGo4Analysis::Instance()->Message(2,"Analysis LoadFolder: Retrying to read key %s ...",
1632  key->GetName());
1633  ob=source->Get(key->GetName());
1634  if(ob==0)
1635  {
1636  TGo4Analysis::Instance()->Message(3,"Analysis LoadFolder: Failed to read key %s !",
1637  key->GetName());
1638  return kFALSE;
1639  }
1640  }
1641 
1642  if(ob->InheritsFrom(TDirectory::Class()))
1643  {
1644  TDirectory* subdir =dynamic_cast<TDirectory*> (ob);
1645  if(subdir)
1646  {
1647  //std::cout <<"LLLLLL Load folder dir scanning for subdir "<< subdir->GetName() << std::endl;
1648  Bool_t inpicturefolder=kFALSE;
1649  if(!strcmp(subdir->GetName(),fgcPICTFOLDER)) inpicturefolder=kTRUE;
1650  if(inpicturefolder) fbSuppressLoadHistograms=kTRUE;
1651  TFolder* subdest=FindSubFolder(destination,subdir->GetName(), kTRUE);
1652  rev=LoadFolder(subdir,subdest,replace); // recursively scan all subfolders
1653  if(inpicturefolder) fbSuppressLoadHistograms=kFALSE;
1654  }
1655  }
1656  else
1657  {
1658  rev=PutToFolder(ob,destination,replace);
1659  }
1660  } // while(..)
1661  savdir->cd();
1662  return rev;
1663 }
1664 
1665 Bool_t TGo4AnalysisObjectManager::PutToFolder(TObject* ob, TFolder* destination, Bool_t replace)
1666 {
1667  if(!ob || !destination) return kFALSE;
1668  Bool_t rev=kTRUE;
1669  //std::cout <<"put to folder for "<<ob->GetName() << std::endl;
1670  if (ob->InheritsFrom(TGo4DynamicEntry::Class())) {
1671  // new autosave file structure will save dynamic entries independently:
1672  TGo4DynamicEntry* dentry =dynamic_cast<TGo4DynamicEntry*> ( ob->Clone() ); // deep copy of source object!
1673  AddDynamicEntry(dentry);
1674  //std::cout <<"Added dynamic entry from file: "<<dentry->GetName() << std::endl;
1675  } else
1676  if(ob->InheritsFrom(TGo4Parameter::Class())) {
1677  // parameters never replaced, but updated
1678  TGo4Parameter* par = dynamic_cast<TGo4Parameter*>(ob);
1679  SetParameter(ob->GetName(),par,destination);
1680  } else
1681  if(ob->InheritsFrom(TGo4Picture::Class())) {
1682  // pictures never replaced, but updated
1683  TGo4Picture* pic =dynamic_cast<TGo4Picture*>(ob);
1684  //std::cout <<"LLLLLoad Folder SetsPicture!!!!!" << std::endl;
1685  SetPicture(ob->GetName(),pic,destination);
1686  } else
1687  if(ob->InheritsFrom(TGo4Condition::Class())) {
1688  // conditions not replaced, but updated
1689  TGo4Condition* con =dynamic_cast<TGo4Condition*>(ob);
1690  SetAnalysisCondition(ob->GetName(),con,kTRUE, destination);
1691  } else
1692  if(ob->InheritsFrom(TH1::Class())) {
1693  if(fbSuppressLoadHistograms) return kFALSE;
1694  // test: do not clone histos, but change dir from asf file to memory
1695  TH1* his = dynamic_cast<TH1*>(ob);
1696  if(AddObjectToFolder(his,destination,0,replace,kFALSE,kFALSE)) {
1697  his->SetDirectory(gROOT); // set directory for histos, needed for TTree::Draw
1698  TGo4Analysis::Instance()->Message(0,"Analysis LoadFolder: Histogram %s was loaded.",
1699  his->GetName());
1700  //std::cout <<"Changed directory of histo "<<his->GetName() << std::endl;
1701  }
1702  } else
1703  if(ob->InheritsFrom(TCanvas::Class())) {
1704  TObject* addob = ob->Clone(); // deep copy of source object!
1705  if(AddObjectToFolder(addob, destination, 0, replace)) {
1706  TGo4Analysis::Instance()->Message(0,"Analysis LoadFolder: Object %s was loaded.", addob->GetName());
1707  } else {
1708  // object already there and noreplace set: delete clone
1709  delete addob;
1710  if (gPad==addob) gPad = 0;
1711  }
1712  } else {
1713  //std::cout << "Make object clone " << ob->GetName() << " class = " << ob->ClassName() << std::endl;
1714 
1715  TObject* addob = ob->Clone(); // deep copy of source object!
1716  if(AddObjectToFolder(addob,destination,0,replace)) {
1717  TGo4Analysis::Instance()->Message(0,"Analysis LoadFolder: Object %s was loaded.", addob->GetName());
1718  } else {
1719  delete addob;
1720  }
1721  }
1722  return rev;
1723 }
1724 
1725 
1726 
1728 {
1729  if (source==0) return kFALSE;
1730  TGo4LockGuard dirguard(fxDirMutex);
1731  Bool_t rev=kTRUE;
1732  TIter folderiter(source->GetListOfFolders());
1733  TObject* ob=0;
1734  while(( ob=folderiter() ) !=0) {
1735  if(ob->InheritsFrom(TFolder::Class())) {
1736  TFolder* subfolder =dynamic_cast<TFolder*> (ob);
1737  if(subfolder)
1738  {
1739  TDirectory* currentdir=gDirectory;
1740  const char* subfoldername=subfolder->GetName();
1741  TDirectory* subdir=dynamic_cast<TDirectory*>(currentdir->Get(subfoldername));
1742  if(subdir==0)
1743  {
1744  subdir=currentdir->mkdir(subfoldername,"subdir");
1745  //std::cout <<"SSSS Save folder created subdir "<<subfoldername << std::endl;
1746  }
1747  else
1748  {
1749  //std::cout <<"SSSS Save folder found existing subdir "<<subfoldername << std::endl;
1750  }
1751 
1752  if(subdir)
1753  {
1754  subdir->cd();
1755  //std::cout <<"SSSS Save folder scanning subfolder "<< subfolder->GetName() << std::endl;
1756  SaveFolder(subfolder); // recursively scan all subfolders
1757  }
1758  else
1759  {
1760  TGo4Analysis::Instance()->Message(2,"Analysis SaveFolder: Could not assign subdirectory %s to folder.",
1761  subfoldername);
1762  }
1763  currentdir->cd();
1764  }
1765  } else
1766  AppendToDir(ob,gDirectory);
1767  } // while(..)
1768  return rev;
1769 }
1770 
1771 void TGo4AnalysisObjectManager::AppendToDir(TObject* ob, TDirectory* dir)
1772 {
1773  if(!ob || !dir) return;
1774  // note: we do not check for old objects anymore, because
1775  // file is generally cleaned up before writing now JA
1776  //TObject* oldob=dir->Get(ob->GetName());
1777  //if(oldob)
1778  // {
1781  // }
1782  dir->Append(ob);
1783 }
1784 
1785 void TGo4AnalysisObjectManager::RemoveFromDir(TFolder* fold, TDirectory* dir)
1786 {
1787  if((fold==0) || (dir==0)) return;
1788 
1789  TIter iter(fold->GetListOfFolders());
1790  TObject* ob = 0;
1791  while((ob = iter()) !=0) {
1792  if(ob->InheritsFrom(TFolder::Class())) {
1793  TFolder* subfolder =dynamic_cast<TFolder*> (ob);
1794  if(subfolder!=0)
1795  RemoveFromDir(subfolder,dir); // recursively scan all subfolders
1796  } else
1797  dir->RecursiveRemove(ob);
1798  }
1799 }
1800 
1801 Int_t TGo4AnalysisObjectManager::PrintFolder(TFolder* fold, Option_t* opt, const char* expression)
1802 {
1803  if(fold==0) return 0;
1804 
1805  GO4TRACE((11,"TGo4AnalysisObjectManager::PrintFolder(TFolder*, Option_t*)",__LINE__, __FILE__));
1806  TGo4LockGuard dirguard(fxDirMutex);
1807  Int_t totalsize=0;
1808  TROOT::IndentLevel();
1809  TROOT::IncreaseDirLevel();
1810  std::cout <<"+Folder "<<fold->GetName()<<" content:" << std::endl;
1811  TIter listiter(fold->GetListOfFolders());
1812  TObject* ob=0;
1813  while((ob=listiter())!=0) {
1814  if(ob->InheritsFrom(TFolder::Class()))
1815  totalsize+=PrintFolder(dynamic_cast<TFolder*>(ob),opt,expression);
1816  else
1817  if(IsMatching(ob->GetName(),expression)) {
1818  TROOT::IndentLevel();
1819  ob->Print(opt);
1821  if(temp!=0) totalsize += temp->GetObjectSize();
1822  delete temp;
1823  }
1824  } // while
1825  TROOT::DecreaseDirLevel();
1826  TROOT::IndentLevel();
1827  std::cout <<"++++End "<<fold->GetName()<<"++++++++++" << std::endl;
1828  return totalsize;
1829 }
1830 
1832 {
1833  GO4TRACE((11,"TGo4AnalysisObjectManager::ClearFolder(TFolder*, Option_t*)",__LINE__, __FILE__));
1834  if(fold==0) return kFALSE;
1835  TGo4LockGuard dirguard(fxDirMutex);
1836  TIter iter(fold->GetListOfFolders());
1837  TObject* ob=0;
1838  while((ob=iter())!=0)
1839  if(ob->InheritsFrom(TFolder::Class()))
1840  ClearFolder(dynamic_cast<TFolder*>(ob));
1841  else
1842  ClearObject(ob);
1843  return kTRUE;
1844 }
1845 
1847 {
1848  GO4TRACE((11,"TGo4AnalysisObjectManager::ClearObject(TObject*)",__LINE__, __FILE__));
1849  Bool_t rev=kFALSE;
1850  if(ob)
1851  {
1852  if(ob->TestBit(TGo4Status::kGo4NoReset)) return kFALSE;
1853  rev=kTRUE;
1854  if(ob->InheritsFrom(TH1::Class()))
1855  {
1856  TH1* his= dynamic_cast<TH1*>(ob);
1857  if (his) his->Reset(); // histogram has no Clear implementation!
1858  }
1859  else if(ob->InheritsFrom(TGo4DynamicEntry::Class()))
1860  {
1861  TGo4DynamicEntry* entry = dynamic_cast<TGo4DynamicEntry*>(ob);
1862  if (entry!=0) entry->Reset(); // dynamic entry has no Clear implementation!
1863  }
1864  else if(ob->InheritsFrom(TGo4Picture::Class()))
1865  {
1866  TGo4Picture* pic = dynamic_cast<TGo4Picture*>(ob);
1867  if (pic) pic->Reset(); // picture has no Clear implementation!
1868  }
1869  else if(ob->InheritsFrom(TGraph::Class()))
1870  {
1871  TGraph* gr= dynamic_cast<TGraph*>(ob);
1872  if (gr) {
1873  //Int_t pn=gr->GetN();
1874  gr->Set(0); // clear array of points
1875  //gr->Set(pn); // this should set all to 0 (JAM we don't want this for time plots!)
1876  }
1877  }
1878  else if(ob->InheritsFrom(TMultiGraph::Class()))
1879  {
1880  TMultiGraph* mg= dynamic_cast<TMultiGraph*>(ob);
1881  if (mg) {
1882  TIter liter(mg->GetListOfGraphs());
1883  TObject* ob=0;
1884  while((ob=liter())!=0)
1885  ClearObject(ob);
1886  }
1887  }
1888  else if(ob->InheritsFrom(TGo4EventElement::Class()))
1889  {
1890  // nop, we do not allow a user clear from gui
1891  // on any event
1892  rev=kFALSE;
1893  }
1894  else if(ob->InheritsFrom(TTree::Class()))
1895  {
1896  // nop, we do not allow a user clear from gui
1897  // on any tree
1898  rev=kFALSE;
1899  }
1900  else
1901  {
1902  ob->Clear();
1903  // use virtual Clear of all objects
1904  // make sure that TNamed::Clear is overwritten in subclasses
1905  }
1906  }
1907  return rev;
1908 }
1909 
1910 
1912 {
1913  GO4TRACE((11,"TGo4AnalysisObjectManager::DeleteFolder(TFolder*, Option_t*)",__LINE__, __FILE__));
1914  if (fold==0) return kFALSE;
1915 
1916  TGo4LockGuard dirguard(fxDirMutex);
1917  TIter iter(fold->GetListOfFolders());
1918  TObject* ob=0;
1919  while((ob=iter())!=0)
1920  if(ob->InheritsFrom(TFolder::Class()))
1921  DeleteFolder(dynamic_cast<TFolder*>(ob));
1922  else
1923  DeleteObject(ob);
1924  return kTRUE;
1925 }
1926 
1928 {
1929  GO4TRACE((11,"TGo4AnalysisObjectManager::DeleteObject(TObject*)",__LINE__, __FILE__));
1930  if(ob==0 || !ob->TestBit(TGo4Status::kGo4CanDelete) ) return kFALSE;
1931  fxGo4Dir->RecursiveRemove(ob);
1932  CleanupDynamicLists(ob);
1933  delete ob;
1934  return kTRUE;;
1935 }
1936 
1937 
1938 
1939 Bool_t TGo4AnalysisObjectManager::ProtectFolder(TFolder* fold, const Option_t* flags)
1940 {
1941  if(fold==0) return kFALSE;
1942  TGo4LockGuard dirguard(fxDirMutex);
1943  TIter listiter(fold->GetListOfFolders());
1944  TObject* ob=0;
1945  while((ob=listiter.Next())!=0)
1946  if(ob->InheritsFrom(TFolder::Class()))
1947  ProtectFolder(dynamic_cast<TFolder*>(ob), flags);
1948  else
1949  ProtectObject(ob, flags);
1950  return kTRUE;
1951 }
1952 
1953 Bool_t TGo4AnalysisObjectManager::ProtectObject(TObject* ob, const Option_t* flags)
1954 {
1955  if((ob==0) || (flags==0)) return kFALSE;
1956  TString opt=flags;
1957  if(opt.Contains("+D")) ob->ResetBit(TGo4Status::kGo4CanDelete);
1958  if(opt.Contains("-D")) ob->SetBit(TGo4Status::kGo4CanDelete);
1959  if(opt.Contains("+C")) ob->SetBit(TGo4Status::kGo4NoReset);
1960  if(opt.Contains("-C")) ob->ResetBit(TGo4Status::kGo4NoReset);
1961  return kTRUE;
1962 }
1963 
1965 {
1966  GO4TRACE((11,"TGo4AnalysisObjectManager::CleanupDynamicLists(TNamed*)",__LINE__, __FILE__));
1967  TGo4LockGuard dirguard(fxDirMutex);
1968  if (oldobject==0) return;
1969  // scan all dynamic lists for this object:
1970  if(oldobject->InheritsFrom(TH1::Class()) ||
1971  oldobject->InheritsFrom(TGo4Condition::Class()) ||
1972  oldobject->InheritsFrom(TGo4EventElement::Class()))
1974 }
1975 
1976 
1978 {
1979  GO4TRACE((11,"TGo4AnalysisObjectManager::PrintConditions(const char*)",__LINE__, __FILE__));
1980  Int_t totalsize = PrintFolder(fxConditionDir, "*", expression);
1981  std::cout << "___________________________________________________________" << std::endl;
1982  std::cout << "Total size of all conditions is: " << totalsize << " bytes." << std::endl;
1983 }
1984 
1986 {
1987  GO4TRACE((11,"TGo4AnalysisObjectManager::PrintHistograms(const char*)",__LINE__, __FILE__));
1988  Int_t totalsize = PrintFolder(fxHistogramDir, "*", expression);
1989  std::cout << "___________________________________________________________" << std::endl;
1990  std::cout << "Total size of all histograms is: " << totalsize << " bytes." << std::endl;
1991 }
1992 
1994 {
1995  GO4TRACE((11,"TGo4AnalysisObjectManager::PrintParameters(const char*)",__LINE__, __FILE__));
1996  Int_t totalsize = PrintFolder(fxParameterDir, "*", expression);
1997  std::cout << "___________________________________________________________" << std::endl;
1998  std::cout << "Total size of all parameters is: " << totalsize << " bytes." << std::endl;
1999 }
2000 
2001 
2003  const char* folder,
2004  Bool_t reset)
2005 {
2006  if(reset) {
2007  delete fxMatchIterator;
2008  delete fxMatchList;
2009  fxMatchList=CreateObjectList(expr,folder);
2010  fxMatchIterator=fxMatchList->MakeIterator();
2011  }
2012  return fxMatchIterator->Next();
2013 }
2014 
2015 TList* TGo4AnalysisObjectManager::CreateObjectList(const char* expr, const char* folder)
2016 {
2017  TGo4LockGuard dirguard(fxDirMutex);
2018  TFolder* searchfold;
2019  if(folder==0 || !strcmp(folder,fgcTOPFOLDER))
2020  searchfold=fxGo4Dir; // default: search topfolder
2021  else
2022  searchfold=FindSubFolder(fxGo4Dir, folder, kFALSE);
2023  return (CreateObjectList(expr, searchfold));
2024 }
2025 
2026 
2027 TList* TGo4AnalysisObjectManager::CreateObjectList(const char* expr, TFolder* fold)
2028 {
2029  TList* result = new TList;
2030  if(fold!=0) {
2031  TIter iter(fold->GetListOfFolders());
2032  TObject* entry=0;
2033  while((entry = iter())!=0) {
2034  if(entry->InheritsFrom(TFolder::Class())) {
2035  TFolder* subfold=dynamic_cast<TFolder*>(entry);
2036  TList* sublist=CreateObjectList(expr,subfold);
2037  // add sublist contents to our result list:
2038  result->AddAll(sublist);
2039  } else
2040  if(entry->InheritsFrom(TTree::Class())) {
2041  } else // disable sending tree to gui!
2042  if(entry->InheritsFrom(TGo4EventElement::Class())) {
2043  } else // disable events
2044  if(entry->InheritsFrom(TGo4EventSource::Class())) {
2045  } else // disable events
2046  if(entry->InheritsFrom(TGo4EventStore::Class())) {
2047  } else // disable events
2048  if(entry->InheritsFrom(TGo4EventProcessor::Class())) {
2049  } else { // disable events
2050  if(IsMatching(entry->GetName(),expr))
2051  result->AddLast(entry);
2052  }
2053  } // while
2054  } // if(fold)
2055  return result;
2056 }
2057 
2058 Bool_t TGo4AnalysisObjectManager::IsMatching(const char* string, const char* expression)
2059 {
2060  if(expression==0) return kTRUE;
2061  Bool_t ismatching=kFALSE;
2062  TString entrystring=string;
2063  TRegexp reg(expression,kTRUE);
2064  if(!strcmp(expression,"*"))
2065  ismatching=kTRUE; // take all in this folder
2066  // else if (strstr(expression,string))
2067  // ismatching=kTRUE; // expression just contained in name
2068  else if (entrystring.Index(reg,0)!=kNPOS)
2069  ismatching=kTRUE; // root regular expression class
2070  else
2071  ismatching=kFALSE;
2072  return ismatching;
2073 }
2074 
2075 
2076 TObject* TGo4AnalysisObjectManager::FindObjectInFolder(TFolder* folder, const char* fullname)
2077 {
2078  GO4TRACE((12,"TGo4AnalysisObjectManager::FindObjectInFolder(TFolder*, const char*)",__LINE__, __FILE__));
2079  TGo4LockGuard listguard(fxDirMutex);
2080 
2081  return folder ? folder->FindObjectAny(fullname) : 0;
2082 }
2083 
2084 
2085 TObject* TGo4AnalysisObjectManager::TestObject(TFolder* folder,
2086  const char* &pathname,
2087  const char* objectname,
2088  const TClass* cl)
2089 {
2090  TString fullname;
2091  if ((pathname!=0) && (strlen(pathname)==0)) pathname = 0;
2092  if (pathname) {
2093  fullname = pathname;
2094  fullname += "/";
2095  }
2096  fullname += objectname;
2097 
2098  TObject* obj = FindObjectInFolder(folder, fullname);
2099 
2100  if ((obj!=0) && (!obj->InheritsFrom(cl))) {
2101  RemoveObjectFromFolder(fullname, folder, kTRUE);
2102  obj = 0;
2103  }
2104 
2105  fbCreatedinMake = (obj==0);
2106  return obj;
2107 }
2108 
2109 Bool_t TGo4AnalysisObjectManager::FindObjectPathName(TObject* obj, TString& pathname, TFolder* fold)
2110 {
2111  if (obj==0) return kFALSE;
2112 
2113  if (fold==0) fold = fxGo4Dir;
2114 
2115  if (fold->GetListOfFolders()->FindObject(obj)==obj) {
2116  pathname = "";
2117  return kTRUE;
2118  }
2119 
2120  TIter iter(fold->GetListOfFolders());
2121  TObject* sub = 0;
2122 
2123  while ((sub = iter())!=0) {
2124  if (!sub->InheritsFrom(TFolder::Class())) continue;
2125  if (FindObjectPathName(obj, pathname, (TFolder*) sub)) {
2126  if (pathname.Length()==0)
2127  pathname = sub->GetName();
2128  else
2129  pathname = TString(sub->GetName()) + "/" + pathname;
2130  return kTRUE;
2131  }
2132  }
2133 
2134  return kFALSE;
2135 }
virtual void Reset()
Bool_t SetParameter(const char *name, TGo4Parameter *par, TFolder *parent=0)
TGo4PolyCond * MakePolyCond(const char *foldername, const char *conditionname, Int_t size, Float_t(*points)[2], const char *bindhistogram=0, Bool_t invert=kFALSE)
Bool_t SetAnalysisCondition(const char *name, TGo4Condition *con, Bool_t counter=kTRUE, TFolder *parent=0)
TFolder * CreateCompositeBranchFolder(TObjArray *branchlist, TGo4CompositeEvent *compevent, Int_t startindex, Int_t *skip, const char *name, const char *title)
Bool_t ProtectObject(TObject *ob, const Option_t *flags)
Bool_t RemoveObjectFromFolder(const char *fullname, TFolder *fold, Bool_t isDel)
Bool_t RemoveEventProcessor(TGo4EventProcessor *pro)
Bool_t RemoveEventStructure(TGo4EventElement *ev)
static void CleanupPointerInEntries(TFolder *folder, TObject *obj)
virtual TGo4EventElement * GetChild(const char *name)
void UpdateFrom(TGo4Picture *source, TClass *selectedobjclass=0)
Bool_t AddObject(TNamed *anything, const char *subfolder=0, Bool_t replace=kTRUE)
virtual Bool_t UpdateFrom(TGo4Condition *cond, Bool_t counts)
Bool_t AddDynamicEntry(TGo4DynamicEntry *entry)
TFolder * CreateBranchFolder(TObjArray *branchlist, const char *name, const char *title, Bool_t istopbranch=kFALSE)
Bool_t IsMatching(const char *string, const char *expression)
void Reset(Bool_t onlyclearflag=kFALSE)
Bool_t RemovePicture(const char *name)
void SetConditionName(const char *name)
void RemoveFromDir(TFolder *fold, TDirectory *dir)
Short_t getNElements() const
Bool_t ClearObjects(const char *name)
Bool_t DeleteObjects(const char *name)
Bool_t RemoveObject(const char *name, Bool_t del=kTRUE)
TGo4Picture * GetPicture(const char *name)
Bool_t AddCanvas(TCanvas *can, const char *subfolder=0)
Bool_t AddPicture(TGo4Picture *pic, const char *subfolder=0)
Bool_t RemoveDynamicEntry(const char *entryname)
TH1 * GetHistogram(const char *name)
void SetConEventName(Int_t ix, const char *name)
static void CleanupSpecials()
void SetHistogramName(const char *name)
TObjArray * getListOfComposites(Bool_t toplevel=kTRUE)
Bool_t FindObjectPathName(TObject *obj, TString &pathname, TFolder *fold=0)
TList * CreateObjectList(const char *expr, const char *folder=0)
void PrintConditions(const char *expression=0)
Bool_t UpdateParameterValues(TGo4Parameter *par)
Bool_t ProtectFolder(TFolder *fold, const Option_t *flags)
TGo4EventElement * GetEventStructure(const char *name)
Bool_t AddHistogram(TH1 *his, const char *subfolder=0, Bool_t replace=kTRUE)
Bool_t RemoveEventStore(TGo4EventStore *store)
Bool_t AddEventProcessor(TGo4EventProcessor *pro)
Bool_t AddEventSource(TGo4EventSource *source)
TGo4Parameter * CreateParameter()
TObject * FindObjectInFolder(TFolder *folder, const char *fullname)
Bool_t AddAnalysisCondition(TGo4Condition *con, const char *subfolder=0)
static void ResetEntries(TFolder *folder)
TObject * TestObject(TFolder *folder, const char *&pathname, const char *objectname, const TClass *cl)
Bool_t PutToFolder(TObject *ob, TFolder *destination, Bool_t replace=kFALSE)
void PrintHistograms(const char *expression=0)
TH1 * MakeTH1(const char *histotype, const char *foldername, const char *histoname, Int_t nbinsx, Axis_t xlow, Axis_t xup, const char *title=0, const char *xtitle=0, const char *ytitle=0)
TFolder * CreateNamesFolder(TFolder *objectfolder)
Bool_t RemoveEventSource(TGo4EventSource *source)
TObject * GetAsTObject(const char *name, const char *folder=0)
void AppendToDir(TObject *ob, TDirectory *dir)
Bool_t RemoveCanvas(const char *name)
Bool_t AddEventStore(TGo4EventStore *store)
void Message(Int_t prio, const char *text,...)
Bool_t AddParameter(TGo4Parameter *par, const char *subfolder=0)
TFolder * FindSubFolder(TFolder *parent, const char *subfolder, Bool_t create=kTRUE)
Bool_t RemoveTree(TTree *tree, const char *stepname=0)
Bool_t ResetBackStores(Bool_t clearflag=kFALSE)
void SetHistogram(const char *name)
void Reset()
Definition: TGo4Picture.h:234
Bool_t AddTree(TTree *tree, const char *subfolder=0)
TGo4Parameter * GetParameter(const char *name, const char *parameter_class=0)
void SetHisEventName(Int_t ix, const char *name)
TGo4AnalysisObjectNames * CreateNamesList()
TObject * NextMatchingObject(const char *expr, const char *folder, Bool_t reset)
virtual void SetValues(Double_t low1, Double_t up1)
#define fguSUBFOLDERMAXLEN
virtual const char * GetName() const
TGo4Condition * GetAnalysisCondition(const char *name, const char *cond_cl=0)
Bool_t RemoveAnalysisCondition(const char *name)
void CleanupDynamicLists(TObject *oldobject)
Int_t PrintFolder(TFolder *fold, Option_t *opt, const char *expression=0)
static void PrintEntries(TFolder *folder)
#define GO4TRACE(X)
Definition: TGo4Log.h:26
Bool_t RemoveHistogram(const char *name, Bool_t del=kTRUE)
void PrintParameters(const char *expression=0)
virtual Bool_t UpdateFrom(TGo4Parameter *rhs)
TFolder * CreateMembersFolder(TObject *obj, const char *membrfoldername, TClass *cl)
TGo4ObjectStatus * CreateObjectStatus(const char *name, const char *folder=0)
Bool_t ProtectObjects(const char *name, const Option_t *flags)
Bool_t AddTreeHistogram(const char *hisname, const char *treename, const char *varexp, const char *cutexp)
void SetConVarName(Int_t ix, const char *name)
TGo4WinCond * MakeWindowCond(const char *foldername, const char *conditionname, Double_t xlow, Double_t xup, const char *bindhistogram=0, Bool_t invert=kFALSE)
Bool_t SetPicture(const char *name, TGo4Picture *pic, TFolder *parent=0)
TNamed * GetObject(const char *name, const char *folder=0)
Bool_t RemoveParameter(const char *name)
Bool_t SetParameterStatus(const char *name, TGo4ParameterStatus *par, TFolder *parent=0)
Bool_t AddDynamicHistogram(const char *name, const char *histo, const char *hevx, const char *hmemx, const char *hevy=0, const char *hmemy=0, const char *hevz=0, const char *hmemz=0, const char *condition=0, const char *cevx=0, const char *cmemx=0, const char *cevy=0, const char *cmemy=0)
TH2 * MakeTH2(const char *histotype, const char *foldername, const char *histoname, Int_t nbinsx, Axis_t xlow, Axis_t xup, Int_t nbinsy, Axis_t ylow, Axis_t yup, const char *title=0, const char *xtitle=0, const char *ytitle=0)
Bool_t AddEventStructure(TGo4EventElement *ev)
Bool_t LoadObjects(TFile *statusfile)
Int_t GetObjectSize() const
static TGo4Analysis * Instance()
TTree * GetTree(const char *name)
TGo4TreeStructure * CreateTreeStructure(TTree *thetree)
static void Info(const char *text,...)
Definition: TGo4Log.cxx:283
Bool_t LoadFolder(TFolder *source, TFolder *destination, Bool_t replace=kFALSE)
Bool_t AddObjectToFolder(TObject *ob, TFolder *fold, const char *subfolder=0, Bool_t replace=kTRUE, Bool_t uniquename=kFALSE, Bool_t resetbits=kTRUE)
TCanvas * GetCanvas(const char *name)
virtual void Invert(Bool_t on)
virtual void RecursiveRemove(TObject *obj)
void SetHisVarName(Int_t ix, const char *name)
static void ProcessEntries(TFolder *folder, Bool_t processtrees, Int_t interval)