Index: trunk/MagicSoft/Mars/Changelog
===================================================================
--- trunk/MagicSoft/Mars/Changelog	(revision 5993)
+++ trunk/MagicSoft/Mars/Changelog	(revision 5994)
@@ -28,4 +28,5 @@
 
 
+
  2005/01/25 Thomas Bretz
 
@@ -37,4 +38,24 @@
      - moved the empty Reset() function into the source file and
        added a lot of comments
+     - implemented new helper-functions: GetNewObject
+
+   * mbase/MContinue.[h,cc]:
+     - allow to use MFilter-classes as filter in ReadEnv
+
+   * mbase/MTaskEnv.cc:
+     - replaced some code by GetNewObject
+
+   * mhbase/MFillH.cc:
+     - handle DrawOption "same" to be able to draw to the same pad
+
+   * mhbase/MH.[h,cc]:
+     - added same-argument to DrawSame
+
+   * mhbase/MH3.cc:
+     - removed some obsolete comments
+     - remove own drawing options before calling fHist->Draw
+
+   * mimage/MHHillas.cc, mimage/MHImagePar.cc:
+     - first try of implementing 'same' drawing option
 
 
Index: trunk/MagicSoft/Mars/mbase/MContinue.cc
===================================================================
--- trunk/MagicSoft/Mars/mbase/MContinue.cc	(revision 5993)
+++ trunk/MagicSoft/Mars/mbase/MContinue.cc	(revision 5994)
@@ -241,5 +241,5 @@
 //     MyContinue.0: MHillas.fSize>1000
 //     MyContinue.1: MHillas.fSize<10000
-//   or
+//   or (the syntax might change in the future!)
 //     MyContinue.Condition: <MMyClass>
 //     MMyClass.Variable1: ...
@@ -250,4 +250,5 @@
 Int_t MContinue::ReadEnv(const TEnv &env, TString prefix, Bool_t print)
 {
+    MFilter *f = 0;
     if (IsEnvDefined(env, prefix, "Condition", print))
     {
@@ -256,10 +257,13 @@
         if (txt.BeginsWith("<") && txt.EndsWith(">"))
         {
-            *fLog << err << "NOT YET IMPLEMENTED..." << endl;
-            return kERROR;
+            const TString name = txt(1, txt.Length()-2);
+            f = (MFilter*)GetNewObject(name, MFilter::Class());
+            if (!f)
+                return kERROR;
         }
     }
 
-    MF *f = new MF;
+    if (!f)
+        f = new MF;
     f->SetName(fName);
 
Index: trunk/MagicSoft/Mars/mbase/MContinue.h
===================================================================
--- trunk/MagicSoft/Mars/mbase/MContinue.h	(revision 5993)
+++ trunk/MagicSoft/Mars/mbase/MContinue.h	(revision 5994)
@@ -30,4 +30,5 @@
     Int_t PostProcess();
 
+    // MContinue
     enum { kIsOwner = BIT(14), kFilterIsPrivate = BIT(15), kAllowEmpty = BIT(16) };
 
Index: trunk/MagicSoft/Mars/mbase/MParContainer.cc
===================================================================
--- trunk/MagicSoft/Mars/mbase/MParContainer.cc	(revision 5993)
+++ trunk/MagicSoft/Mars/mbase/MParContainer.cc	(revision 5994)
@@ -465,4 +465,132 @@
 }
 
+// --------------------------------------------------------------------------
+//
+// Return the pointer to the TClass (from the root dictionary) which
+// corresponds to the class with name name.
+//
+// Make sure, that a new object of this type can be created.
+//
+// In case of failure return NULL
+//
+TClass *MParContainer::GetConstructor(const char *name) const
+{
+    //
+    // try to get class from root environment
+    //
+    TClass *cls = gROOT->GetClass(name);
+    Int_t rc = 0;
+    if (!cls)
+        rc =1;
+    else
+    {
+        if (!cls->Property())
+            rc = 5;
+        if (!cls->Size())
+            rc = 4;
+        if (!cls->IsLoaded())
+            rc = 3;
+        if (!cls->HasDefaultConstructor())
+            rc = 2;
+    }
+
+    if (!rc)
+        return cls;
+
+    *fLog << err << dbginf << GetDescriptor() << " - Cannot create new instance of class '" << name << "': ";
+    switch (rc)
+    {
+    case 1:
+        *fLog << "gROOT->GetClass() returned NULL." << endl;
+        return NULL;
+    case 2:
+        *fLog << "no default constructor." << endl;
+        return NULL;
+    case 3:
+        *fLog << "not loaded." << endl;
+        return NULL;
+    case 4:
+        *fLog << "zero size." << endl;
+        return NULL;
+    case 5:
+        *fLog << "no property." << endl;
+        return NULL;
+    }
+
+    *fLog << "rtlprmft." << endl;
+
+    return NULL;
+}
+
+// --------------------------------------------------------------------------
+//
+// Return a new object of class 'name'. Make sure that the object
+// derives from the class base.
+//
+// In case of failure return NULL
+//
+// The caller is responsible of deleting the object!
+//
+MParContainer *MParContainer::GetNewObject(const char *name, TClass *base) const
+{
+    TClass *cls = GetConstructor(name);
+    if (!cls || !base)
+        return NULL;
+
+    if (!cls->InheritsFrom(base))
+    {
+        *fLog << " - Class doesn't inherit from " << base->GetName() << endl;
+        return NULL;
+    }
+
+    //
+    // create the parameter container of the the given class type
+    //
+    TObject *obj = (TObject*)cls->New();
+    if (!obj)
+    {
+        *fLog << " - Class has no default constructor." << endl;
+        *fLog << " - An abstract member functions of a base class is not overwritten." << endl;
+        return NULL;
+    }
+
+    return (MParContainer*)obj;
+}
+
+// --------------------------------------------------------------------------
+//
+// Return a new object of class 'name'. Make sure that the object
+// derives from the class base.
+//
+// In case of failure return NULL
+//
+// The caller is responsible of deleting the object!
+//
+MParContainer *MParContainer::GetNewObject(const char *name, const char *base) const
+{
+    TClass *cls = GetConstructor(name);
+    if (!cls || !base)
+        return NULL;
+
+    if (!cls->InheritsFrom(base))
+    {
+        *fLog << " - Class doesn't inherit from " << base << endl;
+        return NULL;
+    }
+
+    //
+    // create the parameter container of the the given class type
+    //
+    TObject *obj = (TObject*)cls->New();
+    if (!obj)
+    {
+        *fLog << " - Class has no default constructor." << endl;
+        *fLog << " - An abstract member functions of a base class is not overwritten." << endl;
+        return NULL;
+    }
+
+    return (MParContainer*)obj;
+}
+
 TMethodCall *MParContainer::GetterMethod(const char *name) const
 {
Index: trunk/MagicSoft/Mars/mbase/MParContainer.h
===================================================================
--- trunk/MagicSoft/Mars/mbase/MParContainer.h	(revision 5993)
+++ trunk/MagicSoft/Mars/mbase/MParContainer.h	(revision 5994)
@@ -53,4 +53,6 @@
 
     Bool_t  fReadyToSave; // should be set to true if the contents of the container is changed somehow
+
+    TClass *GetConstructor(const char *name) const;
 
 public:
@@ -140,4 +142,7 @@
     const char *GetEnvValue(const TEnv &env, TString prefix, const char *dflt) const;
 
+    MParContainer *GetNewObject(const char *name, const char *base) const;
+    MParContainer *GetNewObject(const char *name, TClass *base=MParContainer::Class()) const;
+
     ClassDef(MParContainer, 0)  //The basis for all parameter containers
 };
Index: trunk/MagicSoft/Mars/mbase/MTaskEnv.cc
===================================================================
--- trunk/MagicSoft/Mars/mbase/MTaskEnv.cc	(revision 5993)
+++ trunk/MagicSoft/Mars/mbase/MTaskEnv.cc	(revision 5994)
@@ -100,62 +100,7 @@
 MTask *MTaskEnv::GetTask(const char *name) const
 {
-    //
-    // try to get class from root environment
-    //
-    TClass *cls = gROOT->GetClass(name);
-    Int_t rc = 0;
-    if (!cls)
-        rc =1;
-    else
-    {
-        if (!cls->Property())
-            rc = 5;
-        if (!cls->Size())
-            rc = 4;
-        if (!cls->IsLoaded())
-            rc = 3;
-        if (!cls->HasDefaultConstructor())
-            rc = 2;
-    }
-
-    if (rc)
-    {
-        *fLog << err << dbginf << "Cannot create new instance of class '" << name << "': ";
-        switch (rc)
-        {
-        case 1:
-            *fLog << "gROOT->GetClass() returned NULL." << endl;
-            return NULL;
-        case 2:
-            *fLog << "no default constructor." << endl;
-            return NULL;
-        case 3:
-            *fLog << "not loaded." << endl;
-            return NULL;
-        case 4:
-            *fLog << "zero size." << endl;
-            return NULL;
-        case 5:
-            *fLog << "no property." << endl;
-            return NULL;
-        }
-    }
-
-    if (!cls->InheritsFrom(MTask::Class()))
-    {
-        *fLog << " - Class doesn't inherit from MTask." << endl;
+    MTask *task = (MTask*)GetNewObject(name, MTask::Class());
+    if (!task)
         return NULL;
-    }
-
-    //
-    // create the parameter container of the the given class type
-    //
-    MTask *task = (MTask*)cls->New();
-    if (!task)
-    {
-        *fLog << " - Class has no default constructor." << endl;
-        *fLog << " - An abstract member functions of a base class is not overwritten." << endl;
-        return NULL;
-    }
 
     task->SetName(fName);
Index: trunk/MagicSoft/Mars/mhbase/MFillH.cc
===================================================================
--- trunk/MagicSoft/Mars/mhbase/MFillH.cc	(revision 5993)
+++ trunk/MagicSoft/Mars/mhbase/MFillH.cc	(revision 5994)
@@ -358,4 +358,8 @@
 // if fDisplay is set and the MH-class overwrites the Draw function
 //
+// If the draw-option contains 'same' (case insensitive) a tab with the
+// same name as the one which would be created is searched and the
+// MH is drawn to this canvas. If it is not found a new tab is created.
+//
 Bool_t MFillH::DrawToDisplay()
 {
@@ -371,5 +375,13 @@
         return kTRUE;
 
-    fCanvas = &fDisplay->AddTab(fNameTab.IsNull() ? fH->GetName() : fNameTab.Data());
+    const TString tabname = fNameTab.IsNull() ? fH->GetName() : fNameTab.Data();
+
+    fCanvas = 0;
+    if (fDrawOption.Contains("same", TString::kIgnoreCase))
+        fCanvas = fDisplay->GetCanvas(tabname);
+    if (!fCanvas)
+        fCanvas = &fDisplay->AddTab(tabname);
+
+    fCanvas->cd();
     fH->Draw(fDrawOption);
 
Index: trunk/MagicSoft/Mars/mhbase/MH.cc
===================================================================
--- trunk/MagicSoft/Mars/mhbase/MH.cc	(revision 5993)
+++ trunk/MagicSoft/Mars/mhbase/MH.cc	(revision 5994)
@@ -795,10 +795,10 @@
 // Also layout the two statistic boxes and a legend.
 //
-void MH::DrawSame(TH1 &hist1, TH1 &hist2, const TString title)
+void MH::DrawSame(TH1 &hist1, TH1 &hist2, const TString title, Bool_t same)
 {
     //
     // Draw first histogram
     //
-    hist1.Draw();
+    hist1.Draw(same?"same":"");
     gPad->SetBorderMode(0);
     gPad->Update();
Index: trunk/MagicSoft/Mars/mhbase/MH.h
===================================================================
--- trunk/MagicSoft/Mars/mhbase/MH.h	(revision 5993)
+++ trunk/MagicSoft/Mars/mhbase/MH.h	(revision 5994)
@@ -85,5 +85,5 @@
 
     static void DrawSameCopy(const TH1 &hist1, const TH1 &hist2, const TString title);
-    static void DrawSame(TH1 &hist1, TH1 &hist2, const TString title);
+    static void DrawSame(TH1 &hist1, TH1 &hist2, const TString title, Bool_t same=kFALSE);
 
     TObject *Clone(const char *name="") const;
Index: trunk/MagicSoft/Mars/mhbase/MH3.cc
===================================================================
--- trunk/MagicSoft/Mars/mhbase/MH3.cc	(revision 5993)
+++ trunk/MagicSoft/Mars/mhbase/MH3.cc	(revision 5994)
@@ -103,7 +103,5 @@
 //
 MH3::MH3(const unsigned int dim)
-    : fDimension(dim>3?3:dim), fHist(NULL)/*,
-    fNameProfX(Form("ProfX_%p", this)),
-    fNameProfY(Form("ProfY_%p", this))*/
+    : fDimension(dim>3?3:dim), fHist(NULL)
 {  
     switch (fDimension)
@@ -205,5 +203,5 @@
 //
 MH3::MH3(const char *memberx, const char *membery)
-    : fDimension(2)/*, fNameProfX(Form("ProjX_%p", this)), fNameProfY(Form("ProjY_%p", this))*/
+    : fDimension(2)
 {
     fHist = new TH2F;
@@ -539,9 +537,16 @@
 
     TString str(o);
-    str = str.Strip(TString::kBoth);
-
-    Bool_t only = str.Contains("ONLY", TString::kIgnoreCase) && fDimension==2;
-    Bool_t same = str.Contains("SAME", TString::kIgnoreCase) && fDimension==2;
-    Bool_t blue = str.Contains("BLUE", TString::kIgnoreCase) && fDimension==2;
+    str.ToLower();
+
+    const Bool_t only  = str.Contains("only")  && fDimension==2;
+    const Bool_t same  = str.Contains("same")  && fDimension==2;
+    const Bool_t blue  = str.Contains("blue")  && fDimension==2;
+    const Bool_t profx = str.Contains("profx") && fDimension==2;
+    const Bool_t profy = str.Contains("profy") && fDimension==2;
+    // Do NOT replace 'same'-option
+    str.ReplaceAll("only",  "");
+    str.ReplaceAll("blue",  "");
+    str.ReplaceAll("profx", "");
+    str.ReplaceAll("profy", "");
 
     // FIXME: We may have to remove all our own options from str!
@@ -549,5 +554,5 @@
         fHist->Draw(str);
 
-    if (str.Contains("PROFX", TString::kIgnoreCase) && fDimension==2)
+    if (profx)
     {
         TProfile *p = ((TH2*)fHist)->ProfileX("ProfX", -1, 9999, "s");
@@ -563,5 +568,5 @@
         }
     }
-    if (str.Contains("PROFY", TString::kIgnoreCase) && fDimension==2)
+    if (profy)
     {
         TProfile *p = ((TH2*)fHist)->ProfileY("ProfY", -1, 9999, "s");
Index: trunk/MagicSoft/Mars/mimage/MHHillas.cc
===================================================================
--- trunk/MagicSoft/Mars/mimage/MHHillas.cc	(revision 5993)
+++ trunk/MagicSoft/Mars/mimage/MHHillas.cc	(revision 5994)
@@ -286,5 +286,5 @@
 // together with the canvas.
 //
-void MHHillas::Draw(Option_t *)
+void MHHillas::Draw(Option_t *o)
 {
     TVirtualPad *pad = gPad ? gPad : MakeDefCanvas(this);
@@ -293,13 +293,29 @@
     AppendPad("");
 
-    pad->Divide(2,3);
+    TString opt(o);
+    opt.ToLower();
+
+    // FIXME: If same-option given make two independant y-axis!
+    const Bool_t same = opt.Contains("same");
+
+    if (!same)
+        pad->Divide(2,3);
+    else
+    {
+        fDistC->SetLineColor(kGreen);
+        fSize->SetLineColor(kGreen);
+        fDelta->SetLineColor(kGreen);
+
+        fWidth->SetLineColor(kMagenta);
+        fLength->SetLineColor(kCyan);
+    }
 
     pad->cd(1);
     gPad->SetBorderMode(0);
-    MH::DrawSame(*fWidth, *fLength, "Width'n'Length");
+    MH::DrawSame(*fWidth, *fLength, "Width'n'Length", same);
 
     pad->cd(2);
     gPad->SetBorderMode(0);
-    fDistC->Draw();
+    fDistC->Draw(same?"same":"");
 
     pad->cd(3);
@@ -307,24 +323,28 @@
     gPad->SetLogx();
     gPad->SetLogy();
-    fSize->Draw();
-
-    pad->cd(4);
-    gPad->SetBorderMode(0);
-    gPad->SetPad(0.51, 0.01, 0.99, 0.65);
-    SetColors();
-    fCenter->Draw("colz");
-    if (fGeomCam)
-    {
-        MHCamera *cam = new MHCamera(*fGeomCam);
-        cam->Draw("same");
-        cam->SetBit(kCanDelete);
+    fSize->Draw(same?"same":"");
+
+    if (!same)
+    {
+        pad->cd(4);
+        gPad->SetBorderMode(0);
+        gPad->SetPad(0.51, 0.01, 0.99, 0.65);
+        SetColors();
+        fCenter->Draw("colz");
+        if (fGeomCam)
+        {
+            MHCamera *cam = new MHCamera(*fGeomCam);
+            cam->Draw("same");
+            cam->SetBit(kCanDelete);
+        }
     }
 
     pad->cd(5);
     gPad->SetBorderMode(0);
-    fDelta->Draw();
+    fDelta->Draw(same?"same":"");
 
     pad->cd(6);
-    delete gPad;
+    if (gPad && !same)
+        delete gPad;
 
     pad->Modified();
Index: trunk/MagicSoft/Mars/mimage/MHImagePar.cc
===================================================================
--- trunk/MagicSoft/Mars/mimage/MHImagePar.cc	(revision 5993)
+++ trunk/MagicSoft/Mars/mimage/MHImagePar.cc	(revision 5994)
@@ -136,8 +136,14 @@
 void MHImagePar::Paint(Option_t *o)
 {
-    if (TString(o)==(TString)"log1" && fHistSatHi.GetMaximum()>0)
-        gPad->SetLogy();
-    if (TString(o)==(TString)"log2" && fHistIslands.GetMaximum()>0)
-        gPad->SetLogy();
+    /*
+     if (TString(o)==(TString)"log1" && fHistSatHi.GetMaximum()>0)
+     gPad->SetLogy();
+     if (TString(o)==(TString)"log2" && fHistIslands.GetMaximum()>0)
+     gPad->SetLogy();
+     */
+     if (fHistSatHi.GetMaximum()>0 && gPad->GetPad(1))
+         gPad->GetPad(1)->SetLogy();
+     if (fHistIslands.GetMaximum()>0 && gPad->GetPad(2))
+         gPad->GetPad(2)->SetLogy();
 }
 
@@ -148,5 +154,5 @@
 // together with the canvas.
 //
-void MHImagePar::Draw(Option_t *)
+void MHImagePar::Draw(Option_t *o)
 {
     TVirtualPad *pad = gPad ? gPad : MakeDefCanvas(this);
@@ -155,18 +161,30 @@
     AppendPad("");
 
-    pad->Divide(1,2);
-
-    pad->cd(1);
-    gPad->SetBorderMode(0);
-    MH::DrawSame(fHistSatHi, fHistSatLo, "Saturating Pixels");
-    fHistSatHi.SetMinimum(); // switch off to allow log-scale
-    fHistSatLo.SetMinimum(); // switch off to allow log-scale
-    fHistSatLo.SetMaximum(0.1);   // dummy value to allow log-scale
-    AppendPad("log1");
+    TString opt(o);
+    opt.ToLower();
+
+    // FIXME: If same-option given make two independant y-axis!
+    const Bool_t same = opt.Contains("same");
+
+    if (!same)
+        pad->Divide(1,2);
+    else
+        fHistIslands.SetLineColor(kGreen);
+
+    if (!same)
+    {
+        pad->cd(1);
+        gPad->SetBorderMode(0);
+        MH::DrawSame(fHistSatHi, fHistSatLo, "Saturating Pixels");
+        fHistSatHi.SetMinimum(); // switch off to allow log-scale
+        fHistSatLo.SetMinimum(); // switch off to allow log-scale
+        fHistSatLo.SetMaximum(0.1);   // dummy value to allow log-scale
+        //AppendPad("log1");
+    }
 
     pad->cd(2);
     gPad->SetBorderMode(0);
-    fHistIslands.Draw();
-    AppendPad("log2");
+    fHistIslands.Draw(same?"same":"");
+    //AppendPad("log2");
 }
 
