diff --git a/CEP/PyBDSM/doc/source/conf.py b/CEP/PyBDSM/doc/source/conf.py index beb46f3e1f0fee088979df588f68d083fcd58250..457c7341fe324ead8d63359a15ec162e34c25fcd 100644 --- a/CEP/PyBDSM/doc/source/conf.py +++ b/CEP/PyBDSM/doc/source/conf.py @@ -50,7 +50,7 @@ copyright = u'2012, David Rafferty and Niruj Mohan' # The short X.Y version. version = '1.4' # The full version, including alpha/beta/rc tags. -release = '1.4.4' +release = '1.4.5' # The language for content autogenerated by Sphinx. Refer to documentation # for a list of supported languages. diff --git a/CEP/PyBDSM/doc/source/process_image.rst b/CEP/PyBDSM/doc/source/process_image.rst index d7c365b9151d6adf9abb6ee7c6803d26d116ea14..67594324bbba6aa18dfe84d9bec31a6813851d6d 100644 --- a/CEP/PyBDSM/doc/source/process_image.rst +++ b/CEP/PyBDSM/doc/source/process_image.rst @@ -909,7 +909,7 @@ The options for this module are as follows: This parameter is an integer (default is 2). When constructing a set of 'unresolved' sources for psf estimation, this parameter controls the factor of nyquist sample for binning bmaj, etc. vs SNR. psf_smooth - This parameter is a float (default is ``None``) that sets the smoothing scale used to smooth the interpolated images. Generally, artifacts due to noise and the interpolation can be significantly reduced if the smoothing scale is similar to the typical source separation scale. + This parameter is a float (default is ``None``) that sets the smoothing scale (in arcsec) used to smooth the interpolated images. Generally, artifacts due to noise and the interpolation can be significantly reduced if the smoothing scale is similar to the typical source separation scale. psf_snrcut This parameter is a float (default is 10.0). Only Gaussians with SNR greater than this are considered for processing. diff --git a/CEP/PyBDSM/doc/source/whats_new.rst b/CEP/PyBDSM/doc/source/whats_new.rst index 405eeb5c442add35a929a00dd4a4a82281a0a89f..b62ae3fffb345b2de8af56556476b1ba4ca6fa0c 100644 --- a/CEP/PyBDSM/doc/source/whats_new.rst +++ b/CEP/PyBDSM/doc/source/whats_new.rst @@ -4,6 +4,14 @@ What's New ********** +Version 1.4.5 (2012/10/12): + + * Added option (``incl_empty``) to include empty islands (that have no un-flagged Gaussians) in output catalogs. Any such empty islands are given negative source IDs and have positions given by the location of the peak of the island. + + * Fixed a bug in Gaussian fitting that could cause a crash when fitting fails. + + * Fixed a bug in parallelization that could cause a crash due to improper concatenation of result lists. + Version 1.4.4 (2012/10/09): * Fixed a bug related to the parallelization of Gaussian fitting that could cause a crash due to improper mapping of island lists to processes. diff --git a/CEP/PyBDSM/doc/source/write_catalog.rst b/CEP/PyBDSM/doc/source/write_catalog.rst index aeee14b249a706a6622e15eb926fb4b2e55040c3..e5fc7d128aaf49897999c110bd1432d3f1fcdc14 100644 --- a/CEP/PyBDSM/doc/source/write_catalog.rst +++ b/CEP/PyBDSM/doc/source/write_catalog.rst @@ -32,6 +32,8 @@ The task parameters are as follows: :term:`format` ................ 'bbs': Format of output Gaussian list: 'bbs', 'ds9', 'fits', 'star', 'kvis', or 'ascii' :term:`incl_chan` ............ False : Include fluxes from each channel (if any)? + :term:`incl_empty` ........... False : Include islands without any valid Gaussians + (source list only)? :term:`srcroot` ............... None : Root name for entries in the output catalog. None => use image file name @@ -86,6 +88,9 @@ Each of the parameters is described in detail below. incl_chan This parameter is a Boolean (default is ``False``) that determines whether the total flux densities of each source measured in each channel by the spectral index module are included in the output. + incl_empty + This parameter is a Boolean (default is ``False``) that determines whether islands without any valid Gaussians are included in the output catalog. This option is only available for source lists. If True, islands for which Gaussian fitting failed will be included in the output catalog. In these cases, the source IDs are negative. + srcroot This parameter is a string (default is ``None``) that sets the root for source names in the output catalog. diff --git a/CEP/PyBDSM/src/python/_version.py b/CEP/PyBDSM/src/python/_version.py index 33b931ce61a04ad132ba7b5c14925e604615386d..002422b03ae2569f71fa92a5220751962b87e000 100644 --- a/CEP/PyBDSM/src/python/_version.py +++ b/CEP/PyBDSM/src/python/_version.py @@ -9,7 +9,7 @@ adding to the changelog will naturally do this. """ # Version number -__version__ = '1.4.4' +__version__ = '1.4.5' # Store svn Revision number. For this to work, one also needs to do: # @@ -27,6 +27,13 @@ def changelog(): PyBDSM Changelog. ----------------------------------------------------------------------- + 2012/10/09 - Version 1.4.5 + + 2012/10/12 - Added option ("incl_empty") to include empty islands (that + have no un-flagged Gaussians) in output catalogs. Any such empty + islands are given negative source IDs and positions given by the + location of the peak of the island. + 2012/10/10 - Fixed a bug in Gaussian fitting that could cause a crash when fitting fails. Fixed a bug in parallelization that could cause a crash due to improper concatenation of result lists. diff --git a/CEP/PyBDSM/src/python/functions.py b/CEP/PyBDSM/src/python/functions.py index c31481ac9c39558a4a754645ffb70804f8530b17..2a116e72e91bf4187a7459805aa973325737b7a8 100755 --- a/CEP/PyBDSM/src/python/functions.py +++ b/CEP/PyBDSM/src/python/functions.py @@ -734,38 +734,41 @@ def get_errors(img, p, stdav, bm_pix=None): errors = [] for i in range(ngaus): pp = p[i*7:i*7+7] - ### Now do error analysis as in Condon (and fBDSM) + ### Now do error analysis as in Condon (and fBDSM) size = pp[3:6] size = corrected_size(size) # angle is now degrees CCW from +y-axis - sq2 = sqrt(2.0) - if bm_pix == None: - bm_pix = N.array([img.pixel_beam[0]*fwsig, img.pixel_beam[1]*fwsig, img.pixel_beam[2]]) - dumr = sqrt(abs(size[0]*size[1]/(4.0*bm_pix[0]*bm_pix[1]))) - dumrr1 = 1.0+bm_pix[0]*bm_pix[1]/(size[0]*size[0]) - dumrr2 = 1.0+bm_pix[0]*bm_pix[1]/(size[1]*size[1]) - dumrr3 = dumr*pp[0]/stdav - d1 = sqrt(8.0*log(2.0)) - d2 = (size[0]*size[0]-size[1]*size[1])/(size[0]*size[0]) - try: - e_peak = pp[0]*sq2/(dumrr3*pow(dumrr1,0.75)*pow(dumrr2,0.75)) - e_maj=size[0]*sq2/(dumrr3*pow(dumrr1,1.25)*pow(dumrr2,0.25)) - e_min=size[1]*sq2/(dumrr3*pow(dumrr1,0.25)*pow(dumrr2,1.25)) # in fw - pa_rad = size[2]*pi/180.0 - e_x0 = sqrt( (e_maj*N.sin(pa_rad))**2 + (e_min*N.cos(pa_rad))**2 ) / d1 - e_y0 = sqrt( (e_maj*N.cos(pa_rad))**2 + (e_min*N.sin(pa_rad))**2 ) / d1 - e_pa=2.0/(d2*dumrr3*pow(dumrr1,0.25)*pow(dumrr2,1.25)) - e_pa=e_pa*180.0/pi - e_tot=pp[0]*sqrt(e_peak*e_peak/(pp[0]*pp[0])+(0.25/dumr/dumr)*(e_maj*e_maj/(size[0]*size[0])+e_min*e_min/(size[1]*size[1]))) - except: - e_peak = 0.0 - e_x0 = 0.0 - e_y0 = 0.0 - e_maj = 0.0 - e_min = 0.0 - e_pa = 0.0 - e_tot = 0.0 - if abs(e_pa) > 180.0: e_pa=180.0 # dont know why i did this - errors = errors + [e_peak, e_x0, e_y0, e_maj, e_min, e_pa, e_tot] + if size[0] == 0.0 or size[1] == 0.0: + errors = errors + [0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0] + else: + sq2 = sqrt(2.0) + if bm_pix == None: + bm_pix = N.array([img.pixel_beam[0]*fwsig, img.pixel_beam[1]*fwsig, img.pixel_beam[2]]) + dumr = sqrt(abs(size[0]*size[1]/(4.0*bm_pix[0]*bm_pix[1]))) + dumrr1 = 1.0+bm_pix[0]*bm_pix[1]/(size[0]*size[0]) + dumrr2 = 1.0+bm_pix[0]*bm_pix[1]/(size[1]*size[1]) + dumrr3 = dumr*pp[0]/stdav + d1 = sqrt(8.0*log(2.0)) + d2 = (size[0]*size[0]-size[1]*size[1])/(size[0]*size[0]) + try: + e_peak = pp[0]*sq2/(dumrr3*pow(dumrr1,0.75)*pow(dumrr2,0.75)) + e_maj=size[0]*sq2/(dumrr3*pow(dumrr1,1.25)*pow(dumrr2,0.25)) + e_min=size[1]*sq2/(dumrr3*pow(dumrr1,0.25)*pow(dumrr2,1.25)) # in fw + pa_rad = size[2]*pi/180.0 + e_x0 = sqrt( (e_maj*N.sin(pa_rad))**2 + (e_min*N.cos(pa_rad))**2 ) / d1 + e_y0 = sqrt( (e_maj*N.cos(pa_rad))**2 + (e_min*N.sin(pa_rad))**2 ) / d1 + e_pa=2.0/(d2*dumrr3*pow(dumrr1,0.25)*pow(dumrr2,1.25)) + e_pa=e_pa*180.0/pi + e_tot=pp[0]*sqrt(e_peak*e_peak/(pp[0]*pp[0])+(0.25/dumr/dumr)*(e_maj*e_maj/(size[0]*size[0])+e_min*e_min/(size[1]*size[1]))) + except: + e_peak = 0.0 + e_x0 = 0.0 + e_y0 = 0.0 + e_maj = 0.0 + e_min = 0.0 + e_pa = 0.0 + e_tot = 0.0 + if abs(e_pa) > 180.0: e_pa=180.0 # dont know why i did this + errors = errors + [e_peak, e_x0, e_y0, e_maj, e_min, e_pa, e_tot] return errors diff --git a/CEP/PyBDSM/src/python/gaul2srl.py b/CEP/PyBDSM/src/python/gaul2srl.py index 87e1b2914fc1e9e9893ed0a8d58fb13220f1cb85..317b6b35fd82385c591db430a7276b60929c59e9 100644 --- a/CEP/PyBDSM/src/python/gaul2srl.py +++ b/CEP/PyBDSM/src/python/gaul2srl.py @@ -43,11 +43,13 @@ class Op_gaul2srl(Op): img.aperture = None src_index = -1 - src_index_dum = 0 + dsrc_index = 0 sources = [] + dsources = [] no_gaus_islands = [] for iisl, isl in enumerate(img.islands): isl_sources = [] + isl_dsources = [] g_list = [] for g in isl.gaul: if g.flag == 0: @@ -64,21 +66,23 @@ class Op_gaul2srl(Op): isl_sources.extend(source) else: if not img.waveletimage: - no_gaus_islands.append((isl.island_id, isl.origin[0], isl.origin[1])) - # Put in the dummy Gaussian as the source and use negative IDs - #g_list = isl.gaul - #src_index_dum, source = self.process_single_gaussian(img, g_list, src_index_dum, code = 'S') - #sources.append(source) - #isl_sources.append(source) + dg = isl.dgaul[0] + no_gaus_islands.append((isl.island_id, dg.centre_pix[0], dg.centre_pix[1])) + # Put in the dummy Source as the source and use negative IDs + g_list = isl.dgaul + dsrc_index, dsource = self.process_single_gaussian(img, g_list, dsrc_index, code = 'S') + dsources.append(dsource) + isl_dsources.append(dsource) isl.sources = isl_sources - + isl.dsources = isl_dsources img.sources = sources + img.dsources = dsources img.nsrc = src_index + 1 mylogger.userinfo(mylog, "Number of sources formed from Gaussians", str(img.nsrc)) - if not img.waveletimage and len(no_gaus_islands) > 0 and not img.opts.quiet: - message = 'Gaussian fitting failed for the following island' + if not img.waveletimage and not img._pi and len(no_gaus_islands) > 0 and not img.opts.quiet: + message = 'All Gaussians were flagged for the following island' if len(no_gaus_islands) == 1: message += ':\n' else: @@ -90,10 +94,12 @@ class Op_gaul2srl(Op): else: message += 'Please check these islands. If they are valid islands and\n' if img.opts.atrous_do: - message += 'should be fit, try adjusting the flagging options.' + message += 'should be fit, try adjusting the flagging options (use\n'\ + 'show_fit with "ch0_flagged=True" to see the flagged Gaussians).' else: - message += 'should be fit, try adjusting the flagging options or \n'\ - 'enabling the wavelet module (with "atrous_do=True").' + message += 'should be fit, try adjusting the flagging options (use\n'\ + 'show_fit with "ch0_flagged=True" to see the flagged Gaussians)\n'\ + 'or enabling the wavelet module (with "atrous_do=True").' mylog.warning(message) img.completed_Ops.append('gaul2srl') @@ -114,7 +120,10 @@ class Op_gaul2srl(Op): bbox = img.islands[g.island_id].bbox ngaus = 1 island_id = g.island_id - gaussians = list([g]) + if g.gaus_num < 0: + gaussians = [] + else: + gaussians = list([g]) aper_flux = func.ch0_aperture_flux(img, g.centre_pix, img.aperture) source_prop = list([code, total_flux, peak_flux_centroid, peak_flux_max, aper_flux, posn_sky_centroid, \ diff --git a/CEP/PyBDSM/src/python/gausfit.py b/CEP/PyBDSM/src/python/gausfit.py index 996c7e14223ce75d208d9fe300874ff4d4eff963..0b27e19dd01b5c1e8a83aebfc96c3ccb2a2c0c34 100644 --- a/CEP/PyBDSM/src/python/gausfit.py +++ b/CEP/PyBDSM/src/python/gausfit.py @@ -100,22 +100,27 @@ class Op_gausfit(Op): idx = isl.island_id gaul = gaus_list[idx][0] fgaul = gaus_list[idx][1] + dgaul = [] gaul = [Gaussian(img, par, idx, gidx) for (gidx, par) in enumerate(gaul)] if len(gaul) == 0: - # No good Gaussians were fit. In this case, use the flagged - # Gaussian (estimated using moment analysis) as a dummy so + # No good Gaussians were fit. In this case, make a dummy + # Gaussian located at the island center so # that the source may still be included in output catalogs. - # These dummy Gaussians all have an ID of -1. -# gaul= [Gaussian(img, par, idx, -1, flag) -# for (gidx2, (flag, par)) in enumerate(fgaul)] + # These dummy Gaussians all have an ID of -1. They do not + # appear in any of the source or island Gaussian lists except + # the island dgaul list. + posn = N.unravel_index(N.argmax(isl.image*~isl.mask_active), isl.shape) + N.array(isl.origin) + par = [isl.max_value, posn[0], posn[1], 0.0, 0.0, 0.0] + dgaul = [Gaussian(img, par, idx, -1)] gidx = 0 fgaul= [Gaussian(img, par, idx, gidx + gidx2 + 1, flag) for (gidx2, (flag, par)) in enumerate(fgaul)] isl.gaul = gaul isl.fgaul= fgaul + isl.dgaul = dgaul gaussian_list = [g for isl in img.islands for g in isl.gaul] img.gaussians = gaussian_list @@ -133,13 +138,13 @@ class Op_gausfit(Op): for isl in img.islands: m = 0 for g in isl.gaul: - if g.gaussian_idx == -1: - nn -= 1; m = 0 - g.gaus_num = nn - else: - n += 1; m += 1 - g.gaus_num = n - 1 + n += 1; m += 1 + g.gaus_num = n - 1 tot_flux += g.total_flux + for dg in isl.dgaul: + nn -= 1 + dg.gaus_num = nn + isl.ngaus = m img.ngaus = n img.total_flux_gaus = tot_flux diff --git a/CEP/PyBDSM/src/python/image.py b/CEP/PyBDSM/src/python/image.py index 88da33456d3d03aec277570cf2049e3f088bae40..48d4cb48bf454b5619ac25413cb91215b2059748 100644 --- a/CEP/PyBDSM/src/python/image.py +++ b/CEP/PyBDSM/src/python/image.py @@ -41,6 +41,9 @@ class Image(object): basedir = String('DUMMY', doc="Base directory for output files") completed_Ops = List(String(), doc="List of completed operations") _is_interactive_shell = Bool(False, doc="PyBDSM is being used in the interactive shell") + waveletimage = Bool(False, doc="Image is a wavelet transform image") + _pi = Bool(False, doc="Image is a polarized intensity image") + def __init__(self, opts): diff --git a/CEP/PyBDSM/src/python/interface.py b/CEP/PyBDSM/src/python/interface.py index adf26bf88049262b498a8e9b411213c93f1626df..861287cb351e6de3f24588fb777cdcdc780ac342 100644 --- a/CEP/PyBDSM/src/python/interface.py +++ b/CEP/PyBDSM/src/python/interface.py @@ -24,6 +24,7 @@ def process(img, **kwargs): # First, reset img to initial state (in case img is being reprocessed) if hasattr(img, 'use_io'): del img.use_io if hasattr(img, 'sources'): del img.sources + if hasattr(img, 'dsources'): del img.dsources if hasattr(img, 'gaussians'): del img.gaussians if hasattr(img, 'atrous_gaussians'): del img.atrous_gaussians if hasattr(img, 'islands'): del img.islands @@ -703,7 +704,7 @@ def write_catalog(img, outfile=None, format='bbs', srcroot=None, catalog_type='g patch "source" - sources are grouped by source into patches incl_chan - Include fluxes for each channel? - incl_empty - Include islands without any valid Gaussians (if any)? + incl_empty - Include islands without any valid Gaussians (source list only)? sort_by - Property to sort output list by: "flux" - sort by total integrated flux, largest first "indx" - sort by Gaussian and island or source index, smallest first diff --git a/CEP/PyBDSM/src/python/make_residimage.py b/CEP/PyBDSM/src/python/make_residimage.py index e13296df7123b6cd6bc332d81b65f6aef83e133b..93a3268386953d7a2bcb026bc19522e3e2103b05 100644 --- a/CEP/PyBDSM/src/python/make_residimage.py +++ b/CEP/PyBDSM/src/python/make_residimage.py @@ -85,18 +85,7 @@ class Op_make_residimage(Op): ### residual rms and mean per island for isl in img.islands: resid = img.resid_gaus[isl.bbox] - n, m = resid.shape - - ind = N.where(~isl.mask_active) - resid = resid[ind] - isl.gresid_rms = N.std(resid) - isl.gresid_mean = N.mean(resid) - for src in isl.sources: - src.gresid_rms = N.std(resid) - src.gresid_mean = N.mean(resid) - for g in src.gaussians: - g.gresid_rms = N.std(resid) - g.gresid_mean = N.mean(resid) + self.calc_resid_mean_rms(isl, resid, type='gaus') # Calculate some statistics for the Gaussian residual image non_masked = N.where(~N.isnan(img.ch0)) @@ -145,17 +134,7 @@ class Op_make_residimage(Op): ### shapelet residual rms and mean per island for isl in img.islands: resid = img.resid_shap[isl.bbox] - n, m = resid.shape - ind = N.where(~isl.mask_active) - resid = resid[ind] - isl.sresid_rms = N.std(resid) - isl.sresid_mean = N.mean(resid) - for src in isl.sources: - src.sresid_rms = N.std(resid) - src.sresid_mean = N.mean(resid) - for g in src.gaussians: - g.sresid_rms = N.std(resid) - g.sresid_mean = N.mean(resid) + self.calc_resid_mean_rms(isl, resid, type='shap') # Calculate some statistics for the Shapelet residual image non_masked = N.where(~N.isnan(img.ch0)) @@ -193,4 +172,44 @@ class Op_make_residimage(Op): return ceil(S*1.5) return ceil(S*sqrt(-2*log(thresh/A))) + def calc_resid_mean_rms(self, isl, resid, type): + """Inserts mean and rms of residual image into isl, src, and gaussians + + type - specifies 'gaus' or 'shap' + """ + if len(isl.gaul) == 0: + resid = N.zeros(isl.shape) + + ind = N.where(~isl.mask_active) + resid = resid[ind] + if type == 'gaus': + isl.gresid_rms = N.std(resid) + isl.gresid_mean = N.mean(resid) + else: + isl.sresid_rms = N.std(resid) + isl.sresid_mean = N.mean(resid) + if hasattr(isl, 'sources'): + for src in isl.sources: + if type == 'gaus': + src.gresid_rms = N.std(resid) + src.gresid_mean = N.mean(resid) + else: + src.sresid_rms = N.std(resid) + src.sresid_mean = N.mean(resid) + for g in src.gaussians: + if type == 'gaus': + g.gresid_rms = N.std(resid) + g.gresid_mean = N.mean(resid) + else: + g.sresid_rms = N.std(resid) + g.sresid_mean = N.mean(resid) + if hasattr(isl, 'dsources'): + for dsrc in isl.dsources: # Handle dummy sources (if any) + if type == 'gaus': + dsrc.gresid_rms = N.std(resid) + dsrc.gresid_mean = N.mean(resid) + else: + dsrc.sresid_rms = N.std(resid) + dsrc.sresid_mean = N.mean(resid) + diff --git a/CEP/PyBDSM/src/python/opts.py b/CEP/PyBDSM/src/python/opts.py index b7631e66154b4e09c300e89515d4a432fac92ed3..1c8091b724b3545ad3766cd2ff267c14b6b23a32 100644 --- a/CEP/PyBDSM/src/python/opts.py +++ b/CEP/PyBDSM/src/python/opts.py @@ -1087,11 +1087,10 @@ class Opts(object): group = 'hidden') incl_empty = Bool(False, doc = "Include islands without any valid Gaussians "\ - "(if any)?\n"\ + "(source list only)?\n"\ "If True, islands for which Gaussian fitting "\ "failed will be included in the output catalog. "\ - "In these cases, the source properties are "\ - "estimated using moment analysis, and the source IDs "\ + "In these cases, the source IDs "\ "are negative.", group = 'hidden') catalog_type = Enum('gaul', 'shap', 'srl', diff --git a/CEP/PyBDSM/src/python/output.py b/CEP/PyBDSM/src/python/output.py index 491c58c15608837290b03292eceb4ab9fe00952b..ffdc104793b74f58569d258879716e66a72565c6 100644 --- a/CEP/PyBDSM/src/python/output.py +++ b/CEP/PyBDSM/src/python/output.py @@ -266,7 +266,7 @@ def write_lsm_gaul(img, filename=None, srcroot=None, patch=None, def write_ds9_list(img, filename=None, srcroot=None, deconvolve=False, - clobber=False, objtype='gaul'): + clobber=False, incl_empty=False, objtype='gaul'): """Writes Gaussian list to a ds9 region file""" import numpy as N from const import fwsig @@ -279,10 +279,18 @@ def write_ds9_list(img, filename=None, srcroot=None, deconvolve=False, elif objtype == 'srl': root = img.parentname outl = [img.sources] + if incl_empty: + # Append the dummy sources for islands without any unflagged Gaussians + outl[0] += img.dsources outn = [] for src in img.sources: outn.append(root + '_i' + str(src.island_id) + '_s' + str(src.source_id)) + if incl_empty: + # Append the dummy sources for islands without any unflagged Gaussians + for dsrc in img.dsources: + outn.append(root + '_i' + str(dsrc.island_id) + '_s' + + str(dsrc.source_id)) outn = [outn] outstr_list = make_ds9_str(img, outl, outn, deconvolve=deconvolve) if filename == None: @@ -308,6 +316,9 @@ def write_ascii_list(img, filename=None, sort_by='indx', outl, outn, patl = list_and_sort_gaussians(img, patch=None, sort_by=sort_by) elif objtype == 'srl': outl = [img.sources] + if incl_empty: + # Append the dummy sources for islands without any unflagged Gaussians + outl[0] += img.dsources outstr_list = make_ascii_str(img, outl, objtype=objtype) if filename == None: if objtype == 'gaul': @@ -359,6 +370,9 @@ def write_fits_list(img, filename=None, sort_by='index', objtype='gaul', outl, outn, patl = list_and_sort_gaussians(img, patch=None, sort_by=sort_by) elif objtype == 'srl': outl = [img.sources] + if incl_empty: + # Append the dummy sources for islands without any unflagged Gaussians + outl[0] += img.dsources elif objtype == 'shap': outl = [img.islands] diff --git a/CEP/PyBDSM/src/python/plotresults.py b/CEP/PyBDSM/src/python/plotresults.py index cf9db04e38704516e346628013086c374d516958..f2956b98f759086a8624ae0bd1e4f6bdc3c55db7 100644 --- a/CEP/PyBDSM/src/python/plotresults.py +++ b/CEP/PyBDSM/src/python/plotresults.py @@ -300,7 +300,7 @@ def plotresults(img, ch0_image=True, rms_image=True, mean_image=True, valid = g.valid else: valid = True - if g.jlevel == 0 and valid: + if g.jlevel == 0 and valid and g.gaus_num >= 0: gidx = g.gaus_num e = Ellipse(xy=g.centre_pix, width=g.size_pix[0], height=g.size_pix[1], angle=g.size_pix[2]+90.0) @@ -324,7 +324,7 @@ def plotresults(img, ch0_image=True, rms_image=True, mean_image=True, if hasattr(img, 'gaussians'): for atrg in img.gaussians: - if atrg.jlevel > 0: + if atrg.jlevel > 0 and atrg.gaus_num >= 0: col = 'r' style = '-' gidx = atrg.gaus_num diff --git a/CEP/PyBDSM/src/python/pybdsm.py b/CEP/PyBDSM/src/python/pybdsm.py index 13504874593cd3bbacc6d6e0512d87450b163793..a2ca8f2f22c042d9e6ff4a6a9ef1f2dcb64b8e06 100644 --- a/CEP/PyBDSM/src/python/pybdsm.py +++ b/CEP/PyBDSM/src/python/pybdsm.py @@ -452,7 +452,7 @@ def write_catalog(**kwargs): print "\n\033[31;1mAborted\033[0m" write_catalog.arg_list = ['bbs_patches', 'format', 'outfile', 'srcroot', - 'incl_chan', 'clobber', 'catalog_type']#, 'incl_empty'] + 'incl_chan', 'clobber', 'catalog_type', 'incl_empty'] write_catalog.use_groups = False diff --git a/CEP/PyBDSM/src/python/readimage.py b/CEP/PyBDSM/src/python/readimage.py index 5155d2e2235c32e58928975d7d28541fd030687e..50f17569e00bc7d907a3daaf052d9cd10c60a41d 100644 --- a/CEP/PyBDSM/src/python/readimage.py +++ b/CEP/PyBDSM/src/python/readimage.py @@ -112,7 +112,6 @@ class Op_readimage(Op): img.filename = img.opts.filename img.parentname = fname img.imagename = fname + '.pybdsm' - img.waveletimage = False if img.opts.output_all: # Set up directory to write output to basedir = './' + fname + '_pybdsm' diff --git a/CEP/PyBDSM/src/python/wavelet_atrous.py b/CEP/PyBDSM/src/python/wavelet_atrous.py index 7f260b3915fb2107865d1fbeae761d444b5be396..ccf22d5d181c696b75ef16d20b559109ebfa0dfd 100644 --- a/CEP/PyBDSM/src/python/wavelet_atrous.py +++ b/CEP/PyBDSM/src/python/wavelet_atrous.py @@ -269,7 +269,7 @@ class Op_wavelet_atrous(Op): #self.morphfilter_pyramid(img, pdir) img.ngaus += ntot_wvgaus img.total_flux_gaus += total_flux - mylogger.userinfo(mylog, "Total flux density in model over all scales" , '%.3f Jy' % img.total_flux_gaus) + mylogger.userinfo(mylog, "Total flux density in model on all scales" , '%.3f Jy' % img.total_flux_gaus) if img.opts.output_all: func.write_image_to_file(img.use_io, img.imagename + '.atrous.cJ.fits', im_new, img, bdir)