Changeset 2477 for trunk


Ignore:
Timestamp:
11/05/03 18:26:02 (21 years ago)
Author:
tbretz
Message:
*** empty log message ***
Location:
trunk/MagicSoft/Mars
Files:
3 edited

Legend:

Unmodified
Added
Removed
  • trunk/MagicSoft/Mars/Changelog

    r2476 r2477  
    33  2003/11/05: Wolfgang Wittek
    44
    5    * macros/CT1Analysis.C, macros/ONOFFCT1Analysis.C
     5   * macros/CT1Analysis.C, macros/ONOFFCT1Analysis.C:
    66     - current versions of the macros for the analysis of CT1 data
    77 
    8    * manalysis/MMarquardt.[h,cc]
     8   * manalysis/MMarquardt.[h,cc]:
    99     - very pleliminary version of a class performing a minimization
    1010       using the Marquardt method
     
    1414       to the shower image using the maximum likelihood method
    1515
    16    * mimage/M2dimFunction.[h,cc]
     16   * mimage/M2dimFunction.[h,cc]:
    1717     - very pleliminary version of a container which contains the
    1818       parameters of the 2-dim function describing the shower image
     
    5858     - removed some obsolete IsUsed(idx) checks when filling the histogram
    5959     - ExecuteEvent now plots in the same canvas all the time
     60
     61   * mmain/MStatusDisplay.[h,cc]:
     62     - added new data member fUserFrame
     63     - added new member function AddUserFrame
     64     - made call to ProcessEvent() and similar thread safe by
     65       checking whether we run in the main thread or not.
     66     - Set the progress bar range to (0,1)
     67     - Added member function to set progress bar position
     68     - updated comments
     69     - added some workarounds for root bugs in TCanvas (sometimes
     70       they call gPad->cd() indirectly when gPad==NULL)
     71     - Fixed thread safety of UpdateTab()
     72     - Fixed some crashes in case fTab==NULL
     73     - Tried to make HandleConfigureNotify more flexible to allow
     74       the new fUserFrame to work correctly - needs still some
     75       investigations
     76     - made fList a protected data member
     77     - added new member function Update()
    6078
    6179
  • trunk/MagicSoft/Mars/mmain/MStatusDisplay.cc

    r2416 r2477  
    7272#include <TDatime.h>              // TDatime
    7373#include <TRandom.h>              // TRandom
     74#include <TThread.h>              // TThread::Self()
    7475#include <TBrowser.h>             // TBrowser
    7576#include <TObjArray.h>            // TObjArray
    7677#include <TPostScript.h>          // TPostScript
    77 
    78 #include <TRint.h>                // gApplication, TRint::Class()
     78#include <TMethodCall.h>          // TMethodCall
     79
     80//#include <TRint.h>                // gApplication, TRint::Class()
    7981#include <TInterpreter.h>         // gInterpreter
    8082
     
    282284// --------------------------------------------------------------------------
    283285//
     286// Adds an empty TGCompositeFrame which might be filled by the user
     287//
     288void MStatusDisplay::AddUserFrame()
     289{
     290    TGLayoutHints *lay=new TGLayoutHints(kLHintsExpandX);
     291    fList->Add(lay);
     292
     293    fUserFrame = new TGCompositeFrame(this, 1, 1);
     294    AddFrame(fUserFrame, lay);
     295    fList->Add(fUserFrame);
     296}
     297
     298// --------------------------------------------------------------------------
     299//
    284300// Add the title tab
    285301//
     
    376392
    377393        // make it visible
    378         // FIXME: This is a workaround, because TApplication::Run is not thread safe against ProcessEvents
    379         if (gApplication->InheritsFrom(TRint::Class()))
     394        // FIXME: This is a workaround, because TApplication::Run is not
     395        //        thread safe against ProcessEvents. We assume, that if
     396        //        we are not in the Main-Thread ProcessEvents() is
     397        //        called by the TApplication Event Loop...
     398        if (!TThread::Self()/*gApplication->InheritsFrom(TRint::Class())*/)
    380399            gClient->ProcessEventsFor(fTab);
    381400    }
     
    425444// --------------------------------------------------------------------------
    426445//
    427 // Add the progress bar to the GUI
     446// Add the progress bar to the GUI. The Progress Bar range is set to
     447// (0,1) as default.
    428448//
    429449void MStatusDisplay::AddProgressBar()
     
    433453
    434454    fBar=new TGHProgressBar(this);
     455    fBar->SetRange(0, 1);
    435456    fBar->ShowPosition();
    436457    AddFrame(fBar, laybar);
     
    440461// --------------------------------------------------------------------------
    441462//
     463// Set the progress bar position between 0 and 1. The Progress bar range
     464// is assumed to be (0,1)
     465//
     466void MStatusDisplay::SetProgressBarPosition(Float_t p)
     467{
     468    fBar->SetPosition(p);
     469}
     470
     471// --------------------------------------------------------------------------
     472//
    442473// Adds the status bar to the GUI
    443474//
     
    446477    fStatusBar = new TGStatusBar(this, 1, 1);
    447478
     479    //
     480    // Divide it like the 'Golden Cut' (goldener Schnitt)
    448481    //
    449482    //     1-a     a
     
    474507        return;
    475508    fStatusBar->SetText(txt, 0);
    476     // FIXME: This is a workaround, because TApplication::Run is not thread safe against ProcessEvents
    477     if (gApplication->InheritsFrom(TRint::Class()))
     509
     510    // FIXME: This is a workaround, because TApplication::Run is not
     511    //        thread safe against ProcessEvents. We assume, that if
     512    //        we are not in the Main-Thread ProcessEvents() is
     513    //        called by the TApplication Event Loop...
     514    if (!TThread::Self()/*gApplication->InheritsFrom(TRint::Class())*/)
    478515        gClient->ProcessEventsFor(fStatusBar);
    479516}
     
    488525        return;
    489526    fStatusBar->SetText(txt, 1);
    490     // FIXME: This is a workaround, because TApplication::Run is not thread safe against ProcessEvents
    491     if (gApplication->InheritsFrom(TRint::Class()))
     527
     528    // FIXME: This is a workaround, because TApplication::Run is not
     529    //        thread safe against ProcessEvents. We assume, that if
     530    //        we are not in the Main-Thread ProcessEvents() is
     531    //        called by the TApplication Event Loop...
     532    if (!TThread::Self()/*gApplication->InheritsFrom(TRint::Class())*/)
    492533        gClient->ProcessEventsFor(fStatusBar);
    493534}
     
    515556//
    516557MStatusDisplay::MStatusDisplay(Long_t t)
    517 : TGMainFrame(gClient ? gClient->GetRoot() : NULL, 1, 1), fTimer(this, t, kTRUE), fStatus(kLoopNone), fLog(&gLog), fLogIdx(-1), fLogTimer(this, 250, kTRUE), fLogBox(NULL), fIsLocked(0)
     558: TGMainFrame(gClient ? gClient->GetRoot() : NULL, 1, 1), fTab(NULL), fTimer(this, t, kTRUE), fStatus(kLoopNone), fLog(&gLog), fLogIdx(-1), fLogTimer(this, 250, kTRUE), fLogBox(NULL), fIsLocked(0)
    518559{
    519560    //
     
    544585    SetWMSizeHints(570, 480, 1280, 980, 1, 1);
    545586    Move(rand()%100+50, rand()%100+50);
    546     //Resize(740, 600);
    547587    Resize(570, 480);
    548588
     
    559599    {
    560600        AddMenuBar();
     601        AddUserFrame();
    561602        AddTabs();
    562603        AddProgressBar();
     
    575616    MapWindow();
    576617
    577     // FIXME: This is a workaround, because TApplication::Run is not thread safe against ProcessEvents
    578     if (gApplication->InheritsFrom(TRint::Class()))
     618    // FIXME: This is a workaround, because TApplication::Run is not
     619    //        thread safe against ProcessEvents. We assume, that if
     620    //        we are not in the Main-Thread ProcessEvents() is
     621    //        called by the TApplication Event Loop...
     622    if (!TThread::Self()/*gApplication->InheritsFrom(TRint::Class())*/)
    579623        gSystem->ProcessEvents();
    580624}
     
    587631MStatusDisplay::~MStatusDisplay()
    588632{
     633#if ROOT_VERSION_CODE < ROOT_VERSION(3,10,01)
     634    fTab = NULL; // See HandleEvent
     635#endif
     636
    589637    //
    590638    // Delete object from global object table so it cannot
     
    714762}
    715763
    716 /*
    717 class MCanvas : public TRootEmbeddedCanvas
    718 {
    719 public:
    720     MCanvas(const char* name, const TGWindow* p, UInt_t w, UInt_t h, UInt_t o) :
    721               TRootEmbeddedCanvas(name, p, w, h, o) {}
    722               void Layout()
    723               {
    724                   cout << "EmbLayout: " << GetCanvas()->GetName() << endl;
    725 
    726                   // Create layout for canvas. Depending on the size of the container
    727                   // we need to add the scrollbars.
    728                   TRootEmbeddedCanvas::Layout();
    729               }
    730 };
    731 */
    732 
    733764TGCompositeFrame *MStatusDisplay::AddRawTab(const char *name)
    734765{
     
    742773
    743774    // display new tab in the main frame
    744     // FIXME: This is a workaround, because TApplication::Run is not thread safe against ProcessEvents
    745     if (gApplication->InheritsFrom(TRint::Class()))
     775    // FIXME: This is a workaround, because TApplication::Run is not
     776    //        thread safe against ProcessEvents. We assume, that if
     777    //        we are not in the Main-Thread ProcessEvents() is
     778    //        called by the TApplication Event Loop...
     779    if (!TThread::Self()/*gApplication->InheritsFrom(TRint::Class())*/)
    746780        gClient->ProcessEventsFor(fTab);
    747781
     
    786820
    787821    // layout and map new tab
    788 //#if ROOT_VERSION_CODE < ROOT_VERSION(3,03,00)
    789 //    MapSubwindows();
    790 //    Layout();
    791 //#else
    792822    Layout();
    793823    MapSubwindows();
    794824    Layout();
    795 //#endif
    796825
    797826    // display new tab in the main frame
    798     // FIXME: This is a workaround, because TApplication::Run is not thread safe against ProcessEvents
    799     if (gApplication->InheritsFrom(TRint::Class()))
     827    // FIXME: This is a workaround, because TApplication::Run is not
     828    //        thread safe against ProcessEvents. We assume, that if
     829    //        we are not in the Main-Thread ProcessEvents() is
     830    //        called by the TApplication Event Loop...
     831    if (!TThread::Self()/*gApplication->InheritsFrom(TRint::Class())*/)
    800832        gClient->ProcessEventsFor(fTab);
    801833
     
    807839}
    808840
    809 
    810841// --------------------------------------------------------------------------
    811842//
    812843// Update a canvas in a tab, takes the corresponding TGCompositeFrame
    813 // as an argument
     844// as an argument. This is necessary, because not all functions
     845// changing the contents of a canvas or pad can call SetModified()
     846// for the corresponding tab. If this is not called correctly the
     847// tab won't be updated calling TCanvas::Update(). So we simply
     848// redraw it by our own (instead we could recursively call
     849// TPad::Modified() for everything contained by the TCanvas and
     850// call TCanvas::Update() afterwards)
    814851//
    815852void MStatusDisplay::UpdateTab(TGCompositeFrame *f)
     
    822859        return;
    823860
    824     // Code taken from TCanvas::Update() and TCanvas::Paint()
    825     // replaces PaintModified() by Paint()
     861    //
     862    // If we are in a multithreaded environment (gThreadXAR) we
     863    // have to make sure, that thus function is called from
     864    // the main thread.
     865    //
     866    // NOTE: Maybe there is still need to make sure, that only
     867    //       one thread can update the canvas by calling UpdateTab
     868    //       at the same time. Could be done by a TMutex.
     869    //
    826870    if (gThreadXAR)
    827871    {
    828         void *arr[2] = { NULL, c };
    829         if (((*gThreadXAR)("CUPD", 2, arr, NULL)))
     872        // Tell the X-Requester how to call this method
     873        TString str = Form("%d", (ULong_t)f);
     874
     875        TMethodCall call(IsA(), "UpdateTab", "NULL");
     876        void *arr[4] = { NULL, &call, this, (void*)(const char*)str };
     877
     878        // If this is not the main thread return
     879        if (((*gThreadXAR)("METH", 4, arr, NULL)))
    830880            return;
    831881    }
     882
     883#if ROOT_VERSION_CODE < ROOT_VERSION(3,10,01)
     884    TPad *padsav = (TPad*)gPad;
     885    if (!gPad)
     886        c->cd();
     887#endif
    832888
    833889    if (!c->IsBatch())
    834890        c->FeedbackMode(kFALSE);  // Goto double buffer mode
    835891
     892    //
     893    // Doing this ourself gives us the possibility to repaint
     894    // the canvas in any case (Paint() instead of PaintModified())
     895    //
    836896    c->Paint();                   // Repaint all pads
    837897    c->Flush();                   // Copy all pad pixmaps to the screen
    838898
     899#if ROOT_VERSION_CODE < ROOT_VERSION(3,10,01)
     900    if (padsav)
     901        padsav->cd();
     902    else
     903        gPad=NULL;
     904#endif
    839905    //c->SetCursor(kCross);
    840906
     
    924990
    925991    // display new tab in the main frame
    926     // FIXME: This is a workaround, because TApplication::Run is not thread safe against ProcessEvents
    927     if (gApplication->InheritsFrom(TRint::Class()))
     992    // FIXME: This is a workaround, because TApplication::Run is not
     993    //        thread safe against ProcessEvents. We assume, that if
     994    //        we are not in the Main-Thread ProcessEvents() is
     995    //        called by the TApplication Event Loop...
     996    if (!TThread::Self()/*gApplication->InheritsFrom(TRint::Class())*/)
    928997        gClient->ProcessEventsFor(fTab);
    929998
     
    20052074Bool_t MStatusDisplay::HandleConfigureNotify(Event_t *evt)
    20062075{
    2007     //cout << "----- Start -----" << endl;
     2076    //
     2077    // The initialization of the GUI is not yet enough finished...
     2078    //
     2079    if (!fTab)
     2080        return kTRUE;
    20082081
    20092082    UInt_t w = evt->fWidth;
    20102083    UInt_t h = evt->fHeight;
    20112084
    2012     //cout << "Old: " << GetWidth() << " " << GetHeight() << " " << GetBorderWidth() << endl;
    2013     //cout << "New: " << w << " " << h << endl;
    2014 
    2015     Bool_t wchanged = w!=GetWidth();
     2085    /*
     2086     cout << "Old: " << GetWidth() << " " << GetHeight() << " " << GetBorderWidth() << endl;
     2087     cout << "New: " << w << " " << h << " ";
     2088     cout << "New: " << GetDefaultWidth() << " " << GetDefaultHeight() << " " << endl;
     2089     */
     2090
     2091    //Bool_t wchanged = w!=GetWidth();
    20162092    Bool_t hchanged = h!=GetHeight();
    2017 
     2093    /*
    20182094    if (!wchanged && !hchanged)
    20192095    {
    20202096        Layout();
    2021         return kTRUE;
    2022     }
     2097        // FIXME: Make sure that this doesn't result in endless loops.
     2098        // return kTRUE;
     2099    }
     2100    */
    20232101
    20242102    if (GetWidth()==1 && GetHeight()==1)
     
    20292107    const UInt_t ch = GetHeight()-fTab->GetHeight();
    20302108
    2031     // canculate new size of frame (canvas @ 1:sqrt(2))
     2109    // calculate new size of frame (canvas @ 1:sqrt(2))
    20322110    if (hchanged)
    20332111        w = (UInt_t)((h-ch)*sqrt(2.)+.5)+cw;
     
    20352113        h = (UInt_t)((w-cw)/sqrt(2.)+.5)+ch;
    20362114
    2037     //cout << "Res: " << w << " " << h << " " << evt->fX << " " << evt->fY << endl;
    2038 
    20392115    // resize frame
    20402116    Resize(w, h);
     
    20452121Bool_t MStatusDisplay::HandleEvent(Event_t *event)
    20462122{
    2047     /*
    2048     if (event->fType!=9)
    2049     {
    2050         cout << "Event: " << event->fType << " ";
    2051         cout << event->fX << " " << event->fY << endl;
    2052     }
    2053     */
    2054     /*
    2055     switch (event->fType) {
    2056       case kConfigureNotify:
    2057          //while (gVirtualX->CheckEvent(fId, kConfigureNotify, *event))
    2058          //   ;
    2059          HandleConfigureNotify(event);
    2060          return kTRUE;
    2061     }
    2062     */
    2063     //   if (event->fType==kConfigureNotify && event->fX!=0 && event->fY!=0)
    2064     //        return kTRUE;
    2065 
    2066     return TGMainFrame::HandleEvent(event);
    2067 }
    2068 
     2123    Bool_t rc = TGMainFrame::HandleEvent(event);
     2124
     2125    //
     2126    // This fixes a bug in older root versions which makes
     2127    // TCanvas crash if gPad==NULL. So we make sure, that
     2128    // gPad!=NULL -- be carfull, this may have other side
     2129    // effects.
     2130    //
     2131#if ROOT_VERSION_CODE < ROOT_VERSION(3,10,01)
     2132    if (!gPad && fTab)
     2133        for (int i=0; i<fTab->GetNumberOfTabs(); i++)
     2134        {
     2135            TCanvas *c = GetCanvas(i);
     2136            if (c)
     2137            {
     2138                c->cd();
     2139                gLog << dbg << "MStatusDisplay::HandleEvent - Workaround: gPad=" << gPad << "." << endl;
     2140                break;
     2141            }
     2142        }
     2143#endif
     2144
     2145    return rc;
     2146}
     2147
     2148/*
     2149 // --------------------------------------------------------------------------
     2150//
     2151//  Opens a save as dialog, and tries to store the canvas
     2152//  in the given output format
     2153//
     2154void MGEvtDisplay::SaveAsDialog() const
     2155{
     2156    static const char *gSaveAsTypes[] =
     2157    {
     2158        "PostScript",   "*.ps",
     2159        "Encapsulated PostScript", "*.eps",
     2160        "Gif files",    "*.gif",
     2161        "Macro files",  "*.C",
     2162        "ROOT files",   "*.root",
     2163        "All files",    "*",
     2164        NULL,           NULL
     2165    };
     2166
     2167    static TString dir(".");
     2168
     2169    TGFileInfo fi; // fFileName and fIniDir deleted in ~TGFileInfo
     2170
     2171    fi.fFileTypes = (const char**)gSaveAsTypes;
     2172    fi.fIniDir    = StrDup(dir);
     2173
     2174    new TGFileDialog(fClient->GetRoot(), this, kFDSave, &fi);
     2175
     2176    if (!fi.fFilename)
     2177        return;
     2178
     2179    dir = fi.fIniDir;
     2180
     2181    if (strstr(fi.fFilename, ".root") ||
     2182        strstr(fi.fFilename, ".ps")   ||
     2183        strstr(fi.fFilename, ".eps")  ||
     2184        strstr(fi.fFilename, ".gif"))
     2185    {
     2186        fCanvas->SaveAs(fi.fFilename);
     2187        return;
     2188    }
     2189    if (strstr(fi.fFilename, ".C"))
     2190    {
     2191        fCanvas->SaveSource(fi.fFilename);
     2192        return;
     2193    }
     2194    Warning("SaveAsDialog", "Unknown Extension: %s", fi.fFilename);
     2195}
     2196*/
  • trunk/MagicSoft/Mars/mmain/MStatusDisplay.h

    r2397 r2477  
    2727class TGProgressBar;
    2828class TGHProgressBar;
     29class TGCompositeFrame;
    2930class TRootEmbeddedCanvas;
    3031
     
    3334public:
    3435    typedef enum {
    35         // KFile
     36        // kFile
    3637        kFileBrowser, kFileCanvas, kFileSave, kFileSaveAs, kFileSaveAsPS,
    3738        kFileSaveAsRoot, kFileSaveAsGIF, kFileSaveAsC, kFilePrint,
     
    5253    } Status_t;
    5354
     55protected:
     56    MGList           *fList;
     57    TGCompositeFrame *fUserFrame;
     58
     59    Bool_t ProcessMessage(Long_t msg, Long_t mp1, Long_t mp2);
     60
    5461private:
    55     MGList         *fList;
    56     TGHProgressBar *fBar;
    57     TGTab          *fTab;
    58     TGLayoutHints  *fLayCanvas;
     62    TGHProgressBar   *fBar;
     63    TGTab            *fTab;
     64    TGLayoutHints    *fLayCanvas;
    5965
    6066    TTimer fTimer;
     
    7884
    7985    void AddMenuBar();
     86    void AddUserFrame();
     87    void AddTabs();
    8088    void AddProgressBar();
     89    void AddStatusBar();
    8190    void AddMarsTab();
    8291    void AddLogTab();
    83     void AddTabs();
    84     void AddStatusBar();
    8592
    8693    TCanvas *GetCanvas(TGCompositeFrame *f) const;
     
    9097    Bool_t ProcessMessageTextview(Long_t submsg, Long_t mp1, Long_t mp2);
    9198    Bool_t ProcessMessageUser(Long_t submsg, Long_t mp1, Long_t mp2);
    92     Bool_t ProcessMessage(Long_t msg, Long_t mp1, Long_t mp2);
    9399    void   CloseWindow();
    94100    Bool_t HandleConfigureNotify(Event_t *);
     
    119125     void SetUpdateTime(Long_t t);       
    120126
     127     void SetProgressBarPosition(Float_t p);
    121128     TGProgressBar *GetBar() const { return (TGProgressBar*)fBar; }
    122129
     
    142149
    143150     Bool_t CdCanvas(const TString &name);
     151     void   Update() { HandleTimer(&fTimer); HandleTimer(&fLogTimer); }
    144152
    145153     void SetNoContextMenu(Bool_t flag=kTRUE);
Note: See TracChangeset for help on using the changeset viewer.