; function conspec, f,cmin,cmax,cint,nlev0,iprnt ; ; On input: ; f = array to be plotted ; cmin,cmax,cint = requested contour min,max, and interval ; (cmin >= cmax, and cmin <= 0. for no use) ; nlev = default number of contour levels (from slider) ; (slider value is used if cmin,cmax,cint are not used) ; On output: ; nlev = number of levels to use in contouring ; return levels = array of contour levels to use (or = 0.) ; nf = n_elements(f) fminmax, f,nf,rmin,rmax,!spval if rmin eq 1.e36 and rmax eq -1.e36 then begin print,'>>> conspec: no data (array is all special value)' nlev0 = 0 return,[0.] endif ccase = 0 nlev = nlev0 ; ; There are 4 cases: ; if cmin ge cmax and cint le 0. then ccase = 1 if cmin lt cmax and cint le 0. then ccase = 2 if cmin ge cmax and cint gt 0. then ccase = 3 if cmin lt cmax and cint gt 0. then ccase = 4 case ccase of ; ; Do not use cmin, cmax, or cint (nlev unchanged): ; (use rmin,rmax and nlev to determine interval and levels) ; 1: begin conint = (rmax-rmin) / (nlev-1) levels = fltarr(nlev) for i=0,nlev-1 do levels(i) = rmin+i*conint if iprnt gt 0 then begin print,'conspec: not using cmin,cmax, or cint' print,format=$ "(' nlevels=',i2,' interval=',e12.4,' levels=')",nlev,conint print,levels endif end ; ; Use cmin and cmax, but not cint (nlev unchanged): ; (use cmin, cmax and nlev to determine interval and levels) ; 2: begin if iprnt gt 0 then print,$ 'conspec: using cmin (',cmin,') ,cmax (',cmax,'), but not cint' ; ; Set any values > cmax to spval: nmax = 0 indx = where(f gt cmax, nmax) if nmax ne 0 then f(indx) = !spval if iprnt gt 0 then $ print,' cut ',nmax,' values above cmax=',cmax if nmax ge nf then begin print,'>>> no data found >= cmax=',cmax return,[0.] endif ; ; Set any values < cmin to spval: nmin = 0 indx = where(f lt cmin, nmin) if nmin ne 0 then f(indx) = !spval if iprnt gt 0 then $ print,' cut ',nmin,' values below cmin=',cmin if nmin ge nf then begin print,'>>> no data found <= cmin=',cmin return,[0.] endif ; ; Get a contour interval and set the levels, using cmin,cmax: conint = (cmax-cmin) / (nlev-1) levels = fltarr(nlev) for i=0,nlev-1 do levels(i) = cmin+i*conint if iprnt gt 0 then begin print,format=$ "(' nlevels=',i2,' interval=',e12.4,' levels=')",nlev,conint print,levels endif end ; ; Use cint but not cmin or cmax: ; (nlev determined from rmin,rmax, and cint) ; 3: begin if iprnt gt 0 then $ print,'conspec: using cint (',cint,') but not cmin,cmax: nlev = fix((rmax-rmin)/cint+.5) ; +.5 is to get nearest int if cmin+float(nlev)*cint le cmax then nlev = nlev+1 if nlev le 30 then begin if iprnt gt 0 then $ print,format=$ "(' nlevels=',i2,' interval=',e12.4,' levels=')",nlev,cint endif else begin if iprnt gt 0 then begin print,'>>> conspec: nlevels=',nlev,': must have <= 30 levels' print,' changing nlev to 30. levels=' endif nlev = 30 endelse levels = fltarr(nlev) for i=0,nlev-1 do levels(i) = rmin+i*cint if iprnt gt 0 then print,levels end ; ; Use cmin,cmax, and cint: ; 4: begin if iprnt gt 0 then $ print,'conspec: using cmin (',cmin,'), cmax (',cmax,$ '), and cint (',cint,'):' ; ; Set any values > cmax to spval: nmax = 0 indx = where(f gt cmax, nmax) if nmax ne 0 then f(indx) = !spval if iprnt gt 0 then $ print,' cut ',nmax,' values above cmax=',cmax if nmax ge nf then begin print,'>>> no data found >= cmax=',cmax return,[0.] endif ; ; Set any values < cmin to spval: nmin = 0 indx = where(f lt cmin, nmin) if nmin ne 0 then f(indx) = !spval if iprnt gt 0 then $ print,' cut ',nmin,' values below cmin=',cmin if nmin ge nf then begin print,'>>> no data found <= cmin=',cmin return,[0.] endif ; ; Calculate levels: nlev = fix((cmax-cmin)/cint+.5) ; +.5 is to get nearest int if cmin+float(nlev)*cint le cmax then nlev = nlev+1 if nlev le 30 then begin if iprnt gt 0 then $ print,format=$ "(' nlevels=',i2,' interval=',e12.4,' levels=')",nlev,cint endif else begin if iprnt gt 0 then begin print,'>>> conspec: nlevels=',nlev,': must have <= 30 levels' print,' changing nlev to 30. levels=' endif nlev = 30 endelse levels = fltarr(nlev) for i=0,nlev-1 do levels(i) = cmin+i*cint if iprnt gt 0 then print,levels end else: endcase if nlev ne nlev0 and nlev le 2 then begin nlev0 = nlev ; widget_control,wsl_nlev,set_value=nlev,bad_id=badid endif else if nlev le 2 then print,'conspec warning: nlev too small=',nlev return,levels end