#ifndef MARS_MCalibrationChargeCam
#define MARS_MCalibrationChargeCam

#ifndef MARS_MParContainer
#include "MParContainer.h"
#endif
#ifndef MARS_MCamEvent
#include "MCamEvent.h"
#endif

class TH1D;
class TH2D;
class TClonesArray;

class MCalibrationChargeBlindPix;
class MCalibrationChargePINDiode;
class MCalibrationChargePix;
class MCalibrationChargeCam : public MParContainer, public MCamEvent
{
private:
  
  Int_t fNumPixels;
  TClonesArray *fPixels;                                        //-> Array of MCalibrationPix with fit results
  MCalibrationChargePix *fAverageInnerPix;                      //-> Average Pixel of all events
  MCalibrationChargePix *fAverageOuterPix;                      //-> Average Pixel of all events
  
  const MCalibrationChargeBlindPix *fBlindPixel;                //! Pointer to the Blind Pixel with fit results
  const MCalibrationChargePINDiode *fPINDiode;                  //! Pointer to the PIN Diode with fit results

  const MGeomCam             *fGeomCam;                         //! Need geom cam to know which pixel in inner or outer

  TH1D* fOffsets;                                               //! 
  TH1D* fSlopes;                                                //! 
  
  TH2D* fOffvsSlope;                                            //! 

  UInt_t  fNumExcludedPixels;

  Byte_t  fFlags;

  enum  { kBlindPixelMethodValid, kPINDiodeMethodValid, kCombinedMethodValid };
  
public:

  MCalibrationChargeCam(const char *name=NULL, const char *title=NULL);
  ~MCalibrationChargeCam();
  
  void Clear(    Option_t *o="" );
  void InitSize( const UInt_t i );

  // Setters   
  void SetNumPixelsExcluded(  const UInt_t n )            {  fNumExcludedPixels = n; }
  void SetGeomCam(  const MGeomCam *geom)                 {  fGeomCam = geom;        }

  void SetPINDiode  ( const MCalibrationChargePINDiode *d ) {  fPINDiode   = d;      }
  void SetBlindPixel( const MCalibrationChargeBlindPix *b ) {  fBlindPixel = b;      }

  // Setters only for MC!!
  void SetBlindPixelMethodValid( const Bool_t b = kTRUE );
  void SetPINDiodeMethodValid(   const Bool_t b = kTRUE );  

  // Getters
  Int_t  GetSize()               const;
  UInt_t GetNumPixels()          const { return fNumPixels; }

  Bool_t GetConversionFactorFFactor(    Int_t ipx, Float_t &mean, Float_t &err, Float_t &sigma );
  Bool_t GetConversionFactorBlindPixel( Int_t ipx, Float_t &mean, Float_t &err, Float_t &sigma );
  Bool_t GetConversionFactorPINDiode(   Int_t ipx, Float_t &mean, Float_t &err, Float_t &sigma );
  Bool_t GetConversionFactorCombined(   Int_t ipx, Float_t &mean, Float_t &err, Float_t &sigma );

  Bool_t IsBlindPixelMethodValid()   const;
  Bool_t IsPINDiodeMethodValid()     const;  

  // Others
  MCalibrationChargePix &operator[](UInt_t i);
  const MCalibrationChargePix &operator[](UInt_t i) const;

  MCalibrationChargePix *GetAverageInnerPix()              { return fAverageInnerPix; }
  const MCalibrationChargePix *GetAverageInnerPix() const  { return fAverageInnerPix; }

  MCalibrationChargePix *GetAverageOuterPix()              { return fAverageOuterPix; }
  const MCalibrationChargePix *GetAverageOuterPix() const  { return fAverageOuterPix; }

  // Prints
  void Print(Option_t *o="") const;
  
  // Draws
  void DrawPixelContent(Int_t num) const;    
//  void DrawHiLoFits();
  
  // Others
  Bool_t GetPixelContent(Double_t &val, Int_t idx, const MGeomCam &cam, Int_t type=0) const;

  void   ApplyPINDiodeCalibration();
  void   ApplyBlindPixelCalibration();

  ClassDef(MCalibrationChargeCam, 1)	// Container for calibration information of the camera
};

#endif





