; $Id: ascii_gui__define.pro,v 1.11 2006/09/21 16:16:07 kneller Exp $
;###############################################################################
;
; NAME:
;  ASCII_GUI__DEFINE
;
; PURPOSE:
;  Class definition for the ascii data reader GUI.
;
; CATEGORY:
;  DAVE, ASCII data reader.
;
; AUTHOR:
;   Robert M. Dimeo, Ph.D.
;   NIST Center for Neutron Research
;   100 Bureau Drive
;   Gaithersburg, MD 20899
;   Phone: (301) 975-8135
;   E-mail: robert.dimeo@nist.gov
;   http://www.ncnr.nist.gov/staff/dimeo
;
; LICENSE:
;  The software in this file is written by an employee of
;  National Institute of Standards and Technology
;  as part of the DAVE software project.
;
;  The DAVE software package is not subject to copyright protection
;  and is in the public domain. It should be considered as an
;  experimental neutron scattering data reduction, visualization, and
;  analysis system. As such, the authors assume no responsibility
;  whatsoever for its use, and make no guarantees, expressed or
;  implied, about its quality, reliability, or any other
;  characteristic. The use of certain trade names or commercial
;  products does not imply any endorsement of a particular product,
;  nor does it imply that the named product is necessarily the best
;  product for the stated purpose. We would appreciate acknowledgment
;  if the DAVE software is used of if the code in this file is
;  included in another product.
;
;###############################################################################
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
function get_file_name,filename
delimiter = path_sep()
dpos = strpos(filename,delimiter,/reverse_search)
return,strmid(filename,dpos+1)
end
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
pro ascii_gui::cleanup
obj_destroy,self.data_container
wdelete,self.winpix
end
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
function ascii_gui::get_notify_ids
return,self.notify_ids
end
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
pro ascii_gui_cleanup,tlb
widget_control,tlb,get_uvalue = self
if obj_valid(self) then begin
  s = size(self->get_notify_ids())
  if s[0] ne 0 then begin
      asciiInfo = {ASCII_EVENT,$
                            ID:(self->get_notify_ids())[0],$
                            Top:(self->get_notify_ids())[1],$
                            Handler:0l}
      if widget_info((self->get_notify_ids())[0],/valid_id) then begin $
        widget_control,(self->get_notify_ids())[0],send_event = asciiInfo
      endif
  endif else begin
  endelse
endif
obj_destroy,self

;help,/heap,/brief
end
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
function ascii_gui::quit,event
widget_control,self.tlb,/destroy
return,1
end
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
function ascii_gui::draw,event
; Determine which leaf is currently selected
leaf_sel = widget_info(self.file_tree,/tree_select)
if not widget_info(leaf_sel,/valid_id) then return,0
uname = widget_info(leaf_sel,/uname)
if uname ne 'DATA LEAF' then return,0
widget_control,leaf_sel,get_uvalue = uval
o = uval.data_object
if self.autoscale eq 1 then begin
   ret = o->get_property(xvals = xvals,zvals = zvals,dzvals = dzvals)
   xmin = min(xvals,max = xmax)
   ymin = min(zvals+dzvals,max = ymax)
   dx = xmax-xmin & dy = ymax-ymin
   self.xrange = [xmin-0.2*dx,xmax+0.2*dx]
   self.yrange = [ymin-0.2*dy,ymax+0.2*dy]
endif
; Get the titles out
ret = o->get_property(xunits = xunits,yunits = yunits,data_type = data_type,  $
   yindex = yindex,filename = filename)
display_name = get_file_name(filename)
x_unit_poss = ['x:arb_units','energy:mev','energy:uev','temperature:k']
xtitles = ['!3x (arb units)','!3E (meV)','!3E (!4l!3eV)','!3T (K)']
wherexok = where(strlowcase(x_unit_poss) eq strlowcase(xunits),count_xok)
if count_xok eq 1 then begin
   xtitle = xtitles[wherexok[0]]
endif else begin
   xtitle = '!3x (arb units)'
endelse
y_unit_poss = ['y:arb_units','angle:degrees','wavevector:A-1']
ytitles = ['!3y (arb units)','!4h!3 (!eo!n)','!3Q (!3!sA!r!u!9 %!3!n!E-1!N)']
whereyok = where(strlowcase(y_unit_poss) eq strlowcase(yunits),count_yok)
if count_yok eq 1 then begin
   ytitle = ytitles[whereyok[0]]
endif else begin
   ytitle = '!3y (arb units)'
endelse
title = display_name
ret = o->plot(psym = 4,xrange = self.xrange,  title = title,$
   /xsty,/ysty,yrange = self.yrange,xtitle = xtitle)
return,1
end
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
function ascii_gui::refresh,event
wset,self.winpix
ret = self->draw(event)
wset,self.winvis
device,copy = [0,0,!d.x_size,!d.y_size,0,0,self.winpix]
empty
return,1
end
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
function ascii_gui::resize,event
tree_base = widget_info(self.tlb,find_by_uname = 'TREE_BASE')
ctrl_base = widget_info(self.tlb,find_by_uname = 'CTRL BASE')
ctrl_geom = widget_info(ctrl_base,/geometry)
tree_geom = widget_info(tree_base,/geometry)
device,get_screen_size = scr_size
tree_xsize = fix(0.2*scr_size[0])
winxsize = (event.x - tree_geom.xsize) > 300
winysize = event.y > 300
tree_ysize = winysize-ctrl_geom.ysize
widget_control,self.file_tree,xsize = tree_xsize,ysize = tree_ysize
widget_control,self.win,draw_xsize = winxsize,draw_ysize = winysize
wdelete,self.winpix
window,/free,/pixmap,xsize = winxsize,ysize = winysize
self.winpix = !d.window
ret = self->refresh(event)
return,1
end
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
function ascii_gui::change_groups,event
widget_control,event.id,get_value = val & val = val[0]
; Which widget is selected?
sel_leaf = widget_info(self.file_tree,/tree_select)
; Test if the selected leaf is valid
if not widget_info(sel_leaf,/valid_id) then return,0
uname = widget_info(sel_leaf,/uname)
if uname ne 'DATA LEAF' then return,0
widget_control,sel_leaf,get_uvalue = cmd
the_object = cmd.data_object
ret = the_object->set_property(yindex = val)
ret = self->refresh(event)
return,1
end
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
function ascii_gui::select_data,event
widget_control,event.id,get_uvalue = uval
data_object = uval.data_object
ret = data_object->get_property(yvals = yvals,yunits = yunits)
ny = n_elements(yvals)
ret = data_object->get_property(data_type = data_type)
slider_id = widget_info(self.tlb,find_by_uname = 'SLIDER')
if data_type eq 'MULTIPLE' then begin
   widget_control,slider_id,set_slider_max = (ny-1),sensitive = 1
endif else begin
   widget_control,slider_id,sensitive = 0
endelse

; Display the data to the window
ret = self->refresh(event)

; Remove all checks boxes
xunits_id = widget_info(self.tlb,find_by_uname = 'X UNITS')
yunits_id = widget_info(self.tlb,find_by_uname = 'Y UNITS')
xlist = get_list_items(xunits_id,IDS = x_ids,UNAMES = xunames)
ylist = get_list_items(yunits_id,IDS = y_ids,UNAMES = yunames)

for i = 0,n_elements(xlist)-1 do widget_control,x_ids[i],set_button = 0B
for i = 0,n_elements(ylist)-1 do widget_control,y_ids[i],set_button = 0B

; Update the check boxes for the x- and y-units
ret = data_object->get_property(xunits = xunits,yunits = yunits)
x_unit_poss = ['x:arb_units','energy:mev','energy:uev','temperature:k']
wherexok = where(strlowcase(x_unit_poss) eq strlowcase(xunits),count_xok)
if count_xok eq 1 then begin
   widget_control,x_ids[wherexok[0]],set_button = 1B
   ret = data_object->set_property(xunits = x_unit_poss[wherexok[0]])
endif else begin
   widget_control,x_ids[0],set_button = 1B
   ret = data_object->set_property(xunits = x_unit_poss[0])
endelse
y_unit_poss = ['y:arb_units','angle:degrees','wavevector:A-1']
whereyok = where(strlowcase(y_unit_poss) eq strlowcase(yunits),count_yok)
if count_yok eq 1 then begin
   widget_control,y_ids[whereyok[0]],set_button = 1B
   ret = data_object->set_property(yunits = y_unit_poss[whereyok[0]])
endif else begin
   widget_control,y_ids[0],set_button = 1B
   ret = data_object->set_property(yunits = y_unit_poss[0])
endelse
ret = data_object->get_property(yunits = yunits)
return,1
end
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
function ascii_gui::add_leaf,the_object
; Determine if the data object is a single group or multi-group data set
ret = the_object->get_property(data_type = data_type)
ret = the_object->get_property(filename = filename)
display_name = get_file_name(filename)

if data_type eq 'MULTIPLE' then begin
   root = widget_info(self.tlb,find_by_uname = 'GROUP_FILE_ROOT')
endif else begin
   root = widget_info(self.tlb,find_by_uname = 'SINGLE_FILE_ROOT')
endelse
uname = 'DATA LEAF'
new_leaf =  widget_tree(root,value = display_name,             $
                        uname = uname,                         $
                        uvalue = {  object:self,               $
                                    method:'select_data',      $
                                    data_object:the_object})

return,1
end
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
function ascii_gui::load_single_group,event
;092106 KNELLER
;MAKING A DEFAULT OPTION TO GO TO SINGLE GROUP AT USER'S REQUEST.

; User selects files via the DIALOG_PICKFILE routine...

filename = dialog_pickfile(dialog_parent = self.tlb, $
   title = 'Select Single-Group files for loading',/multiple_files, $
   /must_exist,path = self.datdir,filter = '*.*')

; So first test out the validity of the files.
for i = 0,n_elements(filename)-1 do begin

   if file_test(filename[i]) then begin
   ; Ok it is a valid filename, but can we read it in here?


    ;SET THIS FLAG TO GO TO SINGLE GROUP BY DEFAULT.
        err = 1


;;;;;         o = obj_new('ascii_data',filename = filename[i])
;;;;;         ret = o->read_group_ascii(err = err,emsg = emsg)
;;;;;         if err eq 0 then begin
;;;;;            ; add the new valid data object to the data container object
;;;;;            self.data_container->add,o
;;;;;            ; Create the new leaf widgets in the appropriate container
;;;;;            ret = self->add_leaf(o)
;;;;;         endif
;;;;;
;;;;;;      o = obj_new('ascii_data',filename = filename[i])
;;;;;;      ret = o->read_three_column_ascii(err = err,emsg = emsg)
;;;;;;      if err eq 0 then begin
;;;;;;            ; add the new valid data object to the data container object
;;;;;;         self.data_container->add,o
;;;;;;            ; Create the new leaf widgets in the appropriate container
;;;;;;         ret = self->add_leaf(o)
;;;;;;      endif

      if err eq 1 then begin
         ;obj_destroy,o
      o = obj_new('ascii_data',filename = filename[i])
      ret = o->read_three_column_ascii(err = err,emsg = emsg)
      if err eq 0 then begin
            ; add the new valid data object to the data container object
         self.data_container->add,o
            ; Create the new leaf widgets in the appropriate container
         ret = self->add_leaf(o)
      endif
;         o = obj_new('ascii_data',filename = filename[i])
;         ret = o->read_group_ascii(err = err,emsg = emsg)
;         if err eq 0 then begin
;            ; add the new valid data object to the data container object
;            self.data_container->add,o
;            ; Create the new leaf widgets in the appropriate container
;            ret = self->add_leaf(o)
;         endif
      endif
;      if err eq 1 then begin
;         obj_destroy,o
;         o = obj_new('ascii_data',filename = filename[i])
;         ret = o->read_three_column_ascii(err = err,emsg = emsg)
;         if err eq 0 then begin
;            ; add the new valid data object to the data container object
;            self.data_container->add,o
;            ; Create the new leaf widgets in the appropriate container
;            ret = self->add_leaf(o)
;         endif
;      endif

      if err eq 1 then begin
         obj_destroy,o
         o = obj_new('ascii_data',filename = filename[i])
         ret = o->read_other_ascii(err = err,emsg = emsg)
         if err eq 0 then begin
            ; add the new valid data object to the data container object
            self.data_container->add,o
            ; Create the new leaf widgets in the appropriate container
            ret = self->add_leaf(o)
         endif
      endif
      if err eq 1 then begin
         if obj_valid(o) then obj_destroy,o
         void = dialog_message(dialog_parent = event.top,emsg)
      endif
   endif

endfor
return,0
end;ascii_gui::load_single_group

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
function ascii_gui::load,event
; User selects files via the DIALOG_PICKFILE routine...
filename = dialog_pickfile(dialog_parent = self.tlb, $
   title = 'Select files for loading',/multiple_files, $
   /must_exist,path = self.datdir,filter = '*.*')

; So first test out the validity of the files.
for i = 0,n_elements(filename)-1 do begin

   if file_test(filename[i]) then begin
   ; Ok it is a valid filename, but can we read it in here?

         o = obj_new('ascii_data',filename = filename[i])
         ret = o->read_group_ascii(err = err,emsg = emsg)
         if err eq 0 then begin
            ; add the new valid data object to the data container object
            self.data_container->add,o
            ; Create the new leaf widgets in the appropriate container
            ret = self->add_leaf(o)
         endif

;      o = obj_new('ascii_data',filename = filename[i])
;      ret = o->read_three_column_ascii(err = err,emsg = emsg)
;      if err eq 0 then begin
;            ; add the new valid data object to the data container object
;         self.data_container->add,o
;            ; Create the new leaf widgets in the appropriate container
;         ret = self->add_leaf(o)
;      endif

      if err eq 1 then begin
         obj_destroy,o
      o = obj_new('ascii_data',filename = filename[i])
      ret = o->read_three_column_ascii(err = err,emsg = emsg)
      if err eq 0 then begin
            ; add the new valid data object to the data container object
         self.data_container->add,o
            ; Create the new leaf widgets in the appropriate container
         ret = self->add_leaf(o)
      endif
;         o = obj_new('ascii_data',filename = filename[i])
;         ret = o->read_group_ascii(err = err,emsg = emsg)
;         if err eq 0 then begin
;            ; add the new valid data object to the data container object
;            self.data_container->add,o
;            ; Create the new leaf widgets in the appropriate container
;            ret = self->add_leaf(o)
;         endif
      endif
;      if err eq 1 then begin
;         obj_destroy,o
;         o = obj_new('ascii_data',filename = filename[i])
;         ret = o->read_three_column_ascii(err = err,emsg = emsg)
;         if err eq 0 then begin
;            ; add the new valid data object to the data container object
;            self.data_container->add,o
;            ; Create the new leaf widgets in the appropriate container
;            ret = self->add_leaf(o)
;         endif
;      endif

      if err eq 1 then begin
         obj_destroy,o
         o = obj_new('ascii_data',filename = filename[i])
         ret = o->read_other_ascii(err = err,emsg = emsg)
         if err eq 0 then begin
            ; add the new valid data object to the data container object
            self.data_container->add,o
            ; Create the new leaf widgets in the appropriate container
            ret = self->add_leaf(o)
         endif
      endif
      if err eq 1 then begin
         if obj_valid(o) then obj_destroy,o
         void = dialog_message(dialog_parent = event.top,emsg)
      endif
   endif

endfor
return,0
end
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
function ascii_gui::zoom,event
nobj = self.data_container->count()
if nobj eq 0 then return,0
case event.type of
0: begin    ; button press
      self.mouse = event.press
      if self.mouse eq 4 then begin
         self.autoscale = 1
         ret = self->refresh(event)
     endif
     if self.mouse eq 1 then begin
         self.xbox[0] = event.x
         self.ybox[0] = event.y
         ret = self->refresh(event)
         empty
         self.autoscale = 0
     endif
   end
1: begin ; button release
    if self.mouse eq 1 then begin
     xll = self.xbox[0] < self.xbox[1]
     yll = self.ybox[0] < self.ybox[1]
     w = abs(self.xbox[1] - self.xbox[0])
     h = abs(self.ybox[1] - self.ybox[0])
     xur = xll + w
     yur = yll + h
     ll = convert_coord(xll,yll,/device,/to_data)
     ur = convert_coord(xur,yur,/device,/to_data)
     self.xrange = [ll[0],ur[0]]
     self.yrange = [ll[1],ur[1]]
     ret = self->refresh(event)
     self.mouse = 0B
    endif
    if self.mouse eq 4 then begin
     ret = self->refresh(event)
     self.mouse = 0B
    endif
   end
2: begin ; mouse motion
     if self.mouse eq 1 then begin
        self.xbox[1] = event.x
        self.ybox[1] = event.y
        xc = [self.xbox[0],event.x,event.x,$
              self.xbox[0],$
              self.xbox[0]]
        yc = [self.ybox[0],self.ybox[0],$
              event.y,event.y,$
              self.ybox[0]]
        wset,self.winvis
        device,copy = [0,0,!d.x_size,!d.y_size,0,0,self.winpix]
        plots,xc,yc,/device
        empty
     endif
   end
else:
endcase
return,1
end
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
function ascii_gui::save_as_dave,event
ndata = self.data_container->count()
if ndata eq 0 then return,0
oall = self.data_container->get(/all)
for i = 0,ndata-1 do begin
   ret = oall[i]->get_property(filename = filename)
   display_name = get_file_name(filename)
   ppos = strpos(display_name,'.')
   file_out = self.workdir+strmid(display_name,0,ppos)+'.dave'
   daveptr = oall[i]->write_dave()
   if i eq 0 then out_file = file_out else out_file = [out_file,file_out]
   save,daveptr,filename = file_out
   if self.group_leader eq 0L then heap_free,daveptr
endfor
void = dialog_message(dialog_parent = self.tlb,out_file,/information, $
   title = 'Files written out as DAVE files')
return,1
end
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
function ascii_gui::sel_x,event
uname = widget_info(event.id,/uname)
; Which leaf has been selected?
sel_leaf = widget_info(self.file_tree,/tree_select)
if widget_info(sel_leaf,/valid_id) eq 0 then return,0
if widget_info(sel_leaf,/uname) ne 'DATA LEAF' then return,0
widget_control,sel_leaf,get_uvalue = cmd
ret = cmd.data_object->set_property(xunits = strlowcase(uname))
; Clear all checkmarks...
xunits_id = widget_info(event.top,find_by_uname = 'X UNITS')
list = get_list_items(xunits_id,IDS = ids)
for i = 0,n_elements(ids)-1 do widget_control,ids[i],set_button = 0B
;...and put a check next to this leaf
widget_control,event.id,/set_button
ret = self->refresh(event)
return,1
end
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
function ascii_gui::sel_y,event
uname = widget_info(event.id,/uname)
; Which leaf has been selected?
sel_leaf = widget_info(self.file_tree,/tree_select)
if widget_info(sel_leaf,/valid_id) eq 0 then return,0
if widget_info(sel_leaf,/uname) ne 'DATA LEAF' then return,0
widget_control,sel_leaf,get_uvalue = cmd
ret = cmd.data_object->set_property(yunits = strlowcase(uname))
; Clear all checkmarks...
yunits_id = widget_info(event.top,find_by_uname = 'Y UNITS')
list = get_list_items(yunits_id,IDS = ids)
for i = 0,n_elements(ids)-1 do widget_control,ids[i],set_button = 0B
;...and put a check next to this leaf
widget_control,event.id,/set_button
ret = self->refresh(event)
return,1
end
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
function ascii_gui::sample_info,event
; Which leaf has been selected?
sel_leaf = widget_info(self.file_tree,/tree_select)
if widget_info(sel_leaf,/valid_id) eq 0 then return,0
if widget_info(sel_leaf,/uname) ne 'DATA LEAF' then return,0
widget_control,sel_leaf,get_uvalue = cmd
o = cmd.data_object
str = {  descriptrstr,  $
         name:'',       $
         units:'',      $
         legend:'',     $
         qty:0.0,       $
         err:0.0        }
descriptr = ptr_new(str,/no_copy)
ret_val = db_editDescriPtr(descriPtr,group_leader=self.tlb)
ret = o->set_property(descriptr = descriptr)
ptr_free,descriptr
return,1
end
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
function ascii_gui::do_nothing,event
return,1
end
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
function ascii_gui::help,event
;pdf_file = file_which('ascii_help.pdf',/include_current_dir)
pdf_file = !DAVE_AUXILIARY_DIR+'ascii_help.pdf'
void = launch_help(pdf_file,tlb = event.top)
return,1
end
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
pro ascii_gui_events,event
widget_control,event.id,get_uvalue = cmd
if tag_names(event,/structure_name) eq 'WIDGET_BASE' then begin
   widget_control,event.top,get_uvalue = the_object
   ret = the_object->resize(event)
   return
endif
ret = call_method(cmd.method,cmd.object,event)
end
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
function ascii_gui::create_widgets
self.tlb = widget_base( title = 'ASCII->Dave Data Transformation', $
                        /tlb_size_events, /row, mbar = bar, $
                        group_leader = self.group_leader)
; Create the menu items
filemenu = widget_button(bar,value = 'File',/menu)
void = widget_button(filemenu,value = 'Load ASCII file',   $
   uvalue = {object:self,method:'load'})
void = widget_button(filemenu,value = 'Load Single-Group ASCII file',   $
   uvalue = {object:self,method:'load_single_group'})

void = widget_button(filemenu,value = 'Quit',   $
   uvalue = {object:self,method:'quit'})
; Create the tree widget
device,get_screen_size = scr_size
xsize = 400 & ysize = 300
tree_xsize = fix(0.2*scr_size[0])
tree_ysize = ysize
tree_base = widget_base(self.tlb,/col,uname = 'TREE_BASE')
self.file_tree = widget_tree(tree_base, $
   uname = 'FILE_TREE', scr_xsize = tree_xsize,scr_ysize = tree_ysize)
; Create the single data folder...
single_file_root = widget_tree(self.file_tree,value = 'SINGLE GROUP DATA',/folder, $
   /expanded, uname = 'SINGLE_FILE_ROOT',uvalue = {object:self,method:'do_nothing'})
group_file_root = widget_tree(self.file_tree,value = 'MULTI GROUP DATA',/folder, $
   /expanded, uname = 'GROUP_FILE_ROOT',uvalue = {object:self,method:'do_nothing'})
ctrl_base = widget_base(tree_base,/row,uname = 'CTRL BASE')
col_base_1 = widget_base(ctrl_base,/col)
void = widget_button(col_base_1,value = 'Load ASCII file',   $
   uvalue = {object:self,method:'load'})
void = widget_button(col_base_1,value = 'save as DAVE',  $
   uvalue = {object:self,method:'save_as_dave'})
slider = widget_slider(col_base_1,title = 'Group',value = 0,min = 0,max = 1, $
   uvalue = {object:self,method:'change_groups'},sensitive = 0,uname = 'SLIDER')
col_base_2 = widget_base(ctrl_base,/col)
units_menu = widget_button(col_base_2,value = 'Data units',/menu)
x_units_menu = widget_button(units_menu,value = 'x-units',/menu,uname = 'X UNITS')
void = widget_button(x_units_menu,value = 'x (arb units)', /checked_menu,$
   uvalue = {object:self,method:'sel_x'},uname = 'x:arb_units')
void = widget_button(x_units_menu,value = 'energy (meV)', /checked_menu,$
   uvalue = {object:self,method:'sel_x'},uname = 'energy:mev')
void = widget_button(x_units_menu,value = 'energy (ueV)', /checked_menu,$
   uvalue = {object:self,method:'sel_x'},uname = 'energy:uev')
void = widget_button(x_units_menu,value = 'temperature (K)', /checked_menu,$
   uvalue = {object:self,method:'sel_x'},uname = 'temperature:k')
y_units_menu = widget_button(units_menu,value = 'y-units',/menu,uname = 'Y UNITS')
void = widget_button(y_units_menu,value = 'y (arb units)', /checked_menu,$
   uvalue = {object:self,method:'sel_y'},uname = 'y:arb_units')
void = widget_button(y_units_menu,value = 'angle (degrees)', /checked_menu,$
   uvalue = {object:self,method:'sel_y'},uname = 'angle:degrees')
void = widget_button(y_units_menu,value = 'wavevector (inverse angstroms)', /checked_menu,$
   uvalue = {object:self,method:'sel_y'},uname = 'wavevector:A-1')

void = widget_button(col_base_2,value = 'Help',  $
   uvalue = {object:self,method:'help'})
void = widget_button(col_base_2,value = 'Quit',  $
   uvalue = {object:self,method:'quit'})
col_base_3 = widget_base(ctrl_base,/col)
void = widget_button(col_base_3,value = 'Sample info',  $
   uvalue = {object:self,method:'sample_info'})
self.win = widget_draw(self.tlb,xsize = xsize,ysize = ysize,/button_events, $
   /motion_events,uvalue = {object:self,method:'zoom'})
centertlb,self.tlb
widget_control,self.tlb,/realize
tree_geom = widget_info(tree_base,/geometry)
widget_control,self.win,draw_ysize = tree_geom.ysize
; Get the relevant window information out after realizing the widgets
widget_control,self.win,get_value = winvis
self.winvis = winvis
window,/free,/pixmap,xsize = xsize,ysize = tree_geom.ysize
self.winpix = !d.window

widget_control,self.tlb,set_uvalue = self
register_name = 'ascii_gui'
xmanager,register_name,self.tlb,/no_block,cleanup = 'ascii_gui_cleanup', $
   event_handler = 'ascii_gui_events'
return,1
end
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
function ascii_gui::init,  filename = filename,             $
                           group_leader = group_leader,     $
                           datdir = datdir,                 $
                           workdir = workdir,               $
                           notify_ids = notify_ids

if n_elements(group_leader) eq 0 then group_leader = 0L
;if group_leader ne 0L then begin
;  ; Get the DAVE pointer information from group leader
;  ; Note that the DAVE pointer is not valid if there is no
;  ; group leader specified here!
;;  widget_control,group_leader,get_uvalue = statePtr
;;  self.davePtr = (*statePtr).davePtr
;  ; DO NOT FREE THE STATEPTR HERE!!!! IT BELONGS TO THE
;  ; PARENT (CALLING) WIDGET!!!!
;endif
if n_elements(notify_ids) eq 0 then notify_ids = [0L,0L]
self.notify_ids = notify_ids
if n_elements(filename) eq 0 then filename = ''
if n_elements(datdir) eq 0 then begin
   cd,current = datdir
endif
if n_elements(workdir) eq 0 then cd,current = workdir
self.workdir = workdir
self.autoscale = 1
self.datdir = datdir
self.data_container = obj_new('IDL_CONTAINER')
ret = self->create_widgets()

; The use can pass in filenames so that, if valid, these can be added to the
; tree widget automatically.
; So first test out the validity of the files.
for i = 0,n_elements(filename)-1 do begin
   if file_test(filename[i]) then begin
   ; Ok it is a valid filename, but can we read it in here?
      o = obj_new('ascii_data',filename = filename[i])
      ret = o->read_group_ascii(err = err,emsg = emsg)
      if err eq 1 then begin
         ret = o->read_three_column_ascii(err = err,emsg = emsg)
      endif
      if err eq 0 then begin
         ; add the new valid data object to the data container object
         self.data_container->add,o
         ; Create the new leaf widgets in the appropriate container
         ret = self->add_leaf(o)
      endif
   endif
endfor
return,1
end
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
pro ascii_gui__define
;
define = {  ascii_gui,                 $
            tlb:0L,                    $
            datdir:'',                 $
            workdir:'',                $
            group_leader:0L,           $
            notify_ids:lonarr(2),      $
            data_container:obj_new(),  $
            file_tree:0L,              $
            ; Plotting information for resizing and zooming
            win:0L,                    $
            winpix:0L,                 $
            winvis:0L,                 $
            autoscale:0L,              $
            xrange:fltarr(2),          $
            yrange:fltarr(2),          $
            xbox:intarr(2),            $
            ybox:intarr(2),            $
            filename:'',               $
            mouse:0B                   }

end
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
pro ascii_gui_app
; Test launcher for the gui application
dir = 'c:\bhd\dave_development\dave\programs\ascii\'
file1 = dir+'single_data.txt'
file2 = dir+'my_data.txt'
datdir = dir+'russo\'
ogui = obj_new('ascii_gui',filename = [file1,file2],datdir = datdir)

end
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
