// A cheating cluster code that uses the MCParticle 
// history to define calorimeter clusters.
// Apr 23,2001 Toshi      Marjor changes...
// Feb  5,1999 Rob Shanks Replacement of all pointers in class with objects
// Jan 15,1999 Rob Shanks Creation of Cluster class

#ifndef LCDCLUSTER_H
#define LCDCLUSTER_H

#include "TObject.h"
#include "TClonesArray.h"

class LCDCluster: public TObject {
  
public:
  LCDCluster() : m_energy(0),
		 m_PosTheta(0),m_PosThetaErr(0.),
		 m_PosPhi(0),m_PosPhiErr(0.),
		 m_PosR(0),m_PosRErr(0.),
		 m_ClusterStartDepth(0.),
		 m_CalHitN(0),
		 m_McListN(0),
		 m_barend(0),m_system(0){}
  ~LCDCluster() {}

  void AddCalHit(Int_t hit_index);
  void AddParticle(Int_t part_index, Double_t epart);

  Int_t    GetBarEnd()            { return m_barend;            }
  // = 0 barrel  =1 endcap
  Int_t*   GetCalHit()            { return m_CalHitI;           }
  Int_t    GetCalHitAt(Int_t a)   { return m_CalHitI[a];        }
  Int_t    GetCalHitEntries()     { return m_CalHitN;           }
  Double_t GetClusterStartDepth() { return m_ClusterStartDepth; }
  Double_t GetEnergy()            { return m_energy;            }
  Double_t GetEnergyPhi()         { return m_PosPhi;            }
  Double_t GetEnergyPhiRMS()      { return m_PosPhiErr;         }
  Double_t GetEnergyTheta()       { return m_PosTheta;          }
  Double_t GetEnergyThetaRMS()    { return m_PosThetaErr;       }
  Double_t GetEnergyR()           { return m_PosR;              }
  Double_t GetEnergyRRMS()        { return m_PosRErr;           }
  Int_t    GetSystem()            { return m_system;            }
  // = 0 EM  =1 HAD  =2 MU  =3 LUM     

  Int_t*   GetMcList()            { return m_McListI;           }
  Int_t    GetMcListAt(Int_t a)   { return m_McListI[a];        }
  Float_t* GetMcListE()           { return m_McListE;           }
  Double_t GetMcListEAt(Int_t a)  { return m_McListE[a];        }
  Int_t    GetMcListEntries()     { return m_McListN;           }
  
  void RemoveCalHit(Int_t hit_index);
  void RemoveParticle(Int_t part_index, Double_t epart);
  
  void SetBarEnd(Int_t a)               { m_barend           = a; }
  void SetClusterStartDepth(Double_t a) { m_ClusterStartDepth= a; }
  void SetEnergy(Double_t a)            { m_energy           = a; }
  void SetEnergyPhi(Double_t a)         { m_PosPhi           = a; }
  void SetEnergyPhiRMS(Double_t a)      { m_PosPhiErr        = a; }
  void SetEnergyR(Double_t a)           { m_PosR             = a; }
  // Not cylindrical R but distance between IP and Cluster.
  void SetEnergyRRMS(Double_t a)        { m_PosRErr          = a; }
  void SetEnergyTheta(Double_t a)       { m_PosTheta         = a; }
  void SetEnergyThetaRMS(Double_t a)    { m_PosThetaErr      = a; }
  void SetSystem(Int_t a)               { m_system           = a; }
  void SetUpCluster(Double_t energy,
		    Double_t pos_phi,  Double_t pos_phierr,
		    Double_t pos_theta,Double_t pos_thetaerr,
		    Double_t pos_r,    Double_t pos_rerr,
		    Int_t barend, Int_t sysid
		    );
  
  //---Sort related part.
  Bool_t IsSortable() const { return kTRUE; }
  Int_t  Compare(const TObject *obj) const {
    if (m_energy < ((LCDCluster*)obj)->GetEnergy()) {
      return -1;
    } else if (m_energy > ((LCDCluster*)obj)->GetEnergy()) {
      return 1;
    } else {
      return 0;
    }
  }
  
private:  
  Float_t m_energy;     // energy
  Float_t m_PosTheta;   // theta (position) (energy weight)
  Float_t m_PosThetaErr;// error of theta (position) (energy weight)
  Float_t m_PosPhi;     // phi (position) (energy weight)
  Float_t m_PosPhiErr;  // error of phi(position) (energy weight)
  Float_t m_PosR;       // r (energy weight)
  Float_t m_PosRErr;    // error of r (energy weight)

  Float_t m_ClusterStartDepth; // radius where cluster goes above min-I
  
  Int_t   m_CalHitN;      // # of CalHit.
  Int_t   m_CalHitI[1000];// CalHit Index
  Int_t   m_McListN;      // # of contributing MC particles.
  Int_t   m_McListI[50];  // list of indices of contributing MC particles. 
  Float_t m_McListE[50];  // list of energy contribution of MC particles.
  
  Int_t   m_barend;        // = 0 barrel  =1 endcap
  Int_t   m_system;        // = 0 EM      =1 HAD    =2 MU  =3 LUM

public:  
  ClassDef(LCDCluster,3)  // Cluster class
};

#endif
 
