ROOT logo
// @(#)root/gl:$Id$
// Author:  Timur Pocheptsov / Richard Maunder

/*************************************************************************
 * Copyright (C) 1995-2004, Rene Brun and Fons Rademakers.               *
 * All rights reserved.                                                  *
 *                                                                       *
 * For the licensing terms see $ROOTSYS/LICENSE.                         *
 * For the list of contributors see $ROOTSYS/README/CREDITS.             *
 *************************************************************************/

#include <memory>

#include "TRootHelpDialog.h"
#include "TPluginManager.h"
#include "TApplication.h"
#include "TGClient.h"
#include "TGCanvas.h"
#include "HelpText.h"
#include "GuiTypes.h"
#include "TG3DLine.h"
#include "TSystem.h"
#include "TGFrame.h"
#include "TGLabel.h"
#include "TGMenu.h"
#include "TGButton.h"
#include "TGSplitter.h"
#include "TColor.h"

#include "TVirtualPad.h"
#include "TGedEditor.h"
#include "TRootEmbeddedCanvas.h"
#include "TString.h"
#include "TGFileDialog.h"

#include "TGLOutput.h"
#include "TGLFormat.h"

#include "TGLLogicalShape.h"
#include "TGLPhysicalShape.h"
#include "TGLPShapeObj.h"
#include "TGLClip.h"
#include "TROOT.h"

#ifdef WIN32
#include "TWin32SplashThread.h"
#endif

#include "TGLPhysicalShape.h"
#include "TGLWidget.h"
#include "TGLSAViewer.h"
#include "TGLSAFrame.h"
#include "TGLOutput.h"
#include "TGLEventHandler.h"


const char * TGLSAViewer::fgHelpText1 = "\
DIRECT SCENE INTERACTIONS\n\n\
   Press:\n\
   \tw          --- wireframe mode\n\
   \te          --- switch between dark / light color-set\n\
   \tr          --- filled polygons mode\n\
   \tt          --- outline mode\n\
   \tj          --- ZOOM in\n\
   \tk          --- ZOOM out\n\
   \ta          --- switch on/off arc-ball camera rotation control\n\
   \tArrow Keys --- PAN (TRUCK) across scene\n\
   \tHome       --- reset current camera\n\
   \tCtrl-Home  --- switch external/automatic camera center\n\
\n\
   LEFT mouse button -- ROTATE (ORBIT) the scene by holding the mouse button and moving\n\
   the mouse (perspective camera, needs to be enabled in menu for orthograpic cameras).\n\
   By default, the scene will be rotated about its center. To select arbitrary center\n\
   bring up the viewer-editor (e.g., shift-click into empty background) and use\n\
   'Camera center' controls in the 'Guides' tab.\n\
\n\
   MIDDLE mouse button or arrow keys --  PAN (TRUCK) the camera.\n\
\n\
   RIGHT mouse button action depends on camera type:\n\
     orthographic -- zoom,\n\
     perspective  -- move camera forwards / backwards\n\
\n\
   By pressing Ctrl and Shift keys the mouse precision can be changed:\n\
     Shift      -- 10 times less precise\n\
     Ctrl       -- 10 times more precise\n\
     Ctrl Shift -- 100 times more precise\n\
\n\
   Mouse wheel action depends on camera type:\n\
     orthographic -- zoom,\n\
     perspective  -- change field-of-view (focal length)\n\
\n\
   To invert direction of mouse and key actions from scene-centric\n\
   to viewer-centric, set in your .rootrc file:\n\
      OpenGL.EventHandler.ViewerCentricControls: 1\n\
\n\
   Double clik will show GUI editor of the viewer (if assigned).\n\
\n\
   RESET the camera via the button in viewer-editor or Home key.\n\
\n\
   SELECT a shape with Shift+Left mouse button click.\n\
\n\
   SELECT the viewer with Shift+Left mouse button click on a free space.\n\
\n\
   MOVE a selected shape using Shift+Mid mouse drag.\n\
\n\
   Invoke the CONTEXT menu with Shift+Right mouse click.\n\n"
   "Secondary selection and direct render object interaction is initiated\n\
   by Alt+Left mouse click (Mod1, actually). Only few classes support this option.\n\
   When 'Alt' is taken by window manager, try Alt-Ctrl-Left.\n\
\n\
CAMERA\n\
\n\
   The \"Camera\" menu is used to select the different projections from \n\
   the 3D world onto the 2D viewport. There are three perspective cameras:\n\
\n\
   \tPerspective (Floor XOZ)\n\
   \tPerspective (Floor YOZ)\n\
   \tPerspective (Floor XOY)\n\
\n\
   In each case the floor plane (defined by two axes) is kept level.\n\
\n\
   There are also three orthographic cameras:\n\
\n\
   \tOrthographic (XOY)\n\
   \tOrthographic (XOZ)\n\
   \tOrthographic (ZOY)\n\
\n\
   In each case the first axis is placed horizontal, the second vertical e.g.\n\
   XOY means X horizontal, Y vertical.\n\n";

const char * TGLSAViewer::fgHelpText2 = "\
SHAPES COLOR AND MATERIAL\n\
\n\
   The selected shape's color can be modified in the Shapes-Color tabs.\n\
   Shape's color is specified by the percentage of red, green, blue light\n\
   it reflects. A surface can reflect DIFFUSE, AMBIENT and SPECULAR light.\n\
   A surface can also emit light. The EMISSIVE parameter allows to define it.\n\
   The surface SHININESS can also be modified.\n\
\n\
SHAPES GEOMETRY\n\
\n\
   The selected shape's location and geometry can be modified in the Shapes-Geom\n\
   tabs by entering desired values in respective number entry controls.\n\
\n\
SCENE CLIPPING\n\
\n\
   In the Scene-Clipping tabs select a 'Clip Type': None, Plane, Box\n\
\n\
   For 'Plane' and 'Box' the lower pane shows the relevant parameters:\n\
\n\
\tPlane: Equation coefficients of form aX + bY + cZ + d = 0\n\
\tBox: Center X/Y/Z and Length X/Y/Z\n\n"
   "For Box checking the 'Show / Edit' checkbox shows the clip box (in light blue)\n\
   in viewer. It also attaches the current manipulator to the box - enabling\n\
   direct editing in viewer.\n\
\n\
MANIPULATORS\n\
\n\
   A widget attached to the selected object - allowing direct manipulation\n\
   of the object with respect to its local axes.\n\
\n\
   There are three modes, toggled with keys while manipulator is active, that is,\n\
   mouse pointer is above it (switches color to yellow):\n\
   \tMode\t\tWidget Component Style\t\tKey\n\
   \t----\t\t----------------------\t\t---\n\
   \tTranslation\tLocal axes with arrows\t\tv\n\
   \tScale\t\tLocal axes with boxes\t\tx\n\
   \tRotate\t\tLocal axes rings\t\tc\n\
\n\
   Each widget has three axis components - red (X), green (Y) and blue (Z).\n\
   The component turns yellow, indicating an active state, when the mouse is moved\n\
   over it. Left click and drag on the active component to adjust the objects\n\
   translation, scale or rotation.\n\
   Some objects do not support all manipulations (e.g. clipping planes cannot be \n\
   scaled). If a manipulation is not permitted the component it drawn in grey and \n\
   cannot be selected/dragged.\n";


//==============================================================================
// TGLSAViewer
//==============================================================================

//______________________________________________________________________________
//
// The top level standalone GL-viewer - created via plugin manager.


ClassImp(TGLSAViewer);

Long_t TGLSAViewer::fgMenuHidingTimeout = 400;

const Int_t TGLSAViewer::fgInitX = 0;
const Int_t TGLSAViewer::fgInitY = 0;
const Int_t TGLSAViewer::fgInitW = 780;
const Int_t TGLSAViewer::fgInitH = 670;

// A lot of raw pointers/naked new-expressions - good way to discredit C++ (or C++ programmer
// ROOT has system to cleanup - I'll try to use it

const char *gGLSaveAsTypes[] = {"Encapsulated PostScript", "*.eps",
                                "PDF",                     "*.pdf",
                                "GIF",                     "*.gif",
                                "Animated GIF",            "*.gif+",
                                "JPEG",                    "*.jpg",
                                "PNG",                     "*.png",
                                0, 0};

//______________________________________________________________________________
TGLSAViewer::TGLSAViewer(TVirtualPad *pad, TGLFormat* format) :
   TGLViewer(pad, fgInitX, fgInitY, fgInitW, fgInitH),
   fFrame(0),
   fFormat(format),
   fFileMenu(0),
   fFileSaveMenu(0),
   fCameraMenu(0),
   fHelpMenu(0),
   fLeftVerticalFrame(0),
   fRightVerticalFrame(0),
   fDirName("."),
   fTypeIdx(0),
   fOverwrite(kFALSE),
   fMenuBar(0),
   fMenuBut(0),
   fHideMenuBar(kFALSE),
   fMenuHidingTimer(0),
   fMenuHidingShowMenu(kTRUE),
   fDeleteMenuBar(kFALSE)
{
   // Construct a standalone viewer, bound to supplied 'pad'.

   fFrame = new TGLSAFrame(*this);

   CreateMenus();
   CreateFrames();

   fFrame->SetWindowName("ROOT's GL viewer");
   fFrame->SetClassHints("GLViewer", "GLViewer");
   fFrame->SetMWMHints(kMWMDecorAll, kMWMFuncAll, kMWMInputModeless);
   fFrame->MapSubwindows();
   fFrame->HideFrame(fMenuBut);

   fFrame->Resize(fFrame->GetDefaultSize());
   fFrame->MoveResize(fgInitX, fgInitY, fgInitW, fgInitH);
   fFrame->SetWMPosition(fgInitX, fgInitY);

   // set recursive cleanup, but exclude fGedEditor
   // destructor of fGedEditor has own way of handling child nodes
   TObject* fe = fLeftVerticalFrame->GetList()->First();
   fLeftVerticalFrame->GetList()->Remove(fe);
   fFrame->SetCleanup(kDeepCleanup);
   fLeftVerticalFrame->GetList()->AddFirst(fe);

   Show();
}

//______________________________________________________________________________
TGLSAViewer::TGLSAViewer(const TGWindow *parent, TVirtualPad *pad, TGedEditor *ged,
                         TGLFormat* format) :
   TGLViewer(pad, fgInitX, fgInitY, fgInitW, fgInitH),
   fFrame(0),
   fFormat(format),
   fFileMenu(0),
   fCameraMenu(0),
   fHelpMenu(0),
   fLeftVerticalFrame(0),
   fRightVerticalFrame(0),
   fTypeIdx(0),
   fMenuBar(0),
   fMenuBut(0),
   fHideMenuBar(kFALSE),
   fMenuHidingTimer(0),
   fMenuHidingShowMenu(kTRUE),
   fDeleteMenuBar(kFALSE)
{
   // Construct an embedded standalone viewer, bound to supplied 'pad'.
   // If format is passed, it gets adopted by the viewer as it might
   // need to be reused several times when recreating the GL-widget.
   //
   // Modified version of the previous constructor for embedding the
   // viewer into another frame (parent).

   fGedEditor = ged;
   fFrame = new TGLSAFrame(parent, *this);

   CreateMenus();
   CreateFrames();

   fFrame->MapSubwindows();
   fFrame->HideFrame(fMenuBut);
   fFrame->Resize(fFrame->GetDefaultSize());
   fFrame->Resize(fgInitW, fgInitH);

   // set recursive cleanup, but exclude fGedEditor
   // destructor of fGedEditor has own way of handling child nodes
   if (fLeftVerticalFrame)
   {
      TObject* fe = fLeftVerticalFrame->GetList()->First();
      fLeftVerticalFrame->GetList()->Remove(fe);
      fFrame->SetCleanup(kDeepCleanup);
      fLeftVerticalFrame->GetList()->AddFirst(fe);
   }

   Show();
}

//______________________________________________________________________________
TGLSAViewer::~TGLSAViewer()
{
   // Destroy standalone viewer object.

   fGedEditor->DisconnectFromCanvas();

   DisableMenuBarHiding();

   delete fHelpMenu;
   delete fCameraMenu;
   delete fFileSaveMenu;
   delete fFileMenu;
   if(fDeleteMenuBar) {
      delete fMenuBar;
   }
   delete fFormat;
   delete fFrame;
   fGLWidget = 0;
}

//______________________________________________________________________________
TGCompositeFrame* TGLSAViewer::GetFrame() const
{
   // Return the main-frame.

   return fFrame;
}

//______________________________________________________________________________
void TGLSAViewer::CreateGLWidget()
{
   // Create a GLwidget, it is an error if it is already created.
   // This is needed for frame-swapping on mac.

   if (fGLWidget) {
      Error("CreateGLWidget", "Widget already exists.");
      return;
   }

   if (fFormat == 0)
      fFormat = new TGLFormat;

   fGLWidget = TGLWidget::Create(*fFormat, fRightVerticalFrame, kTRUE, kTRUE, 0, 10, 10);
   fGLWidget->SetEventHandler(fEventHandler);

   fRightVerticalFrame->AddFrame(fGLWidget, new TGLayoutHints(kLHintsExpandX | kLHintsExpandY));
   fFrame->Layout();

   fGLWidget->MapWindow();
}

//______________________________________________________________________________
void TGLSAViewer::DestroyGLWidget()
{
   // Destroy the GLwidget, it is an error if it does not exist.
   // This is needed for frame-swapping on mac.

   if (fGLWidget == 0) {
      Error("DestroyGLWidget", "Widget does not exist.");
      return;
   }

   fGLWidget->UnmapWindow();
   fGLWidget->SetEventHandler(0);

   fRightVerticalFrame->RemoveFrame(fGLWidget);
   fGLWidget->DeleteWindow();
   fGLWidget = 0;
}

//______________________________________________________________________________
void TGLSAViewer::CreateMenus()
{
   //File/Camera/Help menus.

   fFileMenu = new TGPopupMenu(fFrame->GetClient()->GetDefaultRoot());
   fFileMenu->AddEntry("&Hide Menus", kGLHideMenus);
   fFileMenu->AddEntry("&Edit Object", kGLEditObject);
   fFileMenu->AddSeparator();
   fFileMenu->AddEntry("&Close Viewer", kGLCloseViewer);
   fFileMenu->AddSeparator();
   fFileSaveMenu = new TGPopupMenu(fFrame->GetClient()->GetDefaultRoot());
   fFileSaveMenu->AddEntry("viewer.&eps", kGLSaveEPS);
   fFileSaveMenu->AddEntry("viewer.&pdf", kGLSavePDF);
   fFileSaveMenu->AddEntry("viewer.&gif", kGLSaveGIF);
   fFileSaveMenu->AddEntry("viewer.g&if+", kGLSaveAnimGIF);
   fFileSaveMenu->AddEntry("viewer.&jpg", kGLSaveJPG);
   fFileSaveMenu->AddEntry("viewer.p&ng", kGLSavePNG);
   fFileMenu->AddPopup("&Save", fFileSaveMenu);
   fFileMenu->AddEntry("Save &As...", kGLSaveAS);
   fFileMenu->AddSeparator();
   fFileMenu->AddEntry("&Quit ROOT", kGLQuitROOT);
   fFileMenu->Associate(fFrame);

   fCameraMenu = new TGPopupMenu(fFrame->GetClient()->GetDefaultRoot());
   fCameraMenu->AddEntry("Perspective (Floor XOZ)", kGLPerspXOZ);
   fCameraMenu->AddEntry("Perspective (Floor YOZ)", kGLPerspYOZ);
   fCameraMenu->AddEntry("Perspective (Floor XOY)", kGLPerspXOY);
   fCameraMenu->AddEntry("Orthographic (XOY)", kGLXOY);
   fCameraMenu->AddEntry("Orthographic (XOZ)", kGLXOZ);
   fCameraMenu->AddEntry("Orthographic (ZOY)", kGLZOY);
   fCameraMenu->AddEntry("Orthographic (XnOY)", kGLXnOY);
   fCameraMenu->AddEntry("Orthographic (XnOZ)", kGLXnOZ);
   fCameraMenu->AddEntry("Orthographic (ZnOY)", kGLZnOY);
   fCameraMenu->AddSeparator();
   fCameraMenu->AddEntry("Ortho allow rotate", kGLOrthoRotate);
   fCameraMenu->AddEntry("Ortho allow dolly",  kGLOrthoDolly);
   fCameraMenu->Associate(fFrame);

   fHelpMenu = new TGPopupMenu(fFrame->GetClient()->GetDefaultRoot());
   fHelpMenu->AddEntry("Help on GL Viewer...", kGLHelpViewer);
   fHelpMenu->AddSeparator();
   fHelpMenu->AddEntry("&About ROOT...", kGLHelpAbout);
   fHelpMenu->Associate(fFrame);

   // Create menubar
   fMenuBar = new TGMenuBar(fFrame);
   fMenuBar->AddPopup("&File", fFileMenu, new TGLayoutHints(kLHintsTop | kLHintsLeft, 0, 4, 0, 0));
   fMenuBar->AddPopup("&Camera", fCameraMenu, new TGLayoutHints(kLHintsTop | kLHintsLeft, 0, 4, 0, 0));
   fMenuBar->AddPopup("&Help",   fHelpMenu,   new TGLayoutHints(kLHintsTop | kLHintsRight));
   fFrame->AddFrame(fMenuBar, new TGLayoutHints(kLHintsTop | kLHintsLeft | kLHintsExpandX, 0, 0, 1, 1));
   gVirtualX->SelectInput(fMenuBar->GetId(),
                          kKeyPressMask | kExposureMask | kPointerMotionMask
                          | kStructureNotifyMask | kFocusChangeMask
                          | kEnterWindowMask | kLeaveWindowMask);

   fMenuBut = new TGButton(fFrame);
   fMenuBut->ChangeOptions(kRaisedFrame | kFixedHeight);
   fMenuBut->Resize(20, 4);
   fMenuBut->SetBackgroundColor(0x80A0C0);
   fFrame->AddFrame(fMenuBut, new TGLayoutHints(kLHintsNormal | kLHintsExpandX, 0, 0, 1, 1));
}

//______________________________________________________________________________
void TGLSAViewer::CreateFrames()
{
   // Internal frames creation.

   TGCompositeFrame* compositeFrame = fFrame;
   if (fGedEditor == 0)
   {
      compositeFrame = new TGCompositeFrame(fFrame, 100, 100, kHorizontalFrame | kRaisedFrame);
      fFrame->AddFrame(compositeFrame, new TGLayoutHints(kLHintsExpandX | kLHintsExpandY));

      fLeftVerticalFrame = new TGVerticalFrame(compositeFrame, 195, 10, kFixedWidth);
      compositeFrame->AddFrame(fLeftVerticalFrame, new TGLayoutHints(kLHintsLeft | kLHintsExpandY, 2, 2, 2, 2));

      const TGWindow* cw =  fFrame->GetClient()->GetRoot();
      fFrame->GetClient()->SetRoot(fLeftVerticalFrame);

      fGedEditor = new TGedEditor();
      fGedEditor->GetTGCanvas()->ChangeOptions(0);
      fLeftVerticalFrame->RemoveFrame(fGedEditor);
      fLeftVerticalFrame->AddFrame(fGedEditor, new TGLayoutHints(kLHintsTop | kLHintsLeft | kLHintsExpandX | kLHintsExpandY, 0, 0, 2, 2));
      fLeftVerticalFrame->GetClient()->SetRoot((TGWindow*)cw);
      fLeftVerticalFrame->MapSubwindows();

      TGVSplitter *splitter = new TGVSplitter(compositeFrame);
      splitter->SetFrame(fLeftVerticalFrame, kTRUE);
      compositeFrame->AddFrame(splitter, new TGLayoutHints(kLHintsLeft | kLHintsExpandY, 0,1,2,2) );
   }

   // SunkenFrame introduces 1-pixel offset - in TGFrame.cxx:163
   //
   // TGVerticalFrame *rightVerticalFrame = new TGVerticalFrame(compositeFrame, 10, 10, kSunkenFrame);
   // compositeFrame->AddFrame(rightVerticalFrame, new TGLayoutHints(kLHintsRight | kLHintsExpandX | kLHintsExpandY,0,2,2,2));
   fRightVerticalFrame = new TGVerticalFrame(compositeFrame, 10, 10);
   compositeFrame->AddFrame(fRightVerticalFrame, new TGLayoutHints(kLHintsRight | kLHintsExpandX | kLHintsExpandY));

   fEventHandler = new TGLEventHandler(0, this);
   CreateGLWidget();
}

//______________________________________________________________________________
void TGLSAViewer::SelectionChanged()
{
   // Update GUI components for embedded viewer selection change.
   // Override from TGLViewer.

   TGLPhysicalShape *selected = const_cast<TGLPhysicalShape*>(GetSelected());

   if (selected) {
      fPShapeWrap->fPShape = selected;
      if (fFileMenu->IsEntryChecked(kGLEditObject))
         fGedEditor->SetModel(fPad, selected->GetLogical()->GetExternal(), kButton1Down);
      else
         fGedEditor->SetModel(fPad, fPShapeWrap, kButton1Down);
   } else {
      fPShapeWrap->fPShape = 0;
      fGedEditor->SetModel(fPad, this, kButton1Down);
   }
}

//______________________________________________________________________________
void TGLSAViewer::Show()
{
   // Show the viewer
   fFrame->MapRaised();
   fGedEditor->SetModel(fPad, this, kButton1Down);
   RequestDraw();
}

//______________________________________________________________________________
void TGLSAViewer::Close()
{
   // Close the viewer - destructed.

   // Commit suicide when contained GUI is closed.
   delete this;
}

//______________________________________________________________________________
void TGLSAViewer::DeleteMenuBar()
{
   // Delete the menu bar.
   fDeleteMenuBar=kTRUE;
}

//______________________________________________________________________________
void TGLSAViewer::DisableCloseMenuEntries()
{
   // Deactivate menu entries for closing the GL window and exiting ROOT.

   fFileMenu->DeleteEntry(kGLCloseViewer);
   fFileMenu->DeleteEntry(kGLQuitROOT);
}

//______________________________________________________________________________
void TGLSAViewer::EnableMenuBarHiding()
{
   // Enable hiding of menu bar.

   if (fHideMenuBar)
      return;

   fHideMenuBar = kTRUE;

   fMenuBar->Connect("ProcessedEvent(Event_t*)", "TGLSAViewer", this, "HandleMenuBarHiding(Event_t*)");
   fMenuBut->Connect("ProcessedEvent(Event_t*)", "TGLSAViewer", this, "HandleMenuBarHiding(Event_t*)");

   fFrame->HideFrame(fMenuBar);
   fFrame->ShowFrame(fMenuBut);
   fFrame->Layout();

   fMenuHidingTimer = new TTimer;
   fMenuHidingTimer->Connect("Timeout()", "TGLSAViewer", this, "MenuHidingTimeout()");

   fFileMenu->CheckEntry(kGLHideMenus);
}

//______________________________________________________________________________
void TGLSAViewer::DisableMenuBarHiding()
{
   // Disable hiding of menu bar.

   if (!fHideMenuBar)
      return;

   fHideMenuBar = kFALSE;

   fMenuBar->Disconnect("ProcessedEvent(Event_t*)", this, "HandleMenuBarHiding(Event_t*)");
   fMenuBut->Disconnect("ProcessedEvent(Event_t*)", this, "HandleMenuBarHiding(Event_t*)");

   fFrame->ShowFrame(fMenuBar);
   fFrame->HideFrame(fMenuBut);
   fFrame->Layout();

   fMenuHidingTimer->TurnOff();
   delete fMenuHidingTimer;
   fMenuHidingTimer = 0;

   fFileMenu->UnCheckEntry(kGLHideMenus);
}

//______________________________________________________________________________
void TGLSAViewer::HandleMenuBarHiding(Event_t* ev)
{
   // Maybe switch menu-bar / menu-button.

   TGFrame *f = (TGFrame*) gTQSender;

   if (f == fMenuBut)
   {
      if (ev->fType == kEnterNotify)
         ResetMenuHidingTimer(kTRUE);
      else
         fMenuHidingTimer->TurnOff();
   }
   else if (f == fMenuBar)
   {
      if (ev->fType == kLeaveNotify &&
          (ev->fX < 0 || ev->fX >= (Int_t) f->GetWidth() ||
           ev->fY < 0 || ev->fY >= (Int_t) f->GetHeight()))
      {
         if (fMenuBar->GetCurrent() == 0)
            ResetMenuHidingTimer(kFALSE);
         else
            fMenuBar->GetCurrent()->Connect("ProcessedEvent(Event_t*)", "TGLSAViewer", this, "HandleMenuBarHiding(Event_t*)");
      }
      else
      {
         fMenuHidingTimer->TurnOff();
      }
   }
   else
   {
      f->Disconnect("ProcessedEvent(Event_t*)", this);
      ResetMenuHidingTimer(kFALSE);
   }
}

//______________________________________________________________________________
void TGLSAViewer::ResetMenuHidingTimer(Bool_t show_menu)
{
   // Reset the timer for menu-bar hiding.

   // This happens, mysteriously.
   if (fMenuHidingTimer == 0)
      return;

   fMenuHidingTimer->TurnOff();

   fMenuHidingShowMenu = show_menu;

   fMenuHidingTimer->SetTime(fgMenuHidingTimeout);
   fMenuHidingTimer->Reset();
   fMenuHidingTimer->TurnOn();
}

//______________________________________________________________________________
void TGLSAViewer::MenuHidingTimeout()
{
   // Action for menu-hiding timeout.

   fMenuHidingTimer->TurnOff();
   if (fMenuHidingShowMenu) {
      fFrame->HideFrame(fMenuBut);
      fFrame->ShowFrame(fMenuBar);
   } else {
      fFrame->HideFrame(fMenuBar);
      fFrame->ShowFrame(fMenuBut);
   }
   fFrame->Layout();
}

//______________________________________________________________________________
void TGLSAViewer::SetMenuHidingTimeout(Long_t timeout)
{
   // Set global timeout for menu-hiding in mili-seconds.
   // Static function.

   fgMenuHidingTimeout = timeout;
}

//______________________________________________________________________________
Bool_t TGLSAViewer::ProcessFrameMessage(Long_t msg, Long_t parm1, Long_t)
{
   // Process GUI message capture by the main GUI frame (TGLSAFrame).

   switch (GET_MSG(msg)) {
   case kC_COMMAND:
      switch (GET_SUBMSG(msg)) {
      case kCM_BUTTON:
      case kCM_MENU:
         switch (parm1) {
         case kGLHelpAbout: {
#ifdef R__UNIX
            TString rootx;
#ifdef ROOTBINDIR
            rootx = ROOTBINDIR;
#else
            rootx = gSystem->Getenv("ROOTSYS");
            if (!rootx.IsNull()) rootx += "/bin";
#endif
            rootx += "/root -a &";
            gSystem->Exec(rootx);
#else
#ifdef WIN32
            new TWin32SplashThread(kTRUE);
#else
            char str[32];
            snprintf(str,32, "About ROOT %s...", gROOT->GetVersion());
            hd = new TRootHelpDialog(this, str, 600, 400);
            hd->SetText(gHelpAbout);
            hd->Popup();
#endif
#endif
            break;
         }
         case kGLHelpViewer: {
            TRootHelpDialog * hd = new TRootHelpDialog(fFrame, "Help on GL Viewer...", 660, 400);
            hd->AddText(fgHelpText1);
            hd->AddText(fgHelpText2);
            hd->Popup();
            break;
         }
         case kGLPerspYOZ:
            SetCurrentCamera(TGLViewer::kCameraPerspYOZ);
            break;
         case kGLPerspXOZ:
            SetCurrentCamera(TGLViewer::kCameraPerspXOZ);
            break;
         case kGLPerspXOY:
            SetCurrentCamera(TGLViewer::kCameraPerspXOY);
            break;
         case kGLXOY:
            SetCurrentCamera(TGLViewer::kCameraOrthoXOY);
            break;
         case kGLXOZ:
            SetCurrentCamera(TGLViewer::kCameraOrthoXOZ);
            break;
         case kGLZOY:
            SetCurrentCamera(TGLViewer::kCameraOrthoZOY);
            break;
         case kGLXnOY:
            SetCurrentCamera(TGLViewer::kCameraOrthoXnOY);
            break;
         case kGLXnOZ:
            SetCurrentCamera(TGLViewer::kCameraOrthoXnOZ);
            break;
         case kGLZnOY:
            SetCurrentCamera(TGLViewer::kCameraOrthoZnOY);
            break;
         case kGLOrthoRotate:
            ToggleOrthoRotate();
            break;
         case kGLOrthoDolly:
            ToggleOrthoDolly();
            break;
         case kGLSaveEPS:
            SavePicture("viewer.eps");
            break;
         case kGLSavePDF:
            SavePicture("viewer.pdf");
            break;
         case kGLSaveGIF:
            SavePicture("viewer.gif");
            break;
         case kGLSaveAnimGIF:
            SavePicture("viewer.gif+");
            break;
         case kGLSaveJPG:
            SavePicture("viewer.jpg");
            break;
         case kGLSavePNG:
            SavePicture("viewer.png");
            break;
         case kGLSaveAS:
            {
               TGFileInfo fi;
               fi.fFileTypes   = gGLSaveAsTypes;
               fi.fIniDir      = StrDup(fDirName);
               fi.fFileTypeIdx = fTypeIdx;
               fi.fOverwrite   = fOverwrite;
               new TGFileDialog(gClient->GetDefaultRoot(), fFrame, kFDSave, &fi);
               if (!fi.fFilename) return kTRUE;
               TString ft(fi.fFileTypes[fi.fFileTypeIdx+1]);
               fDirName   = fi.fIniDir;
               fTypeIdx   = fi.fFileTypeIdx;
               fOverwrite = fi.fOverwrite;

               TString file = fi.fFilename;
               Bool_t  match = kFALSE;
               const char** fin = gGLSaveAsTypes; ++fin;
               while (*fin != 0)
               {
                  if (file.EndsWith(*fin + 1))
                  {
                     match = kTRUE;
                     break;
                  }
                  fin += 2;
               }
               if ( ! match)
               {
                  file += ft(ft.Index("."), ft.Length());
               }
               SavePicture(file);
            }
            break;
         case kGLHideMenus:
            if (fHideMenuBar)
               DisableMenuBarHiding();
            else
               EnableMenuBarHiding();
            break;
         case kGLEditObject:
            ToggleEditObject();
            break;
         case kGLCloseViewer:
            // Exit needs to be delayed to avoid bad drawable X ids - GUI
            // will all be changed in future anyway
            TTimer::SingleShot(50, "TGLSAFrame", fFrame, "SendCloseMessage()");
            break;
         case kGLQuitROOT:
            if (!gApplication->ReturnFromRun())
               delete this;
            gApplication->Terminate(0);
            break;
         default:
            break;
         }
      default:
         break;
      }
   default:
      break;
   }

   return kTRUE;
}

//______________________________________________________________________________
void TGLSAViewer::ToggleEditObject()
{
   // Toggle state of the 'Edit Object' menu entry.

   if (fFileMenu->IsEntryChecked(kGLEditObject))
      fFileMenu->UnCheckEntry(kGLEditObject);
   else
      fFileMenu->CheckEntry(kGLEditObject);
   SelectionChanged();
}

//______________________________________________________________________________
void TGLSAViewer::ToggleOrthoRotate()
{
   // Toggle state of the 'Ortho allow rotate' menu entry.

   if (fCameraMenu->IsEntryChecked(kGLOrthoRotate))
      fCameraMenu->UnCheckEntry(kGLOrthoRotate);
   else
      fCameraMenu->CheckEntry(kGLOrthoRotate);
   Bool_t state = fCameraMenu->IsEntryChecked(kGLOrthoRotate);
   fOrthoXOYCamera.SetEnableRotate(state);
   fOrthoXOZCamera.SetEnableRotate(state);
   fOrthoZOYCamera.SetEnableRotate(state);
   fOrthoXnOYCamera.SetEnableRotate(state);
   fOrthoXnOZCamera.SetEnableRotate(state);
   fOrthoZnOYCamera.SetEnableRotate(state);
}

//______________________________________________________________________________
void TGLSAViewer::ToggleOrthoDolly()
{
   // Toggle state of the 'Ortho allow dolly' menu entry.

   if (fCameraMenu->IsEntryChecked(kGLOrthoDolly))
      fCameraMenu->UnCheckEntry(kGLOrthoDolly);
   else
      fCameraMenu->CheckEntry(kGLOrthoDolly);
   Bool_t state = ! fCameraMenu->IsEntryChecked(kGLOrthoDolly);
   fOrthoXOYCamera.SetDollyToZoom(state);
   fOrthoXOZCamera.SetDollyToZoom(state);
   fOrthoZOYCamera.SetDollyToZoom(state);
}
 TGLSAViewer.cxx:1
 TGLSAViewer.cxx:2
 TGLSAViewer.cxx:3
 TGLSAViewer.cxx:4
 TGLSAViewer.cxx:5
 TGLSAViewer.cxx:6
 TGLSAViewer.cxx:7
 TGLSAViewer.cxx:8
 TGLSAViewer.cxx:9
 TGLSAViewer.cxx:10
 TGLSAViewer.cxx:11
 TGLSAViewer.cxx:12
 TGLSAViewer.cxx:13
 TGLSAViewer.cxx:14
 TGLSAViewer.cxx:15
 TGLSAViewer.cxx:16
 TGLSAViewer.cxx:17
 TGLSAViewer.cxx:18
 TGLSAViewer.cxx:19
 TGLSAViewer.cxx:20
 TGLSAViewer.cxx:21
 TGLSAViewer.cxx:22
 TGLSAViewer.cxx:23
 TGLSAViewer.cxx:24
 TGLSAViewer.cxx:25
 TGLSAViewer.cxx:26
 TGLSAViewer.cxx:27
 TGLSAViewer.cxx:28
 TGLSAViewer.cxx:29
 TGLSAViewer.cxx:30
 TGLSAViewer.cxx:31
 TGLSAViewer.cxx:32
 TGLSAViewer.cxx:33
 TGLSAViewer.cxx:34
 TGLSAViewer.cxx:35
 TGLSAViewer.cxx:36
 TGLSAViewer.cxx:37
 TGLSAViewer.cxx:38
 TGLSAViewer.cxx:39
 TGLSAViewer.cxx:40
 TGLSAViewer.cxx:41
 TGLSAViewer.cxx:42
 TGLSAViewer.cxx:43
 TGLSAViewer.cxx:44
 TGLSAViewer.cxx:45
 TGLSAViewer.cxx:46
 TGLSAViewer.cxx:47
 TGLSAViewer.cxx:48
 TGLSAViewer.cxx:49
 TGLSAViewer.cxx:50
 TGLSAViewer.cxx:51
 TGLSAViewer.cxx:52
 TGLSAViewer.cxx:53
 TGLSAViewer.cxx:54
 TGLSAViewer.cxx:55
 TGLSAViewer.cxx:56
 TGLSAViewer.cxx:57
 TGLSAViewer.cxx:58
 TGLSAViewer.cxx:59
 TGLSAViewer.cxx:60
 TGLSAViewer.cxx:61
 TGLSAViewer.cxx:62
 TGLSAViewer.cxx:63
 TGLSAViewer.cxx:64
 TGLSAViewer.cxx:65
 TGLSAViewer.cxx:66
 TGLSAViewer.cxx:67
 TGLSAViewer.cxx:68
 TGLSAViewer.cxx:69
 TGLSAViewer.cxx:70
 TGLSAViewer.cxx:71
 TGLSAViewer.cxx:72
 TGLSAViewer.cxx:73
 TGLSAViewer.cxx:74
 TGLSAViewer.cxx:75
 TGLSAViewer.cxx:76
 TGLSAViewer.cxx:77
 TGLSAViewer.cxx:78
 TGLSAViewer.cxx:79
 TGLSAViewer.cxx:80
 TGLSAViewer.cxx:81
 TGLSAViewer.cxx:82
 TGLSAViewer.cxx:83
 TGLSAViewer.cxx:84
 TGLSAViewer.cxx:85
 TGLSAViewer.cxx:86
 TGLSAViewer.cxx:87
 TGLSAViewer.cxx:88
 TGLSAViewer.cxx:89
 TGLSAViewer.cxx:90
 TGLSAViewer.cxx:91
 TGLSAViewer.cxx:92
 TGLSAViewer.cxx:93
 TGLSAViewer.cxx:94
 TGLSAViewer.cxx:95
 TGLSAViewer.cxx:96
 TGLSAViewer.cxx:97
 TGLSAViewer.cxx:98
 TGLSAViewer.cxx:99
 TGLSAViewer.cxx:100
 TGLSAViewer.cxx:101
 TGLSAViewer.cxx:102
 TGLSAViewer.cxx:103
 TGLSAViewer.cxx:104
 TGLSAViewer.cxx:105
 TGLSAViewer.cxx:106
 TGLSAViewer.cxx:107
 TGLSAViewer.cxx:108
 TGLSAViewer.cxx:109
 TGLSAViewer.cxx:110
 TGLSAViewer.cxx:111
 TGLSAViewer.cxx:112
 TGLSAViewer.cxx:113
 TGLSAViewer.cxx:114
 TGLSAViewer.cxx:115
 TGLSAViewer.cxx:116
 TGLSAViewer.cxx:117
 TGLSAViewer.cxx:118
 TGLSAViewer.cxx:119
 TGLSAViewer.cxx:120
 TGLSAViewer.cxx:121
 TGLSAViewer.cxx:122
 TGLSAViewer.cxx:123
 TGLSAViewer.cxx:124
 TGLSAViewer.cxx:125
 TGLSAViewer.cxx:126
 TGLSAViewer.cxx:127
 TGLSAViewer.cxx:128
 TGLSAViewer.cxx:129
 TGLSAViewer.cxx:130
 TGLSAViewer.cxx:131
 TGLSAViewer.cxx:132
 TGLSAViewer.cxx:133
 TGLSAViewer.cxx:134
 TGLSAViewer.cxx:135
 TGLSAViewer.cxx:136
 TGLSAViewer.cxx:137
 TGLSAViewer.cxx:138
 TGLSAViewer.cxx:139
 TGLSAViewer.cxx:140
 TGLSAViewer.cxx:141
 TGLSAViewer.cxx:142
 TGLSAViewer.cxx:143
 TGLSAViewer.cxx:144
 TGLSAViewer.cxx:145
 TGLSAViewer.cxx:146
 TGLSAViewer.cxx:147
 TGLSAViewer.cxx:148
 TGLSAViewer.cxx:149
 TGLSAViewer.cxx:150
 TGLSAViewer.cxx:151
 TGLSAViewer.cxx:152
 TGLSAViewer.cxx:153
 TGLSAViewer.cxx:154
 TGLSAViewer.cxx:155
 TGLSAViewer.cxx:156
 TGLSAViewer.cxx:157
 TGLSAViewer.cxx:158
 TGLSAViewer.cxx:159
 TGLSAViewer.cxx:160
 TGLSAViewer.cxx:161
 TGLSAViewer.cxx:162
 TGLSAViewer.cxx:163
 TGLSAViewer.cxx:164
 TGLSAViewer.cxx:165
 TGLSAViewer.cxx:166
 TGLSAViewer.cxx:167
 TGLSAViewer.cxx:168
 TGLSAViewer.cxx:169
 TGLSAViewer.cxx:170
 TGLSAViewer.cxx:171
 TGLSAViewer.cxx:172
 TGLSAViewer.cxx:173
 TGLSAViewer.cxx:174
 TGLSAViewer.cxx:175
 TGLSAViewer.cxx:176
 TGLSAViewer.cxx:177
 TGLSAViewer.cxx:178
 TGLSAViewer.cxx:179
 TGLSAViewer.cxx:180
 TGLSAViewer.cxx:181
 TGLSAViewer.cxx:182
 TGLSAViewer.cxx:183
 TGLSAViewer.cxx:184
 TGLSAViewer.cxx:185
 TGLSAViewer.cxx:186
 TGLSAViewer.cxx:187
 TGLSAViewer.cxx:188
 TGLSAViewer.cxx:189
 TGLSAViewer.cxx:190
 TGLSAViewer.cxx:191
 TGLSAViewer.cxx:192
 TGLSAViewer.cxx:193
 TGLSAViewer.cxx:194
 TGLSAViewer.cxx:195
 TGLSAViewer.cxx:196
 TGLSAViewer.cxx:197
 TGLSAViewer.cxx:198
 TGLSAViewer.cxx:199
 TGLSAViewer.cxx:200
 TGLSAViewer.cxx:201
 TGLSAViewer.cxx:202
 TGLSAViewer.cxx:203
 TGLSAViewer.cxx:204
 TGLSAViewer.cxx:205
 TGLSAViewer.cxx:206
 TGLSAViewer.cxx:207
 TGLSAViewer.cxx:208
 TGLSAViewer.cxx:209
 TGLSAViewer.cxx:210
 TGLSAViewer.cxx:211
 TGLSAViewer.cxx:212
 TGLSAViewer.cxx:213
 TGLSAViewer.cxx:214
 TGLSAViewer.cxx:215
 TGLSAViewer.cxx:216
 TGLSAViewer.cxx:217
 TGLSAViewer.cxx:218
 TGLSAViewer.cxx:219
 TGLSAViewer.cxx:220
 TGLSAViewer.cxx:221
 TGLSAViewer.cxx:222
 TGLSAViewer.cxx:223
 TGLSAViewer.cxx:224
 TGLSAViewer.cxx:225
 TGLSAViewer.cxx:226
 TGLSAViewer.cxx:227
 TGLSAViewer.cxx:228
 TGLSAViewer.cxx:229
 TGLSAViewer.cxx:230
 TGLSAViewer.cxx:231
 TGLSAViewer.cxx:232
 TGLSAViewer.cxx:233
 TGLSAViewer.cxx:234
 TGLSAViewer.cxx:235
 TGLSAViewer.cxx:236
 TGLSAViewer.cxx:237
 TGLSAViewer.cxx:238
 TGLSAViewer.cxx:239
 TGLSAViewer.cxx:240
 TGLSAViewer.cxx:241
 TGLSAViewer.cxx:242
 TGLSAViewer.cxx:243
 TGLSAViewer.cxx:244
 TGLSAViewer.cxx:245
 TGLSAViewer.cxx:246
 TGLSAViewer.cxx:247
 TGLSAViewer.cxx:248
 TGLSAViewer.cxx:249
 TGLSAViewer.cxx:250
 TGLSAViewer.cxx:251
 TGLSAViewer.cxx:252
 TGLSAViewer.cxx:253
 TGLSAViewer.cxx:254
 TGLSAViewer.cxx:255
 TGLSAViewer.cxx:256
 TGLSAViewer.cxx:257
 TGLSAViewer.cxx:258
 TGLSAViewer.cxx:259
 TGLSAViewer.cxx:260
 TGLSAViewer.cxx:261
 TGLSAViewer.cxx:262
 TGLSAViewer.cxx:263
 TGLSAViewer.cxx:264
 TGLSAViewer.cxx:265
 TGLSAViewer.cxx:266
 TGLSAViewer.cxx:267
 TGLSAViewer.cxx:268
 TGLSAViewer.cxx:269
 TGLSAViewer.cxx:270
 TGLSAViewer.cxx:271
 TGLSAViewer.cxx:272
 TGLSAViewer.cxx:273
 TGLSAViewer.cxx:274
 TGLSAViewer.cxx:275
 TGLSAViewer.cxx:276
 TGLSAViewer.cxx:277
 TGLSAViewer.cxx:278
 TGLSAViewer.cxx:279
 TGLSAViewer.cxx:280
 TGLSAViewer.cxx:281
 TGLSAViewer.cxx:282
 TGLSAViewer.cxx:283
 TGLSAViewer.cxx:284
 TGLSAViewer.cxx:285
 TGLSAViewer.cxx:286
 TGLSAViewer.cxx:287
 TGLSAViewer.cxx:288
 TGLSAViewer.cxx:289
 TGLSAViewer.cxx:290
 TGLSAViewer.cxx:291
 TGLSAViewer.cxx:292
 TGLSAViewer.cxx:293
 TGLSAViewer.cxx:294
 TGLSAViewer.cxx:295
 TGLSAViewer.cxx:296
 TGLSAViewer.cxx:297
 TGLSAViewer.cxx:298
 TGLSAViewer.cxx:299
 TGLSAViewer.cxx:300
 TGLSAViewer.cxx:301
 TGLSAViewer.cxx:302
 TGLSAViewer.cxx:303
 TGLSAViewer.cxx:304
 TGLSAViewer.cxx:305
 TGLSAViewer.cxx:306
 TGLSAViewer.cxx:307
 TGLSAViewer.cxx:308
 TGLSAViewer.cxx:309
 TGLSAViewer.cxx:310
 TGLSAViewer.cxx:311
 TGLSAViewer.cxx:312
 TGLSAViewer.cxx:313
 TGLSAViewer.cxx:314
 TGLSAViewer.cxx:315
 TGLSAViewer.cxx:316
 TGLSAViewer.cxx:317
 TGLSAViewer.cxx:318
 TGLSAViewer.cxx:319
 TGLSAViewer.cxx:320
 TGLSAViewer.cxx:321
 TGLSAViewer.cxx:322
 TGLSAViewer.cxx:323
 TGLSAViewer.cxx:324
 TGLSAViewer.cxx:325
 TGLSAViewer.cxx:326
 TGLSAViewer.cxx:327
 TGLSAViewer.cxx:328
 TGLSAViewer.cxx:329
 TGLSAViewer.cxx:330
 TGLSAViewer.cxx:331
 TGLSAViewer.cxx:332
 TGLSAViewer.cxx:333
 TGLSAViewer.cxx:334
 TGLSAViewer.cxx:335
 TGLSAViewer.cxx:336
 TGLSAViewer.cxx:337
 TGLSAViewer.cxx:338
 TGLSAViewer.cxx:339
 TGLSAViewer.cxx:340
 TGLSAViewer.cxx:341
 TGLSAViewer.cxx:342
 TGLSAViewer.cxx:343
 TGLSAViewer.cxx:344
 TGLSAViewer.cxx:345
 TGLSAViewer.cxx:346
 TGLSAViewer.cxx:347
 TGLSAViewer.cxx:348
 TGLSAViewer.cxx:349
 TGLSAViewer.cxx:350
 TGLSAViewer.cxx:351
 TGLSAViewer.cxx:352
 TGLSAViewer.cxx:353
 TGLSAViewer.cxx:354
 TGLSAViewer.cxx:355
 TGLSAViewer.cxx:356
 TGLSAViewer.cxx:357
 TGLSAViewer.cxx:358
 TGLSAViewer.cxx:359
 TGLSAViewer.cxx:360
 TGLSAViewer.cxx:361
 TGLSAViewer.cxx:362
 TGLSAViewer.cxx:363
 TGLSAViewer.cxx:364
 TGLSAViewer.cxx:365
 TGLSAViewer.cxx:366
 TGLSAViewer.cxx:367
 TGLSAViewer.cxx:368
 TGLSAViewer.cxx:369
 TGLSAViewer.cxx:370
 TGLSAViewer.cxx:371
 TGLSAViewer.cxx:372
 TGLSAViewer.cxx:373
 TGLSAViewer.cxx:374
 TGLSAViewer.cxx:375
 TGLSAViewer.cxx:376
 TGLSAViewer.cxx:377
 TGLSAViewer.cxx:378
 TGLSAViewer.cxx:379
 TGLSAViewer.cxx:380
 TGLSAViewer.cxx:381
 TGLSAViewer.cxx:382
 TGLSAViewer.cxx:383
 TGLSAViewer.cxx:384
 TGLSAViewer.cxx:385
 TGLSAViewer.cxx:386
 TGLSAViewer.cxx:387
 TGLSAViewer.cxx:388
 TGLSAViewer.cxx:389
 TGLSAViewer.cxx:390
 TGLSAViewer.cxx:391
 TGLSAViewer.cxx:392
 TGLSAViewer.cxx:393
 TGLSAViewer.cxx:394
 TGLSAViewer.cxx:395
 TGLSAViewer.cxx:396
 TGLSAViewer.cxx:397
 TGLSAViewer.cxx:398
 TGLSAViewer.cxx:399
 TGLSAViewer.cxx:400
 TGLSAViewer.cxx:401
 TGLSAViewer.cxx:402
 TGLSAViewer.cxx:403
 TGLSAViewer.cxx:404
 TGLSAViewer.cxx:405
 TGLSAViewer.cxx:406
 TGLSAViewer.cxx:407
 TGLSAViewer.cxx:408
 TGLSAViewer.cxx:409
 TGLSAViewer.cxx:410
 TGLSAViewer.cxx:411
 TGLSAViewer.cxx:412
 TGLSAViewer.cxx:413
 TGLSAViewer.cxx:414
 TGLSAViewer.cxx:415
 TGLSAViewer.cxx:416
 TGLSAViewer.cxx:417
 TGLSAViewer.cxx:418
 TGLSAViewer.cxx:419
 TGLSAViewer.cxx:420
 TGLSAViewer.cxx:421
 TGLSAViewer.cxx:422
 TGLSAViewer.cxx:423
 TGLSAViewer.cxx:424
 TGLSAViewer.cxx:425
 TGLSAViewer.cxx:426
 TGLSAViewer.cxx:427
 TGLSAViewer.cxx:428
 TGLSAViewer.cxx:429
 TGLSAViewer.cxx:430
 TGLSAViewer.cxx:431
 TGLSAViewer.cxx:432
 TGLSAViewer.cxx:433
 TGLSAViewer.cxx:434
 TGLSAViewer.cxx:435
 TGLSAViewer.cxx:436
 TGLSAViewer.cxx:437
 TGLSAViewer.cxx:438
 TGLSAViewer.cxx:439
 TGLSAViewer.cxx:440
 TGLSAViewer.cxx:441
 TGLSAViewer.cxx:442
 TGLSAViewer.cxx:443
 TGLSAViewer.cxx:444
 TGLSAViewer.cxx:445
 TGLSAViewer.cxx:446
 TGLSAViewer.cxx:447
 TGLSAViewer.cxx:448
 TGLSAViewer.cxx:449
 TGLSAViewer.cxx:450
 TGLSAViewer.cxx:451
 TGLSAViewer.cxx:452
 TGLSAViewer.cxx:453
 TGLSAViewer.cxx:454
 TGLSAViewer.cxx:455
 TGLSAViewer.cxx:456
 TGLSAViewer.cxx:457
 TGLSAViewer.cxx:458
 TGLSAViewer.cxx:459
 TGLSAViewer.cxx:460
 TGLSAViewer.cxx:461
 TGLSAViewer.cxx:462
 TGLSAViewer.cxx:463
 TGLSAViewer.cxx:464
 TGLSAViewer.cxx:465
 TGLSAViewer.cxx:466
 TGLSAViewer.cxx:467
 TGLSAViewer.cxx:468
 TGLSAViewer.cxx:469
 TGLSAViewer.cxx:470
 TGLSAViewer.cxx:471
 TGLSAViewer.cxx:472
 TGLSAViewer.cxx:473
 TGLSAViewer.cxx:474
 TGLSAViewer.cxx:475
 TGLSAViewer.cxx:476
 TGLSAViewer.cxx:477
 TGLSAViewer.cxx:478
 TGLSAViewer.cxx:479
 TGLSAViewer.cxx:480
 TGLSAViewer.cxx:481
 TGLSAViewer.cxx:482
 TGLSAViewer.cxx:483
 TGLSAViewer.cxx:484
 TGLSAViewer.cxx:485
 TGLSAViewer.cxx:486
 TGLSAViewer.cxx:487
 TGLSAViewer.cxx:488
 TGLSAViewer.cxx:489
 TGLSAViewer.cxx:490
 TGLSAViewer.cxx:491
 TGLSAViewer.cxx:492
 TGLSAViewer.cxx:493
 TGLSAViewer.cxx:494
 TGLSAViewer.cxx:495
 TGLSAViewer.cxx:496
 TGLSAViewer.cxx:497
 TGLSAViewer.cxx:498
 TGLSAViewer.cxx:499
 TGLSAViewer.cxx:500
 TGLSAViewer.cxx:501
 TGLSAViewer.cxx:502
 TGLSAViewer.cxx:503
 TGLSAViewer.cxx:504
 TGLSAViewer.cxx:505
 TGLSAViewer.cxx:506
 TGLSAViewer.cxx:507
 TGLSAViewer.cxx:508
 TGLSAViewer.cxx:509
 TGLSAViewer.cxx:510
 TGLSAViewer.cxx:511
 TGLSAViewer.cxx:512
 TGLSAViewer.cxx:513
 TGLSAViewer.cxx:514
 TGLSAViewer.cxx:515
 TGLSAViewer.cxx:516
 TGLSAViewer.cxx:517
 TGLSAViewer.cxx:518
 TGLSAViewer.cxx:519
 TGLSAViewer.cxx:520
 TGLSAViewer.cxx:521
 TGLSAViewer.cxx:522
 TGLSAViewer.cxx:523
 TGLSAViewer.cxx:524
 TGLSAViewer.cxx:525
 TGLSAViewer.cxx:526
 TGLSAViewer.cxx:527
 TGLSAViewer.cxx:528
 TGLSAViewer.cxx:529
 TGLSAViewer.cxx:530
 TGLSAViewer.cxx:531
 TGLSAViewer.cxx:532
 TGLSAViewer.cxx:533
 TGLSAViewer.cxx:534
 TGLSAViewer.cxx:535
 TGLSAViewer.cxx:536
 TGLSAViewer.cxx:537
 TGLSAViewer.cxx:538
 TGLSAViewer.cxx:539
 TGLSAViewer.cxx:540
 TGLSAViewer.cxx:541
 TGLSAViewer.cxx:542
 TGLSAViewer.cxx:543
 TGLSAViewer.cxx:544
 TGLSAViewer.cxx:545
 TGLSAViewer.cxx:546
 TGLSAViewer.cxx:547
 TGLSAViewer.cxx:548
 TGLSAViewer.cxx:549
 TGLSAViewer.cxx:550
 TGLSAViewer.cxx:551
 TGLSAViewer.cxx:552
 TGLSAViewer.cxx:553
 TGLSAViewer.cxx:554
 TGLSAViewer.cxx:555
 TGLSAViewer.cxx:556
 TGLSAViewer.cxx:557
 TGLSAViewer.cxx:558
 TGLSAViewer.cxx:559
 TGLSAViewer.cxx:560
 TGLSAViewer.cxx:561
 TGLSAViewer.cxx:562
 TGLSAViewer.cxx:563
 TGLSAViewer.cxx:564
 TGLSAViewer.cxx:565
 TGLSAViewer.cxx:566
 TGLSAViewer.cxx:567
 TGLSAViewer.cxx:568
 TGLSAViewer.cxx:569
 TGLSAViewer.cxx:570
 TGLSAViewer.cxx:571
 TGLSAViewer.cxx:572
 TGLSAViewer.cxx:573
 TGLSAViewer.cxx:574
 TGLSAViewer.cxx:575
 TGLSAViewer.cxx:576
 TGLSAViewer.cxx:577
 TGLSAViewer.cxx:578
 TGLSAViewer.cxx:579
 TGLSAViewer.cxx:580
 TGLSAViewer.cxx:581
 TGLSAViewer.cxx:582
 TGLSAViewer.cxx:583
 TGLSAViewer.cxx:584
 TGLSAViewer.cxx:585
 TGLSAViewer.cxx:586
 TGLSAViewer.cxx:587
 TGLSAViewer.cxx:588
 TGLSAViewer.cxx:589
 TGLSAViewer.cxx:590
 TGLSAViewer.cxx:591
 TGLSAViewer.cxx:592
 TGLSAViewer.cxx:593
 TGLSAViewer.cxx:594
 TGLSAViewer.cxx:595
 TGLSAViewer.cxx:596
 TGLSAViewer.cxx:597
 TGLSAViewer.cxx:598
 TGLSAViewer.cxx:599
 TGLSAViewer.cxx:600
 TGLSAViewer.cxx:601
 TGLSAViewer.cxx:602
 TGLSAViewer.cxx:603
 TGLSAViewer.cxx:604
 TGLSAViewer.cxx:605
 TGLSAViewer.cxx:606
 TGLSAViewer.cxx:607
 TGLSAViewer.cxx:608
 TGLSAViewer.cxx:609
 TGLSAViewer.cxx:610
 TGLSAViewer.cxx:611
 TGLSAViewer.cxx:612
 TGLSAViewer.cxx:613
 TGLSAViewer.cxx:614
 TGLSAViewer.cxx:615
 TGLSAViewer.cxx:616
 TGLSAViewer.cxx:617
 TGLSAViewer.cxx:618
 TGLSAViewer.cxx:619
 TGLSAViewer.cxx:620
 TGLSAViewer.cxx:621
 TGLSAViewer.cxx:622
 TGLSAViewer.cxx:623
 TGLSAViewer.cxx:624
 TGLSAViewer.cxx:625
 TGLSAViewer.cxx:626
 TGLSAViewer.cxx:627
 TGLSAViewer.cxx:628
 TGLSAViewer.cxx:629
 TGLSAViewer.cxx:630
 TGLSAViewer.cxx:631
 TGLSAViewer.cxx:632
 TGLSAViewer.cxx:633
 TGLSAViewer.cxx:634
 TGLSAViewer.cxx:635
 TGLSAViewer.cxx:636
 TGLSAViewer.cxx:637
 TGLSAViewer.cxx:638
 TGLSAViewer.cxx:639
 TGLSAViewer.cxx:640
 TGLSAViewer.cxx:641
 TGLSAViewer.cxx:642
 TGLSAViewer.cxx:643
 TGLSAViewer.cxx:644
 TGLSAViewer.cxx:645
 TGLSAViewer.cxx:646
 TGLSAViewer.cxx:647
 TGLSAViewer.cxx:648
 TGLSAViewer.cxx:649
 TGLSAViewer.cxx:650
 TGLSAViewer.cxx:651
 TGLSAViewer.cxx:652
 TGLSAViewer.cxx:653
 TGLSAViewer.cxx:654
 TGLSAViewer.cxx:655
 TGLSAViewer.cxx:656
 TGLSAViewer.cxx:657
 TGLSAViewer.cxx:658
 TGLSAViewer.cxx:659
 TGLSAViewer.cxx:660
 TGLSAViewer.cxx:661
 TGLSAViewer.cxx:662
 TGLSAViewer.cxx:663
 TGLSAViewer.cxx:664
 TGLSAViewer.cxx:665
 TGLSAViewer.cxx:666
 TGLSAViewer.cxx:667
 TGLSAViewer.cxx:668
 TGLSAViewer.cxx:669
 TGLSAViewer.cxx:670
 TGLSAViewer.cxx:671
 TGLSAViewer.cxx:672
 TGLSAViewer.cxx:673
 TGLSAViewer.cxx:674
 TGLSAViewer.cxx:675
 TGLSAViewer.cxx:676
 TGLSAViewer.cxx:677
 TGLSAViewer.cxx:678
 TGLSAViewer.cxx:679
 TGLSAViewer.cxx:680
 TGLSAViewer.cxx:681
 TGLSAViewer.cxx:682
 TGLSAViewer.cxx:683
 TGLSAViewer.cxx:684
 TGLSAViewer.cxx:685
 TGLSAViewer.cxx:686
 TGLSAViewer.cxx:687
 TGLSAViewer.cxx:688
 TGLSAViewer.cxx:689
 TGLSAViewer.cxx:690
 TGLSAViewer.cxx:691
 TGLSAViewer.cxx:692
 TGLSAViewer.cxx:693
 TGLSAViewer.cxx:694
 TGLSAViewer.cxx:695
 TGLSAViewer.cxx:696
 TGLSAViewer.cxx:697
 TGLSAViewer.cxx:698
 TGLSAViewer.cxx:699
 TGLSAViewer.cxx:700
 TGLSAViewer.cxx:701
 TGLSAViewer.cxx:702
 TGLSAViewer.cxx:703
 TGLSAViewer.cxx:704
 TGLSAViewer.cxx:705
 TGLSAViewer.cxx:706
 TGLSAViewer.cxx:707
 TGLSAViewer.cxx:708
 TGLSAViewer.cxx:709
 TGLSAViewer.cxx:710
 TGLSAViewer.cxx:711
 TGLSAViewer.cxx:712
 TGLSAViewer.cxx:713
 TGLSAViewer.cxx:714
 TGLSAViewer.cxx:715
 TGLSAViewer.cxx:716
 TGLSAViewer.cxx:717
 TGLSAViewer.cxx:718
 TGLSAViewer.cxx:719
 TGLSAViewer.cxx:720
 TGLSAViewer.cxx:721
 TGLSAViewer.cxx:722
 TGLSAViewer.cxx:723
 TGLSAViewer.cxx:724
 TGLSAViewer.cxx:725
 TGLSAViewer.cxx:726
 TGLSAViewer.cxx:727
 TGLSAViewer.cxx:728
 TGLSAViewer.cxx:729
 TGLSAViewer.cxx:730
 TGLSAViewer.cxx:731
 TGLSAViewer.cxx:732
 TGLSAViewer.cxx:733
 TGLSAViewer.cxx:734
 TGLSAViewer.cxx:735
 TGLSAViewer.cxx:736
 TGLSAViewer.cxx:737
 TGLSAViewer.cxx:738
 TGLSAViewer.cxx:739
 TGLSAViewer.cxx:740
 TGLSAViewer.cxx:741
 TGLSAViewer.cxx:742
 TGLSAViewer.cxx:743
 TGLSAViewer.cxx:744
 TGLSAViewer.cxx:745
 TGLSAViewer.cxx:746
 TGLSAViewer.cxx:747
 TGLSAViewer.cxx:748
 TGLSAViewer.cxx:749
 TGLSAViewer.cxx:750
 TGLSAViewer.cxx:751
 TGLSAViewer.cxx:752
 TGLSAViewer.cxx:753
 TGLSAViewer.cxx:754
 TGLSAViewer.cxx:755
 TGLSAViewer.cxx:756
 TGLSAViewer.cxx:757
 TGLSAViewer.cxx:758
 TGLSAViewer.cxx:759
 TGLSAViewer.cxx:760
 TGLSAViewer.cxx:761
 TGLSAViewer.cxx:762
 TGLSAViewer.cxx:763
 TGLSAViewer.cxx:764
 TGLSAViewer.cxx:765
 TGLSAViewer.cxx:766
 TGLSAViewer.cxx:767
 TGLSAViewer.cxx:768
 TGLSAViewer.cxx:769
 TGLSAViewer.cxx:770
 TGLSAViewer.cxx:771
 TGLSAViewer.cxx:772
 TGLSAViewer.cxx:773
 TGLSAViewer.cxx:774
 TGLSAViewer.cxx:775
 TGLSAViewer.cxx:776
 TGLSAViewer.cxx:777
 TGLSAViewer.cxx:778
 TGLSAViewer.cxx:779
 TGLSAViewer.cxx:780
 TGLSAViewer.cxx:781
 TGLSAViewer.cxx:782
 TGLSAViewer.cxx:783
 TGLSAViewer.cxx:784
 TGLSAViewer.cxx:785
 TGLSAViewer.cxx:786
 TGLSAViewer.cxx:787
 TGLSAViewer.cxx:788
 TGLSAViewer.cxx:789
 TGLSAViewer.cxx:790
 TGLSAViewer.cxx:791
 TGLSAViewer.cxx:792
 TGLSAViewer.cxx:793
 TGLSAViewer.cxx:794
 TGLSAViewer.cxx:795
 TGLSAViewer.cxx:796
 TGLSAViewer.cxx:797
 TGLSAViewer.cxx:798
 TGLSAViewer.cxx:799
 TGLSAViewer.cxx:800
 TGLSAViewer.cxx:801
 TGLSAViewer.cxx:802
 TGLSAViewer.cxx:803
 TGLSAViewer.cxx:804
 TGLSAViewer.cxx:805
 TGLSAViewer.cxx:806
 TGLSAViewer.cxx:807
 TGLSAViewer.cxx:808
 TGLSAViewer.cxx:809
 TGLSAViewer.cxx:810
 TGLSAViewer.cxx:811
 TGLSAViewer.cxx:812
 TGLSAViewer.cxx:813
 TGLSAViewer.cxx:814
 TGLSAViewer.cxx:815
 TGLSAViewer.cxx:816
 TGLSAViewer.cxx:817
 TGLSAViewer.cxx:818
 TGLSAViewer.cxx:819
 TGLSAViewer.cxx:820
 TGLSAViewer.cxx:821
 TGLSAViewer.cxx:822
 TGLSAViewer.cxx:823
 TGLSAViewer.cxx:824
 TGLSAViewer.cxx:825
 TGLSAViewer.cxx:826
 TGLSAViewer.cxx:827
 TGLSAViewer.cxx:828
 TGLSAViewer.cxx:829
 TGLSAViewer.cxx:830
 TGLSAViewer.cxx:831
 TGLSAViewer.cxx:832
 TGLSAViewer.cxx:833
 TGLSAViewer.cxx:834
 TGLSAViewer.cxx:835
 TGLSAViewer.cxx:836
 TGLSAViewer.cxx:837
 TGLSAViewer.cxx:838
 TGLSAViewer.cxx:839
 TGLSAViewer.cxx:840
 TGLSAViewer.cxx:841
 TGLSAViewer.cxx:842
 TGLSAViewer.cxx:843
 TGLSAViewer.cxx:844
 TGLSAViewer.cxx:845
 TGLSAViewer.cxx:846
 TGLSAViewer.cxx:847
 TGLSAViewer.cxx:848
 TGLSAViewer.cxx:849
 TGLSAViewer.cxx:850
 TGLSAViewer.cxx:851
 TGLSAViewer.cxx:852
 TGLSAViewer.cxx:853
 TGLSAViewer.cxx:854
 TGLSAViewer.cxx:855
 TGLSAViewer.cxx:856
 TGLSAViewer.cxx:857
 TGLSAViewer.cxx:858
 TGLSAViewer.cxx:859
 TGLSAViewer.cxx:860
 TGLSAViewer.cxx:861
 TGLSAViewer.cxx:862