TGSpeedo.cxx

Go to the documentation of this file.
00001 // @(#)root/gui:$Id: TGSpeedo.cxx
00002 // Author: Bertrand Bellenot   26/10/06
00003 
00004 /*************************************************************************
00005  * Copyright (C) 1995-2006, Rene Brun and Fons Rademakers.               *
00006  * All rights reserved.                                                  *
00007  *                                                                       *
00008  * For the licensing terms see $ROOTSYS/LICENSE.                         *
00009  * For the list of contributors see $ROOTSYS/README/CREDITS.             *
00010  *************************************************************************/
00011 
00012 //////////////////////////////////////////////////////////////////////////
00013 //                                                                      //
00014 // TGSpeedo                                                             //
00015 //                                                                      //
00016 // TGSpeedo is a widget looking like a speedometer, with a needle,      //
00017 // a counter and a small odometer window.                               //
00018 //                                                                      //
00019 //Begin_Html
00020 /*
00021 <img src="gif/speedometer.gif">
00022 */
00023 //End_Html                                                              //
00024 //                                                                      //
00025 // Three thresholds are configurable, with their glowing color          //
00026 // A peak mark can be enabled, allowing to keep track of the highest    //
00027 // value displayed. The mark can be reset by right-clicking on the      //
00028 // widget.                                                              //
00029 // Two signals are available:                                           //
00030 //    OdoClicked(): when user click on the small odometer window        //
00031 //    LedClicked(): when user click on the small led near the counter   //
00032 //                                                                      //
00033 //////////////////////////////////////////////////////////////////////////
00034 
00035 #include "TSystem.h"
00036 #include "TGClient.h"
00037 #include "TGResourcePool.h"
00038 #include "TImage.h"
00039 #include "TEnv.h"
00040 #include "TMath.h"
00041 
00042 #include "TGSpeedo.h"
00043 
00044 
00045 ClassImp(TGSpeedo)
00046 
00047 //______________________________________________________________________________
00048 TGSpeedo::TGSpeedo(const TGWindow *p, int id)
00049    : TGFrame(p, 1, 1), TGWidget (id), fImage(0), fImage2(0), fBase(0)
00050 {
00051    // TGSpeedo widget constructor.
00052 
00053    fAngleMin = -133.5;
00054    fAngleMax =  133.5;
00055    fAngle    = -133.5;
00056    fScaleMin = 0.0;
00057    fScaleMax = 100.0;
00058    fValue    = 0.0;
00059    fCounter  = 0;
00060    fPeakMark = kFALSE;
00061    fMeanMark = kFALSE;
00062    fPeakVal  = 0.0;
00063    fMeanVal  = 0.0;
00064    fThreshold[0] = fThreshold[1] = fThreshold[2] = 0.0;
00065    fThresholdColor[0] = kGreen;
00066    fThresholdColor[1] = kOrange;
00067    fThresholdColor[2] = kRed;
00068    fThresholdActive = kFALSE;
00069    fPicName  = "speedo.gif";
00070    fImage = TImage::Open(fPicName);
00071    if (!fImage || !fImage->IsValid())
00072       Error("TGSpeedo::Build", "%s not found", fPicName.Data());
00073    Build();
00074    AddInput(kButtonPressMask | kButtonReleaseMask);
00075 }
00076 
00077 //______________________________________________________________________________
00078 TGSpeedo::TGSpeedo(const TGWindow *p, Float_t smin, Float_t smax,
00079                    const char *lbl1, const char *lbl2, const char *dsp1,
00080                    const char *dsp2, int id)
00081    : TGFrame(p, 1, 1), TGWidget (id), fImage(0), fImage2(0), fBase(0)
00082 {
00083    // TGSpeedo widget constructor.
00084 
00085    fAngleMin = -133.5;
00086    fAngleMax =  133.5;
00087    fAngle    = -133.5;
00088    fScaleMin = smin;
00089    fScaleMax = smax;
00090    fValue    = smin;
00091    fCounter  = 0;
00092    fLabel1   = lbl1;
00093    fLabel2   = lbl2;
00094    fDisplay1 = dsp1;
00095    fDisplay2 = dsp2;
00096    fPeakMark = kFALSE;
00097    fMeanMark = kFALSE;
00098    fPeakVal  = 0.0;
00099    fMeanVal  = 0.0;
00100    fThreshold[0] = fThreshold[1] = fThreshold[2] = 0.0;
00101    fThresholdColor[0] = kGreen;
00102    fThresholdColor[1] = kOrange;
00103    fThresholdColor[2] = kRed;
00104    fThresholdActive = kFALSE;
00105    fPicName  = "speedo.gif";
00106    fImage = TImage::Open(fPicName);
00107    if (!fImage || !fImage->IsValid())
00108       Error("TGSpeedo::Build", "%s not found", fPicName.Data());
00109    Build();
00110    AddInput(kButtonPressMask | kButtonReleaseMask);
00111 }
00112 
00113 //______________________________________________________________________________
00114 void TGSpeedo::Build()
00115 {
00116    // Build TGSpeedo widget.
00117 
00118    TString sc;
00119    Float_t step, mark[5];
00120    TString fp = gEnv->GetValue("Root.TTFontPath", "");
00121    TString ar = fp + "/arialbd.ttf";
00122    Int_t i, nexe, offset;
00123 
00124    const TGFont *counterFont = fClient->GetFont("-*-helvetica-bold-r-*-*-12-*-*-*-*-*-*-*");
00125    fCounterFS = counterFont->GetFontStruct();
00126 
00127    const TGFont *textFont = fClient->GetFont("-*-helvetica-bold-r-*-*-8-*-*-*-*-*-*-*");
00128    fTextFS = textFont->GetFontStruct();
00129 
00130    const TGFont *labelFont = fClient->GetFont("-*-helvetica-bold-r-*-*-14-*-*-*-*-*-*-*");
00131    FontStruct_t labelFS = labelFont->GetFontStruct();
00132 
00133    if (fImage && fImage->IsValid()) {
00134       fBase = fClient->GetPicturePool()->GetPicture(gSystem->BaseName(fPicName.Data()),
00135               fImage->GetPixmap(), fImage->GetMask());
00136       // center of the image
00137       Float_t xc = (Float_t)(fBase ? (fBase->GetWidth() + 1) / 2 : 96.0);
00138       Float_t yc = (Float_t)(fBase ? (fBase->GetHeight() + 1) / 2 : 96.0);
00139 
00140       // compute scale ticks steps
00141       step = (fScaleMax - fScaleMin) / 4.0;
00142       mark[0] = fScaleMin;
00143       mark[4] = fScaleMax;
00144       for (i=1; i<4; i++) {
00145          mark[i] = mark[i-1] + step;
00146       }
00147       // format tick labels
00148       if (fScaleMax >= 1000.0) {
00149          nexe = 0;
00150          while (1) {
00151             nexe++;
00152             for (i=0; i<5; i++) {
00153                mark[i] /= 10.0;
00154             }
00155             if (mark[4] < 1000.0) break;
00156          }
00157          // draw multiplier
00158          fImage->DrawText((Int_t)xc - 11, (Int_t)yc + 15, "x10", 12, "#ffffff", ar);
00159          sc.Form("%d", nexe);
00160          fImage->DrawText((Int_t)xc + 11, (Int_t)yc + 13, sc.Data(), 10, "#ffffff", ar);
00161       }
00162       else if (fScaleMax < 100.0) {
00163          nexe = 0;
00164          while (1) {
00165             nexe--;
00166             for (i=0; i<5; i++) {
00167                mark[i] *= 10.0;
00168             }
00169             if (mark[4] > 99.9 ) break;
00170          }
00171          // draw multiplier
00172          fImage->DrawText((Int_t)xc - 11, (Int_t)yc + 15, "x10", 12, "#ffffff", ar);
00173          sc.Form("%d", nexe);
00174          fImage->DrawText((Int_t)xc + 11, (Int_t)yc + 13, sc.Data(), 10, "#ffffff", ar);
00175       }
00176       // Format and draw scale tickmarks
00177       sc.Form("%d",(Int_t)mark[0]);
00178       fImage->DrawText((Int_t)xc - 51, (Int_t)yc + 30, sc.Data(), 14, "#ffffff", ar);
00179       sc.Form("%d",(Int_t)mark[1]);
00180       fImage->DrawText((Int_t)xc - 59, (Int_t)yc - 29, sc.Data(), 14, "#ffffff", ar);
00181       sc.Form("%d",(Int_t)mark[2]);
00182       offset = gVirtualX->TextWidth(labelFS, sc.Data(), sc.Length()) / 2;
00183       fImage->DrawText((Int_t)xc - offset, (Int_t)yc - 65, sc.Data(), 14, "#ffffff", ar);
00184       sc.Form("%d",(Int_t)mark[3]);
00185       offset = 60 - gVirtualX->TextWidth(labelFS, sc.Data(), sc.Length());
00186       fImage->DrawText((Int_t)xc + offset, (Int_t)yc - 29, sc.Data(), 14, "#ffffff", ar);
00187       sc.Form("%d",(Int_t)mark[4]);
00188       offset = 52 - gVirtualX->TextWidth(labelFS, sc.Data(), sc.Length());
00189       fImage->DrawText((Int_t)xc + offset, (Int_t)yc + 30, sc.Data(), 14, "#ffffff", ar);
00190       // draw main label (two lines)
00191       fImage->DrawText((Int_t)xc + 13, (Int_t)yc - 17, fLabel1.Data(), 14, "#ffffff", ar);
00192       fImage->DrawText((Int_t)xc + 13, (Int_t)yc -  4, fLabel2.Data(), 12, "#ffffff", ar);
00193       if (fBase)
00194          gVirtualX->ShapeCombineMask(fId, 0, 0, fBase->GetMask());
00195    }
00196 }
00197 
00198 //______________________________________________________________________________
00199 TGSpeedo::~TGSpeedo()
00200 {
00201    // TGSpeedo widget Destructor.
00202 
00203    if (fImage && fImage->IsValid())
00204       delete fImage;
00205    if (fImage2 && fImage2->IsValid())
00206       delete fImage2;
00207    if (fBase)
00208       fClient->FreePicture(fBase);
00209 }
00210 
00211 //______________________________________________________________________________
00212 TGDimension TGSpeedo::GetDefaultSize() const
00213 {
00214    // Return default dimension of the widget.
00215 
00216    if (fBase)
00217       return TGDimension(fBase->GetWidth(), fBase->GetHeight());
00218    return TGDimension(100, 100);
00219 }
00220 
00221 //______________________________________________________________________________
00222 void TGSpeedo::Glow(EGlowColor col)
00223 {
00224    // Make speedo glowing.
00225 
00226    static EGlowColor act_col = kNoglow;
00227    TImage *glowImage = 0;
00228 
00229    if (col == act_col)
00230       return;
00231 
00232    if (fImage && fImage->IsValid())
00233       delete fImage;
00234 
00235    switch (col) {
00236       case kNoglow:
00237          break;
00238       case kGreen:
00239          glowImage = TImage::Open("glow_green.png");
00240          if (!glowImage || !glowImage->IsValid()) {
00241             Error("TGSpeedo::Glow", "glow_green.png not found");
00242             glowImage = 0;
00243          }
00244          break;
00245       case kOrange:
00246          glowImage = TImage::Open("glow_orange.png");
00247          if (!glowImage || !glowImage->IsValid()) {
00248             Error("TGSpeedo::Glow", "glow_orange.png not found");
00249             glowImage = 0;
00250          }
00251          break;
00252       case kRed:
00253          glowImage = TImage::Open("glow_red.png");
00254          if (!glowImage || !glowImage->IsValid()) {
00255             Error("TGSpeedo::Glow", "glow_red.png not found");
00256             glowImage = 0;
00257          }
00258          break;
00259    }
00260    fImage = TImage::Open(fPicName);
00261    if (fImage && fImage->IsValid() && glowImage && glowImage->IsValid()) {
00262       fImage->Merge(glowImage);
00263       delete glowImage;
00264    }
00265    act_col = col;
00266    Build();
00267    DrawText();
00268 }
00269 
00270 //______________________________________________________________________________
00271 Bool_t TGSpeedo::HandleButton(Event_t *event)
00272 {
00273    // Handle mouse button event.
00274 
00275    if (fBase) {
00276       int xc = (fBase->GetWidth() + 1) / 2;
00277       int yc = (fBase->GetHeight() + 1) / 2;
00278       if (event->fType == kButtonRelease && event->fCode == kButton1) {
00279          // check if in the selector area
00280          if ((event->fX > (xc - 26)) && (event->fX < (xc + 26)) &&
00281              (event->fY < (yc + 50)) && (event->fY > (yc + 28))) {
00282             OdoClicked();
00283          }
00284          // check if in the led area
00285          else if ((event->fX > (xc + 30)) && (event->fX < (xc + 40)) &&
00286                   (event->fY > (yc + 57)) && (event->fY < (yc + 67))) {
00287             LedClicked();
00288          }
00289       }
00290       if (event->fType == kButtonRelease && event->fCode == kButton3) {
00291          ResetPeakVal();
00292       }
00293    }
00294    return kTRUE;
00295 }
00296 
00297 //______________________________________________________________________________
00298 void TGSpeedo::SetOdoValue(Int_t val)
00299 {
00300    // Set actual value of odo meter.
00301 
00302    // avoid useless redraw
00303    if (val == fCounter)
00304       return;
00305    fCounter = val;
00306    DrawText();
00307    DrawNeedle();
00308 }
00309 
00310 //______________________________________________________________________________
00311 void TGSpeedo::SetDisplayText(const char *text1, const char *text2)
00312 {
00313    // Set small display text (two lines).
00314 
00315    if (!(fDisplay1.CompareTo(text1)) &&
00316        !(fDisplay2.CompareTo(text2)))
00317       return;
00318    fDisplay1 = text1;
00319    fDisplay2 = text2;
00320    DrawText();
00321    DrawNeedle();
00322 }
00323 
00324 //______________________________________________________________________________
00325 void TGSpeedo::SetLabelText(const char *text1, const char *text2)
00326 {
00327    // Set main label text (two lines).
00328 
00329    if (fImage && fImage->IsValid())
00330       delete fImage;
00331    fLabel1 = text1;
00332    fLabel2 = text2;
00333    fImage = TImage::Open(fPicName);
00334    if (!fImage || !fImage->IsValid())
00335       Error("TGSpeedo::Build", "%s not found", fPicName.Data());
00336    Build();
00337    DrawText();
00338 }
00339 
00340 //______________________________________________________________________________
00341 void TGSpeedo::SetMinMaxScale(Float_t min, Float_t max)
00342 {
00343    // Set min and max scale values.
00344 
00345    if (fImage && fImage->IsValid())
00346       delete fImage;
00347    fScaleMin = min;
00348    fScaleMax = max;
00349    fImage = TImage::Open(fPicName);
00350    if (!fImage || !fImage->IsValid())
00351       Error("TGSpeedo::Build", "%s not found", fPicName.Data());
00352    Build();
00353    DrawText();
00354 }
00355 
00356 //______________________________________________________________________________
00357 void TGSpeedo::SetScaleValue(Float_t val)
00358 {
00359    // Set actual scale (needle position) value.
00360 
00361    // avoid useless redraw
00362    if (val == fValue)
00363       return;
00364 
00365    fValue = val;
00366    if (fValue > fScaleMax)
00367       fValue = fScaleMax;
00368    else if (fValue < fScaleMin)
00369       fValue = fScaleMin;
00370 
00371    if (fThresholdActive) {
00372       if (fValue < fThreshold[0])
00373          Glow(kNoglow);
00374       if (fValue >= fThreshold[0] && fValue < fThreshold[1])
00375          Glow(fThresholdColor[0]);
00376       if (fValue >= fThreshold[1] && fValue < fThreshold[2])
00377          Glow(fThresholdColor[1]);
00378       if (fValue >= fThreshold[2])
00379          Glow(fThresholdColor[2]);
00380    }
00381    if (fValue > fPeakVal)
00382       fPeakVal = fValue;
00383 
00384    fAngle = fAngleMin + (fValue / ((fScaleMax - fScaleMin) /
00385            (fAngleMax - fAngleMin)));
00386 
00387    if (fAngle > fAngleMax)
00388       fAngle = fAngleMax;
00389    else if (fAngle < fAngleMin)
00390       fAngle = fAngleMin;
00391    DrawNeedle();
00392 }
00393 
00394 //______________________________________________________________________________
00395 void TGSpeedo::SetScaleValue(Float_t val, Int_t damping)
00396 {
00397    // Set actual scale (needle position) value.
00398 
00399    Float_t i;
00400    Float_t old_val = fValue;
00401    Float_t step, new_val = val;
00402    // avoid useless redraw
00403    if (val == fValue)
00404       return;
00405 
00406    if ((damping > 0) || (gVirtualX->InheritsFrom("TGX11")))
00407       step = 2.0;
00408    else
00409       step = 0.15;
00410 
00411    Float_t diff_angle = fAngleMax - fAngleMin;
00412    Float_t diff_scale = fScaleMax - fScaleMin;
00413    Float_t diff_ratio = diff_scale / diff_angle;
00414    Float_t old_angle  = fAngleMin + (old_val / diff_ratio);
00415    Float_t new_angle  = fAngleMin + (new_val / diff_ratio);
00416 
00417    if (new_angle > old_angle) {
00418       for (i=old_angle; i<new_angle; i+=step) {
00419          new_val = (i - fAngleMin) * diff_ratio;
00420          SetScaleValue(new_val);
00421          if (damping > 0)
00422             gSystem->Sleep(damping);
00423       }
00424    }
00425    if (new_angle < old_angle) {
00426       for (i=old_angle; i>new_angle; i-=step) {
00427          new_val = (i - fAngleMin) * diff_ratio;
00428          SetScaleValue(new_val);
00429          if (damping > 0)
00430             gSystem->Sleep(damping);
00431       }
00432    }
00433    // Last step
00434    SetScaleValue(val);
00435 }
00436 
00437 //______________________________________________________________________________
00438 void TGSpeedo::StepScale(Float_t step)
00439 {
00440    // Increment/decrement scale (needle position) of "step" value.
00441 
00442    SetScaleValue(fValue + step);
00443 }
00444 
00445 //______________________________________________________________________________
00446 void TGSpeedo::Translate(Float_t val, Float_t angle, Int_t *x, Int_t *y)
00447 {
00448    // Translate distance from center and angle to xy coordinates.
00449 
00450    Float_t xc = (Float_t)(fBase ? (fBase->GetWidth() + 1) / 2 : 96.0);
00451    Float_t yc = (Float_t)(fBase ? (fBase->GetHeight() + 1) / 2 : 96.0);
00452    *x = (Int_t)(xc + val * sin(angle * TMath::Pi() / 180) + 0.5);
00453    *y = (Int_t)(yc - val * cos(angle * TMath::Pi() / 180) + 0.5);
00454 }
00455 
00456 //______________________________________________________________________________
00457 void TGSpeedo::DrawNeedle()
00458 {
00459    // Draw needle in speedo widget.
00460 
00461    Int_t xch0, xch1, ych0, ych1;
00462    Int_t xpk0, ypk0, xpk1, ypk1;
00463    Int_t xmn0, ymn0, xmn1, ymn1;
00464    fValue = (fAngle - fAngleMin) * ((fScaleMax - fScaleMin) /
00465             (fAngleMax - fAngleMin));
00466 
00467    // compute x/y position of the needle
00468    Translate(9.0, fAngle, &xch0, &ych0);
00469    Translate(73.0, fAngle, &xch1, &ych1);
00470 
00471    // compute x/y position of the peak mark
00472    Float_t angle = fAngleMin + (fPeakVal / ((fScaleMax - fScaleMin) /
00473                   (fAngleMax - fAngleMin)));
00474    Translate(80.0, angle, &xpk0, &ypk0);
00475    Translate(67.0, angle, &xpk1, &ypk1);
00476 
00477    // compute x/y position of the peak mark
00478    angle = fAngleMin + (fMeanVal / ((fScaleMax - fScaleMin) /
00479           (fAngleMax - fAngleMin)));
00480    Translate(80.0, angle, &xmn0, &ymn0);
00481    Translate(70.0, angle, &xmn1, &ymn1);
00482 
00483    if (fImage2 && fImage2->IsValid()) {
00484       // First clone original image.
00485       TImage *img = (TImage*)fImage2->Clone("img");
00486       if (fPeakMark) {
00487          img->DrawLine(xpk0, ypk0, xpk1, ypk1, "#00ff00", 3);
00488          img->DrawLine(xpk0, ypk0, xpk1, ypk1, "#ffffff", 1);
00489       }
00490       if (fMeanMark) {
00491          img->DrawLine(xmn0, ymn0, xmn1, ymn1, "#ffff00", 3);
00492          img->DrawLine(xmn0, ymn0, xmn1, ymn1, "#ff0000", 1);
00493       }
00494       // draw line (used to render the needle) directly on the image
00495       img->DrawLine(xch0, ych0, xch1, ych1, "#ff0000", 2);
00496       // finally paint image to the widget
00497       img->PaintImage(fId, 0, 0, 0, 0, 0, 0, "opaque");
00498       // and finally, to avoid memory leaks
00499       delete img;
00500    }
00501    gVirtualX->Update();
00502 }
00503 
00504 //______________________________________________________________________________
00505 void TGSpeedo::DrawText()
00506 {
00507    // Draw text in speedo widget.
00508 
00509    char sval[80];
00510    char dsval[80];
00511    Int_t strSize;
00512 
00513    // center of the image
00514    Float_t xc = fBase ? (fBase->GetWidth() + 1) / 2 : 96.0;
00515    Float_t yc = fBase ? (fBase->GetHeight() + 1) / 2 : 96.0;
00516 
00517    if (fImage && fImage->IsValid()) {
00518       // First clone original image.
00519       if (fImage2 && fImage2->IsValid())
00520          delete fImage2;
00521       fImage2 = (TImage*)fImage->Clone("fImage2");
00522       TString fp = gEnv->GetValue("Root.TTFontPath", "");
00523       TString ar = fp + "/arialbd.ttf";
00524       // format counter value
00525       Int_t nexe = 0;
00526       Int_t ww = fCounter;
00527       if (fCounter >= 10000) {
00528          while (1) {
00529             nexe++;
00530             ww /= 10;
00531             if (nexe%3 == 0 && ww < 10000) break;
00532          }
00533          fImage2->DrawText((Int_t)xc - 9, (Int_t)yc + 72, "x10", 10, "#ffffff", ar);
00534          snprintf(sval, 80, "%d", nexe);
00535          fImage2->DrawText((Int_t)xc + 9, (Int_t)yc + 69, sval, 8, "#ffffff", ar);
00536       }
00537       snprintf(sval, 80, "%04d", (int)ww);
00538       snprintf(dsval, 80, "%c %c %c %c", sval[0], sval[1], sval[2], sval[3]);
00539       // draw text in the counter
00540       if (gVirtualX->InheritsFrom("TGX11")) {
00541          // as there is a small difference between Windows and Linux...
00542          fImage2->DrawText((Int_t)xc - 18, (Int_t)yc + 55, dsval, 12, "#ffffff", ar);
00543       }
00544       else {
00545          fImage2->DrawText((Int_t)xc - 16, (Int_t)yc + 56, dsval, 12, "#ffffff", ar);
00546       }
00547       // compute the size of the string to draw in the small display box
00548       // first line
00549       strSize = gVirtualX->TextWidth(fTextFS, fDisplay1.Data(), fDisplay1.Length()) - 6;
00550       // draw text directly on the imaget_t)yc + 29, fDispla
00551       fImage2->DrawText((Int_t)xc - (strSize / 2), (Int_t)yc + 29, fDisplay1.Data(), 8, "#ffffff", ar);
00552       // second line
00553       strSize = gVirtualX->TextWidth(fTextFS, fDisplay2.Data(), fDisplay2.Length()) - 6;
00554       fImage2->DrawText((Int_t)xc - (strSize / 2), (Int_t)yc + 38, fDisplay2.Data(), 8, "#ffffff", ar);
00555    }
00556 }
00557 
00558 //______________________________________________________________________________
00559 void TGSpeedo::DoRedraw()
00560 {
00561    // Redraw speedo widget.
00562 
00563    char sval[80];
00564    char dsval[80];
00565    Int_t strSize;
00566    Int_t xch0, xch1, ych0, ych1;
00567    Int_t xpk0, ypk0, xpk1, ypk1;
00568    Int_t xmn0, ymn0, xmn1, ymn1;
00569    static Bool_t first = kTRUE;
00570    if (first) {
00571       TGFrame::DoRedraw();
00572       first = kFALSE;
00573    }
00574    fValue = (fAngle - fAngleMin) * ((fScaleMax - fScaleMin) /
00575             (fAngleMax - fAngleMin));
00576 
00577    // center of the image
00578    Float_t xc = fBase ? (fBase->GetWidth() + 1) / 2 : 96.0;
00579    Float_t yc = fBase ? (fBase->GetHeight() + 1) / 2 : 96.0;
00580 
00581    // compute x/y position of the needle
00582    Translate(9.0, fAngle, &xch0, &ych0);
00583    Translate(73.0, fAngle, &xch1, &ych1);
00584 
00585    // compute x/y position of the peak mark
00586    Float_t angle = fAngleMin + (fPeakVal / ((fScaleMax - fScaleMin) /
00587                   (fAngleMax - fAngleMin)));
00588    Translate(80.0, angle, &xpk0, &ypk0);
00589    Translate(67.0, angle, &xpk1, &ypk1);
00590 
00591    // compute x/y position of the peak mark
00592    angle = fAngleMin + (fMeanVal / ((fScaleMax - fScaleMin) /
00593           (fAngleMax - fAngleMin)));
00594    Translate(80.0, angle, &xmn0, &ymn0);
00595    Translate(70.0, angle, &xmn1, &ymn1);
00596    
00597    if (fImage && fImage->IsValid()) {
00598       // First clone original image.
00599       if (fImage2 && fImage2->IsValid())
00600          delete fImage2;
00601       fImage2 = (TImage*)fImage->Clone("fImage2");
00602       TString fp = gEnv->GetValue("Root.TTFontPath", "");
00603       TString ar = fp + "/arialbd.ttf";
00604       // format counter value
00605       Int_t nexe = 0;
00606       Int_t ww = fCounter;
00607       if (fCounter >= 10000) {
00608          while (1) {
00609             nexe++;
00610             ww /= 10;
00611             if (nexe%3 == 0 && ww < 10000) break;
00612          }
00613          fImage2->DrawText((Int_t)xc - 9, (Int_t)yc + 72, "x10", 10, "#ffffff", ar);
00614          snprintf(sval, 80, "%d", nexe);
00615          fImage2->DrawText((Int_t)xc + 9, (Int_t)yc + 69, sval, 8, "#ffffff", ar);
00616       }
00617       snprintf(sval, 80, "%04d", (int)ww);
00618       snprintf(dsval, 80, "%c %c %c %c", sval[0], sval[1], sval[2], sval[3]);
00619       // draw text in the counter
00620       if (gVirtualX->InheritsFrom("TGX11")) {
00621          // as there is a small difference between Windows and Linux...
00622          fImage2->DrawText((Int_t)xc - 18, (Int_t)yc + 55, dsval, 12, "#ffffff", ar);
00623       }
00624       else {
00625          fImage2->DrawText((Int_t)xc - 16, (Int_t)yc + 56, dsval, 12, "#ffffff", ar);
00626       }
00627       // compute the size of the string to draw in the small display box
00628       // first line
00629       strSize = gVirtualX->TextWidth(fTextFS, fDisplay1.Data(), fDisplay1.Length()) - 6;
00630       // draw text directly on the imaget_t)yc + 29, fDispla
00631       fImage2->DrawText((Int_t)xc - (strSize / 2), (Int_t)yc + 29, fDisplay1.Data(), 8, "#ffffff", ar);
00632       // second line
00633       strSize = gVirtualX->TextWidth(fTextFS, fDisplay2.Data(), fDisplay2.Length()) - 6;
00634       fImage2->DrawText((Int_t)xc - (strSize / 2), (Int_t)yc + 38, fDisplay2.Data(), 8, "#ffffff", ar);
00635       TImage *img = (TImage*)fImage2->Clone("img");
00636       if (fPeakMark) {
00637          img->DrawLine(xpk0, ypk0, xpk1, ypk1, "#00ff00", 3);
00638          img->DrawLine(xpk0, ypk0, xpk1, ypk1, "#ffffff", 1);
00639       }
00640       if (fMeanMark) {
00641          img->DrawLine(xmn0, ymn0, xmn1, ymn1, "#ffff00", 3);
00642          img->DrawLine(xmn0, ymn0, xmn1, ymn1, "#ff0000", 1);
00643       }
00644       // draw line (used to render the needle) directly on the image
00645       img->DrawLine(xch0, ych0, xch1, ych1, "#ff0000", 2);
00646       // finally paint image to the widget
00647       img->PaintImage(fId, 0, 0, 0, 0, 0, 0, "opaque");
00648       // and finally, to avoid memory leaks
00649       delete img;
00650    }
00651 }

Generated on Tue Jul 5 14:22:03 2011 for ROOT_528-00b_version by  doxygen 1.5.1