//  
// Author: Oliver Maria Kind <mailto: kind@mail.desy.de>
// Update: $Id: AtlElectron.h,v 1.52 2016/11/29 18:05:15 kind Exp $
// Copyright: 2008 (C) Oliver Maria Kind
//
#ifndef ATLAS_AtlElectron
#define ATLAS_AtlElectron
#ifndef HEP_HepElectron
#include <HepElectron.h>
#endif
#ifndef ATLAS_AtlEMShower
#include <AtlEMShower.h>
#endif
#ifndef ATLAS_AtlIDTrack
#include <AtlIDTrack.h>
#endif
#ifndef ATLAS_AtlTriggerMatch
#include <AtlTriggerMatch.h>
#endif
#ifndef ATLAS_AtlMCTruthClassifier
#include <AtlMCTruthClassifier.h>
#endif

class TSystem;

class AtlElectron : public HepElectron, public AtlEMShower,
    public AtlTriggerMatch {
    
  private:
    AtlMCTruthClassifier fMCTruthClassifier; // MC truth classifier
    HepTrackHelix *fTrackEMRefit; // Track parameters after refit with electron hypothesis
    TRef          *fIDTrack;      // Link to original Track
    UInt_t         fElectron_trackBlayer; // Electron_trackBlayer SgTop D3PD variable
    Bool_t         fIsTriggerMatched;  //WARNING: Only filled in D3PDTopSlim mode
    Double_t       fEl_SF;            // electron scale factors with syst. variations (SgTopD3PDs)
    Double_t       fEl_SF_reco_up;
    Double_t       fEl_SF_reco_down;
    Double_t       fEl_SF_Id_up;
    Double_t       fEl_SF_Id_down;
    Double_t       fEl_trigger_SF;
    Double_t       fEl_trigger_SF_up;
    Double_t       fEl_trigger_SF_down;
    
  public:
    AtlElectron();
    AtlElectron(Int_t Id, Float_t Px, Float_t Py, Float_t Pz, Float_t E,
		Bool_t IsPositron, 
		Float_t EMWeight,
		Float_t BkgWeight, UInt_t OQFlag,
		UInt_t IsEMBitField, EIsEM IsEM, EAuthor Author,
		TLorentzVector PCluster);
    virtual ~AtlElectron();
    virtual void Clear(Option_t *option = "");
    virtual void Print(Option_t *option = "");
    
    static void PrintHeader();
    static void PrintFooter();

    inline const AtlMCTruthClassifier* GetMCTruthClassifier() const {
	return &fMCTruthClassifier;
    }
    inline void SetMCTruthClassifier(AtlMCTruthClassifier::EParticleOrigin
				     ParticleOrigin) {
	// Set MC truth classifier
	fMCTruthClassifier.Set(ParticleOrigin);
    }
    
    inline Bool_t IsHighPtElectron()  const { return fAuthor & kHighPtElectron; }
    inline Bool_t IsSoftElectron()    const { return fAuthor & kSoftElectron;}
    inline Bool_t IsForwardElectron() const { return fAuthor & kForwardElectron;}
    inline Bool_t IsPhotoConversion() const { return fAuthor & kPhoton;}
    
    inline void SetTrackEMRefit(Float_t Chi2, Int_t NDoF,
				Float_t Xref, Float_t Yref, Float_t Zref, Float_t Phi0,
				Float_t QovP, Float_t D0, Float_t Z0, Float_t Theta0, 
				Float_t CovMat[15]) {
	// Set track refit parameters, Id always 1
	fTrackEMRefit->SetParameters(1, Chi2, NDoF, Xref, Yref, Zref, Phi0,
				     QovP, D0, Z0, Theta0, CovMat);
    }
 

    // Test hardness of cuts
    inline Bool_t IsLoose() const {
	// Loose electron selection
	return fIsEM & kElectronLoose;
    }
    inline Bool_t IsFwdLoose() const {
	// Loose selection for forwrd electrons
	return fIsEM & kElectronFwdLoose;
    }
    inline Bool_t IsMedium() const {
	// Medium electron selection
	return fIsEM & kElectronMedium;
    }
    inline Bool_t IsTight() const {
	// Tight electron selection
	return fIsEM & kElectronTight;
    }
    inline Bool_t IsTightIso() const {
	// Tight + isolation selection for electrons
	return fIsEM & kElectronTightIso;
    }
    inline Bool_t IsMediumIso() const {
	// Medium + isolation selection for electrons
	return fIsEM & kElectronMediumIso;
    }
    inline Bool_t IsFwdTight() const {
	// Tight selection for forwrd electrons
	return fIsEM & kElectronFwdTight;
    }
    inline Bool_t IsMediumPP() const {
	// Medium electron selection
	return fIsEM & kElectronMediumPP;
    }
    inline Bool_t IsTightPP() const {
	// Tight electron selection
	return fIsEM & kElectronTightPP;
    }

    inline Bool_t Is90EtCone20() const {
	// Tight electron selection
	return fIsEM & kElectron90EtCone20;
    }

    inline Bool_t Is90PtCone30() const {
	// Tight electron selection
	return fIsEM & kElectron90PtCone30;
    }
    
    // Get OQ decision
    UInt_t  IsGoodOQ(); // 0: is good OQ, 1: is bad OQ
    
    // Test individual IsEM flags
    inline virtual Bool_t IsEM_ClusterEtaRange() const {
      // Cut eta range
      return (fIsEMBitField & (0x1<<0))==0;
    }
    inline virtual Bool_t IsEM_ClusterHadronicLeakage() const {
      // Cluster leakage into the hadronic calorimeter
      return (fIsEMBitField & (0x1<<2))==0;
    }
    inline virtual Bool_t IsEM_ClusterMiddleEnergy() const {
      // Energy in 2nd sampling (e277)
      return (fIsEMBitField & (0x1<<3))==0;
    }
    inline virtual Bool_t IsEM_ClusterMiddleEratio37() const {
      // Energy ratio in 2nd sampling
      return (fIsEMBitField & (0x1<<4))==0;
    }
    inline virtual Bool_t IsEM_ClusterMiddleEratio33() const {
      // Energy ratio in 2nd sampling
      return (fIsEMBitField & (0x1<<5))==0;
    }
    inline virtual Bool_t IsEM_ClusterMiddleWidth() const {
      // Width in the second sampling */
      return (fIsEMBitField & (0x1<<6))==0;
    }
    inline virtual Bool_t IsEM_ClusterStripsEratio() const {
      // Fraction of energy found in 1st sampling
      return (fIsEMBitField & (0x1<<8))==0;
    }
    inline virtual Bool_t IsEM_ClusterStripsDeltaEmax2() const {
      // Energy of 2nd maximum in 1st sampling
      // ~e2tsts1/(1000+const_lumi*et)
      return (fIsEMBitField & (0x1<<9))==0;
    }
    inline virtual Bool_t IsEM_ClusterStripsDeltaE() const {
      // Difference between 2nd maximum and 1st minimum in
      // strips (e2tsts1-emins1)
      return (fIsEMBitField & (0x1<<10))==0;
    }
    inline virtual Bool_t IsEM_ClusterStripsWtot() const {
      // Shower width in 1st sampling
      return (fIsEMBitField & (0x1<<11))==0;
    }
    inline virtual Bool_t IsEM_ClusterStripsFracm() const {
      // Shower shape in shower core 1st sampling
      return (fIsEMBitField & (0x1<<12))==0;
    }
    inline virtual Bool_t IsEM_ClusterStripsWeta1c() const {
      // Shower width weighted by distance from the maximum one
      return (fIsEMBitField & (0x1<<13))==0;
    }
    inline virtual Bool_t IsEM_ClusterStripsDEmaxs1() const {
      // Difference between max and 2nd max in strips
      return (fIsEMBitField & (0x1<<15))==0;
    }
    inline virtual Bool_t IsEM_TrackBlayer() const {
      // B layer hit
      return (fIsEMBitField & (0x1<<16))==0;
    }
    inline virtual Bool_t IsEM_TrackPixel() const {
      // Number of Pixel hits
      return (fIsEMBitField & (0x1<<17))==0;
    }
    inline virtual Bool_t IsEM_TrackSi() const {
      // Number of Pixel and SCT hits
      return (fIsEMBitField & (0x1<<18))==0;
    }
    inline virtual Bool_t IsEM_TrackA0() const {
      // Distance of closet approach
      return (fIsEMBitField & (0x1<<19))==0;
    }
    inline virtual Bool_t IsEM_TrackMatchEta() const {
      // Eta difference between cluster and
      // extrapolated track in the 1st sampling
	return (fIsEMBitField & (0x1<<20))==0;
    }
    inline virtual Bool_t IsEM_TrackMatchPhi() const {
      // Phi difference between cluster and
      // extrapolated track in the 2nd sampling
      return (fIsEMBitField & (0x1<<21))==0;
    }
    inline virtual Bool_t IsEM_TrackMatchEoverP() const {
      // Energy-momentum match
      return (fIsEMBitField & (0x1<<22))==0;
    }
    inline virtual Bool_t IsEM_TrackTRThits() const {
      // Number of TRT hits
      return (fIsEMBitField & (0x1<<24))==0;
    }
    inline virtual Bool_t IsEM_TrackTRTratio() const {
      // Ratio of high to all TRT hits for
      // isolated electrons
      return (fIsEMBitField & (0x1<<25))==0;
    }
    inline virtual Bool_t IsEM_TrackTRTratio90() const {
      // Ratio of high to all TRT hits for
      // non-isolated electrons
      return (fIsEMBitField & (0x1<<26))==0;
    }
    inline virtual Bool_t IsEM_Isolation() const {
      // Isolation
      return (fIsEMBitField & (0x1<<29))==0;
    }
    inline virtual Bool_t IsEM_ClusterIsolation() const {
      // Calorimetric isolation
      return (fIsEMBitField & (0x1<<30))==0;
    }
    inline virtual Bool_t IsEM_TrackIsolation() const {
      // Tracker isolation
      return (fIsEMBitField & (0x1<<31))==0;
    }
    
    // Tracking
    inline HepTrackHelix* GetTrackEMRefit() const {
      // Returns track helix with track parameters of 
      // associated track after refit with electron hypothesis
      return fTrackEMRefit;
    }
    inline void SetIDTrack(AtlIDTrack *trk) { *fIDTrack = (TObject*)trk; }
    inline AtlIDTrack* GetIDTrack() const{
      // Returns original associated track
      return (AtlIDTrack*)fIDTrack->GetObject(); 
    }
    inline virtual void GetCovMatrixPtEtaPhi(TMatrixD& CovMatPtEtaPhi) const {
	// Returns Covariance Matrix from track fit after coordinate transformation
	GetIDTrack()->GetCovMatrixPtEtaPhi(CovMatPtEtaPhi);
    }

    // SgTop D3PD variables
    inline void SetElectron_trackBlayer(UInt_t Electron_trackBlayer) {
	// Set Electron_trackBlayer SgTop D3PD variable 
	fElectron_trackBlayer = Electron_trackBlayer;
    }
    inline UInt_t GetElectron_trackBlayer() const {
	// Returns Electron_trackBlayer SgTop D3PD variable 
	return fElectron_trackBlayer;
    }
    inline Bool_t IsTriggerMatched() const { return fIsTriggerMatched; }
    inline void SetIsTriggerMatched(Bool_t is_matched) {
	fIsTriggerMatched = is_matched;
    }
    inline void SetElectronScaleFactors(Double_t el_SF, Double_t el_SF_reco_up, Double_t el_SF_reco_down, Double_t el_SF_Id_up, Double_t el_SF_Id_down, Double_t el_trigger_SF,Double_t el_trigger_SF_up, Double_t el_trigger_SF_down) {
	// Set Electron scale factors (nominal, up, down) SgTop D3PD variables
	fEl_SF      = el_SF;
	fEl_SF_reco_up   = el_SF_reco_up;
	fEl_SF_reco_down = el_SF_reco_down;
	fEl_SF_Id_up   = el_SF_Id_up;
	fEl_SF_Id_down = el_SF_Id_down;
	fEl_trigger_SF   = el_trigger_SF;
	fEl_trigger_SF_up   = el_trigger_SF_up;
	fEl_trigger_SF_down = el_trigger_SF_down;
    }
    inline Double_t GetElectronScaleFactor()      { return fEl_SF;}
    inline Double_t GetElectronScaleFactor_reco_up()   { return fEl_SF_reco_up;}
    inline Double_t GetElectronScaleFactor_reco_down() { return fEl_SF_reco_down;}
    inline Double_t GetElectronScaleFactor_Id_up()   { return fEl_SF_Id_up;}
    inline Double_t GetElectronScaleFactor_Id_down() { return fEl_SF_Id_down;}
    inline Double_t GetElectronScaleFactor_trigger()   { return fEl_trigger_SF;}
    inline Double_t GetElectronScaleFactor_trigger_up()   { return fEl_trigger_SF_up;}
    inline Double_t GetElectronScaleFactor_trigger_down() { return fEl_trigger_SF_down;}
 

    ClassDef(AtlElectron,29) // Atlas electron class
};
#endif
      
 AtlElectron.h:1
 AtlElectron.h:2
 AtlElectron.h:3
 AtlElectron.h:4
 AtlElectron.h:5
 AtlElectron.h:6
 AtlElectron.h:7
 AtlElectron.h:8
 AtlElectron.h:9
 AtlElectron.h:10
 AtlElectron.h:11
 AtlElectron.h:12
 AtlElectron.h:13
 AtlElectron.h:14
 AtlElectron.h:15
 AtlElectron.h:16
 AtlElectron.h:17
 AtlElectron.h:18
 AtlElectron.h:19
 AtlElectron.h:20
 AtlElectron.h:21
 AtlElectron.h:22
 AtlElectron.h:23
 AtlElectron.h:24
 AtlElectron.h:25
 AtlElectron.h:26
 AtlElectron.h:27
 AtlElectron.h:28
 AtlElectron.h:29
 AtlElectron.h:30
 AtlElectron.h:31
 AtlElectron.h:32
 AtlElectron.h:33
 AtlElectron.h:34
 AtlElectron.h:35
 AtlElectron.h:36
 AtlElectron.h:37
 AtlElectron.h:38
 AtlElectron.h:39
 AtlElectron.h:40
 AtlElectron.h:41
 AtlElectron.h:42
 AtlElectron.h:43
 AtlElectron.h:44
 AtlElectron.h:45
 AtlElectron.h:46
 AtlElectron.h:47
 AtlElectron.h:48
 AtlElectron.h:49
 AtlElectron.h:50
 AtlElectron.h:51
 AtlElectron.h:52
 AtlElectron.h:53
 AtlElectron.h:54
 AtlElectron.h:55
 AtlElectron.h:56
 AtlElectron.h:57
 AtlElectron.h:58
 AtlElectron.h:59
 AtlElectron.h:60
 AtlElectron.h:61
 AtlElectron.h:62
 AtlElectron.h:63
 AtlElectron.h:64
 AtlElectron.h:65
 AtlElectron.h:66
 AtlElectron.h:67
 AtlElectron.h:68
 AtlElectron.h:69
 AtlElectron.h:70
 AtlElectron.h:71
 AtlElectron.h:72
 AtlElectron.h:73
 AtlElectron.h:74
 AtlElectron.h:75
 AtlElectron.h:76
 AtlElectron.h:77
 AtlElectron.h:78
 AtlElectron.h:79
 AtlElectron.h:80
 AtlElectron.h:81
 AtlElectron.h:82
 AtlElectron.h:83
 AtlElectron.h:84
 AtlElectron.h:85
 AtlElectron.h:86
 AtlElectron.h:87
 AtlElectron.h:88
 AtlElectron.h:89
 AtlElectron.h:90
 AtlElectron.h:91
 AtlElectron.h:92
 AtlElectron.h:93
 AtlElectron.h:94
 AtlElectron.h:95
 AtlElectron.h:96
 AtlElectron.h:97
 AtlElectron.h:98
 AtlElectron.h:99
 AtlElectron.h:100
 AtlElectron.h:101
 AtlElectron.h:102
 AtlElectron.h:103
 AtlElectron.h:104
 AtlElectron.h:105
 AtlElectron.h:106
 AtlElectron.h:107
 AtlElectron.h:108
 AtlElectron.h:109
 AtlElectron.h:110
 AtlElectron.h:111
 AtlElectron.h:112
 AtlElectron.h:113
 AtlElectron.h:114
 AtlElectron.h:115
 AtlElectron.h:116
 AtlElectron.h:117
 AtlElectron.h:118
 AtlElectron.h:119
 AtlElectron.h:120
 AtlElectron.h:121
 AtlElectron.h:122
 AtlElectron.h:123
 AtlElectron.h:124
 AtlElectron.h:125
 AtlElectron.h:126
 AtlElectron.h:127
 AtlElectron.h:128
 AtlElectron.h:129
 AtlElectron.h:130
 AtlElectron.h:131
 AtlElectron.h:132
 AtlElectron.h:133
 AtlElectron.h:134
 AtlElectron.h:135
 AtlElectron.h:136
 AtlElectron.h:137
 AtlElectron.h:138
 AtlElectron.h:139
 AtlElectron.h:140
 AtlElectron.h:141
 AtlElectron.h:142
 AtlElectron.h:143
 AtlElectron.h:144
 AtlElectron.h:145
 AtlElectron.h:146
 AtlElectron.h:147
 AtlElectron.h:148
 AtlElectron.h:149
 AtlElectron.h:150
 AtlElectron.h:151
 AtlElectron.h:152
 AtlElectron.h:153
 AtlElectron.h:154
 AtlElectron.h:155
 AtlElectron.h:156
 AtlElectron.h:157
 AtlElectron.h:158
 AtlElectron.h:159
 AtlElectron.h:160
 AtlElectron.h:161
 AtlElectron.h:162
 AtlElectron.h:163
 AtlElectron.h:164
 AtlElectron.h:165
 AtlElectron.h:166
 AtlElectron.h:167
 AtlElectron.h:168
 AtlElectron.h:169
 AtlElectron.h:170
 AtlElectron.h:171
 AtlElectron.h:172
 AtlElectron.h:173
 AtlElectron.h:174
 AtlElectron.h:175
 AtlElectron.h:176
 AtlElectron.h:177
 AtlElectron.h:178
 AtlElectron.h:179
 AtlElectron.h:180
 AtlElectron.h:181
 AtlElectron.h:182
 AtlElectron.h:183
 AtlElectron.h:184
 AtlElectron.h:185
 AtlElectron.h:186
 AtlElectron.h:187
 AtlElectron.h:188
 AtlElectron.h:189
 AtlElectron.h:190
 AtlElectron.h:191
 AtlElectron.h:192
 AtlElectron.h:193
 AtlElectron.h:194
 AtlElectron.h:195
 AtlElectron.h:196
 AtlElectron.h:197
 AtlElectron.h:198
 AtlElectron.h:199
 AtlElectron.h:200
 AtlElectron.h:201
 AtlElectron.h:202
 AtlElectron.h:203
 AtlElectron.h:204
 AtlElectron.h:205
 AtlElectron.h:206
 AtlElectron.h:207
 AtlElectron.h:208
 AtlElectron.h:209
 AtlElectron.h:210
 AtlElectron.h:211
 AtlElectron.h:212
 AtlElectron.h:213
 AtlElectron.h:214
 AtlElectron.h:215
 AtlElectron.h:216
 AtlElectron.h:217
 AtlElectron.h:218
 AtlElectron.h:219
 AtlElectron.h:220
 AtlElectron.h:221
 AtlElectron.h:222
 AtlElectron.h:223
 AtlElectron.h:224
 AtlElectron.h:225
 AtlElectron.h:226
 AtlElectron.h:227
 AtlElectron.h:228
 AtlElectron.h:229
 AtlElectron.h:230
 AtlElectron.h:231
 AtlElectron.h:232
 AtlElectron.h:233
 AtlElectron.h:234
 AtlElectron.h:235
 AtlElectron.h:236
 AtlElectron.h:237
 AtlElectron.h:238
 AtlElectron.h:239
 AtlElectron.h:240
 AtlElectron.h:241
 AtlElectron.h:242
 AtlElectron.h:243
 AtlElectron.h:244
 AtlElectron.h:245
 AtlElectron.h:246
 AtlElectron.h:247
 AtlElectron.h:248
 AtlElectron.h:249
 AtlElectron.h:250
 AtlElectron.h:251
 AtlElectron.h:252
 AtlElectron.h:253
 AtlElectron.h:254
 AtlElectron.h:255
 AtlElectron.h:256
 AtlElectron.h:257
 AtlElectron.h:258
 AtlElectron.h:259
 AtlElectron.h:260
 AtlElectron.h:261
 AtlElectron.h:262
 AtlElectron.h:263
 AtlElectron.h:264
 AtlElectron.h:265
 AtlElectron.h:266
 AtlElectron.h:267
 AtlElectron.h:268
 AtlElectron.h:269
 AtlElectron.h:270
 AtlElectron.h:271
 AtlElectron.h:272
 AtlElectron.h:273
 AtlElectron.h:274
 AtlElectron.h:275
 AtlElectron.h:276
 AtlElectron.h:277
 AtlElectron.h:278
 AtlElectron.h:279
 AtlElectron.h:280
 AtlElectron.h:281
 AtlElectron.h:282
 AtlElectron.h:283
 AtlElectron.h:284
 AtlElectron.h:285
 AtlElectron.h:286
 AtlElectron.h:287
 AtlElectron.h:288
 AtlElectron.h:289
 AtlElectron.h:290
 AtlElectron.h:291
 AtlElectron.h:292
 AtlElectron.h:293
 AtlElectron.h:294
 AtlElectron.h:295
 AtlElectron.h:296
 AtlElectron.h:297
 AtlElectron.h:298
 AtlElectron.h:299