

function first,x
 return,x[0]
end

function last,x
 return,x[n_elements(x)-1]
end


;*************************************************************************
;+
; NAME:psk_correlate
;
; PURPOSE:
;    compute correlation and significance level between two arrays
;    using three methods: classical linear, rank Spearman, or rank Kendall
;
; CATEGORY:
;
; CALLING SEQUENCE:
;    r=psk_correlate(x,y[,corr=corr,/spearman,/kendall])
;
; INPUTS:
; x,y two equal length array
;
; OPTIONAL (KEYWORD) INPUT PARAMETERS:
; no keyword to compute Pearson linear correlation
; spearman: to compute Spearman rank correlation
; kendall:  to compute Kendall rank correlation
; corr=1,2,3 alternative keyword to specify the type of correlation in the above order
;
; ROUTINES CALLED: correlate,r_correlate
;
; OUTPUTS:
; [r,prob], where prob is the null hypothesis probability, the less the better.
;
; COMMENTS:
;
; SIDE EFFECTS:
; If none element verctors are provided, [nan,nan] is returned
; RESTRICTIONS:
; Only one parametr is allowed in call
; If two ellement vectors are provided, a probability of 1 ( 0-significace) is assigned
; MODIFICATION HISTORY:
;  Created 26-March-2003 Gelu M. Nita
;
;-


function psk_correlate,x,y,corr=corr,spearman=spearman,kendall=kendall
    on_error,2
    if keyword_set(corr)+keyword_set(spearman)+keyword_set(kendall) gt 1 then message,'Only one keyword allowed!)
    nx = n_elements(x)
    ny=  n_elements(y)
    if (nx ne ny) or (nx eq 1) then return,[!values.f_nan,!values.f_nan]
    if keyword_set(spearman) then corr=2
    if keyword_set(kendall) then corr=3
    if not keyword_set(corr) then corr=1
    ;if nx eq 2 then return,[1.0,1.0] ;assign anull significance to such a perfect correlation of 2 data pairs
    case corr of
     2:return,r_correlate(x,y); Spearman rank correlation
     3:return,r_correlate(x,y,/kendall);Kendall rank correlation
     else: begin;compute Pearson linear correlaation
           rs=correlate(x,y)
         print,rs
         if nx eq 2 then begin
          probrs=1
          print,probrs
         endif else begin
           en=n_elements(x)
           fac = (1.0 + rs) * (1.0 - rs)
           if (fac gt 0.0) then begin
             t = rs * sqrt((en - 2.0)/fac)
             df = en - 2
             probrs = ibeta(0.5*df, 0.5, df/(df+t^2))
           endif else probrs = 0.0
           endelse
           return,[rs,probrs]
          end
    end
end
;*************************************************************************
;+
; NAME:W_HISTOGRAM
;
; PURPOSE:
;   Return a distribution in which the number of elements in each bin is replaced by
;   the sum of each data element weight, if provided
;
; CATEGORY:
;
; CALLING SEQUENCE:
;    W_HISTOGRAM,DATA[,WEIGHT[,NORMALIZE=NORMALIZE]]
;
; INPUTS:
; data: array for each histogram has to be computed
; WEIGHT: an array defining the wieght of each data point
;
; OPTIONAL (KEYWORD) INPUT PARAMETERS:
; some of the keywords accepted by IDL histogram function
; NORMALIZE: set this keyword to normalize the histogram to unity area (1) or to number of data points (2)
;
; ROUTINES CALLED:histogram
;
; OUTPUTS:
; The distributed histogram in which the number of elements in each bin is replaced by the sum
; of the coresponding weight. The result may be normalized to unitt area or to total
; number of elements of data array . If all weight's elements are set two 1, the result of w_histogram
; is the same with that of histogram function.
;
; COMMENTS:
;
; SIDE EFFECTS:
; RESTRICTIONS:
;
; MODIFICATION HISTORY:
;  Create 28-March-2003 Gelu M. Nita
;
;-
function W_HISTOGRAM, DATA, WEIGHT,BINSIZE=BINSIZE,MAX=MAX,MIN=MIN,NBINS=NBINS, REVERSE_INDICES=REVERSE_INDICES,NAN=NAN,NORMALIZE=NORMALIZE
    on_error,2
    nweight=n_elements(weight)
    if nweight eq 0 then return,histogram(DATA,BINSIZE=BINSIZE,MAX=MAX,MIN=MIN,NBINS=NBINS, REVERSE_INDICES=REVERSE_INDICES,NAN=NAN)
    npoints=n_elements(data)
    if nweight ne npoints then weight=1.d*data/data else weight=weight*1.d
    result=histogram(DATA,BINSIZE=BINSIZE,MAX=MAX,MIN=MIN,NBINS=NBINS, REVERSE_INDICES=R,/NAN)
    REVERSE_INDECES=R
    for i=0, n_elements(result)-1 do begin
     IF R[i] NE R[i+1] THEN result[i]=Total(weight[R[R[i] : R[i+1]-1]])*1.d
    end
    if keyword_set(normalize) then begin
     result=result/total(result)
     if normalize ne 1 then result=result*npoints
    end
    return,result
end
;****************************************************************************************************************
;+
; NAME:
;     plot_w
; PURPOSE:
;     To plot a set of datapoints with user defined weight.
;     The W array should have the same dimension as x and y
;     The routine normalize W to its maximum value and assigns to each
;     datapoint a circle symbol with a radius equal with its normalized weight.
; CATEGORY:
;     OVRO DATA ANALYSIS
; CALLING SEQUENCE:
;     plot_w,x,y,w
; INPUTS:
;
; OPTIONAL (KEYWORD) INPUT PARAMETERS:
; Some of the parameters of the IDL plot function
;
; ROUTINES CALLED:
;
; OUTPUTS:
; COMMENTS:
; SIDE EFFECTS:
; RESTRICTIONS:
; MODIFICATION HISTORY:
;     Written 28-March-2003 by Gelu Nita
pro plot_w,x,y,w, xrange=xrange,yrange=yrange,xtitle=xtitle,ytitle=ytitle,title=title,subtitle=subtitle,psym=psym,$
           xstyle=xstyle,ystyle=ystyle,background=background,color=color,device=device,position=position,$
           xlog=xlog,ylog=ylog

 if psym eq 10 then begin
  dx=0.5*(x[1]-x[0])
  plot,x+dx,y, xrange=xrange,yrange=yrange,xtitle=xtitle,ytitle=ytitle,title=title,subtitle=subtitle,psym=psym,$
           xstyle=1,ystyle=ystyle,background=background,color=color,device=device,position=position,xlog=xlog,ylog=ylog
  oplot,[x[0],x[0]+dx],[y[0],y[0]] ,color=color
  oplot,[last(x),last(x)+dx],[last(y),last(y)],color=color
  return
  end

 if psym ne 8 then begin
  plot,x,y, xrange=xrange,yrange=yrange,xtitle=xtitle,ytitle=ytitle,title=title,subtitle=subtitle,psym=psym,$
           xstyle=xstyle,ystyle=ystyle,background=background,color=color,device=device,position=position,xlog=xlog,ylog=ylog
  return
 end
 t=findgen(40)/39.*2*!pi
 usersym,cos(t),sin(t),color=color

 if n_elements(w) lt n_elements(x) then begin
  plot,x,y, xrange=xrange,yrange=yrange,xtitle=xtitle,ytitle=ytitle,title=title,subtitle=subtitle,psym=psym,$
           xstyle=xstyle,ystyle=ystyle,background=background,color=color,device=device,position=position,xlog=xlog,ylog=ylog
  return
 end
 plot,x,y, xrange=xrange,yrange=yrange,xtitle=xtitle,ytitle=ytitle,title=title,subtitle=subtitle,$
          xstyle=xstyle,ystyle=ystyle,background=background,color=color,device=device,position=position,xlog=xlog,ylog=ylog,/nodata
 mw= max(w,/nan)
 if mw gt 1 then sz=abs(1.0*w/mw) else sz=w
 sz=sz>0.1
 for i=0, n_elements(x)-1 do plots,x[i],y[i],psym=8,symsize=sz[i]
 return
end
;***************************************************************************************************************
pro plot_med,med,varx,vary,index,data=data
    if n_elements(med) eq 0 then med=read_med()
    if n_elements(vary) eq 0 then vary='PEAKFLUX'
    if n_elements(varx) eq 0 then varx='PEAKFREQ'
    if n_elements(index) eq 0 then index=0
    peak=med.peak[index]
    r=peak.r
    p=peak.p

    case strupcase(varx) of
     'DURATION':begin
                 varx='peakflux'
                end
     'WAITING TIME':begin
                 varx='peakflux'
                end
     'ENERGY':begin
                 varx='peakflux'
                end
      else:
    endcase

    case strupcase(vary) of
     'DURATION':begin
                 vary='peakflux'
                end
     'WAITING TIME':begin
                 vary='peakflux'
                end
     'ENERGY':begin
                 vary='peakflux'
                end
      else:
    endcase
    varx=strupcase(varx)
    vary=strupcase(vary)
    tags=tag_names((med).curves)
    tagx=where(tags eq strupcase(varx))
    tagy=where(tags eq strupcase(vary))
    tagx=tagx[0]
    tagy=tagy[0]
    xcurve=reform(med.curves.(tagx)[r,*])
    ycurve=reform(med.curves.(tagy)[r,*])
    time=med.time
    !p.multi=[0,1,3]
    yrange=[min(xcurve,/nan),max(xcurve,/nan)]
    utplot, time,xcurve,med.datstr,ytitle=tags[tagx],psym=10,ystyle=1,yrange=yrange,back=255,color=0,xsty=1,xcharsize=1.5,ycharsize=1.5
    outplot,[time[peak.all.range[0]],time[peak.all.range[0]]],yrange,color=0
    outplot,[time[peak.all.range[1]],time[peak.all.range[1]]],yrange,color=0
    outplot,[time[peak.peak.range[0]],time[peak.peak.range[0]]],yrange,color=0,linestyle=1
    outplot,[time[peak.peak.range[1]],time[peak.peak.range[1]]],yrange,color=0,linestyle=1
    if keyword_set(data) then outplot,data.t,data.x,psym=2,color=250
    yrange=[min(ycurve,/nan),max(ycurve,/nan)]
    utplot, time,ycurve,med.datstr,ytitle=tags[tagy],psym=10,ystyle=1,yrange=yrange,back=255,color=0,xsty=1,xcharsize=1.5,ycharsize=1.5
    outplot,[time[peak.all.range[0]],time[peak.all.range[0]]],yrange,color=0
    outplot,[time[peak.all.range[1]],time[peak.all.range[1]]],yrange,color=0
    outplot,[time[peak.peak.range[0]],time[peak.peak.range[0]]],yrange,color=0,linestyle=1
    outplot,[time[peak.peak.range[1]],time[peak.peak.range[1]]],yrange,color=0,linestyle=1
    if keyword_set(data) then outplot,data.t,data.y,psym=2,color=250
    ;plot,xcurve,ycurve,xsty=1,ysty=1,xtitle=tags[tagx],ytitle=tags[tagy],back=0,color=1,psym=2,xcharsize=1.5,ycharsize=1.5
    ;if keyword_set(data) then oplot,data.x,data.y,psym=2,color=250
    tagx=where(tags eq strupcase('peakflux'))
    tagx=tagx[0]
    xcurve=reform(med.curves.(tagx)[r,*])
    yrange=[min(xcurve,/nan),max(xcurve,/nan)]
    utplot, time,xcurve,med.datstr,ytitle=tags[tagx],psym=10,ystyle=1,yrange=yrange,back=255,color=0,xsty=1,xcharsize=1.5,ycharsize=1.5
    outplot,[time[peak.all.range[0]],time[peak.all.range[0]]],yrange,color=0
    outplot,[time[peak.all.range[1]],time[peak.all.range[1]]],yrange,color=0
    outplot,[time[peak.peak.range[0]],time[peak.peak.range[0]]],yrange,color=0,linestyle=1
    outplot,[time[peak.peak.range[1]],time[peak.peak.range[1]]],yrange,color=0,linestyle=1
    !p.multi=0
end
;****************************************************************************************************************
pro plotdata__define
tmp={plotdata,data:ptr_new()}
end
;****************************************************************************************************************
;+
; NAME:
;     WQUERY
; PURPOSE:
;     To query OVSA datacub generated using READ_MED function
; CATEGORY:
;     OVRO DATA ANALYSIS
; CALLING SEQUENCE:
;     wquery
; INPUTS:
;
; OPTIONAL (KEYWORD) INPUT PARAMETERS:
;
; ROUTINES CALLED:
;
; OUTPUTS:
; COMMENTS:
; SIDE EFFECTS:
; RESTRICTIONS:
; MODIFICATION HISTORY:
;     Written 18-March-2003 by Gelu Nita
;

;THIS IS THE MAIN QUERY ROUTINE CALLED BY WQUERY WIDGET INTERFACE

function QUERY,data,varx=varx,vary=vary,time=time,$
            gyro=gyro,freqrange=freqrange,fluxrange=fluxrange,$
            onepoint=onepoint,onetype=onetype,duration=duration,normalize=normalize,$
            corr=corr,waiting=waiting,mainpeak=mainpeak,query=query,dx=dx,dy=dy,rel=rel

   empty_event={ID:0l,TOP:0l,HANDLER:0l}
   CATCH,Error_Status
   IF Error_status NE 0 THEN BEGIN
      ans=DIALOG_MESSAGE(!ERROR_STATE.MSG,/error,display_name='QUERY')
      CATCH,/CANCEL
      return,empty_event
   ENDIF

    if n_elements(data) eq 0 then begin
      ans=dialog_message(['No data provided.','Action canceled!'],/error,title='Error: Query')
      return,empty_event
    end

    if n_elements(vary) eq 0 then vary='PEAKFLUX'
    if n_elements(varx) eq 0 then varx='PEAKFREQ'
    if n_elements(time) eq 0 then time='ALL'
    if n_elements(corr) eq 0 then corr=0
    if n_elements(onepoint) eq 0 then onepoint=0
    if n_elements(mainpeak) eq 0 then mainpeak=0
    if n_elements(onetype) eq 0 then onetype=0
    varx=strupcase(varx)
    vary=strupcase(vary)
    time=strupcase(time)
    if varx eq vary then begin
     ans=DIALOG_MESSAGE('The X and Y variable must be different!',/error,title='Error: Query')
    return,empty_event
    end

    if n_elements(freqrange) eq 0 then freqrange=[1,18]
    if n_elements(fluxrange) eq 0 then fluxrange=[1,10.0^6]

    DWE=0
    D_X=(D_Y=(W_X=(W_Y=(E_X=(E_Y=0)))))

    case strupcase(varx) of
     'DURATION':begin
                 duration=1
                 varx='peakflux';just for intern purposes
                 xtitle='Duration [s]'
                 DWE=DWE+1
                 D_X=1
                end
     'WAITING TIME':begin
                 waiting=1
                 varx='peakflux';just for intern purposes
                 xtitle='Waiting time [s]'
                 DWE=DWE+1
                 W_X=1
                end
     'ENERGY':begin
                 energy=1
                 varx='peakflux';just for intern purposes
                 xtitle='Energy density [sfu x s]'
                 DWE=DWE+1
                 E_X=1
                end
      else: xtitle=varx
    endcase


    case strupcase(vary) of
     'DURATION':begin
                 duration=1
                 vary='peakflux';just for intern purposes
                 ytitle='Duration [s]'
                 D_Y=1
                 DWE=DWE+1
                end
     'WAITING TIME':begin
                 waiting=1
                 vary='peakflux';just for intern purposes
                 ytitle='Waiting time [s]'
                 W_Y=1
                 DWE=DWE+1
                end
     'ENERGY':begin
                 energy=1
                 vary='peakflux';just for intern purposes
                 ytitle='Energy density [sfu x s]'
                 E_Y=1
                 DWE=DWE+1
                end
      else:ytitle=vary
    endcase

    if keyword_set(dx) then xtitle='Delta '+xtitle
    if keyword_set(dy) then ytitle='Delta '+ytitle
    if keyword_set(dx) and keyword_set(rel) then  xtitle='Rel '+xtitle
    if keyword_set(dy) and keyword_set(rel) then  ytitle='Rel '+ytitle

    ;Here computation begins


    tags=tag_names((*data[0]).peak)
    tagt=where(tags eq strupcase(time))
    tagt=tagt[0]

    tags=tag_names((*data[0]).curves)

    tagx=where(tags eq strupcase(varx))
    tagy=where(tags eq strupcase(vary))

    freqtag=where(tags eq strupcase('PEAKFREQ'))
    fluxtag=where(tags eq strupcase('PEAKFLUX'))
    tagx=tagx[0]
    tagy=tagy[0]
    freqtag=freqtag[0]
    fluxtag=fluxtag[0]
    x=[0.d];variable x
    y=[0.d];variable y
    n=[0l]; number of points used to compute each x and y
    w=[1.d];weigth of each datapoint
    f=['']; filenames used in computation
    tavg=[0.0];corresponding times
    idx={file:0,index:0};database index
    med=*data[0]
    t=[julday(strmid(med.datstr,5,2),strmid(med.datstr,9,2),strmid(med.datstr,0,4))*86400.d]

    for i=0,n_elements(data)-1 do begin
     med=*data[i]
     npeaks=n_elements(med.peak)
     for index=0,npeaks-1 do begin
      valid=med.valid[index]
      peak=med.peak[index]
      if mainpeak eq 1 then valid=peak.main
     if valid gt 0 then begin
      r=peak.r
      p=peak.p
      xcurve=reform(med.curves.(tagx)[r,*])
      ycurve=reform(med.curves.(tagy)[r,*])
      freqcurve=reform(med.curves.(freqtag)[r,*])
      fluxcurve=reform(med.curves.(fluxtag)[r,*])
      timecurve=med.time
      istart=peak.(tagt).range[0]
      iend=peak.(tagt).range[1]

      if istart ge 0 and iend ge 0 then begin

      ;Apply TIME filter

      newx=xcurve[istart:iend]
      newy=ycurve[istart:iend]
      newfreq=freqcurve[istart:iend]
      newflux=fluxcurve[istart:iend]
      newtime=timecurve[istart:iend]

      ;Apply finite data filter

      good=where(finite(newx) eq 1 and finite(newy) eq 1,count)
      if count eq 0 then goto, skip

      newx=newx[good]
      newy=newy[good]
      newfreq=newfreq[good]
      newflux=newflux[good]
      newtime=newtime[good]

      ;Apply FREQ and Flux filters

      good=where(newfreq ge freqrange[0] and newfreq le freqrange[1] and newflux ge fluxrange[0] and newflux le fluxrange[1],count)

      skip:
      if count gt 0 then begin

       newx=newx[good]
       newy=newy[good]
       newfreq=newfreq[good];even we might not need it
       newflux=newflux[good];used to compute the local peakflux
       newtime=newtime[good]


       maxflux=max(newflux,imax,/nan)
       maxx=newx(imax);value of x variable at maxflux time
       maxy=newy(imax);value of y variable at maxflux time
       case onetype of
        1:begin & onex=median([newx,newx],/even) & oney=median([newy,newy],/even) & end
       else:begin & onex=maxx & oney=maxy & end
       endcase
       newenergy=peak.(tagt).energy
       newduration=peak.(tagt).duration;newenergy/maxflux;
       newmoment=med.time[istart]+julday(strmid(med.datstr,5,2),strmid(med.datstr,9,2),strmid(med.datstr,0,4))*86400.d

       if keyword_set(duration) then begin
        if D_X eq 1 then begin
          newx=newduration
          if DWE eq 1 then newy=oney
        end
        if D_Y eq 1 then begin
          newy=newduration
          if DWE eq 1 then newx=onex
        end
        if finite(newx) eq 0 or finite(newy) eq 0 then valid=valid-1
        cross=1
       end

       if keyword_set(waiting) then begin
        if W_X eq 1 then begin
          newx=newmoment-last(t)
          if DWE eq 1 then newy=oney
          if newx lt 2 then valid=valid-1
        end
        if W_Y eq 1 then begin
          newy=newmoment-last(t)
          if DWE eq 1 then newx=onex
          if newy lt 2 then valid=valid-1
        end
        if finite(newx) eq 0 or finite(newy) eq 0 then valid=valid-1
        cross=1
       end

       if keyword_set(energy) then begin
        if E_X eq 1 then begin
          newx=newenergy
          if DWE eq 1 then newy=oney
        end
        if E_Y eq 1 then begin
          newy=newenergy
          if DWE eq 1 then newx=onex
        end
        if finite(newx) eq 0 or finite(newy) eq 0 then valid=valid-1
        cross=1
       end


       ;compute onepoint if possible
       if keyword_set(onepoint) then begin
           newx=onex
           newy=oney
           newx=newx[0]
           newy=newy[0]
           if finite(newx) eq 0 or finite(newy) eq 0 then valid=valid-1
           cross=1
       endif




       if keyword_set(dx) then begin
        good=where(finite(newx),count)
        if count ge 2 then begin
         a=indgen(count)
         b=newx(good)
         fit=linfit(a,b,yfit=yfit)
         newx=last(yfit)-first(yfit)
         if keyword_set(rel) then newx=newx/abs(first(yfit))
        endif else valid=0
       end

       if keyword_set(dy) then begin
        good=where(finite(newy),count)
        if count ge 2 then begin
         a=indgen(count)
         b=newy(good)
         fit=linfit(a,b,yfit=yfit)
         newy=last(yfit)-first(yfit)
         if keyword_set(rel) then newy=newy/abs(first(yfit))
        endif else valid=0
       end

      ;compute correlation if possible
       if keyword_set(corr) and not keyword_set(cross) then begin
           psk=psk_correlate(newx,newy,corr=corr)
           newy=oney
           newx=psk[0]
           neww=1-psk[1]; if /corr then neww is repaced by statistical significance of the correlation
           if finite(newx) eq 0 or finite(newy) eq 0 or finite(neww) eq 0 then valid=valid-1
       end

       if keyword_set(query) then begin
       fgood=where(newx ge query[0,0] and newx le query[1,0] and newy ge query[0,1] and newy le query[1,1],fcount)
        if fcount eq 0 then begin
         valid=valid-1
        endif else begin
         newx=newx[fgood]
         newy=newy[fgood]
        end
       end


       if valid eq 1 then begin
         newn=newx
         newn[*]=n_elements(f)-1
         if n_elements(neww) eq 0 then begin
          neww=newx; assign default weighting for each datapoint
          neww[*]=1
         end

         x=[x,newx]
        y=[y,newy]
        n=[n,newn]
        f=[f,med.file+' '+string(r,format='(i1)')+' '+string(p,format='(i1)')]
        t=[t,newmoment]
        w=[w,neww]
        tavg=[tavg,newtime]
        idx=[idx,{file:i,index:index}]
       end
       end
      endif
     end
     end
    end

    if n_elements(x) eq 1 then begin
     ans=dialog_message('No record in this range',title='Error: Querry',/error)
     return,empty_event
    end

    ;Remove blanck initialization in all other cases
    x=x[1:*]
    y=y[1:*]
    n=n[1:*]
    f=f[1:*]
    w=w[1:*]
    tavg=tavg[1:*]
    idx=idx[1:*]

    ;Compute waiting time
    if keyword_set(waiting) then begin
    if W_X eq 1 then begin
     good= where(x ge 1 and x lt 8*3600.d)
     x=x[good]
     y=y[good]
     n=n[good]
     f=f[good]
     w=w[good]
     idx=idx[good]
    end
    if W_Y eq 1 then begin
     good= where(y ge 1 and y lt 8*3600.d)
     x=x[good]
     y=y[good]
     n=n[good]
     f=f[good]
     w=w[good]
     idx=idx[good]
    end
    end


    IF keyword_set(corr) THEN BEGIN
        if not keyword_set(cross) then begin
          good=where(finite(w) eq 1, count)
          if count gt 0 then begin
           x=x[good]
           y=y[good]
           n=n[good]
           f=f[good]
           w=w[good]
           idx=idx[good]
           xtitle='Correlation ['+varx+','+vary+']'
           corr=0
          endif else begin
            ans=dialog_message(['Invalid data to compute correlation'],title='Error: Querry',/error)
            return,empty_event
          endelse
        endif
     END

if DWE eq 1 then begin
 if D_X eq 0 and W_X eq 0 and E_X eq 0 then begin
  case onetype of
   1:xtitle='MEDIAN '+xtitle
   else:xtitle=xtitle+' at MAXFLUX in range'
  endcase
 end
 if D_Y eq 0 and W_Y eq 0 and E_Y eq 0 then  begin
  case onetype of
   1:ytitle='MEDIAN '+ytitle
   else:ytitle=ytitle+' at MAXFLUX in range'
  endcase
 end
end

if keyword_set(onepoint) then begin
 case onetype of
 1:begin
    xtitle='MEDIAN '+xtitle
    ytitle='MEDIAN '+ytitle
   end
 else: begin
        xtitle=xtitle+' at MAXFLUX in range'
        ytitle=ytitle+' at MAXFLUX in range'
       end
 endcase
end


if not keyword_set(query) then begin
    plotdata={plotdata,ptr_new({varx:xtitle,vary:ytitle,x:x,y:y,f:f,n:n,w:w,idx:idx,tavg:tavg,time:time,$
    corr:corr,onepoint:onepoint,onetype:onetype,mainpeak:mainpeak})}
    event={newdata,ID:0L,TOP:0L,HANDLER:0L,data:plotdata}
endif else event={query,ID:0L,TOP:0L,HANDLER:0L,f:ptr_new(f)}


return,event
end

;****************************************************************************************************************

pro WQuery_event,event
 ; Read the state structure from the child base
   base = event.handler
   stash = widget_info(base,/child)
   widget_control,stash,get_uvalue=state,/no_copy
   CATCH, Error_status
   IF Error_status NE 0 THEN BEGIN
     ans=DIALOG_MESSAGE(!ERROR_STATE.MSG,/error,display_name='WQUERY_EVENT')
     CATCH,/CANCEL
     goto,write_state
   ENDIF


   wdraw=WIDGET_INFO(event.handler,Find_BY_UNAME='DRAW')


   IF (TAG_NAMES(Event, /STRUCTURE_NAME) EQ 'WIDGET_KILL_REQUEST') THEN BEGIN
     exit_line:
     state=0
     WIDGET_CONTROL, Event.top, /DESTROY
     heap_gc
     RETURN
   ENDIF

   type=Tag_Names(event,/Structure)
   case type of
   'WIDGET_BUTTON':BEGIN
          WIDGET_CONTROL,Event.Id,GET_UVALUE=Ev
          CASE strupcase(Ev) OF
            'BROWSE': BEGIN
                       filename=dialog_pickfile(filter='*.sav',/multiple)
                       if filename[0] ne '' then begin
                        ptr_free,state.data
                        for f=0,n_elements(filename)-1 do begin
                        restore,filename[f]
                        if n_elements(data) ne 0 then begin
                         if n_elements(newdata) eq 0 then newdata=data else newdata=[newdata,data]
                        end
                        end

                        if n_elements(newdata) ne 0 then begin
                         data=newdata
                         files=strarr(n_elements(data))
                         for f=0,n_elements(data)-1 do files[f]=(*data[f]).file
                         data=data(sort(files))
                         state.data=ptr_new(data,/no_copy)
                         Widget_Control,event.top,TLB_SET_TITLE='WQuery-['+arr2str(filename)+']'
                         Widget_Control,wdraw,SEND_EVENT={SelDelAll,ID:event.id,TOP:event.top,Handler:0l},/no_copy
                         heap_gc
                         goto,analyze
                        endif else ans=dialog_message(['This is not a  valid datacub file','Action canceled !'],/error)
                       end
                      END

            'MED':BEGIN
                   data=[ptr_new(read_med(filename=filename))]
                   ptr_free,state.data
                   state.data=ptr_new(data,/no_copy)
                   nfiles=1
                   Widget_Control,event.top,TLB_SET_TITLE='WQuery-['+arr2str(filename)+']'
                   Widget_Control,wdraw,SEND_EVENT={SelDelAll,ID:event.id,TOP:event.top,Handler:0l},/no_copy
                   heap_gc
                   goto, analyze
                  END

            'FREQUENCY RANGE':BEGIN
                       wfreqrange=WIDGET_INFO(event.handler,Find_By_Uname='freqrange')
                       WIDGET_CONTROL,wfreqrange,Set_Value='[1,18]'
                      END

            'FLUX RANGE':BEGIN
                       wfluxrange=WIDGET_INFO(event.handler,Find_By_Uname='fluxrange')
                       WIDGET_CONTROL,wfluxrange,Set_Value='[1,10.0^6]'
                      END
            'X RANGE':BEGIN
                       wxrange=WIDGET_INFO(event.handler,Find_By_Uname='XRANGE')
                       WIDGET_CONTROL,wxrange,Set_Value='[AUTO,AUTO]'
                      END
            'Y RANGE':BEGIN
                       wyrange=WIDGET_INFO(event.handler,Find_By_Uname='YRANGE')
                       WIDGET_CONTROL,wyrange,Set_Value='[AUTO,AUTO]'
                      END
            '# OF BINS':BEGIN
                       wbin=WIDGET_INFO(event.handler,Find_By_Uname='bin')
                       WIDGET_CONTROL,wbin,Set_Value='20'
                      END

             'ONEPOINT' : begin
                         state.onepoint=1-state.onepoint
                         goto,analyze
                        end

             'MAINPEAK' : begin
                         state.mainpeak=1-state.mainpeak
                         goto,analyze
                        end

            'CORR'   : begin
                         state.corr=1-state.corr
                         goto,analyze
                       end

             'DX'   : begin
                         state.dx=1-state.dx
                         goto,analyze
                       end
            'DY'   : begin
                         state.dy=1-state.dy
                         goto,analyze
                     end

          'REL'   : begin
                         state.rel=1-state.rel
                         goto,analyze
                       end
             'DBCREATE': BEGIN
                          db_create:
                          files=dialog_pickfile(path=!defaults.datadir,filter='*.med',/multiple,title='Select MED files to be included')
                          nfiles=n_elements(files)
                          if nfiles gt 0 and files[0] ne '' then begin
                              id = progmeter(/INIT,label='Creating database',button='Abort')
                        val = 0
                        for i = 0, nfiles-1 do begin
                           BREAK_FILE, FILES[i], DISK, DIR, FILENAME, EXT, FVERSION, NODE
                           Widget_Control,id,TLB_SET_TITLE='Creating database: '+Filename+ext
                           file=files[i]
                     med=read_med(file)
                     if n_elements(data) eq 0 then data=[ptr_new(med)] else data=[data,ptr_new(med)]
                           val = i/(1.0*nfiles)
                           prog=progmeter(id,val)
                          if  prog eq 'Cancel' then goto,escape
                        endfor
                        escape: status = progmeter(id,/DESTROY)
                        if prog ne 'Cancel' then begin
                         file=dialog_pickfile(filter='*.sav',title='Select a database name')
                      if file ne '' then save,data,file=file,/compress
                     end
                        data=0
                     heap_gc
                   end
                         END
            'ANALYZE': BEGIN
                       analyze:
                       wfreqrange=WIDGET_INFO(event.handler,Find_By_Uname='freqrange')
                       WIDGET_CONTROL,wfreqrange,Get_Value=freqtext
                       freqtext=freqtext[0]
                       if freqtext ne '' then begin
                          r=execute('freqrange='+freqtext,1)
                          if r eq 0 then begin
                           ans=dialog_message(['Freq range should be the form of',$
                                                '[min,max]','Action canceled !'],/error)
                           goto, write_state
                          endif
                       endif

                       wfluxrange=WIDGET_INFO(event.handler,Find_By_Uname='fluxrange')
                       WIDGET_CONTROL,wfluxrange,Get_Value=fluxtext
                       fluxtext=fluxtext[0]
                       if fluxtext ne '' then begin
                          r=execute('fluxrange='+fluxtext,1)
                          if r eq 0 then begin
                           ans=dialog_message(['Flux range should be the form of',$
                                                '[min,max]','Action canceled !'],/error)
                           goto, write_state
                          endif
                       endif


                        if state.corr eq 1 then corr=state.corrtype

                       WIDGET_CONTROL,/HOURGLASS
                       newdata=query(*state.data,varx=state.varx,vary=state.vary,time=state.time,$
                          fluxrange=fluxrange,freqrange=freqrange,$
                          onepoint=state.onepoint,corr=corr,onetype=state.onetype,$
                          mainpeak=state.mainpeak,query=query,$
                          dx=state.dx,dy=state.dy,rel=state.rel)
                       newdata.id=event.id
                       newdata.top=event.top
                       Widget_Control,wdraw,SEND_EVENT=newdata,/no_copy

                      END


             ;messages sent to draw widget
             'COLAPSE':  begin
                          Widget_Control,wdraw,SEND_EVENT={colapse,ID:event.id,TOP:event.top,Handler:0l},/no_copy
                         end

              'PRINT':   begin
                         Widget_Control,wdraw,SEND_EVENT={print,ID:event.id,TOP:event.top,Handler:0l},/no_copy
                      end
             'PRINT TO PS':begin
                          Widget_Control,wdraw,SEND_EVENT={psprint,ID:event.id,TOP:event.top,Handler:0l},/no_copy
                         end
             'SAVE': begin
                       Widget_Control,wdraw,SEND_EVENT={save,ID:event.id,TOP:event.top,Handler:0l},/no_copy
                     end

             'NORM': begin
                       Widget_Control,wdraw,SEND_EVENT={norm,ID:event.id,TOP:event.top,Handler:0l},/no_copy
                     end

             'STAT': begin
                       Widget_Control,wdraw,SEND_EVENT={stat,ID:event.id,TOP:event.top,Handler:0l},/no_copy
                     end
             'REFRESH':Widget_Control,wdraw,SEND_EVENT={refresh,ID:event.id,TOP:event.top,Handler:0l},/no_copy

             'DBDISPLAY':begin
                          Widget_Control,wdraw,SEND_EVENT={dbdisplay,ID:event.id,TOP:event.top,Handler:0l,$
                          varx:state.varx,vary:state.vary,pdata:state.data}
                         end
             'DBSELECT':Widget_Control,wdraw,SEND_EVENT={dbselect,ID:event.id,TOP:event.top,Handler:0l},/no_copy
             'DBSELALL':Widget_Control,wdraw,SEND_EVENT={dbselall,ID:event.id,TOP:event.top,Handler:0l},/no_copy
              'DBSAVE':Widget_Control,wdraw,SEND_EVENT={dbsave,ID:event.id,TOP:event.top,Handler:0l},/no_copy
              'SELDISPLAY':Widget_Control,wdraw,SEND_EVENT={seldisplay,ID:event.id,TOP:event.top,Handler:0l},/no_copy
             'SELDELETE':Widget_Control,wdraw,SEND_EVENT={seldelete,ID:event.id,TOP:event.top,Handler:0l},/no_copy
             'SELDELALL':Widget_Control,wdraw,SEND_EVENT={SelDelAll,ID:event.id,TOP:event.top,Handler:0l},/no_copy
              'SELSAVE':Widget_Control,wdraw,SEND_EVENT={selsave,ID:event.id,TOP:event.top,Handler:0l},/no_copy
              'SELNEWDB':Widget_Control,wdraw,SEND_EVENT={selnewdb,ID:event.id,TOP:event.top,Handler:0l},/no_copy
              'LINFIT':Widget_Control,wdraw,SEND_EVENT={linfit,ID:event.id,TOP:event.top,Handler:0l},/no_copy
              'QUERYPLOT':Widget_Control,wdraw,SEND_EVENT={queryplot,ID:event.id,TOP:event.top,Handler:0l},/no_copy
             'EXIT': goto,exit_line

          ELSE:
          ENDCASE
        END;widget_button
   'WIDGET_LIST': BEGIN
                   WIDGET_CONTROL,Event.Id,GET_UVALUE=Ev
                  CASE strupcase(Ev) OF
                   'FILES': BEGIN
                             WIDGET_CONTROL,wdraw,SEND_EVENT={datalist,ID:event.ID,TOP:event.top,HANDLER:event.handler,INDEX:event.index}
                            END
                   'QUERY': BEGIN
                             WIDGET_CONTROL,wdraw,SEND_EVENT={querylist,ID:event.ID,TOP:event.top,HANDLER:event.handler,INDEX:event.index}
                            END
                  ELSE:
                  ENDCASE
                  END; widget_list
   'WIDGET_DROPLIST': BEGIN
                       WIDGET_CONTROL,Event.Id,GET_UVALUE=Ev
                    CASE strupcase(Ev) OF
                        'ONETYPE': begin
                                    state.onetype=event.index
                                    if state.onepoint then goto,analyze
                                   end
                        'CORRTYPE':begin
                                    state.corrtype=event.index+1
                                    if state.corr eq 1 then goto,analyze
                                   end
                        'HISTTYPE':  begin
                                      Widget_Control,wdraw,SEND_EVENT=$
                                      {histtype,ID:event.id,TOP:event.top,Handler:0l,Index:event.index},/no_copy
                                     end
                        'XLIST'  : state.varx=state.varlist[Event.Index]
                     'YLIST'  : state.vary=state.varlist[Event.Index]
                     'TLIST'  : state.time=state.tlist[Event.Index]
                     'XSCALE' : begin
                                 Widget_Control,wdraw,$
                                 SEND_EVENT={xscale,ID:event.id,TOP:event.top,Handler:0l,index:event.index},/no_copy
                                end
                     'YSCALE' : begin
                                 Widget_Control,wdraw,$
                                 SEND_EVENT={yscale,ID:event.id,TOP:event.top,Handler:0l,index:event.index},/no_copy
                                end
                     'MOUSEMODE' : begin
                                 Widget_Control,wdraw,$
                                 SEND_EVENT={mousemode,ID:event.id,TOP:event.top,Handler:0l,index:event.index},/no_copy
                                end
                 ELSE:
                 ENDCASE
                END
    'SENDQUERY':BEGIN
              query=event.query
              goto,analyze
            END
    'GETNEWDB':BEGIN
                idx=(*event.dbidx).file
                valid=(*event.dbidx).index
                subdata=*state.data
                subdata=subdata[idx]
                data=ptrarr(n_elements(subdata))
                for i=0, n_elements(data)-1 do begin
                 med=ptr_new(*subdata[i])
                 (*med).valid[*]=0
                 (*med).valid[valid[i]]=1
                 data[i]=med
                end
                for i=0, n_elements(data)-1 do begin
                 same=where(idx eq idx[i],count)
                 if count gt 0 then begin
                  for r=0,n_elements(same)-1 do (*data[same[r]]).valid=((*data[same[r]]).valid or (*data[i]).valid)
                 end
                end
                data=data[uniq(idx,sort(idx))]
                save,data,file=event.file,/compress
                data=0
                ptr_free,event.dbidx
                heap_gc
               END

   ELSE:
   ENDCASE;type
   write_state:
   WIDGET_CONTROL, stash, SET_UVALUE=state, /NO_COPY
   return
end


function ROTATE_EVENT,event
    ; Read the state structure from the child base
    base = event.top
    stash = widget_info(base,/child)
    widget_control,stash,get_uvalue=state,/no_copy
   CATCH, Error_status
   IF Error_status NE 0 THEN BEGIN
      ans=DIALOG_MESSAGE(!ERROR_STATE.MSG,/error,display_name='SEND_QUERY_EVENT')
      CATCH,/CANCEL
      goto,write_state
   ENDIF
    wdraw=WIDGET_INFO(base,Find_BY_UNAME='DRAW')
    ;interchange variable in the main widget
     xvar=state.vary
     yvar=state.varx
     state.varx=xvar
     state.vary=yvar
     selx=where(strupcase(state.varlist) eq strupcase(state.varx))
     sely=where(strupcase(state.varlist) eq strupcase(state.vary))
     WIDGET_CONTROL,WIDGET_INFO(base,Find_By_Uname='XLIST'),SET_DROPLIST_SELECT=selx[0]
     WIDGET_CONTROL,WIDGET_INFO(base,Find_By_Uname='YLIST'),SET_DROPLIST_SELECT=sely[0]
     dx=state.dx
     dy=state.dy
     state.dx=dy
     state.dy=dx
     WIDGET_CONTROL,WIDGET_INFO(base,Find_By_Uname='DX'),SET_BUTTON=state.dx
     WIDGET_CONTROL,WIDGET_INFO(base,Find_By_Uname='DY'),SET_BUTTON=state.dy

     wxrange=WIDGET_INFO(event.top,Find_By_Uname='XRANGE')
     wyrange=WIDGET_INFO(event.top,Find_By_Uname='YRANGE')
     Widget_Control,wxrange,Get_Value=xrange
     Widget_Control,wyrange,Get_Value=yrange
     Widget_Control,wxrange,Set_Value=yrange
     Widget_Control,wyrange,Set_Value=xrange

     ;interchange variables in the draw widget
     Widget_Control,wdraw,Get_UVALUE=draw,/no_copy
      xtitle=(*draw.data.data).varx
      ytitle=(*draw.data.data).vary
      xscale=draw.xscale
      yscale=draw.yscale
      (*draw.data.data).varx=ytitle
      (*draw.data.data).vary=xtitle
      draw.xscale=yscale
      draw.yscale=xscale
      pivot=(*draw.data.data).x
      (*draw.data.data).x=(*draw.data.data).y
      (*draw.data.data).y=pivot
      pivot=draw.xrange
      draw.xrange=draw.yrange
      draw.yrange=pivot
     WIDGET_CONTROL,WIDGET_INFO(base,Find_By_Uname='XSCALE'),SET_DROPLIST_SELECT=draw.xscale
     WIDGET_CONTROL,WIDGET_INFO(base,Find_By_Uname='YSCALE'),SET_DROPLIST_SELECT=draw.yscale
     write_state:
     Widget_Control,wdraw,Set_UVALUE=draw,/no_copy
     WIDGET_CONTROL, stash, SET_UVALUE=state, /NO_COPY
     Widget_Control,wdraw,SEND_EVENT={plot,ID:base,TOP:base,Handler:0L},/no_copy
    END

pro DRAW_EVENT,event
 type=Tag_Names(event,/Structure)
 Widget_Control,event.handler,Get_UVALUE=draw,/no_copy
  CATCH, Error_status
   IF Error_status NE 0 THEN BEGIN
      ans=DIALOG_MESSAGE(!ERROR_STATE.MSG,/error,display_name='DRAW_EVENT')
     CATCH,/CANCEL
      set_plot,'win'
      wset,draw.wplot
      goto,write_state
   ENDIF
 case type of
 'WIDGET_DRAW': BEGIN
                 xmin=draw.window.position[0]
                 xmax=draw.window.position[2]
                 ymin=draw.window.position[1]
                 ymax=draw.window.position[3]
                 x=event.x<xmax>xmin
                 y=event.y<ymax>ymin
                 case event.type of
                  0:begin ; Mouse button press event.
                        case event.press of
                         1:begin
                            DEVICE, GET_GRAPHICS_FUNCTION = graphics_function, SET_GRAPHICS_FUNCTION = 6
                            draw.box.press=1
                         draw.box.x0=x
                         draw.box.x1=x
                         if draw.keywords.colapse eq 0 then draw.box.y0=y  else  draw.box.y0=ymin
                      if draw.keywords.colapse eq 0 then draw.box.y1=y else draw.box.y1=ymax
                         if draw.mouse eq 2 then begin
                             draw.box.y0=ymin
                          draw.box.y1=ymax
                         end
                         draw.graphics_function=graphics_function
                         plots,/dev,[x,x,x,x,x],[y,y,y,y,y]
                           end
                         else:
                        endcase;press case
                    end
                 1:begin ; Mouse button release event.
                      case event.release of
                       1:begin
                          draw.box.press=0
                          x0=draw.box.x0
                       y0=draw.box.y0
                       x1=draw.box.x1
                       y1=draw.box.y1
                          plots,/dev,[x0,x0,x1,x1,x0],[y0,y1,y1,y0,y0]   ; Erase current box
                          DEVICE,SET_GRAPHICS_FUNCTION = draw.graphics_function
                          x=[x0,x1]
                          x=x[sort(x)]
                          y=[y0,y1]
                          y=y[sort(y)]
                          if draw.valid eq 1 and draw.med eq 0 then begin
                              D = CONVERT_COORD(x,y, /DEVICE, /TO_DATA)
                              query=transpose(reform(d[0:1,*]))
                              ;if keyword_set(draw.keywords.colapse) then begin
                               ;query[*,1]=[min((*draw.data.data).y,/nan),max((*draw.data.data).y,/nan)]
                              ;end
                              case draw.mouse of
                              0: begin ;zoom mode
                                   xmin=query[0,0]
                                   xmax=query[1,0]
                                   ymin=query[0,1]
                                   ymax=query[1,1]
                                   if xmin ne xmax and ymin ne ymax then begin
                                    draw.xrange=[xmin,xmax]
                                    draw.yrange=[ymin,ymax]
                                   endif else begin
                                    wxrange=WIDGET_INFO(event.top,Find_By_Uname='XRANGE')
                              WIDGET_CONTROL,wxrange,Get_Value=xtext
                              xtext=xtext[0]
                              if xtext ne '[AUTO,AUTO]' then begin
                                 r=execute('xr='+xtext,1)
                                 if r eq 0 or n_elements(xr) ne 2 then begin
                                  ;ans=dialog_message(['X Range should be the form of',$
                                                      ;'[min,max]','Action canceled !'],/error)
                                  Widget_Control,wxrange,Set_Value='[AUTO,AUTO]'
                                  draw.xrange=[min((*draw.data.data).x,/nan),max((*draw.data.data).x,/nan)]
                                  ;goto, write_state
                                 endif else draw.xrange=xr
                              endif else draw.xrange=[min((*draw.data.data).x,/nan),max((*draw.data.data).x,/nan)]

                              wYRANGE=WIDGET_INFO(event.top,Find_By_Uname='YRANGE')
                              WIDGET_CONTROL,wYRANGE,Get_Value=ytext
                              ytext=ytext[0]
                              if ytext ne '[AUTO,AUTO]' then begin
                                 r=execute('yr='+ytext,1)
                                 if r eq 0 or n_elements(yr) ne 2 then begin
                                  ;ans=dialog_message(['Y Range should be the form of',$
                                                       ;'[min,max]','Action canceled !'],/error)
                                  Widget_Control,wYRANGE,Set_Value='[AUTO,AUTO]'
                                  draw.yrange=[min((*draw.data.data).y,/nan),max((*draw.data.data).y,/nan)]
                                  ;goto, write_state
                                 endif else draw.yrange=yr
                              endif else draw.yrange=[min((*draw.data.data).y,/nan),max((*draw.data.data).y,/nan)]
                                   endelse
                                   goto, plot_line
                                  end
                               1:WIDGET_CONTROL,event.top,SEND_EVENT={sendquery,ID:event.handler,TOP:event.top,Handler:0l,query:query}
                               2: begin ;fit mode
                                   xmin=query[0,0]
                                   xmax=query[1,0]
                                   ymin=query[0,1]
                                   ymax=query[1,1]
                                   if xmin ne xmax and ymin ne ymax then begin
                                    fitrange=[xmin,xmax]
                                    draw.fitrange=fitrange
                                    goto, plot_line
                                   endif else draw.fitrange=[0.0,0.0]
                                  end
                               else:
                              endcase
                          end
                         end
                       else:
                      endcase;release case
                     end

                 2:    begin ;move event
                        if draw.box.press eq 1 then begin
                         x0=draw.box.x0
                         y0=draw.box.y0
                         x1=draw.box.x1
                         y1=draw.box.y1
                         if draw.keywords.colapse eq 1 or draw.mouse eq 2 then y=ymax
                         plots,/dev,[x0,x0,x1,x1,x0],[y0,y1,y1,y0,y0]   ; Erase current box
                          plots,/dev,[x0,x0,x,x,x0],[y0,y,y,y0,y0];Draw new box
                          draw.box.x1=x ;store new box
                         draw.box.y1=y
                       end
                       end
                 else:
                 endcase
                END

    'COLAPSE':  begin
                 draw.keywords.colapse=1-draw.keywords.colapse
                 if draw.valid eq 1 then goto,plot_line
               end

    'HISTTYPE': begin
                draw.weight=event.index
                if draw.keywords.colapse eq 1 and draw.valid eq 1 then goto,plot_line
               end

    'NORM': begin
             draw.keywords.norm=1-draw.keywords.norm
             if draw.valid eq 1 then goto,plot_line
            end

    'STAT': begin
             draw.keywords.stat=1-draw.keywords.stat
             if draw.valid eq 1 then goto,plot_line
            end

    'XSCALE':begin
              draw.xscale=event.index
              if draw.valid eq 1 then goto,plot_line
             end

    'YSCALE':begin
              draw.yscale=event.index
              if draw.valid eq 1 then goto,plot_line
             end
'DATALIST': BEGIN
             draw.med=0
             index=event.index
             draw.dbindex=index
             if draw.keywords.colapse eq 0 then begin
                 highlight:
                 x=(*draw.data.data).x
                 y=(*draw.data.data).y
                 n=(*draw.data.data).n
                 f=(*draw.data.data).f
                 if n_elements(x) gt 1 then begin
                   wset,draw.wplot
                   device,copy=[0,0,draw.window.size.x,draw.window.size.y,0,0,draw.wmap]
                   range=where(n eq draw.dbindex)
                   oplot,x[range],y[range],psym=2,color=250
                 end
             end
            END

'DBDISPLAY':BEGIN
            if draw.dbindex ge 0 then begin
             draw.med=1
             xx=!x
             yy=!y
             pp=!p
             data=*event.pdata
             f=(*draw.data.data).f
             file=f[draw.dbindex]
             n=(*draw.data.data).n
             x=(*draw.data.data).x
             y=(*draw.data.data).y
             tavg=(*draw.data.data).tavg
             range=where(n eq draw.dbindex)
             med=*data[(*draw.data.data).idx[draw.dbindex].file]
             index=(*draw.data.data).idx[draw.dbindex].index
             plot_med,med,event.varx,event.vary,index,data={x:x[range],y:y[range],t:tavg[range]}
             data=0
             !x=xx
             !y=yy
             !p=pp
             !p.multi=0
            end
            END
'DBSELECT': BEGIN
             dbindex=draw.dbindex
             if dbindex ge 0 then begin
             dblist=(*draw.data.data).f
             selfile=dblist[dbindex]
             if draw.selindex ge 0 then sellist=[*draw.q,selfile] else sellist=[selfile]
             sellist=sellist[uniq(sellist,sort(sellist))]
             ptr_free,draw.q
             draw.q=ptr_new(sellist)
             draw.selindex=where(sellist eq selfile)
             querylist=widget_info(event.top,find_by_uname='QUERY')
             WIDGET_CONTROL,querylist,Set_Value=sellist
             WIDGET_CONTROL,WIDGET_INFO(event.top,FIND_BY_UNAME='SELDISPLAY'),$
             SET_VALUE=string(n_elements(sellist),format="('Selected Events: ',I3)")
             WIDGET_CONTROL,querylist,SET_LIST_SELECT=draw.selindex
             end
            END

'DBSELALL': BEGIN
             ;dbindex=draw.dbindex
             ;if dbindex ge 0 then begin
             dblist=(*draw.data.data).f
             sellist=dblist
             ptr_free,draw.q
             draw.q=ptr_new(sellist)
             draw.selindex=0
             querylist=widget_info(event.top,find_by_uname='QUERY')
             WIDGET_CONTROL,querylist,Set_Value=sellist
             WIDGET_CONTROL,WIDGET_INFO(event.top,FIND_BY_UNAME='SELDISPLAY'),$
             SET_VALUE=string(n_elements(sellist),format="('Selected Events: ',I3)")
             WIDGET_CONTROL,querylist,SET_LIST_SELECT=draw.selindex
             ;end
            END

'SELDISPLAY':BEGIN
             END
'SELDELETE':BEGIN
             selindex=draw.selindex
             if selindex ge 0 then begin
              sellist=*draw.q
              index=where(sellist eq sellist[selindex],complement=remaining,ncomplement=count)
              if count gt 0 then begin
               sellist=sellist[remaining]
               ptr_free,draw.q
               draw.q=ptr_new(sellist)
               draw.selindex=0
               querylist=widget_info(event.top,find_by_uname='QUERY')
               WIDGET_CONTROL,querylist,Set_Value=sellist
               WIDGET_CONTROL,querylist,SET_LIST_SELECT=draw.selindex
               WIDGET_CONTROL,WIDGET_INFO(event.top,FIND_BY_UNAME='SELDISPLAY'),$
               SET_VALUE=string(n_elements(sellist),format="('Selected Events: ',I3)")
              endif else begin
               ptr_free,draw.q
               draw.q=ptr_new('')
               draw.selindex=-1
               querylist=widget_info(event.top,find_by_uname='QUERY')
               WIDGET_CONTROL,querylist,Set_Value=''
               WIDGET_CONTROL,WIDGET_INFO(event.top,FIND_BY_UNAME='SELDISPLAY'),$
               SET_VALUE=string(0,format="('Selected Events: ',I3)")
              end
             end
            END
 'SELDELALL':BEGIN
               querylist=widget_info(event.top,find_by_uname='QUERY')
               WIDGET_CONTROL,querylist,Set_Value=''
               ptr_free,draw.q
               draw.q=ptr_new('')
               draw.selindex=-1
               WIDGET_CONTROL,WIDGET_INFO(event.top,FIND_BY_UNAME='SELDISPLAY'),$
               SET_VALUE=string(0,format="('Selected Events: ',I3)")
             END

'SELSAVE':  BEGIN
             files=*draw.q
             if files[0] ne '' then begin
                 file=dialog_pickfile(filter='*.sav',title='Select a file to save selected file list')
                 if file ne '' then begin
                  files=*draw.q
                  save,files,file=file
                 end
             end
            END

'SELNEWDB': BEGIN
             file=dialog_pickfile(filter='*.sav',title='Select a file to save selected database subset')
             if file ne '' then begin
              selected=*draw.q
              nsel=n_elements(selected)
              selidx=intarr(nsel)
              displayed=(*draw.data.data).f
              for s=0,nsel-1 do selidx[s]=where(displayed eq selected[s])
              dbidx=(*draw.data.data).idx[selidx]
              Widget_Control,event.top,Send_Event={getnewdb,ID:event.id,Top:Event.top,Handler:0l,dbidx:ptr_new(dbidx),file:file}
             end
            END



 'QUERYLIST':BEGIN
              draw.selindex=event.index
              q=*draw.q
              f=(*draw.data.data).f
              index=where(f eq q[event.index],count)
              if count ne 0 then begin
               index=index[0]
               WIDGET_CONTROL,WIDGET_INFO(event.top,FIND_BY_UNAME='FILES'),SET_LIST_SELECT=index
               draw.dbindex=index
               if draw.keywords.colapse eq 0 then goto,highlight
              end
             END

  'QUERY':   BEGIN
                 f=*event.f
                 WIDGET_CONTROL,WIDGET_INFO(event.top,FIND_BY_UNAME='SELDISPLAY'),$
                 SET_VALUE=string(n_elements(f),format="('Selected Events: ',I4)")
                 WIDGET_CONTROL,WIDGET_INFO(event.top,FIND_BY_UNAME='QUERY'),SET_VALUE=f
                 ptr_free,draw.q
                 draw.q=event.f
                 f=0
            END
 'QUERYPLOT':BEGIN
              query=fltarr(2,2)
              query[*,0]=draw.xrange
              query[*,1]=draw.yrange
              WIDGET_CONTROL,event.top,SEND_EVENT={sendquery,ID:event.handler,TOP:event.top,Handler:0l,query:query}
             END

 'LINFIT': BEGIN
           ;fitrange=[min((*draw.data.data).x,/nan),max((*draw.data.data).x,/nan)]
           fitrange=draw.xrange
           draw.fitrange=fitrange
           goto,plot_line
           END
 'REFRESH': BEGIN
               wset,draw.wplot
               device,copy=[0,0,draw.window.size.x,draw.window.size.y,0,0,draw.wmap]
            END

 'NEWDATA': BEGIN
             ptr_free,draw.data.data
             draw.data=event.data
             draw.valid=1
             WIDGET_CONTROL,WIDGET_INFO(event.top,FIND_BY_UNAME='FILES'),SET_VALUE=(*draw.data.data).f
             WIDGET_CONTROL,WIDGET_INFO(event.top,FIND_BY_UNAME='DBDISPLAY'),$
             SET_VALUE=string(n_elements((*draw.data.data).f),format="('Displayed Events: ',I4)")
             draw.xrange=[min((*draw.data.data).x,/nan),max((*draw.data.data).x,/nan)]
             draw.yrange=[min((*draw.data.data).y,/nan),max((*draw.data.data).y,/nan)]
             goto,plot_line
            END

'MOUSEMODE':BEGIN
             draw.mouse=event.index
            END

 'PLOT':     BEGIN
 plot_line:
            WIDGET_CONTROL,/HOURGLASS
            draw.med=0
            if draw.valid eq 0 then message,'No valid data points!'
         x=(*draw.data.data).x
         y=(*draw.data.data).y
         n=(*draw.data.data).n
            f=(*draw.data.data).f
             wxrange=WIDGET_INFO(event.top,Find_By_Uname='XRANGE')
                       WIDGET_CONTROL,wxrange,Get_Value=xtext
                       xtext=xtext[0]
                       if xtext ne '[AUTO,AUTO]' then begin
                          r=execute('xr='+xtext,1)
                          if r eq 0 or n_elements(xr) ne 2 then begin
                           ans=dialog_message(['X Range should be the form of',$
                                                '[min,max]','Action canceled !'],/error)
                           Widget_Control,wxrange,Set_Value='[AUTO,AUTO]'
                           goto, write_state
                          endif else draw.xrange=xr
                       endif

                        wYRANGE=WIDGET_INFO(event.top,Find_By_Uname='YRANGE')
                       WIDGET_CONTROL,wYRANGE,Get_Value=ytext
                       ytext=ytext[0]
                       if ytext ne '[AUTO,AUTO]' then begin
                          r=execute('yr='+ytext,1)
                          if r eq 0 or n_elements(yr) ne 2 then begin
                           ans=dialog_message(['Y Range should be the form of',$
                                                '[min,max]','Action canceled !'],/error)
                           Widget_Control,wYRANGE,Set_Value='[AUTO,AUTO]'
                           goto, write_state
                          endif else draw.yrange=yr
                       endif


            if keyword_set(draw.weight) then w=(*draw.data.data).w
         timerange=(*draw.data.data).time
         corr=(*draw.data.data).corr
         onepoint=(*draw.data.data).onepoint
         mainpeak=(*draw.data.data).mainpeak
           xtitle=(*draw.data.data).varx
         ytitle=(*draw.data.data).vary
         colapse=draw.keywords.colapse
         norm=draw.keywords.norm
         stat=draw.keywords.stat
         test_x= draw.xrange eq [min((*draw.data.data).x,/nan),max((*draw.data.data).x,/nan)]
         if total(test_x) ne 2 then xrange=draw.xrange
            test_y= draw.yrange eq [min((*draw.data.data).y,/nan),max((*draw.data.data).y,/nan)]
            if total(test_y) ne 2 then yrange=draw.yrange
              if keyword_set(xrange) then begin
          fgood=where(x ge xrange[0] and x le xrange[1],fcount)
             if fcount eq 0 then begin
              ans=dialog_message(['No data in this X range',$
                                         'Action canceled !'],/error)
             endif else begin
              x=x[fgood]
              y=y[fgood]
              n=n[fgood]
              if keyword_set(draw.weight) then w=w[fgood]
             end
            end

              if keyword_set(yrange) and not keyword_set(colapse) then begin
          fgood=where(y ge yrange[0] and y le yrange[1],fcount)
             if fcount eq 0 then begin
              ans=dialog_message(['No data in this Y range',$
                                         'Action canceled !'],/error)
             endif else begin
              x=x[fgood]
              y=y[fgood]
              n=n[fgood]
              if keyword_set(draw.weight) then w=w[fgood]
             end
            end

         if keyword_set(colapse) then begin
              wbin=WIDGET_INFO(event.top,Find_By_Uname='bin')
                       WIDGET_CONTROL,wbin,Get_Value=bintext
                       bintext=bintext[0]
                       if bintext ne '' then begin
                          r=execute('nbins='+bintext,1)
                          if r eq 0 then begin
                           ans=dialog_message(['Number of bins must be an integer number',$
                                               'Action canceled !'],/error)
                           goto, write_state
                          endif
                       endif
           end

         ;SET X AND Y SCALES

         case draw.xscale of
          1:xlog=0
          2:xlog=1
          0 :begin
                  if max(x,/nan) gt 1000 then begin
                xlog=1
               endif else xlog=0
              end
          else:
         endcase

         case draw.yscale of
          1:ylog=0
          2:ylog=1
          0:begin
                  if not keyword_set(colapse) then begin
                if max(y,/nan) gt 1000 then begin
                 ylog=1
                endif else ylog=0
               endif else ylog=0
              end
          else:
         endcase

         if keyword_set(corr) then begin
          good=where(finite(x) eq 1 and finite(y) eq 1,npoints)
          if npoints gt 0 then begin
           xc=x[good]
           yc=y[good]
           if not keyword_set(fitrange) then fitrange=[min(xc,/nan),max(xc,/nan)]
           if keyword_set(xlog) then xc=alog10(xc)
           if keyword_set(ylog) then yc=alog10(yc)
           xc=xc[good]
           yc=yc[good]
           result=psk_correlate(xc,yc,corr=corr)
           cross=result[0]
           prob=1-result[1]
          end
         end

         if keyword_set(stat) then begin
          mean=moment(x,/nan,sdev=sdev)
          mean=mean[0]
          good=where(finite(x) eq 1 and finite(y) eq 1,npoints)
          subtitle='MEAN:'+string(mean,format='(f0.2)')+$
          ' SDEV:'+string(sdev,format='(f0.2)')+ $
          ' N EVENTS:'+string(n_elements(f),format='(I32)')+ $
          ' N POINTS:'+string(npoints,format='(I32)')
          if keyword_set(corr) then subtitle=subtitle+string(cross,100*prob,format="(' R:',f5.2,' P:',f7.2,'%')")
          subtitle=strcompress(subtitle)
         end

         if keyword_set(colapse) then begin
              xrange=draw.xrange
              if xlog eq 1 then begin
                maxx=max(alog10(xrange[1]),/nan);max(alog10(x),/nan)
                binsz=maxx/nbins
                k=10^binsz
                xscale=k^indgen(nbins)
                ;y=w_histogram(alog10(x),w,min=alog10(xscale[0]),max=alog10(xscale[nbins-1]),nbins=nbins)
                y=w_histogram(alog10(x),w,min=alog10(xscale[0]),binsize=binsz,nbins=nbins)
                nonzero=y(where(y gt 0))
             yrange=[min(nonzero,/nan),max(y,/nan)]
                x=xscale
              endif else begin
                minx=xrange[0];min(x,/nan)
             maxx=xrange[1];max(x,/nan)
             ;if strmid(xtitle,0,11) eq 'Correlation' then begin
              ;minx=-1.0
              ;maxx=1.0
              ;xrange=[-1.001,1.001]
             ;end
             ;binsz=(maxx-minx)/(nbins-1)
             binsz=(maxx-minx)/nbins
             ;y=w_histogram(x,w,min=minx,max=maxx,nbins=nbins,/nan)
             y=w_histogram(x,w,min=minx,nbins=nbins,binsize=binsz,/nan)
             nonzero=y(where(y gt 0))
             yrange=[min(nonzero,/nan),max(y,/nan)]
             x=minx+indgen(n_elements(y))*binsz
           end

           psym=10
           ytitle='Number of data points'

           if keyword_set(norm) then begin
            if ylog eq 0 then begin
             y=y/total(y)
             ytitle='Normalized distribution'
             nonzero=y(where(y gt 0))
             yrange=[min(nonzero,/nan),max(y,/nan)]
             ysty=1
            end
            if xlog eq 1 then begin
             y=y/x
             ytitle='Density distribution'
             nonzero=y(where(y gt 0))
             yrange=[min(nonzero,/nan),max(y,/nan)]
            end
           end

           if keyword_set(stat) then begin
           if n_elements(yrange) eq 0 then yrange=[min(y,/nan),max(y,/nan)]
            ;yrange=1.1*yrange
            ysty=1
           end

         end
         if not keyword_set(psym) then if n_elements(x) gt 1000 then psym=3 else psym=8

            if not keyword_set(xrange) then begin
            if xlog eq 1 then if not keyword_set(draw.keywords.norm) then $
              xrange=[min(x,/nan)>1,1.1*max(x,/nan)] else xrange=[min(x,/nan)>0.00001,1.1*max(x,/nan)]
            end

         if not keyword_set(yrange) then begin
            if ylog eq 1 then if not keyword_set(draw.keywords.norm) then $
            yrange=[min(y,/nan)>1,1.1*max(y,/nan)] else yrange=[min(y,/nan)>0.00001,1.1*max(y,/nan)]
            end

            if keyword_set(fitrange) then begin
             if not keyword_set(yrange) then yrange=draw.yrange
             good=where(finite(x) eq 1 and finite(y) eq 1,npoints)
          if npoints gt 0 then begin
           xc=x[good]
           yc=y[good]
           good=where( xc ge fitrange[0] and xc le fitrange[1] $
           and yc ge yrange[0] and yc le yrange[1],npoints)
           if npoints gt 0 then begin
               if keyword_set(xlog) then xc=alog10(xc)
               if keyword_set(ylog) then yc=alog10(yc)
               xc=xc[good]
               yc=yc[good]
               fit=linfit(xc,yc,yfit=yfit)
               crossfit=y*!values.f_nan
               crossfit[good]=yfit
               if keyword_set(ylog) then crossfit=10.0^crossfit
           end
          end
         end

         if not keyword_set(colapse) and not keyword_set(stat) and keyword_set(corr) $
         then subtitle=string(cross,100*prob,format="('R=',f5.2,' P=',f7.2,'%')")

         title='TIME RANGE: '+strupcase(timerange)
         if keyword_set(fit) then title= title+' LinFit slope:'+string(fit[1],format='(f7.3)')

plot_data:
            ;w=(*draw.data.data).w
            if strupcase(xtitle) eq 'SIZE'  then begin
             ;x=x*180*60.0/!pi
             xrange=[min(x,/nan),max(x,/nan)]
             xtitle='Size(arcmin)'
            end
            if strupcase(ytitle) eq 'SIZE'  then begin
             ;y=y*180*60.0/!pi
             yrange=[min(y,/nan),max(y,/nan)]
             ytitle='Size(arcmin)'
            end
            ;if strmid(xtitle,0,11) eq 'Correlation' then begin
            ;  minx=-1.0
            ;  maxx=1.0
            ;  xrange=[-1.001,1.001]
            ; end
            if not keyword_set(print) and not keyword_set(psprint) then begin
          set_plot,'win'
          wset,draw.wplot
          erase,255
          plot_w,x,y,w,xsty=1,ysty=1,psym=psym,xtitle=xtitle,ytitle=ytitle,title=title,$
                       xrange=xrange,yrange=yrange,xlog=xlog,ylog=ylog,subtitle=subtitle,color=0,back=255,$
                       position=draw.window.position,/dev
         endif else begin
          plot_w,x,y,w,xsty=1,ysty=1,psym=psym,xtitle=xtitle,ytitle=ytitle,title=title,$
                       xrange=xrange,yrange=yrange,xlog=xlog,ylog=ylog,subtitle=subtitle
         end

         if keyword_set(crossfit) then begin
           oplot,x,crossfit,color=0,thick=2
           ;if not keyword_set(colapse) then oplot,x(sort(x)),crossfit(sort(x)),color=0,thick=2
         end

         if keyword_set(stat) then begin
               if n_elements(yrange) eq 0 then yrange=[min(x,/nan),1.1*max(x,/nan)]
               ysty=1
            oplot,[mean,mean],yrange,linestyle=2,thick=2,color=0
            oplot,mean+[sdev,sdev],yrange,linestyle=1,thick=2,color=0
            oplot,mean-1*[sdev,sdev],yrange,linestyle=1,thick=2,color=0
         end

         if keyword_set(psprint) or keyword_set(print) then begin
          device,/close
          set_plot,'win'
         endif else begin
          wset,draw.wmap
             device,copy=[0,0,draw.window.size.x,draw.window.size.y,0,0,draw.wplot]
             wset,draw.wplot
         end

            if keyword_set(save) then begin
             save,x,y,w,xsty,ysty,psym,xtitle,ytitle,title,$
               xrange,yrange,xlog,ylog,subtitle,color,back,$
               position,file=datafile,/compress
            end


        END

  'PRINT':  BEGIN
             set_plot,'printer'
             print=1
             if total(draw.fitrange) ne 0 then fitrange=draw.fitrange
             goto,plot_line
         END

  'PSPRINT':BEGIN
            psfile=dialog_pickfile(filter='*.ps',title='Please choose a postscript filename')
         if psfile ne '' then begin
          set_plot,'ps'
          device,file=psfile
          psprint=1
          if total(draw.fitrange) ne 0 then fitrange=draw.fitrange
          goto,plot_line
         end
          END

  'SAVE':  begin
          datafile=dialog_pickfile(filter='*.dat',title='Please choose a filename to save data')
          if datafile ne '' then begin
           save=1
           goto,plot_line
          end
         end
 else:
 endcase
write_state:
Widget_Control,event.handler,Set_UVALUE=draw,/no_copy
end



;MAIN WIDGET DEFINITION

pro WQUERY,Group=Group,database=database,med=med,title=title
   CATCH, Error_status
   IF Error_status NE 0 THEN BEGIN
      ans=DIALOG_MESSAGE(!ERROR_STATE.MSG,/error,display_name='WQUERY')
      CATCH,/CANCEL
      return
   ENDIF

    device,decompose=0
    loadct,39

    defsysv,'!DEFAULTS',EXISTS=exists
    if not exists then defparms
    IF N_ELEMENTS(Group) EQ 0 THEN GROUP=0
    if not keyword_set(database)then begin
     if size(med,/type) eq 8 then begin
      data=ptr_new([ptr_new(med)])
      nfiles=1
     endif ;else message,'This is not avalid med structure'
     nodata:
     if n_elements(data) eq 0 then data=ptr_new()
     if n_elements(title) eq 0 then title='WQuery'
     if n_elements(nfiles) eq 0 then nfiles=0
    endif else begin
     restore,database
     nfiles=n_elements(data)
     if nfiles ne 0 then begin
      data=ptr_new(data,/no_copy)
      title='WQuery-['+database+']'
     endif else goto,nodata
    end


   wBase = WIDGET_BASE(GROUP_LEADER=Group, $
      COLUMN=1, $
      MAP=1, $
      MBAR=mbar, $
      /TLB_KILL_REQUEST_EVENTS,$
      TITLE=TITLE, $
      UVALUE='MainBase',$
      UNAME='MainBase')

   ; This base is just to carry the STATE structure
   ExtraBase = WIDGET_BASE(wBase, $
      ROW=1, $
      MAP=1, $
      TITLE='ExtraBase', $
      UVALUE='ExtraBase')


   LeftBase  = WIDGET_BASE(ExtraBase, COLUMN=1, MAP=1, $
                         TITLE= 'LeftBase',UVALUE= 'LeftBase')
   FileBase = WIDGET_BASE(ExtraBase, COLUMN=1, MAP=1, $
                         TITLE='FileBase',UVALUE='FileBase',UNAME='FileBase')
   RightBase = WIDGET_BASE(ExtraBase, COLUMN=1, MAP=1, $
                         TITLE='RightBase',UVALUE='RightBase',UNAME='RightBase')

   FileDisplay=Widget_Button(FileBase,VALUE=string(0,format="('Displayed Events: ',I4)"),$
                            Uname='DBDISPLAY',UVALUE='DBDISPLAY', /ALIGN_LEFT )
   FileList=Widget_List(FileBase,UVALUE='FILES',UNAME='FILES',YSIZE=20)
   FileSelect=Widget_Button(FileBase,VALUE=string(0,format="('Selected Events: ',I4)"),$
                            Uname='SELDISPLAY',UVALUE='DbSelect', /ALIGN_LEFT )
   QueryList=Widget_List(FileBase,UVALUE='QUERY',UNAME='QUERY',YSIZE=19)


    file_menu = WIDGET_BUTTON(mbar, VALUE='File', /MENU)
    file_bttn=WIDGET_BUTTON(file_menu, VALUE='Open database',$
       UVALUE='BROWSE')
    file_bttn=WIDGET_BUTTON(file_menu, VALUE='Open MED file',$
       UVALUE='MED')
    file_bttn=WIDGET_BUTTON(file_menu, VALUE='Print',$
       UVALUE='PRINT')
    file_bttn=WIDGET_BUTTON(file_menu, VALUE='Print to PS',$
       UVALUE='PRINT TO PS')
    file_bttn=WIDGET_BUTTON(file_menu, VALUE='Save',$
       UVALUE='SAVE')
    file_bttn=WIDGET_BUTTON(file_menu, VALUE='Exit',$
       UVALUE='Exit')


    display_menu=WIDGET_BUTTON(mbar, VALUE='Displayed Event List',/MENU)
    display_bttn=WIDGET_BUTTON(display_menu, VALUE='Display Item',UVALUE='DbDisplay')
    display_bttn=WIDGET_BUTTON(display_menu, VALUE='Select Item',UVALUE='DbSelect')
    display_bttn=WIDGET_BUTTON(display_menu, VALUE='Select All',UVALUE='DbSelAll')

    select_menu=WIDGET_BUTTON(mbar, VALUE=' Selected Event List',/MENU)
    select_bttn=WIDGET_BUTTON(select_menu, VALUE='Display Item',UVALUE='SelDisplay')
    select_bttn=WIDGET_BUTTON(select_menu, VALUE='Delete Item',UVALUE='SelDelete')
    select_bttn=WIDGET_BUTTON(select_menu, VALUE='Delete All',UVALUE='SelDelAll')
    select_bttn=WIDGET_BUTTON(select_menu, VALUE='Save File List',UVALUE='SelSave')
    select_bttn=WIDGET_BUTTON(select_menu, VALUE='Save Database Subset',UVALUE='SelNewDb')

    tool_menu = WIDGET_BUTTON(mbar, VALUE='Tools', /MENU)
    tool_bttn=WIDGET_BUTTON(tool_menu, VALUE='Create database',UVALUE='DbCreate')
    tool_bttn=Widget_Button(tool_menu,VALUE='Refresh display',Uname='REFRESH',UVALUE='REFRESH')
    tool_bttn=Widget_Button(tool_menu,VALUE='Linear Fit',Uname='LINFIT',UVALUE='LINFIT')


   ; CREATE THE MAIN DISPLAY WINDOW

     WXSIZE=640
     WYSIZE=560
     xoff=0
     yoff=0
     xsize=WXSIZE
     ysize=WYSIZE
     ;define pixelmap
     window,/free,/pixmap,xsize=xsize,ysize=ysize
     erase,255
     wmap = !d.window
     plot,indgen(100),color=0
     x=!x.window*xsize
     y=!y.window*ysize
     position=[x[0],y[0],x[1],y[1]]
     window={size:{x:wxsize,y:wysize},position:[x[0],y[0],x[1],y[1]]}
     wdraw = WIDGET_DRAW(LeftBase, $
     XSIZE=640, YSIZE=560, /BUTTON_EVENTS, /MOTION_EVENTS, $
     EVENT_PRO='DRAW_EVENT',FRAME=1,UNAME='DRAW')



     ;Define draw window's user value to be set later
     wdUVALUE={valid:0,wmap:wmap,wplot:0l,graphics_function:3,window:window,box:{x0:0,y0:0,x1:0,y1:0,press:0},data:{plotdata},$
     keywords:{colapse:0,norm:0,stat:0},xscale:0,yscale:0,mouse:0,q:ptr_new(),dbindex:-1,selindex:-1,med:0,weight:0,$
     xrange:[0.0,0.0],yrange:[0.0,0.0],fitrange:[0.0,0.0]}


   ;wbrowse=Widget_Button(RightBase,VALUE='Database',Uname='Browse',UVALUE='Browse', /ALIGN_LEFT )
   ;wdata=Widget_Text(RightBase,UNAME='Database',Value=database,UVALUE='Database',/editable)


   freqLabel=Widget_Button(RightBase,VALUE='Frequency Range',Uname='Frequency Range',UVALUE='Frequency Range', /ALIGN_LEFT )
   wfreqrange=Widget_Text(RightBase,UNAME='freqrange',Value='[1,18]',/editable,xsize=10)

   fluxLabel=Widget_Button(RightBase,VALUE='Flux Range',Uname='Flux Range',UVALUE='Flux Range', /ALIGN_LEFT )
   wfluxrange=Widget_Text(RightBase,UNAME='fluxrange',Value='[1,10.0^6]',/editable,xsize=10)



   varlist=['PEAKFLUX','PEAKFREQ','THINFLUX', 'THICKFLUX' , 'THICKINDEX', 'THININDEX', 'ABSFLUX','THIN_THICK_RATIO',$
           'DURATION','WAITING TIME','ENERGY','SIZE', 'G_THICKINDEX', 'G_THININDEX','BETA']
   XLabel=Widget_Label(RightBase, VALUE='X Variable',/Align_Left )
   DXList = WIDGET_DROPLIST(RightBase,$
              VALUE=varlist,$
              /DYNAMIC_RESIZE,Uname='XLIST',UValue='XList')

   XLabel=Widget_Label(RightBase, VALUE='Y Variable',/Align_Left )
   DYList = WIDGET_DROPLIST(RightBase,$
              VALUE=varlist,$
              /DYNAMIC_RESIZE,Uname='YLIST',UValue='YList')
   tLabel=Widget_Label(RightBase, VALUE='Time Range',/Align_Left )

   DTimeList = WIDGET_DROPLIST(RightBase,VALUE=['All','Rise Time','Around Peak','Decay Time','Absolute Peak'],$
    /DYNAMIC_RESIZE,Uname='Time List',UValue='TList')

   tlist=['ALL','RISE','PEAK','DECAY','ABS']

   PointLabel=Widget_Label(RightBase, VALUE='One Point Selection',/Align_Left )

   DPoint= WIDGET_DROPLIST(RightBase,VALUE=['at MAXFLUX','MEDIAN'],/DYNAMIC_RESIZE,Uname='ONETYPE',UValue='ONETYPE')

   CorrLabel=Widget_Label(RightBase, VALUE='X-Y Correlation Type',/Align_Left )

   DCorr= WIDGET_DROPLIST(RightBase,VALUE=['Pearson','Spearman','Kendall'],/DYNAMIC_RESIZE,Uname='CORRTYPE',UValue='CORRTYPE')

   HistLabel=Widget_Label(RightBase, VALUE='X-Histogram Type',/Align_Left )

   DHist= WIDGET_DROPLIST(RightBase,VALUE=['Normal','Weighted'],/DYNAMIC_RESIZE,Uname='HISTTYPE',UValue='HISTTYPE')



   ModeBase=WIDGET_BASE(RightBase, COLUMN=1, MAP=1, $
                         TITLE='ModeBase',UVALUE='ModeBase',UNAME='ModeBase',/NONEXCLUSIVE)

   wmainpeak=Widget_Button(ModeBase,VALUE='Main Peak',Uname='MAINPEAK',UValue='MAINPEAK')
   wonepoint=Widget_Button(ModeBase,VALUE='One Point',Uname='ONEPOINT',UValue='ONEPOINT')
   wcorr=Widget_Button(ModeBase,VALUE='Correlate X-Y',Uname='CORR',UValue='CORR')
   wcolapse=Widget_Button(ModeBase,VALUE='Colapse',Uname='COLAPSE',UVALUE='COLAPSE')
   wnorm=Widget_Button(ModeBase,VALUE='Normalize Histogram',Uname='NOR',UValue='NORM')
   wstat=Widget_Button(ModeBase,VALUE='Display info',Uname='STAT',UValue='STAT')

   xrangeLabel=Widget_Button(RightBase,VALUE='X Range',Uname='X Range',UVALUE='X Range', /ALIGN_LEFT )
   wxrange=Widget_Text(RightBase,UNAME='XRANGE',Value='[AUTO,AUTO]',/editable,xsize=11)

   yrangeLabel=Widget_Button(RightBase,VALUE='Y Range',Uname='Y Range',UVALUE='Y Range', /ALIGN_LEFT )
   wyrange=Widget_Text(RightBase,UNAME='YRANGE',Value='[AUTO,AUTO]',/editable,xsize=11)

   BinBase=WIDGET_BASE(RightBase, Row=1, MAP=1, $
                         TITLE='BinBase',UVALUE='BinBase',UNAME='BinBase')
   binLabel=Widget_Button(BinBase,VALUE='# of Bins',Uname='# of Bins',UVALUE='# of Bins', /ALIGN_LEFT )
   wbin=Widget_Text(BinBase,UNAME='bin',Value='20',/editable,xsize=8)



   ;wanalyze=Widget_Button(RightBase,VALUE='ANALYZE',Uname='ANALYZE',UValue='ANALYZE')


   PlotBase=WIDGET_BASE(LeftBase, Row=1)
   wanalyze=Widget_Button(PlotBase,VALUE='ANALYZE',Uname='ANALYZE',UValue='ANALYZE')
   wrotate=Widget_Button(PlotBase,VALUE='ROTATE X-Y',Uname='ROTATE',EVENT_FUNC='ROTATE_EVENT')
   tool_bttn=Widget_Button(PlotBase,VALUE='LINEAR FIT',Uname='LINFIT',UVALUE='LINFIT')
   tool_bttn=Widget_Button(PlotBase,VALUE='QUERY',Uname='QueryPlot',UVALUE='QueryPlot')

   ScaleBase=WIDGET_BASE(PlotBase, ROW=1, MAP=1, $
                         TITLE='ScaleBase',UVALUE='ScaleBase',UNAME='ScaleBase')

   XBase=WIDGET_BASE(ScaleBase, Row=1, MAP=1)
   XLabel=Widget_Label(XBase, VALUE='X-Scale: ',/Align_Left )

   DXSCALE = WIDGET_DROPLIST(XBase,VALUE=['AUTO','LIN','LOG'],/DYNAMIC_RESIZE,Uname='XSCALE',UValue='XSCALE')

   YBase=WIDGET_BASE(ScaleBase, Row=1, MAP=1)

   YLabel=Widget_Label(YBase, VALUE='Y-Scale: ',/Align_Left )

   DYSCALE = WIDGET_DROPLIST(YBase,VALUE=['AUTO','LIN','LOG'],/DYNAMIC_RESIZE,Uname='YSCALE',UValue='YSCALE')

   ;MouseLabel=Widget_Label(YBase, VALUE='  Mouse State: ',/Align_Left )

   MBase=WIDGET_BASE(ScaleBase, Row=1)
   MLabel=Widget_Label(MBase, VALUE='Mouse Mode: ',/Align_Left )
   MouseList=WIDGET_DROPLIST(MBase,VALUE=['ZOOM','QUERY','FIT'],/DYNAMIC_RESIZE,Uname='MouseMode',UValue='MouseMode')

    deltabase=WIDGET_BASE(FileBase, ROW=1, MAP=1, $
                         TITLE='DeltaBase',UVALUE='DeltaBase',UNAME='DeltaBase',/NONEXCLUSIVE)
   wdx=Widget_Button(deltaBase,VALUE='dX',Uname='DX',UValue='DX')
   wdy=Widget_Button(deltaBase,VALUE='dY',Uname='DY',UValue='DY')
   wrel=Widget_Button(deltaBase,VALUE='Rel',Uname='REL',UValue='REL')
   ; Realize the heirarchy
   widget_control,wbase,/realize

   ;Get the plot window
   WIDGET_CONTROL, wdraw, GET_VALUE=wplot
   wset,wplot
   erase,255
   wdUVALUE.wplot=wplot
   Widget_Control,wdraw,SET_UVALUE=wdUVALUE


   ;SET THE STATE VARIABLE
   state={data:data, varx:varlist[0],vary:varlist[1],time:tlist[0],$
          onepoint:0,corr:0,varlist:varlist,tlist:tlist,onetype:0,corrtype:1,mainpeak:0,dx:0,dy:0,rel:0}

   widget_control,widget_info(wBase,/child),set_uvalue=state, /no_copy
   widget_control,dylist,Set_Droplist_Select=1

   ;Call XMANAGER to handle the event messages
   xmanager,'WQuery',wBase, /NO_BLOCK
   if ptr_valid(data) then begin
    Event = {Widget_Button,Id:wanalyze,Top:wBase,Handler:wBase,Select:1}
    Widget_Control,wanalyze,SEND_EVENT=event
   end
   return
end
