Back to home page

Project CMSSW displayed by LXR

 
 

    


File indexing completed on 2024-04-06 12:18:50

0001 /*************************************************
0002   Drawing plots and saving images of histograms
0003   can be tedious. This automates the task.
0004   
0005   Finds all the directories in a given ROOT file
0006   and creates a directory structure exactly like 
0007   it and fills it with image files of hitograms 
0008   found.
0009 
0010   Can be run from a bash prompt as well:
0011     root -b -l -q "saveHistograms.C(\"aFile.root\",\"gif\",640,480)"
0012 
0013   Michael B. Anderson
0014   May 23, 2008
0015 *************************************************/
0016 
0017 #include <string.h>
0018 #include "TChain.h"
0019 #include "TFile.h"
0020 #include "TH1.h"
0021 #include "TTree.h"
0022 #include "TKey.h"
0023 #include "Riostream.h"
0024 
0025 TFile *sourceFile;
0026 TObject *obj;
0027 TString outputFolder;
0028 TH1 *h;
0029 TCanvas *canvasDefault;
0030 
0031 // *******************************************
0032 // Variables
0033 
0034 TString outputType;
0035 Int_t outputXsize;
0036 Int_t outputYsize;
0037 
0038 TString drawOptions1D("");   // Drawing options for 
0039                              // 1D histograms.
0040 TString drawOptions2D("box");// Drawing options for
0041                              // 2D histograms.
0042 
0043 int lineColor = 4; // 2 = Red, 3 = Green, 4 = Blue
0044 int lineWidth = 2; // Line width for 1D histograms.
0045 
0046 Bool_t displayStatsBox = 1;  // 0 = false, 1 = true
0047 Bool_t autoLabelXaxis  = 1;
0048 Bool_t autoLogYaxis    = 0;
0049 Bool_t printOutput     = 1;
0050 
0051 // End of Variables
0052 // *******************************************
0053 
0054 void recurseOverKeys( TDirectory *target );
0055 
0056 void saveHistograms(TString fileName,
0057                 TString imageType = "gif", 
0058                 int outputWidth  = 640, 
0059                 int outputHeight = 480) {
0060 
0061   sourceFile = TFile::Open( fileName );
0062 
0063   outputFolder = fileName+"/"; // Blank to use current directory,
0064                                           // or, for a specific dir type
0065                                           // something like "images/"
0066   outputFolder.ReplaceAll(".root","");
0067   gSystem->MakeDirectory(outputFolder);
0068 
0069   outputType = "."+imageType;
0070   outputXsize = outputWidth; 
0071   outputYsize = outputHeight;
0072   canvasDefault = new TCanvas("canvasDefault","testCanvas",outputWidth,outputHeight);
0073 
0074   // Change settings on plotting histograms
0075   gStyle->SetOptStat(111111);  // This will cause overflow and underflow to be shown
0076   gStyle->SetHistLineWidth(2); // Set the line width to 2 pixels
0077   //gStyle->SetTitleFontSize(0.035); // Shrink Histogram Title Size
0078 
0079   // Now actually find all the directories, histograms, and save them..
0080   recurseOverKeys(sourceFile);  
0081 
0082   sourceFile->Close();
0083 
0084   TString currentDir = gSystem->pwd();
0085   cout << "Done. See images in:" << endl << currentDir << "/" << outputFolder << endl;
0086 }
0087 
0088 void recurseOverKeys( TDirectory *target ) {
0089  
0090   TString path( (char*)strstr( target->GetPath(), ":" ) );
0091   path.Remove( 0, 2 );
0092 
0093   cout << path << endl;
0094 
0095   sourceFile->cd( path );
0096   TDirectory *current_sourcedir = gDirectory;
0097 
0098   TKey *key;
0099   TIter nextkey(current_sourcedir->GetListOfKeys());
0100 
0101   while (key = (TKey*)nextkey()) {
0102 
0103     obj = key->ReadObj();
0104 
0105     if (obj->IsA()->InheritsFrom("TH1")) {
0106 
0107       // **************************
0108       // Plot & Save this Histogram
0109       h = (TH1*)obj;
0110       h->SetStats(displayStatsBox);
0111 
0112       TString histName = h->GetName(); 
0113 
0114 
0115       ///////////////////////////////////////////
0116       // Special & optional drawing commands
0117 
0118       // Now to label the X-axis!
0119       if (autoLabelXaxis) {
0120     if ( histName.Contains("Phi") ) {
0121       h->GetXaxis()->SetTitle("#phi");
0122     } else if ( histName.Contains("eta") || histName.Contains("eta2") ) {
0123       h->GetXaxis()->SetTitle("#eta");
0124     } else if ( histName.Contains("Pt") ) {
0125       h->GetXaxis()->SetTitle("p_{T} (GeV)");
0126     } else if ( histName.Contains("et") || histName.Contains("et2") ) {
0127       h->GetXaxis()->SetTitle("E_{T} (GeV)");
0128     }
0129       }
0130 
0131       // Tricky work-around.
0132       //  Some plots have text labels that are too big.
0133       //  Alter a margin to keep them in the picture.
0134       if (histName.Contains("total ") || histName.Contains("efficiency by step")) {
0135         canvasDefault->SetBottomMargin(0.24);
0136     canvasDefault->SetRightMargin(0.15);
0137       } else {
0138     canvasDefault->SetBottomMargin(0.1);
0139     canvasDefault->SetRightMargin(0.1);
0140       }
0141 
0142       h->SetLineColor(lineColor);
0143       h->SetLineWidth(lineWidth);
0144 
0145 
0146       // ********************************
0147       // A trick to decide whether to have log or no-log y axis
0148       // get hist max y value
0149       if (autoLogYaxis) {
0150         Double_t testYvalue = h->GetMaximum();
0151         //cout << testYvalue << endl;
0152 
0153         if (testYvalue > 1.0) {
0154           Double_t maxy = log10(testYvalue);
0155 
0156           // get hist min y value
0157           Double_t miny = log10(h->GetMinimum(1.0));
0158 
0159           // log scale if more than 2 powers of 10 between low and high bins
0160           if ( (maxy-miny) > 2.0 ) {
0161             canvasDefault->SetLogy(1);
0162           }
0163         }
0164       }
0165       // End of log or no-log y axis decision
0166       // ********************************
0167 
0168       // END Special commands
0169       ///////////////////////////////////////////
0170 
0171       h->Draw(drawOptions1D);
0172       canvasDefault->Modified();
0173       canvasDefault->Update();
0174       
0175       canvasDefault->Print(outputFolder+path+"/"+histName+outputType);
0176       // To store the root file name in image file name:
0177       //canvasDefault->Print(outputFolder+histFileName+histName+outputType);
0178       if (printOutput) cout << outputFolder+path+"/"+histName+outputType << endl;
0179 
0180       canvasDefault->SetLogy(0); // reset to no-log - prevents errors
0181       // **************************
0182 
0183     } else if ( obj->IsA()->InheritsFrom( "TDirectory" ) ) {
0184       // it's a subdirectory
0185 
0186       cout << "Found subdirectory " << obj->GetName() << endl;
0187       gSystem->MakeDirectory(outputFolder+path+"/"+obj->GetName());
0188 
0189       // obj is now the starting point of another round of merging
0190       // obj still knows its depth within the target file via
0191       // GetPath(), so we can still figure out where we are in the recursion
0192       recurseOverKeys( (TDirectory*)obj );
0193 
0194     } // end of IF a TDriectory
0195   } // end of LOOP over keys
0196 }