;+
; NAME:
;	FF_SUMMARY
;
;
; PURPOSE:
;	Get a 1-line summary of a FITS file (SMEI)
;
;
; CATEGORY:
;	UTILS
;
;
; CALLING SEQUENCE:
;	desc = ff_summary(file)
;
;
; INPUTS:
;	file	string	The file to summarize (if the path key is set,
;			then it can be a wildcard).
;
;
; KEYWORD_PARAMETERS:
;	/template	Return a title bar for a summary
;	path	string	A directory to search for the files. (If this
;			is given then file is optional and defaults to
;			the current directory.
;	filelist str	If this is a named variable, then it will
;			return the list of filenames (only really
;			useful when path is given).
;	startlist dbl	If this is a named variable then it will
;			contain the JD's of the image start times.
;	count	long	If this is a named variable, on return it will
;			contain the number of files found.
;	/no_file	If set then actually open each file rather
;			than using the img_hdr.txt file to get the info.
;	/norecurse	If set, then do not look in subdirectories.
;	projections str	A named variable to hold the list of
;			projections of the images.
;	/no_progresss	If set, then do not create a progress bar to
;			show progress through files and directories
;			(mainly for running over a slow network). 		
;
;
; MODIFICATION HISTORY:
;	Original: 13/12/02; SJT
;	Modify for degenerate Aitoff files: 7/3/03; SJT
;	Modify to allow use of a tree to store files: 1/7/03; SJT
;	Add fold_case keyword to file_search calls: 23/7/03; SJT
;	Fix crash in single plane images: 2/10/03; SJT
;	Deal with possibility of files called .fts: 20/11/03; SJT
;	Add projection information, and projections keyword, and save
;	list: 16/2/04; SJT
;	Do recursion explicitly to allow symlinked subdirs to work:
;	12/8/04; SJT
;	Major efficiency changes: 11/11/04; SJT
;	Add list of mal-indexed directories: 31/5/05; SJT
;	Support compressed fits files: 24/5/05; SJT
;	Add no_progress keyword: 25/8/05; SJT
;-

function ff_summary, file, template = template, path = path, $
                     filelist = filelist, startlist = startlist, count $
                     = count, no_file = no_file, projections = $ $
                     projections, norecurse = norecurse, no_progress = $
                     no_progress

common ff_summary_lastpath, lastpath, lastdesc, lastfiles, laststarts

if n_elements(lastpath) eq 0 or keyword_set(no_file) then lastpath = ''

if keyword_set(template) then return, $
  ' Year Day Start Length Cols Rows Flags'

case !version.os_family of
    'unix': sep = '/'
    else: sep = '\'
end
 
if widget_info(/active) eq 0 or keyword_set(no_progress) then $
  isprog = 0b $
else isprog = 1b

if keyword_set(path) then begin
    if path ne lastpath then begin
        if n_params() eq 0 then file = '*.f*t*'
        cfile = file_search(path+sep+file, /fold_case, count = count)
        hfile = file_search(path+sep+'img_hdr.txt', /fold_case, $
                            count = hcount)
        if not keyword_set(norecurse) then begin
            plist = file_search(path+sep+'*',  /test_directory, count $
                                = ndir)
            if ndir ge 1 then for j = 0, ndir-1 do begin
                cfilep = file_search(plist[j], file, /fold_case, count $
                                     = countp)
                if countp ne 0 then begin
                    if count gt 0 then cfile = [cfile, cfilep] $
                    else cfile = cfilep
                    count += countp
                endif
                hfilep = file_search(plist[j], 'img_hdr.txt', /fold_case, $
                                     count = hcountp)
                if hcountp ne 0 then begin
                    if hcount gt 0 then hfile = [hfile, hfilep] $
                    else hfile = hfilep
                    hcount += hcountp
                endif
            endfor
        endif
        cflag = 0b
    endif else cflag = 1b
    if cflag then begin
        desc = lastdesc
        filelist = lastfiles
        startlist = laststarts
        projections = strmid(lastdesc, strlen(lastdesc[0])-7, 7)
        count = n_elements(desc)
        return, desc
    endif
endif else begin
    cfile = [file]
    count = 1
    hfile = 'img_hdr.txt'
endelse

if not keyword_set(no_file) then begin
    if hcount eq 0 then goto, nohdr
    on_ioerror, nohdr
    nfe = hcount*30l
    hfiles = strarr(nfe)
    hdesc = strarr(nfe)

    inln = strarr(2)
    if isprog then $
      pm = cw_progress(title = 'Scanning directories', $
                       value = 0., $
                       /column, $
                       xsize = 200, $
                       ysize = 20, $
                       max = hcount) $
    else pm = 0l

    jf = -1l
    for j = 0, hcount-1 do begin
        openr, ilu, /get, hfile[j]
        while not eof(ilu) do begin
            jf++
            if jf eq nfe then begin
                dn = (hcount-j)*40
                hfiles = [hfiles, strarr(dn)]
                hdesc = [hdesc, strarr(dn)]
                nfe += dn
            endif
            readf, ilu, inln, format = "(A35, A)"
            hfiles[jf] = strtrim(inln[0])
            hdesc[jf] = inln[1]
        endwhile
        free_lun, ilu
        if widget_info(/valid, pm) then $
          widget_control, pm, set_value = j+1
    endfor
    if widget_info(/valid, pm) then $
      widget_control, pm, /destroy

    hfiles = hfiles[0:jf]
    hdesc = hdesc[0:jf]
    nhfiles = jf+1
    goto, hdrok
    nohdr: 
    smei_msg, /warn, "No img_hdr.txt found, this will make things " + $
              "slow"
    hfiles = ''
    hdrok:
    on_ioerror, null
endif else hfiles = ''

iflag = 0b
if count ne 0 and isprog then begin
    pm = cw_progress(title = 'Checking files', $
                     value = 0., $
                     /column, $
                     xsize = 200, $
                     ysize = 20, $
                     max = count)
    ispid = 1b
endif else ispid = 0b

desc = strarr(count > 1)
filelist = strarr(2, count > 1)
startlist = dblarr(count > 1)
projections = strarr(count > 1)

for j = 0l, count-1 do begin
    ed = strpos(cfile[j], sep, /reverse_search)
    if ed eq -1 then sf =  ['', cfile[j]] $
    else sf = [strmid(cfile[j], 0, ed+1), $
               strmid(cfile[j], ed+1, strlen(cfile[j]))]
    locs = where(hfiles eq get_comp_name(sf[1], /return_base),  nf)

    if nf eq 0 then begin
        if not keyword_set(no_file) then begin
            iflag = 1b
            if n_elements(baddir) eq 0 then baddir = sf[0] $
            else baddir = [baddir, sf[0]]
        endif
        head = headfits(cfile[j])

        h = fitshead2struct(head)

        if ((flg = hist_find('Saturation removal', h.history))) ne -1 $
                   then f1 = (['-', 'S'])[flg gt 0] $
        else if struct_contains(h, 'BIAS') then $
          f1 = (['-', 'S'])[h.bias gt 0] $
        else f1 = '.'

        if ((flg = hist_find('Large-scale flatfields', h.history))) ne $
                   -1 then $
                   f1 = f1+(['-', 'L'])[flg gt 0] $
        else if struct_contains(h, 'LSFF') then $
                   f1 = f1+(['-', 'L'])[h.lsff gt 0] $
             else f1 = f1+'.'

        if ((flg = hist_find('Dark offset subtraction', h.history))) ne $
                   -1 then $
                   f1 = f1+(['-', 'D'])[flg gt 0] $
        else if struct_contains(h, 'DARK') then $
                   f1 = f1+(['-', 'D'])[h.dark ne 0] $
             else f1 = f1+'.'

        
        if ((flg = hist_find('Spike removal', h.history))) ne $
                   -1 then $
                   f1 = f1+(['-', 'C'])[flg gt 0] $
        else if struct_contains(h, 'CRAYS') then $
                   f1 = f1+(['-', 'C'])[h.crays ne 0] $
             else f1 = f1+'.'
        
        if ((flg = hist_find('Moon and planet removal', h.history))) $
                   ne -1 then $
          f1 = f1+(['-', 'B'])[flg gt 0] $
        else if struct_contains(h, 'BRIGHT') then $
          f1 = f1+(['-', 'B'])[h.bright gt 0]$
        else f1 = f1+'.'

        if ((flg = hist_find('Camera equalization', h.history))) $
                   ne -1 then $
          f1 = f1+(['-', 'E'])[flg gt 0] $
        else if struct_contains(h, 'GAIN') then $
          f1 = f1+(['-', 'G'])[h.gain gt 0]$
        else f1 = f1+'.'

        if ((flg = hist_find('Pointing', h.history))) ne $
                   -1 then $
                   f1 = f1+(['-', 'L'])[flg gt 1] $
        else if struct_contains(h, 'LPOINT') then $
                   f1 = f1+(['-', 'L'])[h.lpoint gt 0] $
             else f1 = f1+'.'
        
        if ((flg = hist_find('Pointing', h.history))) ne $
                   -1 then $
                   f1 = f1+(['-', 'G'])[flg gt 0] $
        else if struct_contains(h, 'GPOINT') then $
                   f1 = f1+(['-', 'G'])[h.gpoint gt 0] $
             else f1 = f1+'.'
        
        if ((flg = hist_find('Zodiacal subtraction', h.history))) ne $
                   -1 then $
                   f1 = f1+(['-', 'Z'])[flg gt 0] $
        else if struct_contains(h, 'ZODY') then $
                   f1 = f1+(['-', 'Z'])[h.zody gt 0] $
             else f1 = f1+'.'
        
        if ((flg = hist_find('Star subtraction', h.history))) ne $
                   -1 then $
          f1 = f1+(['-', 'S'])[flg gt 0] $
        else if struct_contains(h, 'STELLAR') then $
          f1 = f1+(['-', 'S'])[h.stellar gt 0] $
        else if struct_contains(h, 'BSTARS') then $
          f1 = f1+(['-', 'B'])[h.bstars gt 0] $
        else f1 = f1+'.'

        flg = -1
        for icam = 1, 3 do begin
            mstr = 'Camera '+string(icam, format = '(I1)')+' bad pixel ' + $
                   'mask'
            flg = flg > hist_find(mstr,  h.history, /bool, /line_break) 
        endfor
        if flg ne -1 then f1 = f1+(['-', 'H'])[flg gt 0] $
        else if struct_contains(h, 'FLIPPERS') then $
          f1 = f1+(['-', 'H'])[h.flippers gt 0] $
        else f1 = f1+'.'

; This messy stuff is because early SMEI Aitoffs have several
; different ways of storing their dates.

        if struct_contains(h, 'START_UT') then begin
            jd0 = epoch2jd(h.start_ut)
            date = jd2doy(jd0)
            h0 = date[2]
            m0 = date[3]
            s0 = date[4]
            d = 0
            yr = date[0]
            day = date[1]
            jd1 = epoch2jd(h.stop_ut)
            d = (jd1-jd0)*1440.
;            if d lt 0 then d = d+1440.
        endif else if struct_contains(h, 'MJD_D$OBS') then begin
            jd0 = 2400000.d0 + h.mjd_d$obs
            date = jd2doy(jd0)
            h0 = date[2]
            m0 = date[3]
            s0 = date[4]
            d = 0
            yr = date[0]
            day = date[1]
        endif else if struct_contains(h, 'OBS_MJD') then begin
            jd0 = 2400000.d0 + h.obs_mjd
            date = jd2doy(jd0)
            h0 = date[2]
            m0 = date[3]
            s0 = date[4]
            d = 0
            yr = date[0]
            day = date[1]
        endif else begin
            h0 = 0
            m0 = 0
            s0 = 0
            d = 0
            yr = 0
            day = 0
        endelse
        if h.naxis eq 3 then npl =  h.naxis3 $
        else npl = 1
        case h.ctype1 of
            'ELON-AIT': project = 'Aitoff '
            'ELON-ARC': project = 'Fisheye'
            else:       project = 'Unknown'
        endcase
        desc[j] = string(yr, day, h0, m0, d, $
                         h.naxis1, h.naxis2, npl, f1, project, $
                         format = $
                         "(I4.4,' ',I3.3,' ',I2.2,':',I2.2," + $
                         "' ',F6.1,' ',I4,'x',I4,' ',I1,' ',A,' ',A)")
    endif else if hcount ne 0 then begin
        desc[j] = hdesc[locs[0]]
        yr = 0l & day = 0l
        h0 = 0l & m0 = 0l &  s0 = 0l
        d = 0. & nax1 = 0l & nax2 = 0l & nax3 = 0 & f1p = ''
        reads, hdesc[locs[0]], yr, day, h0, m0, d, nax1, nax2, nax3, $
               f1p, format = $
               "(I5,I4,I3,1x,I2,F7.0,I5,1x,I4,1x,i1,1x,A)"

        f1ps = strsplit(f1p, ' ', /extract, count = nstr)
;         help, f1p, f1ps
;         stop
        f1 = f1ps[0]
        if nstr eq 2 then project = f1ps[1] $
        else begin
            smei_msg, /warn, $
                      "Obsolete img_hdr.txt found, remake it to get " + $
                      "projection information"
            project = "       "
        endelse
    endif
    filelist[*, j]= [sf[0], get_comp_name(sf[1], /return_base)]

    startlist[j] = doy2jd([yr, day, h0, m0, s0])
    projections[j] = project
    
    if (j+1) mod 20 eq 0  or j eq count - 1 then begin  
        if ispid then widget_control, pm, set_value = $
          j+1 $
        else print, string(13b), j+1, count, format = $
                    "($,A,I0,' of ',I0)"
    end
endfor

if ispid then widget_control, pm, /destroy

if iflag then begin
    idx = uniq(baddir, sort(baddir))
    smei_msg, /warn, ["Not all files found are in " + $
                      "img_hdr.txt", $
                      "you should re-run mk_imghdrtxt on " + $
                      "this directory:", $
                      baddir[idx]]
endif

if not ispid then print

if keyword_set(path) then begin
    lastpath = path
    lastdesc = desc
    lastfiles = filelist
    laststarts = startlist
endif

return, desc

end
