;+
;
; Project   : s3drs reconstruction software
;                   
; Name      : s3drs_gui
;               
; Purpose   : part of the s3drs GUI
;               
; Explanation: Main GUI routine, draws and preps initial state,
; includes s3drs_hline, s3drs_satloscreate, s3drs_modelgui, and the
; functions for each tab (s3drs_tab_intro, s3drs_tab_data,
; s3drs_tab_syn, s3drs_tab_mask, s3drs_tab_noise, s3drs_tab_recon,
; s3drs_tab_fm, s3drs_tab_viz)
;               
; Use       : only called from 's3drs.pro' 
;    
; Inputs    : 
;               
; Outputs   : 
;
; Keywords  : 
;               
; Common    : common s3drs, s3drs (a structure)
;               
; Restrictions: none
;               
; Side effects: 
;               
; Category    : GUI
;               
; Prev. Hist. : None.
;
; Written     : Sandy Antunes, NRC, March-April 2009
;               
;-            
PRO s3drs_hline,window
  ; just some window gloss

  common s3drs,s3drs

  ignore=WIDGET_BASE(window,FRAME=2,XSIZE=s3drs.winx,ysize=2)
  ignore=WIDGET_BASE(window,FRAME=2,XSIZE=s3drs.winx,ysize=2)

END

PRO s3drs_satloscreate,parent,nologo=nologo

  common s3drs,s3drs

  nologo=KEYWORD_SET(nologo)

  ; was 119x86, now 142x83
  drawbase=WIDGET_BASE(parent,COL=2,XSIZE=142+150+50+200,YSIZE=83+150+20)

  if (nologo eq 0 and n_elements(s3drs.logo) gt 1) then begin

      wLogo = WIDGET_BUTTON(drawbase,VALUE=s3drs.logo,$
                            XSIZE=142+10,YSIZE=83,/ALIGN_LEFT)

      WIDGET_CONTROL,wLogo,TRACKING_EVENTS=0

  end

  draw_id = WIDGET_DRAW(drawbase,XSize=150,YSize=150,UName='satlos',$
                        RETAIN=2,XOFFSET=50)

END

PRO s3drs_modelgui,wFrame,uname=uname,title=title,fix=fix,arnaud=arnaud,$
                   moveable=moveable


  common s3drs,s3drs

  if (n_elements(uname) eq 0) then uname='model'; placeholder
  arnaud=KEYWORD_SET(arnaud)

  fix=KEYWORD_SET(fix)
  moveable=KEYWORD_SET(moveable)

  if (n_elements(title) eq 0) then title=''

  wM = WIDGET_BASE(wFrame,COLUMN=1,FRAME=1,TITLE=title)

  wMtop = WIDGET_BASE(wM,COLUMN=1)

  if (arnaud) then begin
      for im=0,n_elements(s3drs.models)-1 do $
        if (stregex(strupcase(s3drs.models[im]),'ARNAUD',/BOOLEAN)) then $
        push,mlist,s3drs.models[im]
  end else begin
      mlist=s3drs.models
  end

  clab = WIDGET_LABEL(wMtop,VALUE='Model choice')
  cdrop = WIDGET_LIST(wMtop,VALUE=mlist,$
                      UNAME=uname+'model',$
                      XSIZE=80,YSIZE=3,$
                      UVALUE=[uname,mlist],$
                      EVENT_PRO='s3drs_modelparam')
;                      TITLE='Model choice')

  WIDGET_CONTROL,cdrop,SET_LIST_SELECT=0

  wMeu = WIDGET_BASE(wMtop,ROW=1)
  citem = WIDGET_LABEL(wMeu,VALUE='Optional rotation Euler angles')
  citem = CW_FIELD(wMeu,/FLOAT,UNAME=uname+'euler1',XSIZE=3,VALUE='0',TITLE='')
  citem = CW_FIELD(wMeu,/FLOAT,UNAME=uname+'euler2',XSIZE=3,VALUE='0',TITLE='')
  citem = CW_FIELD(wMeu,/FLOAT,UNAME=uname+'euler3',XSIZE=3,VALUE='0',TITLE='')

  if (moveable) then begin
      wMeu2 = WIDGET_BASE(wMtop,ROW=1)
      citem = WIDGET_LABEL(wMeu2,VALUE='Optional X/Y/Z location of model center')
      n2=s3drs.Nd/2
      citem = CW_FIELD(wMeu2,/LONG,UNAME=uname+'pos1',XSIZE=3,$
                       VALUE=n2,TITLE='X')
      citem = CW_FIELD(wMeu2,/LONG,UNAME=uname+'pos2',XSIZE=3,$
                       VALUE=n2,TITLE='Y')
      citem = CW_FIELD(wMeu2,/LONG,UNAME=uname+'pos3',XSIZE=3,$
                       VALUE=n2,TITLE='Z')
  end

  ; note we store 'fix' here to track the type of modelparam widget we'll need
  wMparam = WIDGET_BASE(wM,COLUMN=3,TITLE='Model parameters',$
                        UNAME=uname+'title',UVALUE=fix)

  wMParamsub = WIDGET_BASE(wMparam,UNAME=uname+'sub',UVALUE=uname,$
                          YSIZE=80+fix*80,GRID_LAYOUT=0,COLUMN=5)
  s3drs_modelparam,parent=wMparamsub

  vals=['allow euler angles to vary','freeze euler angles']
  if (fix) then $
    bbutton = WIDGET_DROPLIST(wM,VALUE=vals,UNAME=uname+'efix')

  wMbut = WIDGET_BASE(wM,COLUMN=2)
  bbutton = WIDGET_BUTTON(wMbut,VALUE='save these values as my favorites')
  WIDGET_CONTROL,bbutton,SENSITIVE=0
  bbutton = WIDGET_BUTTON(wMbut,VALUE='(restore generic defaults)')
  WIDGET_CONTROL,bbutton,SENSITIVE=0

  blank = WIDGET_LABEL(wM, VALUE='')

END

FUNCTION s3drs_tab_intro,wTab

  common s3drs,s3drs

  wTintro = WIDGET_BASE(wTab, TITLE='Introduction', COLUMN=1,$
                      X_SCROLL_SIZE=s3drs.winx,Y_SCROLL_SIZE=s3drs.winy,$
                      /SCROLL,XSIZE=s3drs.winx,YSIZE=s3drs.winy)
  wLabel = WIDGET_LABEL(wTintro, VALUE='STEREO 3D Reconstruction Studio') 

  introtext=s3drs_text_intro()
  ysize=19;
  wLabel = WIDGET_TEXT(wTintro, VALUE=introtext,/WRAP,xsize=80,$
                       ysize=ysize)


  ysize=7
  lictext=s3drs_text_ack(s3drs.pixon)
  if (s3drs.pixon eq 0) then begin
      lictext+=s3drs_text_license()
      ysize+=7
  end
  wLabel = WIDGET_TEXT(wTintro, VALUE=lictext,/WRAP,xsize=80,ysize=ysize)

  blank = WIDGET_LABEL(wTintro, VALUE='')

;  links=s3drs_text_links()
;  wLabel = WIDGET_TEXT(wTintro, VALUE=links,/WRAP,xsize=80,$
;                       ysize=n_elements(links)+1) ;

;  blank = WIDGET_LABEL(wTintro, VALUE='')
;  blank = WIDGET_LABEL(wTintro, VALUE='')
;
;  blank = WIDGET_LABEL(wTintro, VALUE='')

  blurb="Choose whether to use SECCHI/SOHO data or model synthetic data."
  wLabel = WIDGET_LABEL(wTintro, VALUE=blurb,/ALIGN_LEFT,/SUNKEN_FRAME)

  wTout = WIDGET_BASE(wTintro,COL=4)
  wLabel = WIDGET_LABEL(wTout, VALUE='Choose path:') 
  WB1 = WIDGET_BUTTON(wTout,VALUE='Real Data',$
                      UNAME='datasyn',EVENT_FUNC='s3drs_datasyn',YSIZE=40)
  WB2 = WIDGET_BUTTON(wTout,VALUE='Synthetic Data (models)',$
                      UNAME='syndata',EVENT_FUNC='s3drs_datasyn',YSIZE=40)
  if (n_elements(s3drs.arrow) ne 0) then $
    warrow = WIDGET_BUTTON(wTout,VALUE=s3drs.arrow) else $
    warrow = WIDGET_LABEL(wTout,VALUE='<----------------------')

  s3drs_hline,wTintro

;  wBgroup1 = CW_BGROUP(wTintro, ['Real Data', 'Synthetic Data (models)'], $ 
;    /ROW, /EXCLUSIVE, /RETURN_NAME,$
;                       UNAME='datasyn',EVENT_FUNC='s3drs_datasyn') 
  ; used to also do SET_VALUE=0 to default to real data, now requires choice

  s3drs_satloscreate,wTintro

  wTbut=WIDGET_BASE(wTintro,ROW=1)
  b1=WIDGET_BUTTON(wTbut,VAL='Show license terms',EVENT_FUNC='s3drs_popup')
  b2=WIDGET_BUTTON(wTbut,VAL='turn off tab hopping',$
                   EVENT_FUNC='s3drs_togglehop')
  b3=WIDGET_BUTTON(wTbut,VAL='exit s3drs',EVENT_FUNC='s3drs_exit')

  return,wTintro

END

FUNCTION s3drs_tab_data,wTab

  common s3drs,s3drs

  wTdata = WIDGET_BASE(wTab, TITLE='Obs. Data', COLUMN=1,UNAME='tab_data',$
                      X_SCROLL_SIZE=s3drs.winx,Y_SCROLL_SIZE=s3drs.winy,$
                      /SCROLL,XSIZE=s3drs.winx,YSIZE=s3drs.winy)

  titles=['Instruments: (choose all that apply)',$
          'Data Frame',$
          'Subtraction Frame',$
          'Resolution',$
          'Standard Processing',$
          'Polarization Choices',$
          'Occulter Mask Choice']

  bflags=make_array(/long,n_elements(s3drs.instr),value=0)
  bflags[0]=1
  bgroup = CW_BGROUP(wTdata,s3drs.instr,ROW=1,LABEL_LEFT=titles[0],/FRAME, $
                     /NONEXCLUSIVE,UNAME='datainstr',UVALUE=s3drs.instr,$
                     EVENT_FUNC="s3drs_dataoff",SET_VALUE=bflags)

  bgroup = widget_date(wTdata,'datadate',EVENT_FUNC="s3drs_dataoff",$
                       offset=30,/evens)

  labels1=['find nearest match to date']
;currently not using      'use exact date only (will exit if no data found)'
  bgroup = WIDGET_DROPLIST(wTdata,VALUE=labels1,TITLE=titles[1],$
                           UNAME='datamatch',EVENT_FUNC="s3drs_dataoff")

  labels2=['Monthly bkg','Pre-event','none']
  wTdatapre = WIDGET_BASE(wTdata,ROW=1)
  bgroup = WIDGET_DROPLIST(wTdatapre,VALUE=labels2,TITLE=titles[2],$
                           UNAME='datasub',EVENT_PRO='s3drs_predate')
  bgroup = widget_date(wTdatapre,'priordate',EVENT_FUNC="s3drs_dataoff",$
                       offset=31,/evens)
  WIDGET_CONTROL,bgroup,SENSITIVE=0; initially date is turned off

  labels3=int2str(s3drs.res)+'x'+int2str(s3drs.res)
  bgroup = WIDGET_DROPLIST(wTdata,VALUE=labels3,TITLE=titles[3],$
                          UNAME='datares',EVENT_FUNC="s3drs_dataoff")

  labels4=['Scrub cosmic rays and bright pixels']
  bgroup = CW_BGROUP(wTdata,labels4,ROW=1,LABEL_LEFT=titles[4],/FRAME, $
                     /NONEXCLUSIVE,UNAME='datascrub',UVALUE='scrubtoggle',$
                     EVENT_FUNC="s3drs_dataoff",SET_VALUE=1)

  bgroup = WIDGET_DROPLIST(wTdata,VALUE=s3drs.pol,TITLE=titles[5],$
                          UNAME='datapol',EVENT_FUNC="s3drs_dataoff")

  mtype=["same as data (default)",s3drs.instr+" masks",$
         "none (no occulter mask)"]
;  ; use a subframe for this variably-sized, changing set of items
;; I HAD 'per-frame' Occulter choices, but dropped them to avoid having
;; this dynamically change.  On screen 1, you just choose the data.
;; That's it.  Per-frame mask changes are all moved to 'Masking'.
;  wTdatamc = WIDGET_BASE(wTdata,/SCROLL,XSIZE=240,YSIZE=120,COLUMN=1,$
;                      X_SCROLL_SIZE=100,Y_SCROLL_SIZE=120)
;  bLabel = WIDGET_LABEL(wTdatamc, VALUE=titles[6]) 
;
;  for id=0,s3drs.Nframes-1 do begin
;      bgroup = WIDGET_DROPLIST(wTdatamc,VALUE=mtype,TITLE=(*s3drs.names)[id],$
;                              UNAME='datamask'+int2str(id))
;  end

  bgroup = WIDGET_DROPLIST(wTdata,VALUE=mtype,TITLE=titles[6],$
                           UNAME='datamask',EVENT_FUNC="s3drs_dataoff")


  wTout = WIDGET_BASE(wTdata,COL=4)
  wLabel = WIDGET_LABEL(wTout, VALUE='Next step:') 
  active = WIDGET_BUTTON(wTout,VALUE='       Generate these data                ',$
                         EVENT_PRO='s3drs_datagen',UNAME='datawarn',YSIZE=40)
  if (n_elements(s3drs.arrow) ne 0) then $
    warrow = WIDGET_BUTTON(wTout,VALUE=s3drs.arrow) else $
    warrow = WIDGET_LABEL(wTout,VALUE='<----------------------')

  WB2 = WIDGET_BUTTON(wTout,VALUE='never mind, use synthetic data',$
                      UNAME='syndataB',EVENT_FUNC='s3drs_datasyn',YSIZE=40)

  s3drs_hline,wTdata

  wPlot2=s3drs_tv(wTdata,'Data1','Input data')

  s3drs_satloscreate,wTdata

  return,wTdata

END

FUNCTION s3drs_tab_syn,wTab

  common s3drs,s3drs

  wTsyn = WIDGET_BASE(wTab, TITLE='Synthetic Data', COLUMN=1,UNAME='tab_syn',$
                      X_SCROLL_SIZE=s3drs.winx-40,Y_SCROLL_SIZE=s3drs.winy,$
                      /SCROLL,XSIZE=s3drs.winx,YSIZE=s3drs.winy*2)
 

  titles=['Instr.',$
          'Exposure time (seconds) = ',$
          'Number of viewpoints or satellites',$
          'Viewpoint details',$
          'Input model',$
          'Optional rotation Euler angles for initial guess',$
          'Model-specific parameters',$
          'Added background model',$
          'Resolution',$
          'Polarization Choices',$
          'Occulter Mask Choice']

  wTsyntop = WIDGET_BASE(wTsyn,COLUMN=4)

  citem = CW_FIELD(wTsyntop,/INTEGER,UNAME='nviewpoints',TITLE=titles[2],$
                   XSIZE=2,VALUE='2',/RETURN_EVENTS); ,EVENT_FUNC="s3drs_synoff")

  citem = WIDGET_LABEL(wTsyntop,VALUE='(hit enter to apply)')
;  citem = WIDGET_DROPLIST(wTsyntop,VALUE=['1','2','3','4','more'],$
;                          title=titles[2],UNAME='nviewpoints')
  citem = CW_FIELD(wTsyntop,/INTEGER,UNAME='exptime',TITLE=titles[1],$
                   XSIZE=2,VALUE='3')

;  ditems = WIDGET_DROPLIST(wTsyntop,UNAME='syninstr',TITLE='Instrument',$
;                           VALUE=s3drs.instr)

  wlabel = WIDGET_LABEL(wTsyn,VALUE='(Rho=deg along ecliptic, Phi=deg above ecliptic, R=distance from Sun in AU)')

  wTsynmc = WIDGET_BASE(wTsyn,/SCROLL,XSIZE=240,YSIZE=200,ROW=1,$
                        X_SCROLL_SIZE=60*s3drs.Nframes,Y_SCROLL_SIZE=190,$
                        UNAME='synspec')

  s3drs_modelgui,wTsyn,title=titles[6],UNAME='synin',/moveable

  wTsynmini = WIDGET_BASE(wTsyn,COLUMN=2)
  labels8=int2str(s3drs.res)+'x'+int2str(s3drs.res)
  bgroup = WIDGET_DROPLIST(wTsynmini,VALUE=labels8,TITLE=titles[8],$
                          UNAME='synres',EVENT_FUNC="s3drs_synres")
  
  bgroup = WIDGET_DROPLIST(wTsynmini,VALUE=s3drs.pol,TITLE=titles[9],$
                          UNAME='synpol',EVENT_FUNC="s3drs_synoff")

;  occs=['default instrument','use Cor2 masks','use C3 mask',$
;        'use Cor1 masks','use C2 mask','none (no occulter mask)']
  occs=['same as instr (default)',s3drs.instr,'none (no occulter mask)']

  bgroup = WIDGET_DROPLIST(wTsynmini,VALUE=occs,$
                           TITLE=titles[10],UNAME='synmask',$
                           EVENT_FUNC="s3drs_synoff")

  labels7=['none','Saito model','Gaussian','Artificial speckle']
  bgroup = WIDGET_DROPLIST(wTsynmini,VALUE=labels7,TITLE=titles[7],$
                          UNAME='synback',EVENT_FUNC="s3drs_synoff")


  wTout = WIDGET_BASE(wTsyn,COL=4)
  wLabel = WIDGET_LABEL(wTout, VALUE='Next step:') 
  active = WIDGET_BUTTON(wTout,VALUE='        Generate these data                 ',$
                         EVENT_PRO='s3drs_syngen',UNAME='synwarn',YSIZE=40)
  if (n_elements(s3drs.arrow) ne 0) then $
    warrow = WIDGET_BUTTON(wTout,VALUE=s3drs.arrow) else $
    warrow = WIDGET_LABEL(wTout,VALUE='<----------------------')

  WB1 = WIDGET_BUTTON(wTout,VALUE='never mind, use real data',$
                      UNAME='datasynB',EVENT_FUNC='s3drs_datasyn',YSIZE=40)

  s3drs_hline,wTsyn

  wPlot2=s3drs_tv(wTsyn,'Syn1','Synthetic data')

  s3drs_satloscreate,wTsyn

  ; populate with starters
  s3drs_synspec

  return,wTsyn

END

FUNCTION s3drs_tab_mask,wTab

  common s3drs,s3drs

  wTmask = WIDGET_BASE(wTab, TITLE='Masking', COLUMN=1,$
                      X_SCROLL_SIZE=s3drs.winx-40,Y_SCROLL_SIZE=s3drs.winy,$
                      /SCROLL,XSIZE=s3drs.winx,YSIZE=s3drs.winy+200)

  titles=['Data cutoff/zeroing',$
          'Masking',$
          'Additional masking',$
          'Current Data choices (masks indicated in red)']

  blabel = WIDGET_LABEL(wTmask,VALUE=titles[0])
  wTmaskcz = WIDGET_BASE(wTmask,ROW=2)
  cpair=['do not cutoff','cutoff']
  bgroup = WIDGET_DROPLIST(wTmaskcz,VALUE=cpair,UNAME='cutlowtoggle')
  blab = WIDGET_LABEL(wTmaskcz,VALUE='for all data below: ')
  blab = WIDGET_LABEL(wTmaskcz,VALUE='(i.e. pixels < cutoff are set to zero)')
  bcg = CW_FIELD(wTmaskcz,/FLOAT,XSIZE=6,VALUE=1e-11,TITLE='',UNAME='cutlow')
  bgroup = WIDGET_DROPLIST(wTmaskcz,VALUE=cpair,UNAME='cuthightoggle')
  blab = WIDGET_LABEL(wTmaskcz,VALUE='for all data above: ')
  bcg = CW_FIELD(wTmaskcz,/FLOAT,XSIZE=6,VALUE=0.0,TITLE='',UNAME='cuthigh')
  blab = WIDGET_LABEL(wTmaskcz,VALUE='(i.e. pixels > cutoff are set to zero)')

  mpair=['set weight to zero where mask exists (recommended)',$
         'set data to zero where mask exists']
  wTmini = WIDGET_BASE(wTmask,ROW=1)
  bgroup = WIDGET_DROPLIST(wTmini,VALUE=mpair,TITLE=titles[1],UNAME='masktype')
  button = WIDGET_BUTTON(wTmini,VALUE='(Replot using these)',$
                        EVENT_FUNC='s3drs_tv_replot',UVALUE='Input1')

  blank = WIDGET_LABEL(wTmask, VALUE='')
  blank = WIDGET_LABEL(wTmask, VALUE='')

  ; use a subframe for this variably-sized, changing set of items
  wTmaskmc = WIDGET_BASE(wTmask,/SCROLL,XSIZE=240,YSIZE=160,ROW=1,$
                      X_SCROLL_SIZE=100,Y_SCROLL_SIZE=170,UNAME='multimask')

  ; we will populate wTmaskmc later, for now just stick in a label
  bLabel = WIDGET_LABEL(wTmaskmc, VALUE='Additional Masking')

  blank = WIDGET_LABEL(wTmask, VALUE='')
  blank = WIDGET_LABEL(wTmask, VALUE='')

  wTout = WIDGET_BASE(wTmask,COL=3)
  wLabel = WIDGET_LABEL(wTout, VALUE='Next step:') 
  active = WIDGET_BUTTON(wTout,VALUE='Done, check on S/N',$
                         EVENT_PRO='s3drs_tabhop',YSIZE=40)
  if (n_elements(s3drs.arrow) ne 0) then $
    warrow = WIDGET_BUTTON(wTout,VALUE=s3drs.arrow) else $
    warrow = WIDGET_LABEL(wTout,VALUE='<----------------------')

  s3drs_hline,wTmask

  ; guess at initial size, dynamically adjust scrollbars later
  wPlot2=s3drs_tv(wTmask,'Mask1','Masks')

  wPlot3=s3drs_tv(wTmask,'Input1','Masked input data')

  s3drs_satloscreate,wTmask

  return,wTmask

END

FUNCTION s3drs_tab_noise,wTab

  common s3drs,s3drs

  wTnoise = WIDGET_BASE(wTab, TITLE='Noise', COLUMN=1,$
                      X_SCROLL_SIZE=s3drs.winx,Y_SCROLL_SIZE=s3drs.winy,$
                      /SCROLL,XSIZE=s3drs.winx,YSIZE=s3drs.winy)
 

  blank = WIDGET_LABEL(wTnoise, VALUE='')
  blank = WIDGET_LABEL(wTnoise, VALUE='')

  wTitle = WIDGET_LABEL(wTnoise,VALUE='Current noise scaling factors')
  wSliders = WIDGET_BASE(wTnoise,UNAME='snratio',$
                         ROW=1,XSIZE=s3drs.drawx,ysize=40)

  blank = WIDGET_LABEL(wTnoise, VALUE='')
  blank = WIDGET_LABEL(wTnoise, VALUE='')
  blank = WIDGET_LABEL(wTnoise, VALUE='')

  wTout = WIDGET_BASE(wTnoise,COL=3)
  wLabel = WIDGET_LABEL(wTout, VALUE='Next step:') 
  active = WIDGET_BUTTON(wTout,VALUE='Done, go to reconstruction',$
                         EVENT_PRO='s3drs_tabhop',YSIZE=40)
  if (n_elements(s3drs.arrow) ne 0) then $
    warrow = WIDGET_BUTTON(wTout,VALUE=s3drs.arrow) else $
    warrow = WIDGET_LABEL(wTout,VALUE='<----------------------')

  s3drs_hline,wTnoise

  ; guess at initial size, dynamically adjust scrollbars later
  wPlot1 = WIDGET_DRAW(wTnoise,RETAIN=2,/SCROLL,uname='SNHist1',$
                       XSIZE=s3drs.drawx-50,ysize=160,$
                       X_SCROLL_SIZE=s3drs.drawx,Y_SCROLL_SIZE=120)

  blank = WIDGET_LABEL(wTnoise, VALUE='')

  ; guess at initial size, dynamically adjust scrollbars later
  wPlot2=s3drs_tv(wTnoise,'SNPlot1','S/N Plot')

  s3drs_satloscreate,wTnoise

  return,wTnoise

END

FUNCTION s3drs_tab_recon,wTab

  common s3drs,s3drs

  wTrecon = WIDGET_BASE(wTab, TITLE='Recon choices', COLUMN=1,$
                      X_SCROLL_SIZE=s3drs.winx,Y_SCROLL_SIZE=s3drs.winy,$
                      /SCROLL,XSIZE=s3drs.winx,YSIZE=s3drs.winy)
 

  titles=['Pre-conditioning',$
          'Maximum number of iterations to run',$
          'Create standard output diagnostic plots?',$
          'What to do?']

  lset=['back-projection starter image (recommended)',$
        'use native Pixon initial gradient minimization as starter',$
        'external starter image (from a file)',$
        'use previous solution (if one exists)']

  bgroup = WIDGET_DROPLIST(wTrecon,VALUE=lset,TITLE=titles[0],$
                          UNAME='jumpstart')

  bentry = CW_FIELD(wTrecon,/INTEGER,UNAME='mxit',TITLE=titles[1],$
                   XSIZE=3,VALUE='20')

;  lset=['onscreen','postscript']
;  bgroup = CW_BGROUP(wTrecon,lset,ROW=1,/FRAME,/NONEXCLUSIVE,$
;                     LABEL_LEFT=titles[2])

  lset=['Reconstruct with full Pixon!',$
        'Reconstruct with Pixon pseudo-solver',$
        'Reconstruct with forward modeling',$
        'Reconstruct with backprojection minimization',$
        'Just prepare files but do not reconstruct',$
        'Use your own solver']
  bgroup = WIDGET_DROPLIST(wTrecon,VALUE=lset,TITLE=titles[3],$
                          UNAME='reconmethod',EVENT_PRO='s3drs_fmtoggle')


  wTout = WIDGET_BASE(wTrecon,COL=3)
  wLabel = WIDGET_LABEL(wTout, VALUE='Next step:') 
  active = WIDGET_BUTTON(wTout,VALUE='Run reconstruction!',$
                         EVENT_PRO='s3drs_run',UNAME='reconbutton',YSIZE=40)
  if (n_elements(s3drs.arrow) ne 0) then $
    warrow = WIDGET_BUTTON(wTout,VALUE=s3drs.arrow) else $
    warrow = WIDGET_LABEL(wTout,VALUE='<----------------------')

  s3drs_hline,wTrecon

  s3drs_satloscreate,wTrecon

  return,wTrecon

END


FUNCTION s3drs_tab_fm,wTab

  common s3drs,s3drs

  ; Create the fourth tab base, containing a label and a text-entry field. 
  wTfm = WIDGET_BASE(wTab, TITLE='(FM)', COLUMN=1,$
                      X_SCROLL_SIZE=s3drs.winx-40,Y_SCROLL_SIZE=s3drs.winy,$
                      /SCROLL,XSIZE=s3drs.winx,YSIZE=s3drs.winy*2)
 

  ; note we 'skip' the non-Arnaud models
  s3drs_modelgui,wTfm,uname='fmin',title='Forward model choice',/fix,/arnaud

  warntext=s3drs_text_fmwarn()
  wLabel = WIDGET_TEXT(wTfm, VALUE=warntext,/WRAP,xsize=60,ysize=5)


  wTout = WIDGET_BASE(wTfm,COL=3)
  wLabel = WIDGET_LABEL(wTout, VALUE='Next step:') 
  active = WIDGET_BUTTON(wTout,VALUE='Run FM reconstruction',$
                         EVENT_PRO='s3drs_fmrun',YSIZE=40)
  if (n_elements(s3drs.arrow) ne 0) then $
    warrow = WIDGET_BUTTON(wTout,VALUE=s3drs.arrow) else $
    warrow = WIDGET_LABEL(wTout,VALUE='<----------------------')

  s3drs_hline,wTfm

  wPlot1=s3drs_tv(wTfm,'FMplot1','Fit in progress',rows=2)

  s3drs_satloscreate,wTfm

  return,wTfm

END

PRO s3drs_savename

  common s3drs,s3drs

  title='Save file is '+s3drs.title+'_latest.sav, solution (FITS) is in '+$
    s3drs.title+'_latest.fts'

  wid=WIDGET_INFO(s3drs.tabs.vizID,FIND_BY_UNAME='savefile')
  if (wid ne 0) then WIDGET_CONTROL,wid,SET_VALUE=title

END

FUNCTION s3drs_tab_viz,wTab

  common s3drs,s3drs

  ; Create the fourth tab base, containing a label and a text-entry field. 
  wTviz = WIDGET_BASE(wTab, TITLE='Recon. Results', COLUMN=1,$ 
                      X_SCROLL_SIZE=s3drs.winx-40,Y_SCROLL_SIZE=s3drs.winy,$
                      /SCROLL,XSIZE=s3drs.winx,YSIZE=s3drs.winy*2)

  wtLab = WIDGET_LABEL(wTviz,VALUE='Save file is: ',/DYNAMIC_RESIZE,$
                       UNAME='savefile')

  wInfoBase = WIDGET_BASE(wTviz,XSIZE=s3drs.winx/6,YSIZE=200)
  wInfo = WIDGET_TEXT(wInfoBase, VALUE='Hello',/WRAP,xsize=80,ysize=12,$
                      /SCROLL,UNAME='coversheet')

  wTuck = WIDGET_BASE(wTviz,XSIZE=280,ROW=1)
  wBut = WIDGET_BUTTON(wTuck,$
                       VALUE='generate diagnostics with current plot limits',$
                       EVENT_PRO='s3drs_psplots',xsize=280)

  wBut = WIDGET_BUTTON(wTuck,VALUE='show center-of-mass for solution',$
                       EVENT_PRO='s3drs_cm')

  ; guess at initial size, dynamically adjust scrollbars later
  wPlot1=s3drs_tv(wTviz,'VizData','Input data',double=1)
;  wPlot2=s3drs_tv(wTviz,'VizRender','Solution renders')

  wPlot3=s3drs_tv(wTviz,'Trio','Solution Image X/Y/Z',/double)

  wPlot4=s3drs_tv(wTviz,'Chisq','abs[Input-Output]/Sigma')

  s3drs_satloscreate,wTviz

  return,wTviz

END
 

; Widget creation routine. 
PRO s3drs_gui, LOCATION=location 

  common s3drs,s3drs

  if (n_elements(s3drs) eq 0) then s3drs_init

  if (XREGISTERED('s3drs_handler') NE 0) THEN BEGIN
      print,'already running'
      widget_control,s3drs.wTLB,/DESTROY
;      RETURN
  end

  wTLB = WIDGET_BASE(COLUMN=1, /BASE_ALIGN_TOP,/TLB_SIZE_EVENTS,$
                     XSIZE=s3drs.winx,YSIZE=s3drs.winy,$
                     /TLB_KILL_REQUEST,$
                     resource_name='s3drs_main',uname='s3drs_main')

  s3drs.wTLB=wTLB
  WIDGET_CONTROL, wTLB, base_set_title='S3DRS

  wTab = WIDGET_TAB(wTLB, LOCATION=location,xsize=s3drs.winx,TAB_MODE=1)

  ;fake_data; for now, putting in fake values for TESTING ONLY
  ; Create the tab bases and populate
  s3drs.tabs.introID=s3drs_tab_intro(wTab)
  s3drs.tabs.dataID=s3drs_tab_data(wTab)
  s3drs.tabs.synID=s3drs_tab_syn(wTab)
  s3drs.tabs.maskID=s3drs_tab_mask(wTab)
  s3drs.tabs.noiseID=s3drs_tab_noise(wTab)
  s3drs.tabs.reconID=s3drs_tab_recon(wTab)
  s3drs.tabs.fmID=s3drs_tab_fm(wTab)
  s3drs.tabs.vizID=s3drs_tab_viz(wTab)

  ; Create a base widget to hold the navigation and 'Done' buttons, 
  ; and the buttons themselves. Since the first tab is displayed 
  ; initially, make the 'Previous' button insensitive to start. 
  wControl = WIDGET_BASE(wTLB, ROW=1) 
  ; for wrap-around tabs, make sensitive.  For start-to-end, sensitive=0
  bPrev = WIDGET_BUTTON(wControl, VALUE='<< Prev', SENSITIVE=wrap) 
  bNext = WIDGET_BUTTON(wControl, VALUE='Next >>') 
;  bDone = WIDGET_BUTTON(wControl, VALUE='Save Values and Exit') 
;  bCancel = WIDGET_BUTTON(wControl, VALUE='Cancel and Exit') 
  bDone=-1; not using this
  bCancel=-1; not using this

  ; Create an anonymous structure to hold the widget value data 
  ; we are interested in retrieving. Note that we will refer to 
  ; the structure fields by their indices rather than their 
  ; names, so order is important. 
  retStruct={ BGROUP1:[0,0,0], BGROUP2:0, SLIDER:0L, TEXT:'empty'} 
 
  ; Create an anonymous structure to hold widget IDs. This 
  ; structure becomes the user value of the top-level base 
  ; widget. 
  stash = { bDone:bDone, bCancel:bCancel, bNext:bNext, $ 
            bPrev:bPrev, TopTab:wTab, retStruct:retStruct} 
 
  ; Realize the widgets, set the user value of the top-level 
  ; base, and call XMANAGER to manage everything. 
  WIDGET_CONTROL, wTLB, /REALIZE 
  WIDGET_CONTROL, wTLB, SET_UVALUE=stash 
  XMANAGER, 's3drs_handler', wTLB, /NO_BLOCK 

  ; turn off all but the first few
  ;WIDGET_CONTROL,s3drs.tabs.dataID,SENSITIVE=0
  ;WIDGET_CONTROL,s3drs.tabs.synID,SENSITIVE=0
  WIDGET_CONTROL,s3drs.tabs.maskID,SENSITIVE=0
  WIDGET_CONTROL,s3drs.tabs.noiseID,SENSITIVE=0
  WIDGET_CONTROL,s3drs.tabs.reconID,SENSITIVE=0
  WIDGET_CONTROL,s3drs.tabs.fmID,SENSITIVE=0
  WIDGET_CONTROL,s3drs.tabs.vizID,SENSITIVE=0

  ;; demo calls, just for testing
  ;s3drs_floodfill,'Data1'
  ;s3drs_floodfill,'Syn1'
  ;s3drs_floodfill,'Mask1'
  ;s3drs_floodfill,'SNPlot1'

 
END 
