;$Id: db_display1d__define.pro,v 1.46 2006/11/13 18:57:53 azuah Exp $
;###############################################################################
;
; CLASS NAME:
;   DB_Display1D
;
; PURPOSE:
;   A widget object class responsible for displaying DaveGr1D
;   object(s). It constructs a visualization based on the DaveGr1D
;   object(s) and all the widgets necessary to interact with the
;   visualization.
;
; CATEGORY:
;   Data Browser
;
; SUPERCLASSES:
;
; PUBLIC METHODS:
;   GetScene
;   GetView
;   GetWindow
;   AddText
;   DefLimEvent
;   DispConSenMenu
;   DispErorrEvent
;   DispLegendEvent
;   DispTitleEvent
;   DisplayEvent
;   DrawEvent
;   ExitEvent
;   NoRenew
;   Print
;   Refresh
;   Renew
;   TlbEvent
;
; AUTHOR:
;   Richard Tumanjong Azuah
;   NIST Center for Neutron Research
;   100 Bureau Drive, Gaithersburg, MD 20899
;   United States
;   azuah@nist.gov; (301) 9755604
;   Feb, 2003
;
; LICENSE:
;  The software in this file is written by an employee of 
;  National Institute of Standards and Technology 
;  as part of the DAVE software project.
;
;  The DAVE software package is not subject to copyright protection
;  and is in the public domain. It should be considered as an
;  experimental neutron scattering data reduction, visualization, and
;  analysis system. As such, the authors assume no responsibility
;  whatsoever for its use, and make no guarantees, expressed or
;  implied, about its quality, reliability, or any other
;  characteristic. The use of certain trade names or commercial
;  products does not imply any endorsement of a particular product,
;  nor does it imply that the named product is necessarily the best
;  product for the stated purpose. We would appreciate acknowledgment
;  if the DAVE software is used or if the code in this file is
;  included in another product.
;
;###############################################################################



;===============================================================================
; DB_Display1D::Cleanup
;
; PURPOSE:
;   Cleanup procedure for DB_Display1D
;
; PARAMETERS:
;
; KEYWORDS:
;
pro DB_Display1D::Cleanup

; store/save current GUI/widget settings in the DaveGr1D object
void = (self.oDaveGr)->get(guiAttribsPtr=guiAttribsPtr)
(*guiAttribsPtr) = {winDim:self.winDim, $
                    xrangeFlag:self.xrangeFlag, $
                    xrange:self.xrange, $
                    yrangeFlag:self.yrangeFlag, $
                    yrange:self.yrange, $
                    dispType:self.dispType, $
                    dispError:self.dispError, $
                    dispTitle:self.dispTitle $
                   }

obj_destroy, self.oScene
obj_destroy, self.oDest
(self.o_registry)->remove,self      ; unregister self from Object Registry
(self.oActive1DCont)->remove, self.oDaveGr ; unregister DaveGr object from the active view list

; remove this widget object as the visualization object ref of the gr object
void = (self.oDaveGr)->set(visRef=obj_new())

device, decomposed=self.old_dec

end
;-------------------------------------------------------------------------------



;===============================================================================
; DB_Display1D::Refresh
;
; PURPOSE:
;   Refresh the graphics window
;
; PARAMETERS
;   
;
; KEYWORDS:
;   
;
pro DB_Display1D::Refresh, _EXTRA=etc

; require color decomposition (for using rgb colors directly)
; return to previous setting at end of this procedure
device, get_decomposed = old_dec
device, decompose=1

switch self.renewScene of

    0: begin
        self.renewScene = 1  ; reset to default value of 1
        objArr = (self.oScene)->get(/all, count=nObj)
        ;; if Scene is empty, proceed to case '1' by not 'breaking'
        if (nObj gt 0) then begin
            (self.oDest)->draw, self.oScene
            break
        endif
    end

    1: begin
        ;; Modify tlb widget title so it includes the current name tag
        ;; for the DaveGr object being viewed
        void = (self.oDaveGr)->get(nameTag=title)
        widget_control, self.tlb,tlb_set_title='DATABROWSER - '+title

        ;; error bars
        etc = (n_elements(etc) le 0)? {dispError:self.dispError} : $
              create_struct(etc,'dispError',self.dispError)

        ;; Title
        etc = create_struct(etc,'dispTitle',self.dispTitle)

        ;; Set display mode
        case self.dispType of
            0: etc = create_struct(etc,'dispType','POINTS')
            1: etc = create_struct(etc,'dispType','HISTOGRAMS')
        endcase

        ;; x-axis limits
        if (self.xrangeFlag) then begin
            etc = create_struct(etc,'xrange',self.xrange)
        endif
        ;; y-axis limits
        if (self.yrangeFlag) then begin
            etc = create_struct(etc,'yrange',self.yrange)
        endif

        (self.oDaveGr)->display, self.oDest, self.oScene, _EXTRA=etc
        ;Dg1Ddisplay, self.oDest,self.oScene,self.oDataCont, _EXTRA=etc

    end

endswitch

; return color decomposition to previous setting
device, decompose=old_dec

end
;-------------------------------------------------------------------------------



;===============================================================================
; DB_Display1D::HandleConSenMenuEvent
;
; PURPOSE:
;   Handle all events generated by widgets in context-sensitive
;   pop-up dialogs.
;
; PARAMETERS
;   event [in;req] - the event structure
;
; KEYWORDS:
;
pro DB_Display1D::HandleConSenMenuEvent, event

;widget_control, event.top, get_uvalue = sPtr

; Get the selected CSM's name and value
uname = widget_info(event.id,/uname)
widget_control, event.id, get_uvalue=newValue
;newValue = newValueStr.val
;newIndex = newValueStr.ind

; Get the atom/model for which the CSM should act on
objRef = self.csmObjRef

switch uname of

    'STYPE': begin
        validAtomNames = ['SPLOT'] ; ==> only atoms with name matching these will be affected
        objRefType = vartype(objRef) ; IDLgrModels will have multiple atoms
        if (objRefType eq 'IDLGRMODEL') then begin
            ;; loop through atoms in model and make changes
            objArr = objRef->get(/all, count=nObj)
            while (nObj gt 0) do begin
                nObj = nObj - 1
                objArr[nObj]->getProperty, name=atomName
                res = where(validAtomNames eq atomName,valid)
                if (valid) then begin
                    objArr[nObj]->getProperty, symbol=symRef
                    symRef->setProperty, data=newValue
                    objArr[nObj]->getProperty, uvalue=atomUval
                    daveGrRef = atomUval.objRef
                    datInd = atomUval.datInd
                    if (not daveGrRef->set(symType=newValue,position=datInd)) then return
                    self->noRenew
                endif
            endwhile
        endif else begin
            objRef->getProperty, name=atomName
            res = where(validAtomNames eq atomName,valid)
            if (valid) then begin
                objRef->getProperty, symbol=symRef
                symRef->setProperty, data=newValue
                objRef->getProperty, uvalue=atomUval
                daveGrRef = atomUval.objRef
                if (not daveGrRef->set(symType=newValue)) then return
                self->noRenew
            endif
        endelse
        break
    end

    'SSIZE': begin
        validAtomNames = ['SPLOT'] ; ==> only atoms with name matching these will be affected
        objRefType = vartype(objRef) ; IDLgrModels will have multiple atoms
        if (objRefType eq 'IDLGRMODEL') then begin
            ;; loop through atoms in model and make changes
            objArr = objRef->get(/all, count=nObj)
            while (nObj gt 0) do begin
                nObj = nObj - 1
                objArr[nObj]->getProperty, name=atomName
                res = where(validAtomNames eq atomName,valid)
                if (valid) then begin
                    objArr[nObj]->getProperty, symbol=symRef
                    symRef->getProperty, uvalue=symScale
                    symRef->setProperty, size=newValue*symScale
                    objArr[nObj]->getProperty, uvalue=atomUval
                    daveGrRef = atomUval.objRef
                    datInd = atomUval.datInd
                    if (not daveGrRef->set(symSize=newValue,position=datInd)) then return
                    self->noRenew
                endif
            endwhile
        endif else begin
            objRef->getProperty, name=atomName
            res = where(validAtomNames eq atomName,valid)
            if (valid) then begin
                objRef->getProperty, symbol=symRef
                symRef->getProperty, uvalue=symScale
                symRef->setProperty, size=newValue*symScale
                objRef->getProperty, uvalue=atomUval
                daveGrRef = atomUval.objRef
                datInd = atomUval.datInd
                if (not daveGrRef->set(symSize=newValue,position=datInd)) then return
                self->noRenew
            endif
        endelse
        break
    end

    'LSTYLE': begin
        validAtomNames = ['LPLOT'] ; ==> only atoms with name matching these will be affected
        objRefType = vartype(objRef) ; IDLgrModels will have multiple atoms
        if (objRefType eq 'IDLGRMODEL') then begin
            ;; loop through atoms in model and make changes
            objArr = objRef->get(/all, count=nObj)
            while (nObj gt 0) do begin
                nObj = nObj - 1
                objArr[nObj]->getProperty, name=atomName
                res = where(validAtomNames eq atomName,valid)
                if (valid) then begin
                    objArr[nObj]->setProperty,linestyle=newValue
                    objArr[nObj]->getProperty, uvalue=atomUval
                    daveGrRef = atomUval.objRef
                    datInd = atomUval.datInd
                    if (not daveGrRef->set(lineType=newValue,position=datInd)) then return
                    self->noRenew
                endif
            endwhile
        endif else begin
            objRef->getProperty, name=atomName
            res = where(validAtomNames eq atomName,valid)
            if (valid) then begin
                objRef->setProperty,linestyle=newValue
                objRef->getProperty, uvalue=atomUval
                daveGrRef = atomUval.objRef
                datInd = atomUval.datInd
                if (not daveGrRef->set(lineType=newValue,position=datInd)) then return
                self->noRenew
            endif
        endelse
        ;; Update check mark against the item selected/deselected
        ;if (valid) then begin
        ;    widget_control,(*self.csblLSIDPtr)[self.csblLSIND],set_button=0
        ;    self.csblLSIND = newIndex
        ;    widget_control,(*self.csblLSIDPtr)[self.csblLSIND],set_button=1
        ;endif
        break
    end

    'THICK': begin
        validAtomNames = ['LPLOT','SPLOT','EPLOT','AXIS'] ; ==> only atoms with name matching these will be affected
        objRefType = vartype(objRef) ; IDLgrModels will have multiple atoms
        if (objRefType eq 'IDLGRMODEL') then begin
            ;; loop through atoms in model and make changes
            objArr = objRef->get(/all, count=nObj)
            while (nObj gt 0) do begin
                nObj = nObj - 1
                objArr[nObj]->getProperty, name=atomName
                res = where(validAtomNames eq atomName,valid)
                if (valid) then begin
                    objArr[nObj]->setProperty,thick=newValue
                    ;if (atomName eq 'AXIS') then goto, SKIPAXIS0
                    objArr[nObj]->getProperty, uvalue=atomUval
                    daveGrRef = atomUval.objRef
                    datInd = atomUval.datInd
                    if (atomName eq 'AXIS') then begin
                        case datInd of
                            0: kw_val = {xLineSize:newValue} ; x-axis
                            1: kw_val = {zLineSize:newValue} ; y-axis
                            else: kw_val = {dummy:0}
                        endcase
                        if (not daveGrRef->set(_EXTRA=kw_val)) then return
                        goto, SKIPAXIS0
                    endif
                    if (not daveGrRef->set(lineSize=newValue,position=datInd)) then return
                    ;; if a symbol plot, modify the symbols too
                    if (atomName eq 'SPLOT') then begin
                        objArr[nObj]->getProperty, symbol=symRef
                        symRef->setProperty, thick=newValue
                    endif
                    SKIPAXIS0:
                    self->noRenew
                endif
            endwhile
        endif else begin
            objRef->getProperty, name=atomName
            res = where(validAtomNames eq atomName,valid)
            if (valid) then begin
                objRef->setProperty,thick=newValue
                ;if (atomName eq 'AXIS') then goto, SKIPAXIS1
                objRef->getProperty, uvalue=atomUval
                daveGrRef = atomUval.objRef
                datInd = atomUval.datInd
                if (atomName eq 'AXIS') then begin
                    case datInd of
                        0: kw_val = {xLineSize:newValue} ; x-axis
                        1: kw_val = {zLineSize:newValue} ; y-axis
                        else: kw_val = {dummy:0}
                    endcase
                    if (not daveGrRef->set(_EXTRA=kw_val)) then return
                    goto, SKIPAXIS1
                endif
                if (not daveGrRef->set(lineSize=newValue,position=datInd)) then return
                ;; if a symbol plot, modify the symbols too
                if (atomName eq 'SPLOT') then begin
                    objArr[nObj]->getProperty, symbol=symRef
                    symRef->setProperty, thick=newValue
                endif
                SKIPAXIS1:
                self->noRenew
            endif
        endelse
        break
        break
    end

    'COLOR': begin
        validAtomNames = ['LPLOT','SPLOT','EPLOT','AXIS','LABEL'] ; ==> only atoms with name matching these will be affected
        objRefType = vartype(objRef) ; IDLgrModels will have multiple atoms
        if (objRefType eq 'IDLGRMODEL') then begin
            ;; loop through atoms in model and make changes
            objArr = objRef->get(/all, count=nObj)
            while (nObj gt 0) do begin
                nObj = nObj - 1
                objArr[nObj]->getProperty, name=atomName
                res = where(validAtomNames eq atomName,valid)
                if (valid) then begin
                    objArr[nObj]->setProperty,color=newValue
                    objArr[nObj]->getProperty, uvalue=atomUval
                    daveGrRef = atomUval.objRef
                    datInd = atomUval.datInd
                    if (atomName eq 'AXIS') then begin
                        case datInd of
                            0: kw_val = {xColor:newValue} ; x-axis
                            1: kw_val = {zColor:newValue} ; y-axis
                            else: kw_val = {dummy:0}
                        endcase
                        if (not daveGrRef->set(_EXTRA=kw_val)) then return
                        goto, SKIPAXIS2
                    endif
                    if (atomName eq 'LABEL') then begin
                        case datInd of
                            -1: begin ; title
                                if (not daveGrRef->get(title=title)) then return
                                title.color = newValue
                                if (not daveGrRef->set(title=title)) then return
                            end
                            else: begin ; misc label
                                if (not daveGrRef->get(label=label)) then return
                                label[datInd].color = newValue
                                if (not daveGrRef->set(label=label)) then return
                            end
                        endcase
                        goto, SKIPAXIS2
                    endif
                    if (not daveGrRef->set(color=newValue,position=datInd)) then return
                    ;; if a symbol plot, modify the symbols too
                    if (atomName eq 'SPLOT') then begin
                        objArr[nObj]->getProperty, symbol=symRef
                        symRef->setProperty, color=newValue
                    endif
                    SKIPAXIS2:
                    self->noRenew
                endif
            endwhile
        endif else begin
            objRef->getProperty, name=atomName
            res = where(validAtomNames eq atomName,valid)
            if (valid) then begin
                objRef->setProperty,color=newValue
                objRef->getProperty, uvalue=atomUval
                daveGrRef = atomUval.objRef
                datInd = atomUval.datInd
                if (atomName eq 'AXIS') then begin
                    case datInd of
                        0: kw_val = {xColor:newValue} ; x-axis
                        1: kw_val = {zColor:newValue} ; y-axis
                        else: kw_val = {dummy:0}
                    endcase
                    if (not daveGrRef->set(_EXTRA=kw_val)) then return
                    goto, SKIPAXIS3
                endif
                if (not daveGrRef->set(color=newValue,position=datInd)) then return
                ;; if a symbol plot, modify the symbols too
                if (atomName eq 'SPLOT') then begin
                    objArr[nObj]->getProperty, symbol=symRef
                    symRef->setProperty, color=newValue
                endif
                SKIPAXIS3:
                self->noRenew
            endif
        endelse
        break
    end

    'FONT': begin
        validAtomNames = ['AXIS','LABEL'] ; ==> only atoms with name matching these will be affected
        objRefType = vartype(objRef) ; IDLgrModels will have multiple atoms
        if (objRefType eq 'IDLGRMODEL') then begin
            ;; loop through atoms in model and make changes
            objArr = objRef->get(/all, count=nObj)
            while (nObj gt 0) do begin
                nObj = nObj - 1
                objArr[nObj]->getProperty, name=atomName
                res = where(validAtomNames eq atomName,valid)
                if (valid) then begin
                    case atomName of
                        'AXIS': begin
                            objArr[nObj]->getProperty, title=titleRef, uvalue=atomUval
                            if (obj_valid(titleRef)) then begin
                                titleRef->GetProperty, font=fontRef
                                fontRef->GetProperty, name=curValue
                                tokens = strtok(curValue,'*',/extract) ; are there font modifiers present?
                                ntokens = n_elements(tokens)
                                if (ntokens gt 1) then $ ; include current font modifiers
                                  newValue = strjoin([newValue,tokens[1:ntokens-1]],'*',/single)
                                fontRef->setProperty, name=newValue
                                case atomUval.datInd of
                                    0: void = atomUval.objRef->set(xFontVal=newValue) ; x-axis
                                    1: void = atomUval.objRef->set(zFontVal=newValue) ; y-axis
                                    else:
                                endcase
                            endif
                        end
                        'LABEL': begin
                             objArr[nObj]->getProperty, font=fontRef, uvalue=atomUval
                             datInd = atomUval.datInd
                             daveGrRef = atomUval.objRef
                             fontRef->GetProperty, name=curValue
                             tokens = strtok(curValue,'*',/extract) ; are there font modifiers present?
                             ntokens = n_elements(tokens)
                             if (ntokens gt 1) then $ ; include current font modifiers
                               newValue = strjoin([newValue,tokens[1:ntokens-1]],'*',/single)
                             fontRef->setProperty, name=newValue
                             case datInd of
                                 -1: begin ; title
                                     if (not daveGrRef->get(title=title)) then return
                                     title.font = newValue
                                     if (not daveGrRef->set(title=title)) then return
                                 end
                                 else: begin ; misc label
                                     if (not daveGrRef->get(label=label)) then return
                                     label[datInd].font = newValue
                                     if (not daveGrRef->set(label=label)) then return
                                 end
                             endcase
                        end
                    endcase
                    self->noRenew
                endif
            endwhile
        endif 
        break
    end

    'PRECISION': begin
        validAtomNames = ['AXIS'] ; ==> only atoms with name matching these will be affected
        objRefType = vartype(objRef) ; IDLgrModels will have multiple atoms
        if (objRefType eq 'IDLGRMODEL') then begin
            ;; loop through atoms in model and make changes
            objArr = objRef->get(/all, count=nObj)
            while (nObj gt 0) do begin
                nObj = nObj - 1
                objArr[nObj]->getProperty, name=atomName
                res = where(validAtomNames eq atomName,valid)
                if (valid) then begin
                    objArr[nObj]->getProperty, uvalue=atomUval, range=curRange
                    objArr[nObj]->SetProperty, tickformat=getFormatCode(curRange[0],curRange[1],newValue)
                    case atomUval.datInd of
                        0: begin ; x-axis
                            void = atomUval.objRef->get(xMiscAttrib=miscAttribs)
                            miscAttribs.decimalPlaces = newValue
                            void = atomUval.objRef->set(xMiscAttrib=miscAttribs) 
                        end
                        1: begin ; y-axis
                            void = atomUval.objRef->get(zMiscAttrib=miscAttribs)
                            miscAttribs.decimalPlaces = newValue
                            void = atomUval.objRef->set(zMiscAttrib=miscAttribs) 
                        end
                        else:
                    endcase
                    self->noRenew
                endif
            endwhile
        endif 
        break
    end

    'TICKDIR': begin
        validAtomNames = ['AXIS'] ; ==> only atoms with name matching these will be affected
        objRefType = vartype(objRef) ; IDLgrModels will have multiple atoms
        if (objRefType eq 'IDLGRMODEL') then begin
            ;; loop through atoms in model and make changes
            objArr = objRef->get(/all, count=nObj)
            while (nObj gt 0) do begin
                nObj = nObj - 1
                objArr[nObj]->getProperty, name=atomName
                res = where(validAtomNames eq atomName,valid)
                if (valid) then begin
                    objArr[nObj]->getProperty, uvalue=atomUval
                    objArr[nObj]->setProperty, tickDir=newValue
                    case atomUval.datInd of
                        0: begin ; x-axis
                            void = atomUval.objRef->get(xMiscAttrib=miscAttribs)
                            miscAttribs.tickDir = newValue
                            void = atomUval.objRef->set(xMiscAttrib=miscAttribs) 
                        end
                        1: begin ; y-axis
                            void = atomUval.objRef->get(zMiscAttrib=miscAttribs)
                            miscAttribs.tickDir = newValue
                            void = atomUval.objRef->set(zMiscAttrib=miscAttribs) 
                        end
                        else:
                    endcase
                    self->noRenew
                endif
            endwhile
        endif 
        break
    end

    'MINOR': begin
        validAtomNames = ['AXIS'] ; ==> only atoms with name matching these will be affected
        objRefType = vartype(objRef) ; IDLgrModels will have multiple atoms
        if (objRefType eq 'IDLGRMODEL') then begin
            ;; loop through atoms in model and make changes
            objArr = objRef->get(/all, count=nObj)
            while (nObj gt 0) do begin
                nObj = nObj - 1
                objArr[nObj]->getProperty, name=atomName
                res = where(validAtomNames eq atomName,valid)
                if (valid) then begin
                    objArr[nObj]->getProperty, uvalue=atomUval
                    objArr[nObj]->setProperty, minor=newValue
                    case atomUval.datInd of
                        0: begin ; x-axis
                            void = atomUval.objRef->get(xMiscAttrib=miscAttribs)
                            miscAttribs.minorTicks = newValue
                            void = atomUval.objRef->set(xMiscAttrib=miscAttribs) 
                        end
                        1: begin ; y-axis
                            void = atomUval.objRef->get(zMiscAttrib=miscAttribs)
                            miscAttribs.minorTicks = newValue
                            void = atomUval.objRef->set(zMiscAttrib=miscAttribs) 
                        end
                        else:
                    endcase
                    self->noRenew
                endif
            endwhile
        endif 
        break
    end

    'FONTSZ': begin
        validAtomNames = ['AXIS','LABEL'] ; ==> only atoms with name matching these will be affected
        objRefType = vartype(objRef) ; IDLgrModels will have multiple atoms
        if (objRefType eq 'IDLGRMODEL') then begin
            ;; loop through atoms in model and make changes
            objArr = objRef->get(/all, count=nObj)
            while (nObj gt 0) do begin
                nObj = nObj - 1
                objArr[nObj]->getProperty, name=atomName
                res = where(validAtomNames eq atomName,valid)
                if (valid) then begin
                    case atomName of
                        'AXIS': begin
                            objArr[nObj]->getProperty, title=titleRef, uvalue=atomUval, ticktext=ttRef
                            datInd = atomUval.datInd
                            case datInd of
                                0: kw_val = {xFontSize:newValue} ; x-axis
                                1: kw_val = {zFontSize:newValue} ; y-axis
                                else: kw_val = {dummy:0}
                            endcase
                            if (obj_valid(titleRef)) then begin
                                titleRef->getProperty, font=fontRef
                                fontRef->setProperty, size=newValue
                                ;ttRef->setProperty, size=newValue
                                daveGrRef = atomUval.objRef
                                if (not daveGrRef->set(_EXTRA=kw_val)) then return
                            endif
                        end
                        'LABEL': begin
                            objArr[nObj]->getProperty, font=fontRef, uvalue=atomUval
                            datInd = atomUval.datInd
                            daveGrRef = atomUval.objRef
                            fontRef->setProperty, size=newValue
                            case datInd of
                                -1: begin ; title
                                    if (not daveGrRef->get(title=title)) then return
                                    title.fontsize = newValue
                                    if (not daveGrRef->set(title=title)) then return
                                end
                                else: begin ; misc label
                                    if (not daveGrRef->get(label=label)) then return
                                    label[datInd].fontsize = newValue
                                    if (not daveGrRef->set(label=label)) then return
                                end
                            endcase
                        end
                    endcase
                    self->noRenew
                endif
            endwhile
        endif else begin
            objRef->getProperty, name=atomName
            res = where(validAtomNames eq atomName,valid)
            if (valid) then begin
                objRef->getProperty, title=titleRef
                if (obj_valid(titleRef)) then begin
                    titleRef->getProperty, font=fontRef
                    fontRef->setProperty, size=newValue
                endif
                self->noRenew
            endif
        endelse

        break
    end


    'EDITLABEL' : begin
        validAtomNames = ['LABEL'] ; ==> only atoms with name matching these will be affected
        objRefType = vartype(objRef) ; IDLgrModels will have multiple atoms
        if (objRefType eq 'IDLGRMODEL') then begin
            ;; loop through atoms in model and make changes
            objArr = objRef->get(/all, count=nObj)
            while (nObj gt 0) do begin
                nObj = nObj - 1
                objArr[nObj]->getProperty, name=atomName
                res = where(validAtomNames eq atomName,valid)
                if (valid) then begin
                    objArr[nObj]->getProperty, uvalue=atomUval
                    daveGrRef = atomUval.objRef
                    datInd = atomUval.datInd
                    DB_TxtLabel, datInd,objArr[nObj],daveGrRef,self,group_leader=event.top
                    self->noRenew
                endif
            endwhile
        endif
        break
    end

    'REMOVELABEL' : begin
        validAtomNames = ['LABEL'] ; ==> only atoms with name matching these will be affected
        objRefType = vartype(objRef) ; IDLgrModels will have multiple atoms
        if (objRefType eq 'IDLGRMODEL') then begin
            ;; loop through atoms in model and make changes
            objArr = objRef->get(/all, count=nObj)
            while (nObj gt 0) do begin
                nObj = nObj - 1
                objArr[nObj]->getProperty, name=atomName
                res = where(validAtomNames eq atomName,valid)
                if (valid) then begin
                    objArr[nObj]->getProperty, uvalue=atomUval
                    daveGrRef = atomUval.objRef
                    datInd = atomUval.datInd

                    if (~daveGrRef->get(label=labelArray,nlabel=nLabel)) then return
                    if (datInd eq -1) then begin
                        message = 'Cannot delete the main title!'
                        message = [message,"Uncheck the 'Display Title' option instead"]
                        void = dialog_message(message,dialog_parent=event.top)
                        return
                    endif
                    if ((datInd lt 0) || (datInd ge nlabel)) then return ; shouldn't happen but check anyway
                    if (datInd eq nLabel - 1) then begin
                        ;; Removing the last valid entry, simply
                        ;; decreement the nos of labels by 1
                        if (~daveGrRef->set(nlabel=nLabel-1)) then return
                    endif else begin
                        ;; Overwrite the entry to be removed by shifting
                        ;; valid ones down by an index
                        ind2Bmoved = indgen(nlabel-1-datind) + (datind + 1)
                        labelArray[ind2Bmoved-1] = labelArray[ind2Bmoved]
                        if (~daveGrRef->set(label=labelArray[0:nLabel-2])) then return
                    endelse
                    self->Renew
                endif
            endwhile
        endif
        break
    end

    'EDITAXIS' : begin
        validAtomNames = ['AXIS'] ; ==> only atoms with name matching these will be affected
        objRefType = vartype(objRef) ; IDLgrModels will have multiple atoms
        if (objRefType eq 'IDLGRMODEL') then begin
            ;; loop through atoms in model and make changes
            objArr = objRef->get(/all, count=nObj)
            while (nObj gt 0) do begin
                nObj = nObj - 1
                objArr[nObj]->getProperty, name=atomName
                res = where(validAtomNames eq atomName,valid)
                if (valid) then begin
                    objArr[nObj]->getProperty, uvalue=atomUval, notext=emptyTitle
                    if (not emptyTitle) then begin
                        daveGrRef = atomUval.objRef
                        datInd = atomUval.datInd
                        ;datInd = (atomUval.datInd eq 0)? atomUval.datInd : 2 ; for 1D, zaxis == yaxis!!!
                        DB_AxisProp, datInd,objArr[nObj],daveGrRef,self,group_leader=event.top
                        self->noRenew
                    endif
                endif
            endwhile
        endif
        break
    end


    'LOGSCALE' : begin
        validAtomNames = ['AXIS'] ; ==> only atoms with name matching these will be affected
        objRefType = vartype(objRef) ; IDLgrModels will have multiple atoms
        if (objRefType eq 'IDLGRMODEL') then begin
            ;; loop through atoms in model and make changes
            objArr = objRef->get(/all, count=nObj)
            while (nObj gt 0) do begin
                nObj = nObj - 1
                objArr[nObj]->getProperty, name=atomName
                res = where(validAtomNames eq atomName,valid)
                if (valid) then begin
                    objArr[nObj]->getProperty, uvalue=atomUval, notext=emptyTitle
                    if (not emptyTitle) then begin
                        daveGrRef = atomUval.objRef
                        case (atomUval.datInd) of
                            0: void=daveGrRef->get(xMiscAttribs=axisAttribs,xmax=amax)
                            1: void=daveGrRef->get(zMiscAttribs=axisAttribs,zmax=amax)
                        endcase
                        if (amax le 0.0) then begin
                            message = 'Cannot set log scale - whole range is negative!'
                            res = dialog_message(message,dialog_parent=self.tlb)
                            return
                        endif
                        axisAttribs.logFlag = 1 - axisAttribs.logFlag
                        case (atomUval.datInd) of
                            0: begin
                                void=daveGrRef->set(xMiscAttribs=axisAttribs)
                                if (self.xrangeFlag) then begin
                                    if (axisAttribs.logFlag) then begin
                                        if (self.xrange[0] le 0.0) then self.xrange[0] = 0.0001*amax
                                        self.xrange = alog10(self.xrange) 
                                    endif else self.xrange = 10.0^(self.xrange)
                                endif
                            end
                            1: begin 
                                void=daveGrRef->set(zMiscAttribs=axisAttribs)
                                if (self.yrangeFlag) then begin
                                    if (axisAttribs.logFlag) then begin
                                        if (self.yrange[0] le 0.0) then self.yrange[0] = 0.0001*amax
                                        self.yrange = alog10(self.yrange) 
                                    endif else self.yrange = 10.0^(self.yrange)
                                endif
                            end
                        endcase
                        self->Renew
                    endif
                endif
            endwhile
        endif
        break
    end

    'EDITLEGEND' : begin
        if (vartype(objRef) eq 'IDLGRLEGEND') then begin
            DB_legend, objRef,self,group_leader=event.top
            self->noRenew
        endif
        break
    end


    'SWITCHDISPMODE': begin
        validAtomNames = ['LPLOT','SPLOT'] ; ==> only atoms with name matching these will be affected
        objRefType = vartype(objRef) ; IDLgrModels will have multiple atoms
        if (objRefType eq 'IDLGRMODEL') then begin
            ;; loop through atoms in model and make changes
            objArr = objRef->get(/all, count=nObj)
            while (nObj gt 0) do begin
                nObj = nObj - 1
                objArr[nObj]->getProperty, name=atomName
                res = where(validAtomNames eq atomName,valid)
                if (valid) then begin
                    objArr[nObj]->getProperty, uvalue=atomUval
                    daveGrRef = atomUval.objRef
                    datInd = atomUval.datInd
                    if (not daveGrRef->set(lineSymFlag=newValue,position=datInd)) then return
                    self->renew ; reconstruct scene
                    break
                endif
            endwhile
        endif else begin
            objRef->getProperty, name=atomName
            res = where(validAtomNames eq atomName,valid)
            if (valid) then begin
                objRef->getProperty, uvalue=atomUval
                daveGrRef = atomUval.objRef
                datInd = atomUval.datInd
                if (not daveGrRef->set(lineSymFlag=newValue,position=datInd)) then return
                self->renew     ; reconstruct scene
            endif
        endelse                 ;end
        break
    end

    else: begin
        break
    end

endswitch

;(self.o_registry)->refresh      ;db_dispData, sPtr
print, 'renewscene = ',self.renewScene
self->refresh      ; refresh (NOT through registry in db_container!)


return



end





;-------------------------------------------------------------------------------



;===============================================================================
; DB_Display1D::TodoEvent
;
; PURPOSE:
;   Private dummy event handler method
;
; PARAMETERS
;   event [in;req] - the event structure
;
; KEYWORDS:
;
pro DB_Display1D::TodoEvent, event

uname = widget_info(event.id,/uname)
print,'----------------------------------------------------------------'
print,'Handler for "',uname,'" is not yet implimented...'
widget_control,event.id, get_uvalue=uvalue
if (n_elements(uvalue) gt 0) then print, 'Uvalue: ',uvalue
help,event,/struct

end
;-------------------------------------------------------------------------------



;===============================================================================
; DB_Display1D::DispConSenMenu
;
; PURPOSE:
;   Display context-sentive dialog menus when requested
;
; PARAMETERS
;   event [in;req] - the event structure
;
; KEYWORDS:
;
pro DB_Display1D::DispConSenMenu, event

objArr = (self.oScene)->get(/all, count=nObj) ; get nos of objects in scene
while (nObj gt 0) do begin      ; loop through and
    nObj = nObj - 1
    if (vartype(objArr[nObj]) ne 'IDLGRVIEW') then continue
    oView = objArr[nObj]
    dims = [10,10]
    compArr = (self.oDest)->Select(oView,[event.x, event.y],dimensions = dims) ; grab model/atoms in view at mouse loc
    if (obj_valid(compArr[0]) ne 1) then continue
    count = n_elements(compArr)
    missionNotAccomplished = 1  ; don't want to display MORE THAN ONE CSM
    while ((count gt 0) && (missionNotAccomplished)) do begin
        count = count - 1
        ;; Analyse components
        (compArr[count])->getProperty, name=name
        self.csmObjRef = compArr[count]
        case name of
            'LMODEL': begin
                csm = widget_info(event.top,find_by_uname='CSBLINE')
                widget_displaycontextmenu, event.id, event.x, event.y, csm
                missionNotAccomplished = 0
            end
            'SMODEL': begin
                csm = widget_info(event.top,find_by_uname='CSBSYMB')
                widget_displaycontextmenu, event.id, event.x, event.y, csm
                missionNotAccomplished = 0
            end
            'LSMODEL': begin
                csm = widget_info(event.top,find_by_uname='CSBLSYM')
                widget_displaycontextmenu, event.id, event.x, event.y, csm
                missionNotAccomplished = 0
            end
            'AMODEL': begin
                csm = widget_info(event.top,find_by_uname='CSBAXES')
                wid = widget_info(csm, find_by_uname='LOGSCALE')
                objArr = self.csmObjRef->get(/all, count=nObj) ; get all atoms in model container
                objArr[0]->getProperty, uvalue=atomUval ; first one should be the axis - get its uvalue
                case (atomUval.datInd) of
                    0: void = (atomUval.objRef)->get(xMiscAttribs=axisAttribs)
                    1: void = (atomUval.objRef)->get(zMiscAttribs=axisAttribs) 
                endcase
                txt = (axisAttribs.logFlag eq 1)? 'Linear Scale' : 'Log Scale'
                widget_control, wid, set_value=txt
                widget_displaycontextmenu, event.id, event.x, event.y, csm

                ;csm = widget_info(event.top,find_by_uname='CSBAXES')
                ;widget_displaycontextmenu, event.id, event.x, event.y, csm
                missionNotAccomplished = 0
            end
            'LABMODEL': begin
                csm = widget_info(event.top,find_by_uname='CSBLABEL')
                widget_displaycontextmenu, event.id, event.x, event.y, csm
                missionNotAccomplished = 0
            end
            'LEGEND': begin
                csm = widget_info(event.top,find_by_uname='CSBLEGEND')
                widget_displaycontextmenu, event.id, event.x, event.y, csm
                missionNotAccomplished = 0
            end

            else:
        endcase
    endwhile
endwhile


end
;-------------------------------------------------------------------------------



;===============================================================================
; DB_Display1D::AddText
;
; PURPOSE:
;   Add text annotation to the plot
;
; PARAMETERS
;   event [in;req] - the event structure
;
; KEYWORDS:
;
pro DB_Display1D::AddText, event, _EXTRA=etc

; Retrieve required objects from the IDL object graphics heirarchy
oView = (self.oScene)->get(/all,isa='IDLgrView')
oMiscCont = (self.oScene)->get(isa='IDL_Container')
oModel = oView->getByName('DG1DMODEL')

; Get the viewplane rectangle
oView->getProperty, viewplane_rect=vprect

; Get nos of existing labels
if (not (self.oDaveGr)->get(nlabel=nlabel,label=labelArray)) then return

; New Label
newLabel = {annotate}
newLabel.text = 'New text'
newLabel.position = [0.1,0.05,0.0]
newLabel.alignment = 0.5
newLabel.color = [0,0,0]
newLabel.font = 'HELVETICA'
newLabel.fontsize = 10

; Create graphic atom using label
oLabelModel = obj_new('IDLgrModel',name='LABMODEL',/select_target) ; make it selectable
oModel->add, oLabelModel
xs = scale_coord([0,1],[vprect[0],vprect[0]+vprect[2]])
ys = scale_coord([0,1],[vprect[1],vprect[1]+vprect[3]])
oLabelFont = obj_new('IDLgrFont',name=newLabel.font,size=newLabel.fontsize)
oMiscCont->add,oLabelFont       ; so it can be properly cleaned up
oLabel = obj_new('IDLgrText',newLabel.text,name='LABEL',font=oLabelFont,/enable_formatting $
                 ,location=newLabel.position,alignment=newLabel.alignment,color=newLabel.color $
                 ,xcoord_conv=xs,ycoord_conv=ys,uvalue={objRef:(self.oDaveGr),datInd:nlabel})
oLabelModel->add,oLabel

; Add the new label to the DaveGr object
labelArray = (nlabel gt 0)? [labelArray,newLabel] : newLabel
void = (self.oDaveGr)->set(label=labelArray)

print,vprect

; Refresh display
self->noRenew
self->refresh

end
;-------------------------------------------------------------------------------



;===============================================================================
; DB_Display1D::Print
;
; PURPOSE:
;   Print current graphics window to printer or export it to various
;   image formats + postscript.
;
; PARAMETERS
;   event [in;req] - the event structure
;
; KEYWORDS:
;
pro DB_Display1D::Print, event, _EXTRA=etc
uname = widget_info(event.id,/uname)

switch uname of
    'TIFF':
    'BMP':
    'PNG':
    'JPEG': begin
        ;; force a window refresh before capturing image
        self.renewScene = 0
        self->refresh
        ;; capture destination window contents
        oImage = (self.oDest)->read()
        oImage->getProperty, data=image
        obj_destroy, oImage
        title = 'DATABROWSER - Export '+uname+' Image'
        defFile = 'output.'+strlowcase(uname)
        ;print,self.workDir
        result = dialog_write_image(image,dialog_parent=event.top,path=self.workDir, $
                                    title=title,/warn_exist,type=uname,file=defFile)
        break
    end
    'POST': begin
        defFile = 'output.ps'
        title = 'DATABROWSER - Export Postscript'
        options = PSConfig(cancel=cancelled,group_leader=event.top,directory=self.workDir, $
                              filename=defFile)
        if (not cancelled) then begin
            if (options.landscape eq 1) then begin
                yoff = options.xoffset
                xoff = options.yoffset - options.xsize
            endif else begin
                xoff = options.xoffset
                yoff = options.yoffset
            endelse
            paperxsize = 2*xoff + options.xsize
            paperysize = 2*yoff + options.ysize
            units = (options.inches eq 1)? 1 : 2

            ;; Create a clipboard
            oClip = obj_new('IDLgrClipboard',units=units,dimensions=[paperxsize,paperysize])

            ;; Get the scene/view that is being displayed.
            oView = (self.oScene)->get(/all,isa='IDLgrView')
            oView->getProperty, location=winLoc,dimensions=winDim,units=winUnits
            oView->setProperty, units=units, $
                                dimensions=[options.xsize,options.ysize], $
                                location=[xoff,yoff]

            ;; Render the scene to the clipboard
            oClip->draw, self.oScene, file=options.filename,/postscript,/vector

            ;; Cleapup and revert view to previous settings
            obj_destroy, oClip
            oView->setProperty, location=winLoc,dimensions=winDim,units=winUnits
        endif

        break
    end
    'PRINT': begin
        oPrint = obj_new('IDLgrPrinter')
        title = 'DATABROWSER - Printer Setup'
        valid = dialog_printersetup(oPrint,dialog_parent=event.top,title=title)
        if (valid) then begin
            oPrint->draw, (self.oScene), vector=1
            oPrint->newDocument ; forces current document to be sent to printer
        endif
        obj_destroy, oPrint
        break
    end
endswitch


end
;-------------------------------------------------------------------------------



;===============================================================================
; DB_Display1D::DrawEvent
;
; PURPOSE:
;   Handle events from the graphics window
;
; PARAMETERS
;   event [in;req] - the event structure
;
; KEYWORDS:
;
pro DB_Display1D::DrawEvent, event

uname = widget_info(event.id,/uname)

possibleEventTypes = ['DOWN','UP','MOTION','SCROLL','EXPOSE']
eventType = possibleEventTypes[event.type]

case eventType of
    'DOWN': begin               ; Button press event
        self.renewScene = 0     ; ==> don't re-construct Scene
        if (event.press eq 4) then self->dispConSenMenu, event ; Right Mouse button was pressed; display Con Sen Menu
        if (event.press eq 1) then begin ;Left mouse button was pressed; zoomin functionality is required

            self.rbStart = [event.x,event.y] ; register the mouse location
            widget_control, event.id, draw_motion_events=1 ; switch on motion events

            ;; get properties of view which contains current plot
            objArr = (self.oScene)->get(/all, count=nObj)
            while (nObj gt 0) do begin
                nObj = nObj - 1
                if (vartype(objArr[nObj]) ne 'IDLGRVIEW') then continue
                (self.oDest)->getProperty, dimensions = winDims ; dimensions of destination window
                (objArr[nObj])->getProperty, all=allViewProps ; properties of view gr object
                ;; create a rubberband obj gr atom
                rbandColor = 255 - allViewProps.color ; set rub band color to reverse of view color
                vprect = allViewProps.viewplane_rect ; dimensions of viewplane
                vprect[2] = vprect[2]/float(winDims[0])
                vprect[3] = vprect[3]/float(winDims[1])
                self.rbScale = vprect
                rbandModel = obj_new('IDLgrModel',name='RBANDMODEL')
                self.oRband = obj_new('IDLgrPolyline',name='RBAND',color=rbandColor)
                (objArr[nObj])->add, rbandModel
                rbandModel->add, self.oRband
                nObj = 0
            endwhile
        endif
    end
    'UP': begin                 ; Button release event
        if (event.release eq 1) then begin ; Left mouse button released
            ;; cleanup rubberband obj gr model and atom
            if (obj_valid(self.oRband)) then begin
                (self.oRband)->getProperty, parent=rbandModel
                rbandModel->getProperty, parent=oView
                oView->remove, rbandModel
                obj_destroy, rbandModel ; should destroy rub band atom as well
            endif

            widget_control, event.id, draw_motion_events=0 ; switch off motion events
            widget_Control, event.id, /clear_events ; clear any motion events that may have occurred.
                                ;self.LMBisDown = 0

            if (not self.mouseMoved) then break ; Exit now if releasing from same spot that mouse was pressed

            ;; rubberband box is new zoom region
            self.xrangeFlag = 1
            xmin = self.rbStart[0]*self.rbScale[2] + self.rbScale[0]
            xmax = event.x*self.rbScale[2] + self.rbScale[0]
            self.xrange = (xmax gt xmin)? [xmin,xmax] : [xmax,xmin]
            self.yrangeFlag = 1
            ymin = self.rbStart[1]*self.rbScale[3] + self.rbScale[1]
            ymax = event.y*self.rbScale[3] + self.rbScale[1]
            self.yrange = (ymax gt ymin)? [ymin,ymax] : [ymax,ymin]

                                ;self.renewScene = 0 ; ==> don't re-construct Scene
            self->refresh       ; refresh plot scene via self

        endif
    end
    'MOTION': begin             ; Motion event
        self.mouseMoved = 1     ; register mouse move

        ;; determine rubber band box dimensions and modify the rub
        ;; band obj gr atom
        start = self.rbStart
        boxVertices = fltarr(2,5)
        boxVertices[0,*] = [start[0],event.x,event.x,start[0],start[0]]*self.rbScale[2] + self.rbScale[0]
        boxVertices[1,*] = [start[1],start[1],event.y,event.y,start[1]]*self.rbScale[3] + self.rbScale[1]
        (self.oRband)->setProperty, data=boxVertices

                                ;(self.oRband)->getProperty, parent=rbandModel
                                ;rbandModel->getProperty, parent=rbandView
        self->noRenew           ; ==> don't re-construct Scene
        self->refresh           ; refresh plot scene via self
                                ;(self.oDest)->draw, rbandView ; draw rubber band
    end
    'SCROLL':
    'EXPOSE': begin             ; Expose event, so repaint window
                                ;print,'Exposed Event generated...'
        self->noRenew           ; ==> don't re-construct Scene
        if (!debug) then print, 'EXPOSED EVENT: renescene = ',self.renewScene
        self->refresh           ; refresh via self
    end
endcase


end
;-------------------------------------------------------------------------------



;===============================================================================
; DB_Display1D::ExitEvent
;
; PURPOSE:
;   Exit application
;
; PARAMETERS
;   event [in;req] - the event structure
;
; KEYWORDS:
;
pro DB_Display1D::ExitEvent, event

widget_control,event.top,/destroy

end
;-------------------------------------------------------------------------------



;===============================================================================
; DB_Display1D::Displayevent
;
; PURPOSE:
;   Refresh graphics window
;
; PARAMETERS
;   event [in;req] - the event structure
;
; KEYWORDS:
;
pro DB_Display1D::DisplayEvent, event

self->refresh      ; refresh via self

end
;-------------------------------------------------------------------------------



;===============================================================================
; DB_Display1D::NoRenew
;
; PURPOSE:
;   Switch off reconstruction of entire object graphic scene
;
; PARAMETERS
;   event [in;req] - the event structure
;
; KEYWORDS:
;
pro DB_Display1D::NoRenew, event

self.renewScene = 0

end
;-------------------------------------------------------------------------------



;===============================================================================
; DB_Display1D::Renew
;
; PURPOSE:
;   Switch on reconstruction of entire object graphic scene
;
; PARAMETERS
;   event [in;req] - the event structure
;
; KEYWORDS:
;
pro DB_Display1D::Renew, event

self.renewScene = 1

end
;-------------------------------------------------------------------------------



;===============================================================================
; DB_Display1D::GetTLB
;
; PURPOSE:
;   Get the top level base id.
;
; PARAMETERS
;
; KEYWORDS:
;
; RETURN VALUE:
;   the tlb
;
function DB_Display1D::GetTLB

return, self.TLB

end
;-------------------------------------------------------------------------------



;===============================================================================
; DB_Display1D::GetScene
;
; PURPOSE:
;   Get the Scene component of the Graphics Object hierarchy.
;
; PARAMETERS
;   event [in;req] - the event structure
;
; KEYWORDS:
;
; RETURN VALUE:
;   the scene object reference.
;
function DB_Display1D::GetScene, event

return, self.oScene

end
;-------------------------------------------------------------------------------



;===============================================================================
; DB_Display1D::GetWindow
;
; PURPOSE:
;   Get the Window (destination) component of the Graphics Object
;   hierarchy.
;
; PARAMETERS
;   event [in;req] - the event structure
;
; KEYWORDS:
;
; RETURN VALUE:
;   the window object reference.
;

;===============================================================================
; Get the Destination object
function DB_Display1D::GetWindow, event

return, self.oDest

end
;-------------------------------------------------------------------------------



;===============================================================================
; DB_Display1D::GetView
;
; PURPOSE:
;   Get the View component of the Graphics Object hierarchy.
;
; PARAMETERS
;   event [in;req] - the event structure
;
; KEYWORDS:
;
; RETURN VALUE:
;   the scene object reference.
;
function DB_Display1D::GetView, event

return, (self.oScene)->get(/all,isa='IDLgrView')

end
;-------------------------------------------------------------------------------



;===============================================================================
; DB_Display1D::DefLimEvent
;
; PURPOSE:
;   Reset axes limits to their default values.
;
; PARAMETERS
;   event [in;req] - the event structure
;
; KEYWORDS:
;
pro DB_Display1D::DefLimEvent, event

self.xrangeFlag = 0
self.yrangeFlag = 0
self->refresh                   ; refresh via self

end
;-------------------------------------------------------------------------------



;===============================================================================
; DB_Display1D::DispTypeEvent
;
; PURPOSE:
;   Toggle data display between points and histograms
;
; PARAMETERS
;   event [in;req] - the event structure
;
; KEYWORDS:
;
pro DB_Display1D::DispTypeEvent, event

; switch off some items in the CSBLINE con. sen. menu
widget_control, self.csbline_symID, sensitive=self.dispType
widget_control, self.csbline_sylID, sensitive=self.dispType

; swap display type
self.dispType = self.dispType xor 1 ; swap setting (0 <--> 1)

;endcase

self->refresh                   ; refresh via registry

end
;-------------------------------------------------------------------------------



;===============================================================================
; DB_Display1D::DispErrorEvent
;
; PURPOSE:
;   Toggle error bars on/off
;
; PARAMETERS
;   event [in;req] - the event structure
;
; KEYWORDS:
;
pro DB_Display1D::DispErrorEvent, event

self.dispError = self.dispError xor 1 ; swap setting (0 <--> 1)

self->refresh                   ; refresh via self

end
;-------------------------------------------------------------------------------



;===============================================================================
; DB_Display1D::DispLegendEvent
;
; PURPOSE:
;   Toggle legend on/off
;
; PARAMETERS
;   event [in;req] - the event structure
;
; KEYWORDS:
;
pro DB_Display1D::DispLegendEvent, event

if (not (self.oDaveGr)->get(legend=legend)) then return
legend.hideFlag = 1 - legend.hideFlag ; swap setting (0 <--> 1)
if (not (self.oDaveGr)->set(legend=legend)) then return

self->refresh                   ; direct refresh (not via registry)

end
;-------------------------------------------------------------------------------



;===============================================================================
; DB_Display1D::DispTitleEvent
;
; PURPOSE:
;   Toggle display of title on/off
;
; PARAMETERS
;   event [in;req] - the event structure
;
; KEYWORDS:
;
pro DB_Display1D::DispTitleEvent, event

self.dispTitle = 1 - self.dispTitle ; swap setting (0 <--> 1)

self->refresh                   ;  direct refresh (not via registry)

end
;-------------------------------------------------------------------------------



;===============================================================================
; DB_Display1D::TlbEvent
;
; PURPOSE:
;   Handle TLB events (mainly resize events)
;
; PARAMETERS
;   event [in;req] - the event structure
;
; KEYWORDS:
;
pro DB_Display1D::TlbEvent, event

if dave_set_focus(event) then return

res = widget_info(event.top,/geometry)
new_x = event.x - self.dialog_x - 2*res.xpad
new_y = event.y - 2*res.ypad
new_x = new_x > self.min_draw_x
new_y = new_y > self.min_draw_y
(self.oDest)->setProperty, dimensions=[new_x,new_y]
(self.oDest)->getProperty, dimensions=dim
self.winDim = dim

;print,'Refreshing b/c of resize event...'
self->refresh                   ; refresh via self

end
;-------------------------------------------------------------------------------



;===============================================================================
; DB_Display1D_Event
;
; PURPOSE:
;   Main conventional event handler for all events originating from
;   the main UI of the application.
;
; PARAMETERS
;   event [in;req] - the event structure
;
; KEYWORDS:
;
pro DB_Display1D_Event, event
;if dave_set_focus(event) then return

; Basic error Handler
if (n_elements(!debug) && (!debug eq 0)) then begin
    catch, catchError
    if (catchError ne 0) then begin
        ;;print, 'Error handled!'
        eTitle = 'Display1D: Error encountered'
        eMsg = 'An error or unusual condition was encountered!'
        eMsg = [eMsg,'Please, report the following to the DAVE team:']
        eMsg = [eMsg,!error_state.msg]
;    eMsg = [eMsg,'Function/module name: calledfunc()',!error_state.msg]
        void = dialog_message(/error,eMsg,title=eTitle,dialog_parent=event.top)
        catch, /cancel
        return
    endif
endif

; Retrieve the command structure embedded in the uvalue of the
; widget. The command structure is stored in the uvalue of either
; event.id or evend.handler
widget_control, event.id, get_uvalue = cmd

childID = event.id
while (vartype(cmd) ne 'DB_DISPLAY1D_CMD') do begin
    parentID = widget_info(childID,/parent)
    if (parentID eq 0) then break
    widget_control, parentID, get_uvalue = cmd
    childID = parentID
endwhile


if (vartype(cmd) eq 'DB_DISPLAY1D_CMD') then $
   call_method, cmd.method, cmd.object, event

end
;-------------------------------------------------------------------------------



;===============================================================================
; DB_Display1D_Cleanup
;
; PURPOSE:
;   Conventional cleanup procedure called when the tlb for this application is
;   destroyed.
;
; PARAMETERS
;   tlb [in;req] - the widget id that is to be destroyed
;
; KEYWORDS:
;
pro DB_Display1D_Cleanup, tlb
widget_control, tlb, get_uvalue = cmd
; get the Widget Object's reference and destroy it
selfObject = cmd.object
obj_destroy, selfObject

end
;-------------------------------------------------------------------------------



;===============================================================================
; DB_Display1D::Init
;
; PURPOSE:
;   Object initialization method. Builds the main dialog.
;
; PARAMETERS
;
; KEYWORDS:
;   group_leader [in] - the ID of the parent widget from which this
;                       app was launched.
;
;   objRef [in;req] - the DaveGr1D object reference(s) to be
;                     displayed.
;
;   workDir [in] - user's working directory setting from DAVE
;
; RETURN VALUE
;   1 - if sucessful
;   0 - failure
;
function DB_Display1D::Init, group_leader=group_leader, objGrRef=oDaveGr, workDir=workDir

;
device, get_decomposed = old_dec
self.old_dec = old_dec
;device, decomposed=1

; create a structure to specify methods that should act as event
; handlers for widgets defined in DB_Display1D
cmdStr = {DB_DISPLAY1D_CMD, $
          object:self, $ ; reference to the widget object generating events
          method:'' $         ; the method that should handle the event
          ;parPtr:ptr_new() $  ; extra parameters to be passed to the method
         }



; Various tooltips
deTooltip = 'Togle errorbars on/off.'
pmTooltip = 'Switch plot mode. View data as points or histograms.'
refTooltip = 'Refresh the plot window'
resTooltip = 'Reset x,y-axis display limits to full range.'
exitTooltip = 'Close display window. Activate by R-clicking on plot item from main window'
ptTooltip = 'Modify plot type (as lines and/or symbols).'
lsTooltip = 'Modify plot linestyle.'
pthTooltip = 'Modify plot line thickness.'
symTooltip = 'Modify plot symbols.'
stTooltip = 'Modify symbol type.'
szTooltip = 'Modify symbol size.'
pcolTooltip = 'Modify plot color.'
acolTooltip = 'Modify axes color.'
atTooltip = 'Modify axis line thickness.'
addTextTip = "Add 'New Text' label to plot. Then right-click on it to edit/position!"

; define the top-level-base
cmdStr.method = 'tlbEvent'
if (n_elements(group_leader) eq 0) then begin
    group_leader=0L
    modal=0
    self.dispType = 0b
    usingPrevGuiSettings = 0b
    self.tlb = widget_base(/row,title=title,/align_right,/tlb_size_events,uname='TLB' $
                           ,uvalue=cmdStr,group_leader=group_leader,mbar=menubar)
endif else begin
    modal=1
    widget_control, group_leader, get_uvalue=sPtr

    ;; Get the DaveGr object to be viewed
    if (n_elements(oDaveGr) gt 0) then begin
        self.oDaveGr = oDaveGr
    endif else begin
        oSelCont = (*sPtr).sel_cont
        self.oDaveGr = oSelCont->get(position=0)
    endelse

    ;; Can't allow multiple views of the same DaveGr1D object so make
    ;; some checks now
    self.oActive1DCont = (*sPtr).o_active_gr1D_cont
    if ((self.oActive1DCont)->count() gt 0) then begin
        ;; Exit immediately if DaveGr object is already being viewed
        if ((self.oActive1DCont)->isContained(self.oDaveGr)) then return, 0
    endif
    ;; register DaveGr object
    (self.oActive1DCont)->add, self.oDaveGr

    ; Retrieve ptr to previous GUI/widget settings
    if (not (self.oDaveGr)->get(guiAttribsPtr=guiAttribsPtr)) then return, 0
    usingPrevGuiSettings = (n_elements(*guiAttribsPtr) gt 0)? 1b : 0b

    ;; Get the first dataset in the DaveGr1D object and determine the
    ;; x-axis datatype
    if (not (self.oDaveGr)->get(dataRef=dataRef, position=0)) then return, 0
    if (not dataRef->get(xtype=xtype)) then return, 0
    xtype = strmid(strupcase(xtype),0,4)
    self.dispType = (xtype eq 'HIST')? 1b : 0b ; if xtype is not set, use 'points'
    if (usingPrevGuiSettings) then begin
        self.dispType = (*guiAttribsPtr).dispType
        self.xrangeFlag = (*guiAttribsPtr).xrangeFlag
        self.yrangeFlag = (*guiAttribsPtr).yrangeFlag
        self.xrange = (*guiAttribsPtr).xrange
        self.yrange = (*guiAttribsPtr).yrange
    endif

    void = (self.oDaveGr)->get(nameTag=title)
    title = 'DATABROWSER - '+title
    self.o_registry = (*sPtr).o_registry ; get the object registry
    (self.o_registry)->add, self    ; and register
    ;self.tlb = widget_base(group_leader=group_leader,/row,title=title,modal=modal $
    ;                 ,/align_right,/tlb_size_events,uname='TLB',uvalue=cmdStr)
    self.tlb = widget_base(group_leader=group_leader,/row,title=title $
                     ,/align_right,/tlb_size_events,uname='TLB',uvalue=cmdStr,mbar=menubar)
endelse

; Get working directory setting
if (n_elements(workDir) le 0) then $
  cd, current=workDir
self.workDir = workDir

; File Menu
filem = widget_button(menubar,value='File',/menu)
cmdStr.method='print'
expm = widget_button(filem,value='Export image as',/menu)
void = widget_button(expm,value='Postscript',uname='POST',uvalue=cmdStr)
void = widget_button(expm,value='Jpeg',uname='JPEG',uvalue=cmdStr,/separator)
void = widget_button(expm,value='Png',uname='PNG',uvalue=cmdStr)
void = widget_button(expm,value='Bmp',uname='BMP',uvalue=cmdStr)
void = widget_button(expm,value='Tiff',uname='TIFF',uvalue=cmdStr)
void = widget_button(filem,value='Print',uname='PRINT',uvalue=cmdStr)
cmdStr.method = 'exitEvent'
void = widget_button(filem,value='Hide Window',/separator,uname='EXIT',uvalue=cmdStr)

; split TLB into:
;  1) an left pane for placing dialog buttons
;  2) a right pane for placing the draw window
cb1 = widget_base(self.tlb,/col)
cb2 = widget_base(self.tlb,/frame)

; Split the dialog base into several sections for grouping similar controls
cb11 = widget_base(cb1,/col,/align_center,/frame)
cb12 = widget_base(cb1,/col,/align_center,/frame)
cb13 = widget_base(cb1,/col,/align_center,/frame)
cb14 = widget_base(cb1,/col,/align_center)

; Now the buttons
;void = cw_bgroup(cb11,['Multiplot'],/col,/nonexclusive,frame=0,/return_index,uname='MULTIPLOT',set_value=[1])
;values=['Red','Green','Blue']
;void = widget_combobox(cb11,value=values,uname='DATASELECTION',sensitive=0)


plotTypes = ['Point Mode','Histogram Mode']
cmdStr.method = 'dispTypeEvent'
void = cw_bgroup(cb11,plotTypes,/col,/exclusive,/no_release,frame=0,set_value=self.dispType $
                 ,/return_index,uname='DISPTYPE',uvalue=cmdStr)

self.dispError = (usingPrevGuiSettings)? (*guiAttribsPtr).dispError : 1 ; default is yes
cmdStr.method = 'dispErrorEvent'
void = cw_bgroup(cb11,['Display Error'],/col,/nonexclusive,frame=0,/return_index,uname='DISPERROR' $
                 ,set_value=self.dispError,uvalue=cmdStr)

res = widget_info(cb11,/geometry)
xsize = res.xsize - 2*res.xpad

self.dispTitle = (usingPrevGuiSettings)? (*guiAttribsPtr).dispTitle : 1
cmdStr.method = 'dispTitleEvent'
void = cw_bgroup(cb12,['Display Title'],/col,/nonexclusive,frame=0,/return_index,uname='DISPTITLE' $
                 ,set_value=self.dispTitle,uvalue=cmdStr)

cmdStr.method = 'dispLegendEvent'
void = (self.oDaveGr)->get(legend=legend)
void = cw_bgroup(cb12,['Display Legend'],/col,/nonexclusive,frame=0,/return_index,uname='DISPLEGEND' $
                 ,uvalue=cmdStr,set_value=(1 - legend.hideFlag))
cmdStr.method = 'addText'
void = widget_button(cb12,value='Add Text',uname='ADDTEXT',uvalue=cmdStr,tooltip=addTextTip)
cmdStr.method = 'todoEvent'
void = widget_button(cb12,value='Edit X-axis',uname='EXAXIS',xsize=xsize,uvalue=cmdStr,sensitive=0)
void = widget_button(cb12,value='Edit Y-axis',uname='EYAXIS',uvalue=cmdstr,sensitive=0)

cmdStr.method = 'displayEvent'
void = widget_button(cb13,value='Refresh',uname='DISPLAY',xsize=xsize,uvalue=cmdStr,tooltip=refTooltip)
cmdStr.method = 'defLimEvent'
void = widget_button(cb13,value='Reset Limits',uname='DEFLIM',xsize=xsize,uvalue=cmdStr,tooltip=resTooltip)
cmdStr.method = 'exitEvent'
void = widget_button(cb13,value='Hide Window',uname='EXIT',uvalue=cmdstr,tooltip=exitTooltip)

; store useful widget dimensions in self (widget object)
res = widget_info(cb1,/geometry)
self.dialog_x = res.xsize
dialog_y = res.ysize
self.min_draw_y = fix(dialog_y*1.10)
self.min_draw_x = fix(self.min_draw_y*1.333)
self.winDim = (usingPrevGuiSettings)? (*guiAttribsPtr).winDim : [self.min_draw_x,self.min_draw_y]
cmdStr.method = 'drawEvent'
drawID = widget_draw(cb2,xsize=self.winDim[0],ysize=self.winDim[1],graphics_level=2,uname='DRAW' $
                     ,/button_events,/expose_events,uvalue=cmdStr)

;----------------------------------------------------------------------------
; Create Context Sensitive menus for 'Line Plots'.
cmdStr.method = 'handleConSenMenuEvent'
csb1 = widget_base(self.tlb, /context_menu,uname='CSBLINE',uvalue=cmdStr)
lstyle = widget_button(csb1,value='Line Style',/menu,tooltip=lsTooltip)
thick = widget_button(csb1,value='Line Thickness',/menu,tooltip=ltTooltip)
color = widget_button(csb1,value='Line Color',/menu,tooltip=pcolTooltip)
ptm = widget_button(csb1,value='Plot Type',/menu,tooltip=ptTooltip)
void = widget_button(ptm,value='Lines',uvalue=0,uname='SWITCHDISPMODE',/checked_menu)
widget_control, void, set_button=1
self.csbline_symID = widget_button(ptm,value='Symbols',uvalue=1,uname='SWITCHDISPMODE',/checked_menu)
self.csbline_sylID = widget_button(ptm,value='Lines+Symbols',uvalue=2,uname='SWITCHDISPMODE',/checked_menu)

void = widget_button(lstyle,value='Solid',uname='LSTYLE',uvalue=0)
void = widget_button(lstyle,value='Dotted',uname='LSTYLE',uvalue=1)
void = widget_button(lstyle,value='Dashed',uname='LSTYLE',uvalue=2)
void = widget_button(lstyle,value='Dash Dot',uname='LSTYLE',uvalue=3)
void = widget_button(lstyle,value='Dash Dot Dot Dot',uname='LSTYLE',uvalue=4)
void = widget_button(lstyle,value='Long Dashes',uname='LSTYLE',uvalue=5)

void = widget_button(thick,value='1.00',uname='THICK',uvalue=1.00)
void = widget_button(thick,value='1.25',uname='THICK',uvalue=1.25)
void = widget_button(thick,value='1.50',uname='THICK',uvalue=1.50)
void = widget_button(thick,value='1.75',uname='THICK',uvalue=1.75)
void = widget_button(thick,value='2.00',uname='THICK',uvalue=2.00)
void = widget_button(thick,value='2.25',uname='THICK',uvalue=2.25)
void = widget_button(thick,value='2.50',uname='THICK',uvalue=2.50)
void = widget_button(thick,value='2.75',uname='THICK',uvalue=2.75)
void = widget_button(thick,value='3.00',uname='THICK',uvalue=3.00)
void = widget_button(thick,value='3.25',uname='THICK',uvalue=3.25)
void = widget_button(thick,value='3.50',uname='THICK',uvalue=3.50)
void = widget_button(thick,value='3.75',uname='THICK',uvalue=3.75)
void = widget_button(thick,value='4.00',uname='THICK',uvalue=4.00)
void = widget_button(thick,value='4.25',uname='THICK',uvalue=4.25)
void = widget_button(thick,value='4.50',uname='THICK',uvalue=4.50)
void = widget_button(thick,value='4.75',uname='THICK',uvalue=4.75)
void = widget_button(thick,value='5.00',uname='THICK',uvalue=5.00)


void = widget_button(color,value='Aqua',uname='COLOR',uvalue=[0,255,255])
void = widget_button(color,value='Black',uname='COLOR',uvalue=[0,0,0])
void = widget_button(color,value='Blue',uname='COLOR',uvalue=[0,0,255])
void = widget_button(color,value='Fuchsia',uname='COLOR',uvalue=[255,0,255])
void = widget_button(color,value='Gray',uname='COLOR',uvalue=[128,128,128])
void = widget_button(color,value='Green',uname='COLOR',uvalue=[0,128,0])
void = widget_button(color,value='Lime',uname='COLOR',uvalue=[0,255,0])
void = widget_button(color,value='Maroon',uname='COLOR',uvalue=[128,0,0])
void = widget_button(color,value='Navy',uname='COLOR',uvalue=[0,0,128])
void = widget_button(color,value='Olive',uname='COLOR',uvalue=[128,128,0])
void = widget_button(color,value='Purple',uname='COLOR',uvalue=[128,0,128])
void = widget_button(color,value='Red',uname='COLOR',uvalue=[255,0,0])
void = widget_button(color,value='Silver',uname='COLOR',uvalue=[192,192,192])
void = widget_button(color,value='Teal',uname='COLOR',uvalue=[0,128,128])
void = widget_button(color,value='White',uname='COLOR',uvalue=[255,255,255])
void = widget_button(color,value='Yellow',uname='COLOR',uvalue=[255,255,0])

;----------------------------------------------------------------------------
; Create Context Sensitive menus for 'Symbol Plots'
csb2 = widget_base(self.tlb, /context_menu,uname='CSBSYMB',uvalue=cmdStr)
stype = widget_button(csb2,value='Symbol Type',/menu,tooltip=stTooltip)
ssize = widget_button(csb2,value='Symbol Size',/menu,tooltip=szTooltip)
thick = widget_button(csb2,value='Line Thickness',/menu,tooltip=pthTooltip)
color = widget_button(csb2,value='Symbol Color',/menu,tooltip=pcolTooltip)
ptm = widget_button(csb2,value='Plot Type',/menu,tooltip=pttooltip)
void = widget_button(ptm,value='Lines',uvalue=0,uname='SWITCHDISPMODE',/checked_menu)
void = widget_button(ptm,value='Symbols',uvalue=1,uname='SWITCHDISPMODE',/checked_menu)
widget_control, void, set_button=1
void = widget_button(ptm,value='Lines+Symbols',uvalue=2,uname='SWITCHDISPMODE',/checked_menu)

void = widget_button(stype,value='Plus',uname='STYPE',uvalue=1)
void = widget_button(stype,value='Asterisk',uname='STYPE',uvalue=2)
void = widget_button(stype,value='Period',uname='STYPE',uvalue=3)
void = widget_button(stype,value='Diamond',uname='STYPE',uvalue=4)
void = widget_button(stype,value='Triangle',uname='STYPE',uvalue=5)
void = widget_button(stype,value='Square',uname='STYPE',uvalue=6)
void = widget_button(stype,value='Cross',uname='STYPE',uvalue=7)
void = widget_button(stype,value='Arrow Head (>)',uname='STYPE',uvalue=8)
void = widget_button(stype,value='Arrow Head (<)',uname='STYPE',uvalue=9)

void = widget_button(ssize,value='1.00',uname='SSIZE',uvalue=1.00)
void = widget_button(ssize,value='1.25',uname='SSIZE',uvalue=1.25)
void = widget_button(ssize,value='1.50',uname='SSIZE',uvalue=1.50)
void = widget_button(ssize,value='1.75',uname='SSIZE',uvalue=1.75)
void = widget_button(ssize,value='2.00',uname='SSIZE',uvalue=2.00)
void = widget_button(ssize,value='2.25',uname='SSIZE',uvalue=2.25)
void = widget_button(ssize,value='2.50',uname='SSIZE',uvalue=2.50)
void = widget_button(ssize,value='2.75',uname='SSIZE',uvalue=2.75)
void = widget_button(ssize,value='3.00',uname='SSIZE',uvalue=3.00)
void = widget_button(ssize,value='3.25',uname='SSIZE',uvalue=3.25)
void = widget_button(ssize,value='3.50',uname='SSIZE',uvalue=3.50)
void = widget_button(ssize,value='3.75',uname='SSIZE',uvalue=3.75)
void = widget_button(ssize,value='4.00',uname='SSIZE',uvalue=4.00)
void = widget_button(ssize,value='4.25',uname='SSIZE',uvalue=4.25)
void = widget_button(ssize,value='4.50',uname='SSIZE',uvalue=4.50)
void = widget_button(ssize,value='4.75',uname='SSIZE',uvalue=4.75)
void = widget_button(ssize,value='5.00',uname='SSIZE',uvalue=5.00)

void = widget_button(thick,value='1.00',uname='THICK',uvalue=1.00)
void = widget_button(thick,value='1.25',uname='THICK',uvalue=1.25)
void = widget_button(thick,value='1.50',uname='THICK',uvalue=1.50)
void = widget_button(thick,value='1.75',uname='THICK',uvalue=1.75)
void = widget_button(thick,value='2.00',uname='THICK',uvalue=2.00)
void = widget_button(thick,value='2.25',uname='THICK',uvalue=2.25)
void = widget_button(thick,value='2.50',uname='THICK',uvalue=2.50)
void = widget_button(thick,value='2.75',uname='THICK',uvalue=2.75)
void = widget_button(thick,value='3.00',uname='THICK',uvalue=3.00)
void = widget_button(thick,value='3.25',uname='THICK',uvalue=3.25)
void = widget_button(thick,value='3.50',uname='THICK',uvalue=3.50)
void = widget_button(thick,value='3.75',uname='THICK',uvalue=3.75)
void = widget_button(thick,value='4.00',uname='THICK',uvalue=4.00)
void = widget_button(thick,value='4.25',uname='THICK',uvalue=4.25)
void = widget_button(thick,value='4.50',uname='THICK',uvalue=4.50)
void = widget_button(thick,value='4.75',uname='THICK',uvalue=4.75)
void = widget_button(thick,value='5.00',uname='THICK',uvalue=5.00)

void = widget_button(color,value='Aqua',uname='COLOR',uvalue=[0,255,255])
void = widget_button(color,value='Black',uname='COLOR',uvalue=[0,0,0])
void = widget_button(color,value='Blue',uname='COLOR',uvalue=[0,0,255])
void = widget_button(color,value='Fuchsia',uname='COLOR',uvalue=[255,0,255])
void = widget_button(color,value='Gray',uname='COLOR',uvalue=[128,128,128])
void = widget_button(color,value='Green',uname='COLOR',uvalue=[0,128,0])
void = widget_button(color,value='Lime',uname='COLOR',uvalue=[0,255,0])
void = widget_button(color,value='Maroon',uname='COLOR',uvalue=[128,0,0])
void = widget_button(color,value='Navy',uname='COLOR',uvalue=[0,0,128])
void = widget_button(color,value='Olive',uname='COLOR',uvalue=[128,128,0])
void = widget_button(color,value='Purple',uname='COLOR',uvalue=[128,0,128])
void = widget_button(color,value='Red',uname='COLOR',uvalue=[255,0,0])
void = widget_button(color,value='Silver',uname='COLOR',uvalue=[192,192,192])
void = widget_button(color,value='Teal',uname='COLOR',uvalue=[0,128,128])
void = widget_button(color,value='White',uname='COLOR',uvalue=[255,255,255])
void = widget_button(color,value='Yellow',uname='COLOR',uvalue=[255,255,0])


;----------------------------------------------------------------------------
; Create Context Sensitive menus for 'Line + Symbol Plots'
csb3 = widget_base(self.tlb, /context_menu,uname='CSBLSYM',uvalue=cmdStr)
stype = widget_button(csb3,value='Symbol Type',/menu,tooltip=stTooltip)
ssize = widget_button(csb3,value='Symbol Size',/menu,tooltip=szTooltip)
lstyle = widget_button(csb3,value='Line Style',/menu,tooltip=lsTooltip)
thick = widget_button(csb3,value='Line/Symbol Thickness',/menu,tooltip=pthTooltip)
color = widget_button(csb3,value='Line/Symbol Color',/menu,tooltip=pcolTooltip)
ptm = widget_button(csb3,value='Plot Type',/menu,tooltip=ptTooltip)
void = widget_button(ptm,value='Lines',uvalue=0,uname='SWITCHDISPMODE',/checked_menu)
void = widget_button(ptm,value='Symbols',uvalue=1,uname='SWITCHDISPMODE',/checked_menu)
void = widget_button(ptm,value='Lines+Symbols',uvalue=2,uname='SWITCHDISPMODE',/checked_menu)
widget_control, void, set_button=1

void = widget_button(stype,value='Plus',uname='STYPE',uvalue=1)
void = widget_button(stype,value='Asterisk',uname='STYPE',uvalue=2)
void = widget_button(stype,value='Period',uname='STYPE',uvalue=3)
void = widget_button(stype,value='Diamond',uname='STYPE',uvalue=4)
void = widget_button(stype,value='Triangle',uname='STYPE',uvalue=5)
void = widget_button(stype,value='Square',uname='STYPE',uvalue=6)
void = widget_button(stype,value='Cross',uname='STYPE',uvalue=7)
void = widget_button(stype,value='Arrow Head (>)',uname='STYPE',uvalue=8)
void = widget_button(stype,value='Arrow Head (<)',uname='STYPE',uvalue=9)

void = widget_button(ssize,value='1.00',uname='SSIZE',uvalue=1.00)
void = widget_button(ssize,value='1.25',uname='SSIZE',uvalue=1.25)
void = widget_button(ssize,value='1.50',uname='SSIZE',uvalue=1.50)
void = widget_button(ssize,value='1.75',uname='SSIZE',uvalue=1.75)
void = widget_button(ssize,value='2.00',uname='SSIZE',uvalue=2.00)
void = widget_button(ssize,value='2.25',uname='SSIZE',uvalue=2.25)
void = widget_button(ssize,value='2.50',uname='SSIZE',uvalue=2.50)
void = widget_button(ssize,value='2.75',uname='SSIZE',uvalue=2.75)
void = widget_button(ssize,value='3.00',uname='SSIZE',uvalue=3.00)
void = widget_button(ssize,value='3.25',uname='SSIZE',uvalue=3.25)
void = widget_button(ssize,value='3.50',uname='SSIZE',uvalue=3.50)
void = widget_button(ssize,value='3.75',uname='SSIZE',uvalue=3.75)
void = widget_button(ssize,value='4.00',uname='SSIZE',uvalue=4.00)
void = widget_button(ssize,value='4.25',uname='SSIZE',uvalue=4.25)
void = widget_button(ssize,value='4.50',uname='SSIZE',uvalue=4.50)
void = widget_button(ssize,value='4.75',uname='SSIZE',uvalue=4.75)
void = widget_button(ssize,value='5.00',uname='SSIZE',uvalue=5.00)

void = widget_button(lstyle,value='Solid',uname='LSTYLE',uvalue=0)
void = widget_button(lstyle,value='Dotted',uname='LSTYLE',uvalue=1)
void = widget_button(lstyle,value='Dashed',uname='LSTYLE',uvalue=2)
void = widget_button(lstyle,value='Dash Dot',uname='LSTYLE',uvalue=3)
void = widget_button(lstyle,value='Dash Dot Dot Dot',uname='LSTYLE',uvalue=4)
void = widget_button(lstyle,value='Long Dashes',uname='LSTYLE',uvalue=5)

void = widget_button(thick,value='1.00',uname='THICK',uvalue=1.00)
void = widget_button(thick,value='1.25',uname='THICK',uvalue=1.25)
void = widget_button(thick,value='1.50',uname='THICK',uvalue=1.50)
void = widget_button(thick,value='1.75',uname='THICK',uvalue=1.75)
void = widget_button(thick,value='2.00',uname='THICK',uvalue=2.00)
void = widget_button(thick,value='2.25',uname='THICK',uvalue=2.25)
void = widget_button(thick,value='2.50',uname='THICK',uvalue=2.50)
void = widget_button(thick,value='2.75',uname='THICK',uvalue=2.75)
void = widget_button(thick,value='3.00',uname='THICK',uvalue=3.00)
void = widget_button(thick,value='3.25',uname='THICK',uvalue=3.25)
void = widget_button(thick,value='3.50',uname='THICK',uvalue=3.50)
void = widget_button(thick,value='3.75',uname='THICK',uvalue=3.75)
void = widget_button(thick,value='4.00',uname='THICK',uvalue=4.00)
void = widget_button(thick,value='4.25',uname='THICK',uvalue=4.25)
void = widget_button(thick,value='4.50',uname='THICK',uvalue=4.50)
void = widget_button(thick,value='4.75',uname='THICK',uvalue=4.75)
void = widget_button(thick,value='5.00',uname='THICK',uvalue=5.00)

void = widget_button(color,value='Aqua',uname='COLOR',uvalue=[0,255,255])
void = widget_button(color,value='Black',uname='COLOR',uvalue=[0,0,0])
void = widget_button(color,value='Blue',uname='COLOR',uvalue=[0,0,255])
void = widget_button(color,value='Fuchsia',uname='COLOR',uvalue=[255,0,255])
void = widget_button(color,value='Gray',uname='COLOR',uvalue=[128,128,128])
void = widget_button(color,value='Green',uname='COLOR',uvalue=[0,128,0])
void = widget_button(color,value='Lime',uname='COLOR',uvalue=[0,255,0])
void = widget_button(color,value='Maroon',uname='COLOR',uvalue=[128,0,0])
void = widget_button(color,value='Navy',uname='COLOR',uvalue=[0,0,128])
void = widget_button(color,value='Olive',uname='COLOR',uvalue=[128,128,0])
void = widget_button(color,value='Purple',uname='COLOR',uvalue=[128,0,128])
void = widget_button(color,value='Red',uname='COLOR',uvalue=[255,0,0])
void = widget_button(color,value='Silver',uname='COLOR',uvalue=[192,192,192])
void = widget_button(color,value='Teal',uname='COLOR',uvalue=[0,128,128])
void = widget_button(color,value='White',uname='COLOR',uvalue=[255,255,255])
void = widget_button(color,value='Yellow',uname='COLOR',uvalue=[255,255,0])

;----------------------------------------------------------------------------
; Create Context Sensitive menus for 'Axes'
csb4 = widget_base(self.tlb, /context_menu,uname='CSBAXES',uvalue=cmdStr)
thick = widget_button(csb4,value='Line Thickness',/menu)
afont = widget_button(csb4,value='Font',/menu)
fsize = widget_button(csb4,value='Font Size',/menu)
color = widget_button(csb4,value='Color',/menu)
prec =  widget_button(csb4,value='Decimal Places',/menu)
tdir =  widget_button(csb4,value='Tick Direction',/menu)
minor =  widget_button(csb4,value='Minor Ticks',/menu)
alog = widget_button(csb4,value='Log Scale',uname='LOGSCALE')
void = widget_button(csb4,value='Properties...',uname='EDITAXIS')

void = widget_button(afont,value='HELVETICA',uname='FONT',uvalue='HELVETICA')
void = widget_button(afont,value='COURIER',uname='FONT',uvalue='COURIER')
void = widget_button(afont,value='TIMES',uname='FONT',uvalue='TIMES')
void = widget_button(afont,value='HERSHEY',uname='FONT',uvalue='HERSHEY')
void = widget_button(afont,value='SYMBOL',uname='FONT',uvalue='SYMBOL')

void = widget_button(prec,value='0',uname='PRECISION',uvalue=0)
void = widget_button(prec,value='1',uname='PRECISION',uvalue=1)
void = widget_button(prec,value='2',uname='PRECISION',uvalue=2)
void = widget_button(prec,value='3',uname='PRECISION',uvalue=3)
void = widget_button(prec,value='4',uname='PRECISION',uvalue=4)

void = widget_button(tdir,value='Inwards',uname='TICKDIR',uvalue=0)
void = widget_button(tdir,value='Outwards',uname='TICKDIR',uvalue=1)

void = widget_button(minor,value='1',uname='MINOR',uvalue=1)
void = widget_button(minor,value='2',uname='MINOR',uvalue=2)
void = widget_button(minor,value='3',uname='MINOR',uvalue=3)
void = widget_button(minor,value='4',uname='MINOR',uvalue=4)
void = widget_button(minor,value='5',uname='MINOR',uvalue=5)
void = widget_button(minor,value='6',uname='MINOR',uvalue=6)
void = widget_button(minor,value='7',uname='MINOR',uvalue=7)
void = widget_button(minor,value='8',uname='MINOR',uvalue=8)
void = widget_button(minor,value='9',uname='MINOR',uvalue=9)
void = widget_button(minor,value='10',uname='MINOR',uvalue=10)

void = widget_button(thick,value='1.00',uname='THICK',uvalue=1.00)
void = widget_button(thick,value='1.25',uname='THICK',uvalue=1.25)
void = widget_button(thick,value='1.50',uname='THICK',uvalue=1.50)
void = widget_button(thick,value='1.75',uname='THICK',uvalue=1.75)
void = widget_button(thick,value='2.00',uname='THICK',uvalue=2.00)
void = widget_button(thick,value='2.25',uname='THICK',uvalue=2.25)
void = widget_button(thick,value='2.50',uname='THICK',uvalue=2.50)
void = widget_button(thick,value='2.75',uname='THICK',uvalue=2.75)
void = widget_button(thick,value='3.00',uname='THICK',uvalue=3.00)
void = widget_button(thick,value='3.25',uname='THICK',uvalue=3.25)
void = widget_button(thick,value='3.50',uname='THICK',uvalue=3.50)
void = widget_button(thick,value='3.75',uname='THICK',uvalue=3.75)
void = widget_button(thick,value='4.00',uname='THICK',uvalue=4.00)
void = widget_button(thick,value='4.25',uname='THICK',uvalue=4.25)
void = widget_button(thick,value='4.50',uname='THICK',uvalue=4.50)
void = widget_button(thick,value='4.75',uname='THICK',uvalue=4.75)
void = widget_button(thick,value='5.00',uname='THICK',uvalue=5.00)

void = widget_button(color,value='Aqua',uname='COLOR',uvalue=[0,255,255])
void = widget_button(color,value='Black',uname='COLOR',uvalue=[0,0,0])
void = widget_button(color,value='Blue',uname='COLOR',uvalue=[0,0,255])
void = widget_button(color,value='Fuchsia',uname='COLOR',uvalue=[255,0,255])
void = widget_button(color,value='Gray',uname='COLOR',uvalue=[128,128,128])
void = widget_button(color,value='Green',uname='COLOR',uvalue=[0,128,0])
void = widget_button(color,value='Lime',uname='COLOR',uvalue=[0,255,0])
void = widget_button(color,value='Maroon',uname='COLOR',uvalue=[128,0,0])
void = widget_button(color,value='Navy',uname='COLOR',uvalue=[0,0,128])
void = widget_button(color,value='Olive',uname='COLOR',uvalue=[128,128,0])
void = widget_button(color,value='Purple',uname='COLOR',uvalue=[128,0,128])
void = widget_button(color,value='Red',uname='COLOR',uvalue=[255,0,0])
void = widget_button(color,value='Silver',uname='COLOR',uvalue=[192,192,192])
void = widget_button(color,value='Teal',uname='COLOR',uvalue=[0,128,128])
void = widget_button(color,value='White',uname='COLOR',uvalue=[255,255,255])
void = widget_button(color,value='Yellow',uname='COLOR',uvalue=[255,255,0])

void = widget_button(fsize,value='8',uname='FONTSZ',uvalue=8)
void = widget_button(fsize,value='10',uname='FONTSZ',uvalue=10)
void = widget_button(fsize,value='12',uname='FONTSZ',uvalue=12)
void = widget_button(fsize,value='14',uname='FONTSZ',uvalue=14)
void = widget_button(fsize,value='16',uname='FONTSZ',uvalue=16)
void = widget_button(fsize,value='18',uname='FONTSZ',uvalue=18)
void = widget_button(fsize,value='20',uname='FONTSZ',uvalue=20)
void = widget_button(fsize,value='22',uname='FONTSZ',uvalue=22)
void = widget_button(fsize,value='24',uname='FONTSZ',uvalue=24)
void = widget_button(fsize,value='26',uname='FONTSZ',uvalue=26)
void = widget_button(fsize,value='28',uname='FONTSZ',uvalue=28)

;----------------------------------------------------------------------------
; Create Context Sensitive menus for 'Labels'
csb5 = widget_base(self.tlb, /context_menu,uname='CSBLABEL',uvalue=cmdStr)
color = widget_button(csb5,value='Color',/menu)
font = widget_button(csb5,value='Font',/menu)
fsize = widget_button(csb5,value='Font Size',/menu)
void = widget_button(csb5,value='Delete',uname='REMOVELABEL')
void = widget_button(csb5,value='Properties...',uname='EDITLABEL')

void = widget_button(font,value='HELVETICA',uname='FONT',uvalue='HELVETICA')
void = widget_button(font,value='COURIER',uname='FONT',uvalue='COURIER')
void = widget_button(font,value='TIMES',uname='FONT',uvalue='TIMES')
void = widget_button(font,value='HERSHEY',uname='FONT',uvalue='HERSHEY')
void = widget_button(font,value='SYMBOL',uname='FONT',uvalue='SYMBOL')

void = widget_button(color,value='Aqua',uname='COLOR',uvalue=[0,255,255])
void = widget_button(color,value='Black',uname='COLOR',uvalue=[0,0,0])
void = widget_button(color,value='Blue',uname='COLOR',uvalue=[0,0,255])
void = widget_button(color,value='Fuchsia',uname='COLOR',uvalue=[255,0,255])
void = widget_button(color,value='Gray',uname='COLOR',uvalue=[128,128,128])
void = widget_button(color,value='Green',uname='COLOR',uvalue=[0,128,0])
void = widget_button(color,value='Lime',uname='COLOR',uvalue=[0,255,0])
void = widget_button(color,value='Maroon',uname='COLOR',uvalue=[128,0,0])
void = widget_button(color,value='Navy',uname='COLOR',uvalue=[0,0,128])
void = widget_button(color,value='Olive',uname='COLOR',uvalue=[128,128,0])
void = widget_button(color,value='Purple',uname='COLOR',uvalue=[128,0,128])
void = widget_button(color,value='Red',uname='COLOR',uvalue=[255,0,0])
void = widget_button(color,value='Silver',uname='COLOR',uvalue=[192,192,192])
void = widget_button(color,value='Teal',uname='COLOR',uvalue=[0,128,128])
void = widget_button(color,value='White',uname='COLOR',uvalue=[255,255,255])
void = widget_button(color,value='Yellow',uname='COLOR',uvalue=[255,255,0])

void = widget_button(fsize,value='8',uname='FONTSZ',uvalue=8)
void = widget_button(fsize,value='10',uname='FONTSZ',uvalue=10)
void = widget_button(fsize,value='12',uname='FONTSZ',uvalue=12)
void = widget_button(fsize,value='14',uname='FONTSZ',uvalue=14)
void = widget_button(fsize,value='16',uname='FONTSZ',uvalue=16)
void = widget_button(fsize,value='18',uname='FONTSZ',uvalue=18)
void = widget_button(fsize,value='20',uname='FONTSZ',uvalue=20)
void = widget_button(fsize,value='22',uname='FONTSZ',uvalue=22)
void = widget_button(fsize,value='24',uname='FONTSZ',uvalue=24)
void = widget_button(fsize,value='26',uname='FONTSZ',uvalue=26)
void = widget_button(fsize,value='28',uname='FONTSZ',uvalue=28)


;----------------------------------------------------------------------------
; Create Context Sensitive menus for 'Legend'
csb6 = widget_base(self.tlb, /context_menu,uname='CSBLEGEND',uvalue=cmdStr)
void = widget_button(csb6,value='Properties...',uname='EDITLEGEND')



;----------------------------------------------------------------------------
; realize widgets
widget_control, self.tlb,/realize

; add the destination object to self (widget object)
widget_control, drawID, get_value=oDest
self.oDest = oDest
oDest->getProperty, dimensions=dim
self.winDim = dim

; create and add a scene to self (widget object)
self.oScene = obj_new('IDLgrScene')

; assign self to uvalue of tlb
;widget_control, self.tlb, set_uvalue=self

; the graphics scene should be always reconstructed by default
self.renewScene = 1
registerName = 'db_display1d'
ret = dave_set_focus(self.tlb)
xmanager,registerName,self.tlb,/no_block,event_handler='db_display1d_event',cleanup='db_display1d_cleanup'

; Set this widget object as the visualization object ref of the gr object
if (~(self.oDaveGr)->set(visRef=self)) then return, 0

return,1
end


;===============================================================================
;
pro DB_Display1D__define

void = {DB_Display1D, $
        tlb:0L, $
        old_dec:0, $
        o_registry: obj_new(), $ ; object registry which handles communication with other programs
        oDest:obj_new(), $      ; the Destination object
        oScene:obj_new(), $     ; Scene to be drawn in the destination
        oDaveGr:obj_new(), $    ; the DaveGr object to be displayed
        oRband:obj_new(), $     ; a rubber band obj gr atom used for zooming
        oActive1DCont:obj_new(), $ ; contains a list of all DaveGr1D objects being actively viewed
        workDir:'', $           ; user's working directory
        csmObjRef:obj_new(), $  ; will contain the obj ref for object which triggers a con. sen menu
        renewScene:1b, $        ; flag to indicate whether the scene is to be completely reconstructed
        rbStart:[0,0], $        ; rubberband start point (for zooming)
        rbScale:[0.,0.,1.,1.], $ ; x,y scale factor to convert from device to data coordinates (for zooming)
        mouseMoved:0b, $        ; flag to indicate if mouse was moved while LMB is depressed
        xrangeFlag:0b, $        ; flag to indicate that user specified x-axis range should be used
        xrange:[0.,0.], $       ; user specified x-axis limits
        yrangeFlag:0b, $        ; flag to indicate that user specified y-axis range should be used
        yrange:[0.,0.], $       ; user specified y-axis limits
        csbline_symID:0, $      ; widget ID's for switch-to-symbols item in CSBLINE con. sen. base menu
        csbline_sylID:0, $      ; widget ID's for switch-to-symbols+lines item in CSBLINE con. sen. base menu
        min_draw_x:0, $         ; min dimensions for draw widget
        min_draw_y:0, $         ; min dimensions for draw widget
        dialog_x:0, $           ; min width for dialog portion of tlb
        winDim:[0,0], $        ; current draw window dimensions
        dispError:0b, $         ; flag to indicate display of error bars
        dispTitle:1b, $         ; flag to indicate if main title is to be displayed
        dispType:0b $           ; flag to indicate display mode; histogram/points
       }

end
