def make_regions(file=None, filetype=None, outfile='ds9.reg'): ''' This function will read in the input file of type "filetype" and write out to a DS9 region file. Parameters ---------- - file: filename [string] - filetype: type of file, to determine format. supported: 'sextractor', 'scene' [string] - outfile: output filename. default: 'ds9.reg'. [string] ''' # code to read in the input file if (filetype == 'sextractor'): reg_list = read_sextractor(infile=file) # the list of regions can be written to a DG9 region file: write_ds9(reg_list, outfile, coordsys='physical') elif (filetype == 'scene'): reg_list = read_scene(infile=file) # the list of regions can be written to a DG9 region file: write_ds9(reg_list, outfile) else: raise IOError('Input filetype not recognised!') # adjust coordinates to get pixel (x,y) coordinates # write out into a region file return 0
def make_tiles(ra, dec, tile_spacing=0.625, tile_facet_size=0.7): ''' Create the tiling for a 0.3'' mosaic of the central 2.5 degree. Args: ra (float): right ascension of the pointing center. dec (float): declination of the pointing center. Returns: facets (ndarray): a 4 x 4 x 2 array with the central RA and DEC of the tiles. ''' spacing = tile_spacing * u.degree # Have some overlap facet_size = tile_facet_size * u.degree facets = np.zeros((4,4,2)) * u.degree#, dtype=(float, 2)) * u.degree facetlist = [] k = 1 for i in range(4): for j in range(4): RA = phasecenter.ra + (spacing * (j-1.5) / np.cos((phasecenter.dec + spacing*(i-1.5)).rad)) DEC = phasecenter.dec + (spacing * (i-1.5)) facets[i, j, 0] = RA facets[i, j, 1] = DEC facetlist.append((RA.deg,DEC.deg)) PARSET = 'msout.storagemanager=dysco\nmsout.storagemanager.databitrate=4\nmsout.storagemanager.weightbitrate=8\nsteps=[shift,avg]\nshift.type = phaseshift\nshift.phasecenter = [{:f}deg, {:f}deg]\navg.type = average\navg.timeresolution = 4\navg.freqresolution = 48.82kHz'.format(RA.deg, DEC.deg) with open('shift_to_facet_{:d}.parset'.format(k), 'w') as f: f.write(PARSET) k += 1 region_strs = map(lambda pos: 'fk5\nbox({:f},{:f},{:f},{:f},0) # color=green width=4 text=""'.format(*pos, facet_size.value, facet_size.value), facetlist) parser = DS9Parser('\n'.join(list(region_strs))) regions = parser.shapes.to_regions() write_ds9(regions, 'facets.reg') return facets
def dagga(field): "function to tag sources for dd calibration, very smoky" key = 'calibrate_dd' #make a skymodel with only dE taggable sources. #de_only_model = 'de-only-model.txt' de_sources_mode = config[key]['de_sources_mode'] print("de_sources_mode:", de_sources_mode) # if usepb: # model_cube = prefix+"-DD-precal.cube.int.model.fits" # else: # model_cube = prefix+"-DD-precal.cube.app.model.fits" outdir = field+"_ddcal" if de_sources_mode == 'auto': print("Carrying out automatic source taggig for direction dependent calibration") caracal.log.info('Carrying out automatic dE tagging') catdagger_opts = { "ds9-reg-file": "de-{0:s}.reg:output".format(field), "ds9-tag-reg-file" : "de-clusterleads-{0:s}.reg:output".format(field), "noise-map" : prefix+"_"+field+"-DD-precal.app.residual.fits", "sigma" : config[key]['sigma'], "min-distance-from-tracking-centre" : config[key]['min_dist_from_phcentre'], } recipe.add('cab/catdagger', 'tag_sources-auto_mode', catdagger_opts,input=INPUT, output=OUTPUT+"/"+outdir,label='tag_sources-auto_mode::Tag dE sources with CatDagger',shared_memory=shared_mem) if de_sources_mode == 'manual': img = prefix+"_"+field+"-DD-precal.app.restored.fits" imagefile = os.path.join(pipeline.output,DD_DIR,outdir,img) #print("Imagefile",imagefile) #print("Pipeline output", pipeline.output) w = WCS(imagefile) #coords = config[key]['de_sources_manual'] print(de_dict) sources_to_tag = de_dict[field.replace("_","-")] reg = [] for j in range(len(sources_to_tag.split(";"))): coords = sources_to_tag.split(";")[j] size = coords.split(",")[2] coords_str = coords.split(",")[0]+" "+coords.split(",")[1] #print("Coordinate String", coords_str) centre = SkyCoord(coords_str, unit='deg') separation = int(size) * u.arcsec #print("Size",separation) xlist = [] ylist = [] for i in range(5): ang_sep = (306/5)*i*u.deg p = centre.directional_offset_by(ang_sep,separation) pix = PixCoord.from_sky(p,w) xlist.append(pix.x) ylist.append(pix.y) vertices = PixCoord(x=xlist, y=ylist) region_dd = PolygonPixelRegion(vertices=vertices) reg.append(region_dd) regfile = "de-{0:s}.reg".format(field) ds9_file = os.path.join(OUTPUT,outdir,regfile) write_ds9(reg,ds9_file,coordsys='physical')
def write_region(cls, coords, filename, **kwargs): try: iter(coords) except TypeError as te: raise Exception('Coords must be iterable') circles = [] for coord in coords: center = utils.get_skycoord(coord) rad = utils.get_angle(coord['rad']) circles.append(CircleSkyRegion(center=center, radius=rad, visual=kwargs)) write_ds9(circles, filename)
def FindBoxSource(catalog, GorC, srcReg, freeReg, outfile): catalog = LoadModel(catalog) model = NewModel() for srcName in catalog.SrcList: skycrd_C = catalog.GetSrcDir(srcName) if GorC == 'C': xref, yref = skycrd_C if GorC == 'G': skycrd_G = maptools.skycrdC2G(skycrd_C)[0] xref, yref = skycrd_G xmin, xmax, ymin, ymax = srcReg if xref > xmin and xref < xmax and yref > ymin and yref < ymax: print(srcName, xref, yref) srcEle = catalog.GetSrcEle(srcName) if srcEle.attrib['type'] == 'PointSource': model.AddPointSource(srcName) if srcEle.attrib['type'] == 'DiffuseSource': spatialFile = srcEle.find('spatialModel').attrib['file'] model.AddDiffuseSource(srcName, SpatialFile=spatialFile) model.AddSrcEle(srcName, srcEle) model.SaveModel(outfile) regionList = [] model = LoadModel(outfile) for srcName in model.SrcList: skycrd_C = catalog.GetSrcDir(srcName) center = SkyCoord(*skycrd_C, unit='deg') region = PointSkyRegion(center) regionList.append(region) if GorC == 'C': xref, yref = skycrd_C if GorC == 'G': skycrd_G = maptools.skycrdC2G(skycrd_C)[0] xref, yref = skycrd_G xmin, xmax, ymin, ymax = freeReg if xref < xmin or xref > xmax or yref < ymin or yref > ymax: print(srcName, xref, yref) for parName in model.FreeParDict[srcName]: print(parName) model.SetParFree(srcName, parName, 0) model.SaveModel(outfile) regfile = outfile.split('.')[0] + '.reg' write_ds9(regionList, regfile)
def FindCircleSource(catalog, skycrd0_C, srcRad, freeRad, outfile): catalog = LoadModel(catalog) model = NewModel() for srcName in catalog.SrcList: skycrd_C = catalog.GetSrcDir(srcName) rad = maptools.Sep(skycrd_C, skycrd0_C) if rad < srcRad: print(srcName, rad) srcEle = catalog.GetSrcEle(srcName) if srcEle.attrib['type'] == 'PointSource': model.AddPointSource(srcName) if srcEle.attrib['type'] == 'DiffuseSource': spatialFile = srcEle.find('spatialModel').attrib['file'] model.AddDiffuseSource(srcName, SpatialFile=spatialFile) model.AddSrcEle(srcName, srcEle) model.SaveModel(outfile) regionList = [] model = LoadModel(outfile) for srcName in model.SrcList: skycrd_C = catalog.GetSrcDir(srcName) center = SkyCoord(*skycrd_C, unit='deg') region = PointSkyRegion(center) regionList.append(region) rad = maptools.Sep(skycrd_C, skycrd0_C) if rad > freeRad: print(srcName, rad) for parName in model.FreeParDict[srcName]: print(parName) model.SetParFree(srcName, parName, 0) model.SaveModel(outfile) regfile = outfile.split('.')[0] + '.reg' write_ds9(regionList, regfile)
# Python script of generating DS9 region file # from IRAF output mag.1 file # written by Duho Kim (1/18/18) ###################################################### import numpy as np from astropy.io import ascii from astropy.table import Table from regions import DS9Parser, write_ds9 work_dir = '/Users/dhk/work/data/NGC_IC/pilot_script/' mag1 = ascii.read(work_dir+'ic1065.mag.1') reg_string = 'galactic\ncircle(42,43,3) # color=green' parser = DS9Parser(reg_string) parser.run() reg = Table(names=('shape','x','y','rad'),dtype=('S6','f8','f8','f8')) for i in range(len(mag1)): write_ds9('image\ncircle('+mag1['XCENTER'][i]+','+mag1['YCENTER'][i]+')') reg.add_row( ('circle',mag1['XCENTER'][i],mag1['YCENTER'][i],np.sqrt(mag1['AREA'][i]/np.pi)) ) reg.write(work_dir+'ic1065.reg',format='ascii.commented_header',comment='# Region file format: DS9 version 4.1 global color=green dashlist=8 3 width=1 font="helvetica 10 normal roman" select=1 highlite=1 dash=0 fixed=0 edit=1 move=1 delete=1 include=1 source=1')
def main(argv=None): """ Main Function """ # Call initial parser from init_utils parser = ap.ArgumentParser(description="""Create Region Files.""", add_help=True) parser.add_argument( "-s", "--shotid", help="""Shot identifier, an integer""", type=int, default=None, ) parser.add_argument( "-d", "--date", help="""Date, e.g., 20170321, YYYYMMDD""", type=str, default=None, ) parser.add_argument( "-o", "--observation", help='''Observation number, "00000007" or "7"''', type=str, default=None, ) parser.add_argument( "-f", "--field", help="""Options=""", type=str, default=None, ) args = parser.parse_args(argv) args.log = setup_logging() if args.field is not None: S = Survey() survey_table = S.return_astropy_table() sel_field = survey_table["field"] == args.field ifuregions = [] for row in survey_table[sel_field]: args.log.info("Working on " + str(row["shotid"])) ifuregions.extend(get_regions_from_flim(row["shotid"])) outname = args.field elif args.shotid: ifuregions = get_regions_from_flim(args.shotid) outname = str(args.shotid) elif args.date is not None: if args.observation is not None: shotid = int(str(args.date) + str(args.observation).zfill(3)) ifuregions = get_regions_from_flim(shotid) outname = str(shotid) region_file = outname + '.reg' write_ds9(ifuregions, region_file)
overwrite=True) reglist = [ regions.CircleSkyRegion( coordinates.SkyCoord(row['RA'], row['Dec'], frame='fk5', unit=(u.hour, u.deg)), radius=(u.Quantity(float(row['robs']) * 1000, u.au) / (8.5 * u.kpc)).to(u.arcsec, u.dimensionless_angles()), meta={'text': row['ID']}, visual={'name': row['ID']}, ) for row in tbl if row['ID'] ] regions.write_ds9(reglist, paths.rpath('Schmiedeke2016_HIIregions_tableB1.reg')) rslt = requests.get( 'http://www.aanda.org/articles/aa/full_html/2016/04/aa27311-15/T2.html') soup = BeautifulSoup(rslt.text, 'html5lib') htmltable = soup.findAll('table')[-1] allrows = (htmltable.findAll('tr')) colnames_part1 = [ x.text.strip("a0123456789\n \t") for x in allrows[0].findAll('td') ] units = [x.text.strip() for x in allrows[1].findAll('td')] colnames_part2 = [ x.text.strip("0123456789()\n \t") for x in allrows[2].findAll('td') ]
pixX, pixY = (pngX / (2487 / 2100)) / .5, ((1306 - pngY) / (1306 / 1100)) / .5 else: print('what the hell happened!?!') break xy = np.column_stack((pixX, pixY)) print(header) w = WCS(imgHeader) coords = w.wcs_pix2world(xy, 1) raDec = SkyCoord(coords[0][0] * u.deg, coords[0][1] * u.deg) region = CircleSkyRegion(raDec, regRadius * u.deg) region.visual['color'] = 'red' region.visual['width'] = '2' header = Path(header).stem + '_' + str(imgName) print(header) regName = regFile.joinpath(header).with_suffix('.reg') print(regName) write_ds9([region], regName) except: pass regfiles = sorted(regFile.glob('*reg')) for rf, x in zip(regfiles, range(len(regfiles) - 1)): if regfiles[x].stem[:regfiles[x].stem.find('_', 8)] != regfiles[ x + 1].stem[:regfiles[x].stem.find('_', 8)]: print('break') fp.close(regfiles[x].stem[:regfiles[x].stem.find('_', 8)]) else: print('match') fp.open()
region = CircleSkyRegion(center, radius, meta) return region # define path to the main directory if getpass.getuser() == "luisabuzzo": home = "/home/luisabuzzo/Work/Master/SPLUS/" elif getpass.getuser() == "mlgbuzzo": home = "/home/mlgbuzzo/LePhare/" elif getpass.getuser() == "roderik": home = "/Users/roderik/Dropbox/splus/IDR2/" catfile = os.path.join(home,'Catalogs/STRIPE82_all.fits') data = fits.open(catfile) cat = data[1].data #sel = np.logical_and((cat['FIELD'] == 'STRIPE82-0160'),(cat['r_auto']/cat['er_auto'] < 5)) sel = np.logical_and((cat['FIELD'] == 'STRIPE82-0160'),(cat['r_auto'] < 21)) #sel = (cat['FIELD'] == 'STRIPE82-0160') cat = cat[sel] radius_arcsec = 2.0 regions = [] for i in range(0,len(cat)): regions.append(make_region(cat['RA'][i],cat['Dec'][i],radius_arcsec/3600.,np.int_(cat['PhotoFlag'][i]))) #filename = 'tile0160_sn_lt5.reg' filename = 'tile0160_r_lt21.reg' write_ds9(regions, filename)
def make_cosmological_sources(exp_time, fov, sky_center, cat_center=None, absorb_model="wabs", nH=0.05, area=40000.0, output_sources=None, write_regions=None, prng=None): r""" Make an X-ray source made up of contributions from galaxy clusters, galaxy groups, and galaxies. Parameters ---------- exp_time : float, (value, unit) tuple, or :class:`~astropy.units.Quantity` The exposure time of the observation in seconds. fov : float, (value, unit) tuple, or :class:`~astropy.units.Quantity` The field of view in arcminutes. sky_center : array-like The center RA, Dec of the field of view in degrees. cat_center : array-like The center of the field in the coordinates of the halo catalog, which range from -5.0 to 5.0 in degrees in both directions. If None is given, a center will be randomly chosen. absorb_model : string, optional The absorption model to use, "wabs" or "tbabs". Default: "wabs" nH : float, (value, unit) tuple, or :class:`~astropy.units.Quantity`, optional The hydrogen column in units of 10**22 atoms/cm**2. Default: 0.05 area : float, (value, unit) tuple, or :class:`~astropy.units.Quantity`, optional The effective area in cm**2. It must be large enough so that a sufficiently large sample is drawn for the ARF. Default: 40000. output_sources : string, optional If set to a filename, output the properties of the sources within the field of view to a file. Default: None write_regions : string, optional If set to a filename, output circle ds9 regions corresponding to the positions of the halos with radii corresponding to their R500 projected on the sky. Default: None prng : :class:`~numpy.random.RandomState` object, integer, or None A pseudo-random number generator. Typically will only be specified if you have a reason to generate the same set of random numbers, such as for a test. Default is None, which sets the seed based on the system time. """ exp_time = parse_value(exp_time, "s") fov = parse_value(fov, "arcmin") if nH is not None: nH = parse_value(nH, "1.0e22*cm**-2") area = parse_value(area, "cm**2") prng = parse_prng(prng) cosmo = FlatLambdaCDM(H0=100.0*h0, Om0=omega_m) agen = ApecGenerator(0.1, 10.0, 10000, broadening=False) mylog.info("Creating photons from cosmological sources.") mylog.info("Loading halo data from catalog: %s" % halos_cat_file) halo_data = h5py.File(halos_cat_file, "r") scale = cosmo.kpc_comoving_per_arcmin(halo_data["redshift"][()]).to("Mpc/arcmin") # 600. arcmin = 10 degrees (total FOV of catalog = 100 deg^2) fov_cat = 10.0*60.0 w = construct_wcs(*sky_center) cat_min = -0.5*fov_cat cat_max = 0.5*fov_cat if cat_center is None: xc, yc = prng.uniform(low=cat_min+0.5*fov, high=cat_max-0.5*fov, size=2) else: xc, yc = cat_center xc *= 60.0 yc *= 60.0 xc, yc = np.clip([xc, yc], cat_min+0.5*fov, cat_max-0.5*fov) mylog.info("Coordinates of the FOV within the catalog are (%g, %g) deg." % (xc/60.0, yc/60.0)) xlo = (xc-1.1*0.5*fov) xhi = (xc+1.1*0.5*fov) ylo = (yc-1.1*0.5*fov) yhi = (yc+1.1*0.5*fov) mylog.info("Selecting halos in the FOV.") halo_x = halo_data["x"][()].astype("float64")/(h0*scale.value) halo_y = halo_data["y"][()].astype("float64")/(h0*scale.value) fov_idxs = (halo_x >= xlo) & (halo_x <= xhi) fov_idxs = (halo_y >= ylo) & (halo_y <= yhi) & fov_idxs n_halos = fov_idxs.sum() mylog.info("Number of halos in the field of view: %d" % n_halos) # Now select the specific halos which are in the FOV z = halo_data["redshift"][fov_idxs].astype("float64") m = halo_data["M500c"][fov_idxs].astype("float64")/h0 # We need to compute proper scales here s = scale[fov_idxs].to("Mpc/arcsec").value/(1.0+z) ra0, dec0 = w.wcs_pix2world((halo_x[fov_idxs]-xc)*60.0, (halo_y[fov_idxs]-yc)*60.0, 1) # Close the halo catalog file halo_data.close() # Some cosmological stuff rho_crit = cosmo.critical_density(z).to("Msun/Mpc**3").value # halo temperature and k-corrected flux kT = Tx(m, z) flux_kcorr = 1.0e-14*lum(m, z)/flux2lum(kT, z) # halo scale radius r500 = (3.0*m/(4.0*np.pi*500*rho_crit))**(1.0/3.0) r500_kpc = r500 * 1000.0 rc_kpc = r500/conc * 1000.0 rc = r500/conc/s # Halo slope parameter beta = prng.normal(loc=0.666, scale=0.05, size=n_halos) beta[beta < 0.5] = 0.5 # Halo ellipticity ellip = prng.normal(loc=0.85, scale=0.15, size=n_halos) ellip[ellip < 0.0] = 1.0e-3 # Halo orientation theta = 360.0*prng.uniform(size=n_halos) # If requested, output the source properties to a file if output_sources is not None: t = Table([ra0, dec0, rc_kpc, beta, ellip, theta, m, r500_kpc, kT, z, flux_kcorr], names=('RA', 'Dec', 'r_c', 'beta', 'ellipticity', 'theta', 'M500c', 'r500', 'kT', 'redshift', 'flux_0.5_2.0_keV')) t["RA"].unit = "deg" t["Dec"].unit = "deg" t["flux_0.5_2.0_keV"].unit = "erg/(cm**2*s)" t["r_c"].unit = "kpc" t["theta"].unit = "deg" t["M500c"].unit = "solMass" t["r500"].unit = "kpc" t["kT"].unit = "kT" t.write(output_sources, format='ascii.ecsv', overwrite=True) if write_regions is not None: from regions import CircleSkyRegion, write_ds9 from astropy.coordinates import Angle, SkyCoord regs = [] for halo in range(n_halos): c = SkyCoord(ra0[halo], dec0[halo], unit=("deg", "deg"), frame='fk5') scale = cosmo.kpc_proper_per_arcmin(z[halo]).to("kpc/deg") r500c = r500_kpc / scale.value r = Angle(r500c, 'deg') reg = CircleSkyRegion(c, r) regs.append(reg) write_ds9(regs, write_regions) tot_flux = 0.0 ee = [] ra = [] dec = [] pbar = tqdm(leave=True, total=n_halos, desc="Generating photons from halos ") for halo in range(n_halos): spec = agen.get_spectrum(kT[halo], abund, z[halo], 1.0) spec.rescale_flux(flux_kcorr[halo], emin=emin, emax=emax, flux_type="energy") if nH is not None: spec.apply_foreground_absorption(nH, model=absorb_model) e = spec.generate_energies(exp_time, area, prng=prng, quiet=True) beta_model = BetaModel(ra0[halo], dec0[halo], rc[halo], beta[halo], ellipticity=ellip[halo], theta=theta[halo]) xsky, ysky = beta_model.generate_coords(e.size, prng=prng) tot_flux += e.flux ee.append(e.value) ra.append(xsky.value) dec.append(ysky.value) pbar.update() pbar.close() ra = np.concatenate(ra) dec = np.concatenate(dec) ee = np.concatenate(ee) mylog.info("Created %d photons from cosmological sources." % ee.size) output_events = {"ra": ra, "dec": dec, "energy": ee, "flux": tot_flux.value} return output_events
def to_reg(self, filename): regions.write_ds9(self.region_list, filename, coordsys="fk5")
def make_master_catalog(dat,outfolder,remake_catalog=False,norates=True,maximum_ap=np.inf): """makes master catalog for selecting objects CATALOG 1 (FOR ME): Objname, RA, DEC, PA, box dimensions, expected Br gamma flux + EW, recessional velocity, RGB, nearby OH lines + strengths, sSFR, metallicity, Herschel photometry flag CATALOG 2 (CSV): Objname, RA, DEC, equinox (fk5), non-sidereal tracking rate -- this is 2' per 10 minutes in direction perpendicular to PA, in [d(RA), d(DEC)] CATALOG 3 (CSV): (nearby bright stars)? order by brightness, for galaxies with no strong OH lines """ # input catalog DAT has mass, SFR, sSFR, (Br gamma / Pa alpha / H-alpha) (EW/flux/luminosity) # additional inputs # dictionary of RA, DEC, recessional velocity pdat = load_positional_data() # list of objects with Herschel information hnames = load_herschel_data() # PA, box dimensions box_data = load_slit_box() # remove unobservable galaxies lowest_allowed_airmass = 1.6 min_airmass = is_observable(pdat) obs_idx = np.isfinite(min_airmass) & (min_airmass < lowest_allowed_airmass) names, min_airmass = pdat['Name'][obs_idx], min_airmass[obs_idx] # important observing quantities # need exposure time to calculate tracking rate slitlength = (30*u.arcsec).to(u.degree) exposure_time = 5*u.minute # sort by (line flux / photometric area) (surface brightness?) # also remove unobservable galaxies here! brg_flux = [np.median(dat['Br gamma 21657']['flux'][dat['names'].index(name),:]) for name in names] area = [] for name in names: p1, p2 = box_data['phot_size'][box_data['Name']==name.replace(' ','_')][0].split('_') longax = np.clip(np.max([int(p1),int(p2)]),-np.inf,maximum_ap) area += [30*longax] sb = brg_flux/np.array(area) nidx = sb.argsort()[::-1] names, min_airmass = names[nidx], min_airmass[nidx] # Part 1: Rogue's gallery. # figure info if remake_catalog: figsize = (20,20) fs = 10 dx_txt, dy_txt = 0.1, 0.008 xs_start, ys_start = 0.01,0.98 xbox_size, ybox_size = 0.24, 0.11 dx_box = 0.005 # already observed obsed = ['NGC 3690','NGC 3310', 'NGC 4194', 'NGC 4536', 'Mrk 33', 'NGC 6090', 'Mrk 1490', 'UGCA 166', 'NGC_2388','NGC_2798','Mrk_1450','NGC_5194','NGC_5055','NGC_5256','UGC_08696','NGC_4088','IC_4553', 'NGC_6052'] # initialize and start xs, ys = xs_start, ys_start catnum = 1 fig = plt.figure(figsize = figsize) for i, name in enumerate(names): if name in obsed: continue # RA, dec, cz, hflag pidx = pdat['Name'] == name ra = str(pdat['RAh'][pidx][0])+'h '+str(pdat['RAm'][pidx][0])+'m '+str(pdat['RAs'][pidx][0])+'s' dec = str(pdat['DE-'][pidx][0])+str(pdat['DEd'][pidx][0])+'d '+str(pdat['DEm'][pidx][0])+'m '+str(pdat['DEs'][pidx][0])+'s' cz_str = str(pdat['cz'][pidx][0])+ ' km/s' hflag = 'has Herschel photometry' if name not in hnames: hflag = '' # PA, box dimensions bidx = box_data['Name'] == name.replace(' ','_') phot_pa = box_data['phot_pa'][bidx][0] aperture = box_data['phot_size'][bidx][0].replace('_',"'x")+"''" # physical properties didx = np.array(dat['names']) == name brg_flux = np.median(dat['Br gamma 21657']['flux'][didx]) brg_ew = np.median(dat['Br gamma 21657']['ew'][didx]) mass = np.median(dat['stellar_mass'][didx]) ssfr = np.log10(np.median(dat['ssfr'][didx])) # OH lines cz = pdat['cz'][pidx][0] lam_cent = 21657*(1+(cz/(3e5))) lamlist, strlist = oh_lines(lam_cent,cz) lamlist = ", ".join([str(int(lam-lam_cent)) for lam in lamlist]) strlist = ", ".join([str(int(stren)) for stren in strlist]) # put it all together xt = xs + dx_txt + 0.005 fig.text(xt,ys+0.001,name,fontsize=fs+2,weight='bold') strs = ['RA='+ra, 'DEC='+dec, r'log(f$_{\mathrm{Br}\gamma}$)='+'{:.1e}'.format(brg_flux)+r' erg/s/cm$^{2}$', r' EW$_{\mathrm{Br}\gamma}$='+'{:.1f}'.format(brg_ew)+r' $\AA$', r'log(M/M$_{\odot}$)='+'{:.1f}'.format(mass), r' log(sSFR/yr$^{-1}$)='+'{:.2f}'.format(ssfr), r'$\lambda_{\mathrm{Br}\gamma}$='+str(int(lam_cent))+r' $\AA$', r'OH $\Delta \lambda$: '+lamlist+r'$\AA$', 'OH strength: '+strlist, 'aperture: '+phot_pa+r'$^{\circ}$ PA'+', '+aperture, 'min(airmass): '+'{:.2f}'.format(min_airmass[i]), hflag ] for i, s in enumerate(strs): fig.text(xt,ys-dy_txt*(i+1),s,fontsize=fs) # RGB rgb = load_rgb_png(name).swapaxes(0,1) ax = fig.add_axes([xs,ys-dx_txt,dx_txt,dx_txt]) ax.imshow(rgb) ax.set_facecolor('white') ax.set_axis_off() # increment xs += xbox_size+dx_box # check for right edge of page if (xs + xbox_size) > 1: ys = ys - ybox_size-dx_box xs = xs_start # check for off-page if (ys-ybox_size) < 0: plt.savefig(outfolder+'catalog'+str(catnum)+'.png',dpi=150) plt.close() fig = plt.figure(figsize = figsize) catnum += 1 xs, ys = xs_start, ys_start # Part 2: target list # Objname, RA, DEC, equinox (fk5), non-sidereal tracking rate # RA: Specified in sexagesimal hours, minutes and seconds. Internal fields are separated by spaces. # DEC: Specified in sexagesimal degrees, minutes and seconds. # equinox: J2000 # RA_track: arcseconds / second # DEC_track: arcseconds / second objname_list, ra_list, dec_list, ra_track_list, dec_track_list, slit_pa_list = [[] for i in range(6)] for i, name in enumerate(names): # create coord.SkyCoord object # this represents the center of the box pidx = pdat['Name'] == name ra = str(pdat['RAh'][pidx][0])+'h '+str(pdat['RAm'][pidx][0])+'m '+str(pdat['RAs'][pidx][0])+'s' dec = str(pdat['DE-'][pidx][0])+str(pdat['DEd'][pidx][0])+'d '+str(pdat['DEm'][pidx][0])+'m '+str(pdat['DEs'][pidx][0])+'s' galcoords = coord.SkyCoord(ra, dec, frame='fk5') # grab PA bidx = box_data['Name'] == name.replace(' ','_') phot_pa = float(box_data['phot_pa'][bidx][0]) # grab aperture, translate to sky box sizes # the given PA describes the position of the FIRST axis # if this is not the LONGEST axis, redefine by adding 90 to PA # this means we'll need to output a list of PAs (put it in the tracking output) aperture = box_data['phot_size'][bidx][0] ap1, ap2 = aperture.split('_') aps = np.array([float(ap1),float(ap2)])/3600.*u.deg # from arcsec to degrees if aps[0] < aps[1]: phot_pa -= 90 if (phot_pa < 0): phot_pa += 360 print name shortax, longax = aps.min(), aps.max() longax = np.clip(longax,-np.inf,maximum_ap*u.arcsec) shortax = 30*u.arcsecond phot_pa_rad = np.pi/180. * phot_pa * u.radian # generate starting position # check that it has proper distance and PA bot_mid = calc_new_position(galcoords, phot_pa_rad, longax.to(u.radian)/2.) np.testing.assert_almost_equal(galcoords.separation(bot_mid).to(u.arcsec).value,longax.to(u.arcsec).value/2,decimal=0) np.testing.assert_almost_equal(galcoords.position_angle(bot_mid).to(u.degree).value,phot_pa,decimal=1) # non sidereal tracking rate, must be output in RA and DEC (arcseconds/hour) # we travel LONGAX in EXPOSURE_TIME, in the -PA_CAT_PARALLEL direction pa_cat_parallel = np.array([np.sin(phot_pa_rad),np.cos(phot_pa_rad)]) dist = (-1)*pa_cat_parallel*longax rate = dist/exposure_time rate = [x.to(u.arcsecond/u.hour) for x in rate] # create .region file with proper scan positions # for testing purposes pclose = [calc_new_position(bot_mid, phot_pa_rad+np.pi/2.*u.radian,slitlength.to(u.radian)/2.), calc_new_position(bot_mid, phot_pa_rad-np.pi/2.*u.radian,slitlength.to(u.radian)/2.)] pfar = [coord.SkyCoord(pclose[1].ra+dist[0]/np.cos(pclose[0].dec.to(u.rad)),pclose[1].dec+dist[1]), coord.SkyCoord(pclose[0].ra+dist[0]/np.cos(pclose[0].dec.to(u.rad)),pclose[0].dec+dist[1])] points = [pfar+pclose] sregions = [poly_region(point) for point in points] write_ds9(sregions, region_files+name.replace(' ','_')+'.reg') # slit pa # we need this slit_pa = phot_pa - 90 if (slit_pa < 0): slit_pa += 360 # add to lists for output objname_list += [name.replace(' ','_')] ra,dec = bot_mid.to_string('hmsdms').split(' ') ra_list += [ra.split('h')[0] + ' ' + ra.split('m')[0].split('h')[-1] + ' ' + ra.split('m')[-1][:-1]] dec_list += [dec.split('d')[0] + ' ' + dec.split('m')[0].split('d')[-1] + ' ' + dec.split('m')[-1][:-1]] ra_track_list += [rate[0].value] dec_track_list += [rate[1].value] slit_pa_list += [slit_pa] # sky sky_objname, sky_ra, sky_dec = sky_lists() # write to CSV if norates: outloc = outfolder+'target_list_norates.csv' with open(outloc, 'w') as f: for i in range(len(objname_list)): f.write(objname_list[i]+','+ra_list[i]+','+dec_list[i]+',J2000')#,{:.2f},{:.2f}'.format( #ra_track_list[i],dec_track_list[i])) f.write('\n') # write marla objects mnames = ['2M00444105+8351358','2M14390944+4953029'] mcoords = [coord.SkyCoord(11.171077*u.degree, 83.859955*u.degree, frame='fk5'), coord.SkyCoord(219.789356*u.degree, 49.884155*u.degree, frame='fk5')] for i in range(2): ra, dec = mcoords[i].to_string('hmsdms').split(' ') ra_str = ra.split('h')[0] + ' ' + ra.split('m')[0].split('h')[-1] + ' ' + ra.split('m')[-1][:-1] dec_str = dec.split('d')[0] + ' ' + dec.split('m')[0].split('d')[-1] + ' ' + dec.split('m')[-1][:-1] f.write(mnames[i]+','+ra_str+','+dec_str+',J2000')#,0.0,0.0') f.write('\n') for i in range(len(sky_objname)): f.write(sky_objname[i].replace(' ','_')+'_sky,'+sky_ra[i]+','+sky_dec[i]+',J2000') f.write('\n') else: outloc = outfolder+'target_list.csv' with open(outloc, 'w') as f: for i in range(len(objname_list)): f.write(objname_list[i]+','+ra_list[i]+','+dec_list[i]+',J2000,{:.2f},{:.2f},{:.1f}'.format( ra_track_list[i],dec_track_list[i],slit_pa_list[i])) f.write('\n') # write marla objects mnames = ['2M00444105+8351358','2M14390944+4953029'] mcoords = [coord.SkyCoord(11.171077*u.degree, 83.859955*u.degree, frame='fk5'), coord.SkyCoord(219.789356*u.degree, 49.884155*u.degree, frame='fk5')] for i in range(2): ra, dec = mcoords[i].to_string('hmsdms').split(' ') ra_str = ra.split('h')[0] + ' ' + ra.split('m')[0].split('h')[-1] + ' ' + ra.split('m')[-1][:-1] dec_str = dec.split('d')[0] + ' ' + dec.split('m')[0].split('d')[-1] + ' ' + dec.split('m')[-1][:-1] f.write(mnames[i]+','+ra_str+','+dec_str+',J2000,0.0,0.0,0.0') f.write('\n') for i in range(len(sky_objname)): f.write(sky_objname[i].replace(' ','_')+'_sky,'+sky_ra[i]+','+sky_dec[i]+',J2000,0,0,0') f.write('\n')
filename = Path(input("Enter path to file: ")) except (KeyError, TypeError, FileNotFoundError): filename = Path(input("perhaps a typo, try again")) names = input('image name? ') images = sorted(filename.glob(names)) for names in images: image = fits.open(names) data = image[0].data wcs = WCS(image[0].header) # try: # threshold = image[0].header['SATURATE'] # except (KeyError, TypeError): # threshold = 40000 threshold = 55000 tbl = find_peaks(data, threshold, box_size=10, wcs=wcs) regions = [] center = tbl['skycoord_peak'] for i in range(len(tbl)): region = CircleSkyRegion(center[i], radius) region.visual['color'] = 'cyan' region.visual['width'] = '3' regions.append(region) write_ds9(regions, names.parent.joinpath('saturated' + names.stem + '.reg')) print(names) image.close() test = input( "If there is another image, enter 0. If done, enter any key. ")
def dendrocatify(regname, fn, threshold=4, min_npix=100, min_delta=1, cutout=None, cutout_header=None, snr_threshold=5, noiselevel_table='noise_levels.json'): noisefilepath = f"{catalog_path}/{noiselevel_table}" if os.path.exists(noisefilepath): with open(noisefilepath, 'r') as fh: noiselevel_table = json.load(fh) else: noiselevel_table = {} print(f"Starting region {regname}: {fn}") if cutout_header is None or cutout is None: fh = fits.open(fn) data = fh[0].data header = fh[0].header # LONPOLE isn't very relevant and LATPOLE is not part of the coordinate # systems we're interested in. From Calabretta 2002: "LATPOLEa is never # required for zenithal projections" try: del header['LONPOLE'] del header['LATPOLE'] except KeyError: pass ww = wcs.WCS(header) pixscale = wcs.utils.proj_plane_pixel_area(ww)**0.5 * u.deg reg = cutout_regions[regname].to_pixel(ww) mask = reg.to_mask() data_sm = convolve_fft(data, Gaussian2DKernel( (45 * u.arcsec / pixscale).decompose()), allow_huge=True) data_filtered = data - data_sm err = mad_std(data_filtered) cutout = mask.multiply(data_filtered) frame = wcs.utils.wcs_to_celestial_frame(ww) # TODO: check that this is working - the regions output seem to be offset? ww_cutout = ww[mask.bbox.iymin:mask.bbox.iymax, mask.bbox.ixmin:mask.bbox.ixmax] # add beam parameters to header cutout_header = ww_cutout.to_header() cutout_header['BMAJ'] = mustang_beam_fwhm.to(u.deg).value cutout_header['BMIN'] = mustang_beam_fwhm.to(u.deg).value cutout_header['BUNIT'] = 'Jy/beam' cutout_header['TELESCOP'] = 'GBT' cutout_header['FREQ'] = mustang_central_frequency.to(u.Hz).value avg_noise = mad_std(data, ignore_nan=True) filt_avg_noise = mad_std(cutout, ignore_nan=True) noiselevel_table[regname] = { 'noise': avg_noise, 'filtered_noise': filt_avg_noise } with open(noisefilepath, 'w') as fh: json.dump(noiselevel_table, fh) print( f"Beginning cataloging. Noise is {avg_noise:0.4f} before and {filt_avg_noise:0.4f} after filtering" ) radiosource = dendrocat.RadioSource( [fits.PrimaryHDU(data=cutout, header=cutout_header)]) radiosource.nu = mustang_central_frequency radiosource.freq_id = 'MUSTANG' radiosource.set_metadata() print("Running to_dendrogram") radiosource.to_dendrogram( min_value=err * threshold, min_delta=err * min_delta, min_npix=min_npix, ) print("Making plot grid") radiosource.plot_grid( skip_rejects=False, outfile= f'{catalog_figure_path}/{regname}_dendrocat_thr{threshold}_minn{min_npix}_mind{min_delta}_prerejection.png', figurekwargs={'num': 1}, ) pl.figure(1).clf() #radiosource.autoreject(threshold=5.0) rejected = radiosource.catalog[ 'MUSTANG_dend_flux'] / filt_avg_noise < snr_threshold #radiosource.catalog.add_column(Column(rejected, name='rejected')) radiosource.catalog['rejected'] = rejected.astype('int') print("Rejected {0}, kept {1}, of {2} total sources".format( radiosource.catalog['rejected'].sum(), (1 - radiosource.catalog['rejected']).sum(), len(radiosource.catalog))) radiosource.plot_grid( skip_rejects=False, outfile= f'{catalog_figure_path}/{regname}_dendrocat_thr{threshold}_minn{min_npix}_mind{min_delta}_postrejection.png', figurekwargs={'num': 1}, ) pl.figure(1).clf() #dend = astrodendro.Dendrogram.compute(cutout, # min_value=err*threshold, # min_delta=err*min_delta, # verbose=True, min_npix=min_npix, # wcs=ww_cutout) dend = radiosource.dendrogram pl.figure(2).clf() ax = pl.gca() ax.cla() pl.imshow(cutout, cmap='gray_r', interpolation='none', origin='lower', vmax=0.01, vmin=-0.001) pltr = dend.plotter() print("Contouring dendrogram leaves") for struct in ProgressBar(dend.leaves): pltr.plot_contour(ax, structure=struct, colors=['r'], linewidths=[0.9], zorder=5) if struct.parent: while struct.parent: struct = struct.parent pltr.plot_contour(ax, structure=struct, colors=[(0, 1, 0, 1)], linewidths=[0.5]) cntr = pl.gca().collections pl.setp([x for x in cntr if x.get_color()[0, 0] == 1], linewidth=0.25) pl.setp([x for x in cntr if x.get_color()[0, 1] == 1], linewidth=0.25) pl.savefig( f'{catalog_figure_path}/{regname}_dend_contour_thr{threshold}_minn{min_npix}_mind{min_delta}.pdf' ) # zoom only for G31 if regname == 'G31': pl.axis((1125.4006254228616, 1670.3650637799306, 1291.6829155596627, 1871.8063499397681)) pl.setp([x for x in cntr if x.get_color()[0, 0] == 1], linewidth=0.75) # Red pl.setp([x for x in cntr if x.get_color()[0, 1] == 1], linewidth=0.5) # Green pl.savefig( f'{catalog_figure_path}/{regname}_dend_contour_thr{threshold}_minn{min_npix}_mind{min_delta}_zoom.pdf' ) #metadata = {'data_unit': u.Jy / u.beam, # 'beam_major': 8*u.arcsec, # 'beam_minor': 8*u.arcsec, # 'wcs': ww_cutout, # 'spatial_scale': wcs.utils.proj_plane_pixel_scales(ww_cutout).mean()*u.deg, # } #ppcat = astrodendro.pp_catalog(dend, metadata) ppcat = radiosource.catalog mastercatalog = dendrocat.MasterCatalog(radiosource, catalog=ppcat) aperture1 = Circle([0, 0], 10 * u.arcsec, name='10as', frame=frame.name) aperture2 = Circle([0, 0], 15 * u.arcsec, name='15as', frame=frame.name) background = Annulus([0, 0], inner=15 * u.arcsec, outer=20 * u.arcsec, name='background', frame=frame.name) print("Beginning photometry ...") mastercatalog.photometer(aperture1, aperture2, background) print() source_center = coordinates.SkyCoord(mastercatalog.catalog['x_cen'], mastercatalog.catalog['y_cen'], unit=(u.deg, u.deg), frame=frame.name) source_name = [ "G{0:0.3f}{1:+0.3f}".format(sc.galactic.l.deg, sc.galactic.b.deg) for sc in source_center ] mastercatalog.catalog.add_column( Column(name='SourceName', data=source_name)) mastercatalog.catalog.write( f'{catalog_path}/{regname}_dend_contour_thr{threshold}_minn{min_npix}_mind{min_delta}.ipac', format='ascii.ipac') regs = ppcat_to_regions(ppcat, frame.name) regions.write_ds9( regions=regs, filename= f'{catalog_path}/{regname}_dend_contour_thr{threshold}_minn{min_npix}_mind{min_delta}.reg' ) return radiosource, dend, mastercatalog, ppcat
import astropy.units as u imgHeaderPath = Path('headers') regFile = Path('pixCoords/xyreg.lis') regDirec = Path('regionFiles/xyregs') finalReg = Path('regionFiles/skyregs') arcsec2deg = 1 / 3600 regRadius = 20. * arcsec2deg fp = open(regFile, 'r') ll = fp.readlines() fp.close() for name in range(len(ll)): # print(regName) regName = Path(ll[name]) print(regName) imgName = regName.with_suffix('') print(imgName) imgName = imgName.with_suffix('') print(imgName) reg = read_ds9(regDirec.joinpath(regName).with_suffix('.reg')) hdr = Header.fromtextfile( str(imgHeaderPath.joinpath(imgName).with_suffix('.head'))) w = WCS(hdr) for rr in range(len(reg)): reg[rr] = reg[rr].to_sky(wcs=w) write_ds9(reg, finalReg.joinpath(imgName).with_suffix('.sky.reg'))
msnamelist = list(map(lambda s: 'P{:d}.ms'.format(int(s)), positions_25mJy['Source_id'])) print('msout.name=[' + ','.join(msnamelist) + ']') msposlist = list(map(lambda x: '[{:f}deg,{:f}deg]'.format(x[0], x[1]), positions_25mJy['RA', 'DEC'])) print('phasecenter=[' + ','.join(msposlist) + ']') region_strs = map(lambda pos: 'fk5\ncircle({:f},{:f},{:f}) # color=red width=2 text="{:s}"'.format(*pos['RA','DEC'], 30. / 3600, str(pos['Source_id'])), positions_25mJy) for i in range(len(msnamelist)//10): with open('split_25mJy_{:02d}.parset'.format(i), 'w') as f: output = PARSET + '\nmsout.name=[' + ','.join(msnamelist[10*i:10*(i+1)]) + ']\n' +\ 'shift.phasecenter=[' + ','.join(msposlist[10*i:10*(i+1)]) + ']\n' f.write(output) from regions import DS9Parser, write_ds9 parser = DS9Parser('\n'.join(list(region_strs))) regions = parser.shapes.to_regions() write_ds9(regions, 'pointings_25mJy.reg') def make_tiles(ra, dec, tile_spacing=0.625, tile_facet_size=0.7): ''' Create the tiling for a 0.3'' mosaic of the central 2.5 degree. Args: ra (float): right ascension of the pointing center. dec (float): declination of the pointing center. Returns: facets (ndarray): a 4 x 4 x 2 array with the central RA and DEC of the tiles. ''' spacing = tile_spacing * u.degree # Have some overlap facet_size = tile_facet_size * u.degree facets = np.zeros((4,4,2)) * u.degree#, dtype=(float, 2)) * u.degree facetlist = []