def saveCalibration(dim, basedir, dtype, dateid, ccdid, ampid, filterid):
    # CFHTLS/%(dtype)/v%(dateid)/c%(ccdid)-a%(ampid).fits
    # -- or --
    # CFHTLS/%(dtype)/v%(dateid)-f%(filterid)/c%(ccdid)-a%(ampid).fits

    if filterid == None:
        outdir = '%s/calib/%s/v%s' % (basedir, dtype, dateid)
        if dtype == 'dark':
            outdir = '%s/calib/%s/v%s-e%d' % (
                basedir, dtype, dateid, int(dim.getMetadata().get('DARKTIME')))
    else:
        outdir = '%s/calib/%s/v%s-f%s' % (basedir, dtype, dateid, filterid)

    if not os.path.isdir(outdir):
        os.makedirs(outdir)

    outfile = '%s/c%s-a%s.fits' % (outdir, ccdid, ampid)
    print '# writing', outfile

    # convert to exposure
    exp = afwImage.ExposureF(afwImage.MaskedImageF(dim.getImage()),
                             afwImage.Wcs())
    exp.setMetadata(dim.getMetadata())
    if filterid == None:
        # For biases
        exp.setFilter(afwImage.Filter("u"))
    else:
        exp.setFilter(afwImage.Filter(filterid))
    exp.getMetadata().set('DC3BPATH', outfile)
    exp.writeFits(outfile)
Beispiel #2
0
    def test1(self):
        # This fails due to #1386
        #wcsfn = os.path.join(self.datadir, 'imsim-v85518312-fu-R43-S12.wcs')
        wcsfn = os.path.join(self.datadir, 'imsim-v85518312-fu-R43-S12.wcs2')
        hdr = afwImage.readMetadata(wcsfn)
        wcs1 = afwImage.makeWcs(hdr)

        crval = wcs1.getSkyOrigin()
        cd = wcs1.getCDMatrix()
        print cd
        crval_p = afwGeom.Point2D(crval.getLongitude().asDegrees(), 
                                 crval.getLatitude().asDegrees())
        origin = wcs1.getPixelOrigin()
        print crval_p
        print origin
        wcs2 = afwImage.Wcs(crval_p, origin, cd)

        for wcs in [wcs1,wcs2]:
            print wcs
            print 'x, y, RA, Dec, pixscale("/pix), pixscale2'
            for x,y in [(0,0),(300,0),(350,0),(360,0),(370,0),(380,0),(400,0)]:
                radec = wcs.pixelToSky(x,y)
                ra  = radec.getLongitude().asDegrees()
                dec = radec.getLatitude ().asDegrees()
                pixscale = 3600. * sqrt(wcs.pixArea(afwGeom.Point2D(x,y)))
                ps2 = wcs.pixelScale().asArcseconds()
                print x,y,ra,dec,pixscale,ps2
                self.assertTrue(abs(pixscale - 0.2) < 1e-3)
                self.assertTrue(abs(ps2 - 0.2) < 1e-3)
Beispiel #3
0
    def testMeasure(self):
        """Test that we can instantiate and play with RotationAngle"""

        scale = 5.0e-5                  # Pixel scale: 0.18 arcsec/pixel
        for angle in (0, 45, 90, 120, 180, 275):
            angle = angle * afwGeom.degrees
            for expFactory in (afwImage.ExposureF, afwImage.ExposureD):
                cdMatrix = numpy.array([[scale * math.cos(angle.asRadians()), 
                                         scale * math.sin(angle.asRadians())],
                                        [scale * -math.sin(angle.asRadians()),
                                         scale * math.cos(angle.asRadians())]])
                
                wcs = afwImage.Wcs(afwGeom.Point2D(0, 0), afwGeom.Point2D(50, 50), cdMatrix)
                exp = expFactory(afwGeom.ExtentI(100, 100), wcs)
                x, y = 10, 20
                exp.getMaskedImage().getImage().set(x, y, 1.0)

                east, north = self.measureRotAngle(exp, x, y)

                eastTrue = angle
                northTrue = angle + 90 * afwGeom.degrees
                while east < 0 * afwGeom.degrees: east = east + 360 * afwGeom.degrees
                while north < 0 * afwGeom.degrees: north = north + 360 * afwGeom.degrees
                while northTrue > 360 * afwGeom.degrees: northTrue = northTrue - 360 * afwGeom.degrees

                self.assertAlmostEqual(east.asRadians(), eastTrue.asRadians())
                self.assertAlmostEqual(north.asRadians(), northTrue.asRadians())
Beispiel #4
0
 def setUp(self):
     crval = afwGeom.Point2D(1.23, 5.67)
     crpix = afwGeom.Point2D(102., 201.)
     cd = numpy.array([[5.399452e-5, -1.30770e-5], [1.30770e-5, 5.399452e-5]], dtype=float)
     self.plainWcs = afwImage.Wcs(crval, crpix, cd)
     self.sipWcs = afwImage.TanWcs(crval, crpix, cd)
     self.distortedWcs = afwImage.TanWcs(crval, crpix, cd, cd, cd, cd, cd)
    def getSipWcsFromWcs(self, wcs, bbox, ngrid=20, linearizeAtCenter=True):
        """!Get a TAN-SIP WCS, starting from an existing WCS.

        It uses your WCS to compute a fake grid of corresponding "stars" in pixel and sky coords,
        and feeds that to the regular SIP code.

        @param[in] wcs  initial WCS
        @param[in] bbox  bounding box of image
        @param[in] ngrid  number of grid points along x and y for fitting (fit at ngrid^2 points)
        @param[in] linearizeAtCenter  if True, get a linear approximation of the input
          WCS at the image center and use that as the TAN initialization for
          the TAN-SIP solution.  You probably want this if your WCS has its
          CRPIX outside the image bounding box.
        """
        # Ugh, build src and ref tables
        srcSchema = afwTable.SourceTable.makeMinimalSchema()
        key = srcSchema.addField("centroid", type="PointD")
        srcTable = afwTable.SourceTable.make(srcSchema)
        srcTable.defineCentroid("centroid")
        srcs = srcTable
        refs = afwTable.SimpleTable.make(
            afwTable.SimpleTable.makeMinimalSchema())
        cref = []
        csrc = []
        (W, H) = bbox.getDimensions()
        x0, y0 = bbox.getMin()
        for xx in np.linspace(0., W, ngrid):
            for yy in np.linspace(0, H, ngrid):
                src = srcs.makeRecord()
                src.set(key.getX(), x0 + xx)
                src.set(key.getY(), y0 + yy)
                csrc.append(src)
                rd = wcs.pixelToSky(xx + x0, yy + y0)
                ref = refs.makeRecord()
                ref.setCoord(rd)
                cref.append(ref)

        if linearizeAtCenter:
            # Linearize the original WCS around the image center to create a
            # TAN WCS.
            # Reference pixel in LSST coords
            crpix = afwGeom.Box2D(bbox).getCenter()
            crval = wcs.pixelToSky(crpix)
            crval = crval.getPosition(afwGeom.degrees)
            # Linearize *AT* crval to get effective CD at crval.
            # (we use the default skyUnit of degrees as per WCS standard)
            aff = wcs.linearizePixelToSky(crval)
            cd = aff.getLinear().getMatrix()
            wcs = afwImage.Wcs(crval, crpix, cd)

        return self.getSipWcsFromCorrespondences(wcs,
                                                 cref,
                                                 csrc, (W, H),
                                                 x0=x0,
                                                 y0=y0)
Beispiel #6
0
def acsEventCallback(key, source, im, frame):
    """Callback for event handlers to find COSMOS ACS cutout.

    \param key     Key struck
    \param source  The Source under the cursor
    \param im      The (HSC) image cutout displayed in frame
    \param frame   The frame that the HSC data's displayed in (we'll use the next one)

    We also use the following static members of utils.EventHandler (if set):
    sizeCutout   The size of the HSC cutout (arcsec; default: 4.0)
    scale   Make the COSMOS image with pixel size scale*HSC's pixel size (default 0.25 => 0.42mas)

    Use as e.g. utils.eventCallbacks['c'] = cosmos.acsEventCallback
    """
    sizeCutout = utils.EventHandler.sizeCutout if hasattr(
        utils.EventHandler, "sizeCutout") else 4.0  # arcsec
    scale = utils.EventHandler.scale if hasattr(
        utils.EventHandler, "scale") else 0.25  # Pixel size scaling

    pos = source.get("coord")
    exp = getCosmosCutout(*pos.getPosition(), sizeX=sizeCutout)

    if im and exp and exp.getWcs():
        #
        # Resample and rotate to the HSC orientation
        #
        warpingControl = afwMath.WarpingControl("lanczos3")
        rat = im.getWcs().pixelScale().asArcseconds() / exp.getWcs(
        ).pixelScale().asArcseconds()
        hsize = int(0.5 * exp.getWidth() / (scale * rat))
        rexp = afwImage.ExposureF(2 * hsize + 1, 2 * hsize + 1)
        rexp.setWcs(
            afwImage.Wcs(pos.getPosition(), afwGeom.Point2D(hsize, hsize),
                         im.getWcs().getCDMatrix() * scale))
        afwMath.warpExposure(rexp, exp, warpingControl)
    else:
        print "\nI'm unable to remap the cosmos image to your coordinates, sorry"
        rexp = exp.getMaskedImage().getImage()

    frame += 1
    rim = rexp
    if hasattr(rim, "getMaskedImage"):
        rim = rim.getMaskedImage().getImage()
    if hasattr(rim, "getImage"):
        rim = rim.getImage()
    disp = afwDisplay.Display(frame=frame)
    disp.mtv(rim)

    if hasattr(rexp, "getWcs"):
        cen = rexp.getWcs().skyToPixel(pos) - afwGeom.PointD(rexp.getXY0())
        disp.pan(*cen)
        disp.dot('+', *cen)
    def process(self):
        clipboard = self.inputQueue.getNextDataset()
        metadataPolicy = self._policy.getPolicy("metadata")
        datatypePolicy = self._policy.getPolicy("datatype")
        imageKey = self._policy.get("imageKey")
        metadataKey = self._policy.get("metadataKey")
        wcsKey = self._policy.get("wcsKey")
        decoratedImage = clipboard.get(imageKey)
        metadata = decoratedImage.getMetadata()

        if self._policy.exists("suffix"):
            suffix = self._policy.get("suffix")
        else:
            suffix = "Keyword"

        if self._policy.exists("computeWcsGuess"):
            if self._policy.getBool("computeWcsGuess"):
                wcs = afwImage.Wcs(metadata)
                ampBBoxKey = self._policy.getString("ampBBoxKey")
                ampBBox = clipboard.get(ampBBoxKey)
                wcs.shiftReferencePixel(ampBBox.getX0(), ampBBox.getY0())
                clipboard.put(wcsKey, wcs)

        # set various exposure id's needed by downstream stages

        ccdId = clipboard.get("ccdId")
        ampId = clipboard.get("ampId")

        eventName = self._policy.get("eventName")
        event = clipboard.get(eventName)
        exposureId = event.get("exposureId")

        fpaExposureId = exposureId
        ccdExposureId = (fpaExposureId << 8) + ccdId
        ampExposureId = (ccdExposureId << 6) + ampId

        metadata.setLongLong('ampExposureId', ampExposureId)
        metadata.setLongLong('ccdExposureId', ccdExposureId)
        metadata.setLongLong('fpaExposureId', fpaExposureId)
        metadata.set('ampId', ampId)
        metadata.set('ccdId', ampId)
        #        metadata.set('url', metadata.get('filename'))   # who uses this??

        transformMetadata(metadata, datatypePolicy, metadataPolicy, suffix)

        clipboard.put(metadataKey, metadata)
        clipboard.put(imageKey, decoratedImage.getImage())

        self.outputQueue.addDataset(clipboard)
Beispiel #8
0
    def initialWcs(self, matches, wcs):
        """Generate a guess Wcs from the astrometric matches

        We create a Wcs anchored at the center of the matches, with the scale
        of the input Wcs.  This is necessary because matching returns only
        matches with no estimated Wcs, and the input Wcs is a wild guess.
        We're using the best of each: positions from the matches, and scale
        from the input Wcs.
        """
        crpix = afwGeom.Extent2D(0, 0)
        crval = afwGeom.Extent3D(0, 0, 0)
        for mm in matches:
            crpix += afwGeom.Extent2D(mm.second.getCentroid())
            crval += afwGeom.Extent3D(mm.first.getCoord().toIcrs().getVector())
        crpix /= len(matches)
        crval /= len(matches)
        newWcs = afwImage.Wcs(
            afwCoord.IcrsCoord(afwGeom.Point3D(crval)).getPosition(),
            afwGeom.Point2D(crpix), wcs.getCDMatrix())
        return newWcs
Beispiel #9
0
    def std_raw_md(self, md, dataId):
        if False:  # no std_raw_md in baseclass
            md = super(HscMapper,
                       self).std_raw_md(md, dataId)  # not present in baseclass
        #
        # We need to flip the WCS defined by the metadata in case anyone ever constructs a Wcs from it
        #
        wcs = afwImage.makeWcs(md)
        self._flipChipsLR(None,
                          wcs,
                          dataId,
                          dims=afwImage.bboxFromMetadata(md).getDimensions())
        wcsR = afwImage.Wcs(wcs.getSkyOrigin().getPosition(),
                            wcs.getPixelOrigin(),
                            wcs.getCDMatrix() * 0.992)
        wcsMd = wcsR.getFitsMetadata()

        for k in wcsMd.names():
            md.set(k, wcsMd.get(k))

        return md
Beispiel #10
0
    def process(self):
        clipboard = self.inputQueue.getNextDataset()
        metadataPolicy = self._policy.getPolicy("metadata")
        datatypePolicy = self._policy.getPolicy("datatype")
        imageKey = self._policy.get("imageKey")
        metadataKey = self._policy.get("metadataKey")
        exposureMetadataKey = self._policy.get("exposureMetadataKey")
        wcsKey = self._policy.get("wcsKey")
        decoratedImage = clipboard.get(imageKey)
        exposureMetadata = clipboard.get(exposureMetadataKey)
        metadata = decoratedImage.getMetadata()

        if self._policy.exists("suffix"):
            suffix = self._policy.get("suffix")
        else:
            suffix = "Keyword"

        if self._policy.exists("computeWcsGuess"):
            if self._policy.getBool("computeWcsGuess"):
                wcs = afwImage.Wcs(metadata)
                ampBBoxKey = self._policy.getString("ampBBoxKey")
                ampBBox = clipboard.get(ampBBoxKey)
                wcs.shiftReferencePixel(ampBBox.getX0(), ampBBox.getY0())
                clipboard.put(wcsKey, wcs)

        transformMetadata(metadata, datatypePolicy, metadataPolicy, suffix)

        metadata.setLongLong('ampExposureId',
                exposureMetadata.get('ampExposureId'))
        metadata.setLongLong('ccdExposureId',
                exposureMetadata.get('ccdExposureId'))
        metadata.setLongLong('fpaExposureId',
                exposureMetadata.get('fpaExposureId'))
        metadata.set('url', metadata.get('filename'))
        metadata.set('ampId', clipboard.get('ampId'))

        clipboard.put(metadataKey, metadata)
        clipboard.put(imageKey, decoratedImage.getImage())

        self.outputQueue.addDataset(clipboard)
    def std_raw(self, item, dataId):
        exposure = super(LsstSimMapper, self).std_raw(item, dataId)
        md = exposure.getMetadata()
        if md.exists("VERSION") and md.getInt("VERSION") < 16952:
            # Precess crval of WCS from date of observation to J2000
            epoch = exposure.getInfo().getVisitInfo().getDate().get(
                dafBase.DateTime.EPOCH)
            if math.isnan(epoch):
                raise RuntimeError("Date not found in raw exposure %s" %
                                   (dataId, ))
            wcs = exposure.getWcs()
            origin = wcs.getSkyOrigin()
            refCoord = afwCoord.Fk5Coord(origin.getLongitude(),
                                         origin.getLatitude(), epoch)
            newRefCoord = refCoord.precess(2000.)
            crval = afwGeom.PointD()
            crval.setX(newRefCoord.getRa().asDegrees())
            crval.setY(newRefCoord.getDec().asDegrees())
            wcs = afwImage.Wcs(crval, wcs.getPixelOrigin(), wcs.getCDMatrix())
            exposure.setWcs(wcs)

        return exposure
    def run(self, sensorRefList, calibType):
        """Process a calibration frame.

        @param sensorRef: sensor-level butler data reference
        @return pipe_base Struct containing these fields:
        - masterExpList: amp exposures of master calibration products
        """
        referenceAmps = sensorRefList[0].subItems(level="channel")
        masterExpList = []
        dataIdList = []
        expmeta = None
        for amp in referenceAmps:
            if amp.dataId['snap'] == 1:
                continue
            self.log.info("Amp: Processing %s", amp.dataId)
            print "dataid %s" % (amp.dataId)
            butler = amp.butlerSubset.butler
            ampMIList = afwImage.vectorMaskedImageF()
            for sRef in sensorRefList:
                self.log.info("Sensor: Processing %s", sRef.dataId)
                ampSnapMIList = afwImage.vectorMaskedImageF()
                dataId = eval(amp.dataId.__repr__())
                dataId['visit'] = sRef.dataId['visit']
                for snap in (0, 1):
                    dataId['snap'] = snap
                    ampExposure = sRef.butlerSubset.butler.get('raw', dataId)
                    if expmeta is None:
                        expmeta = ampExposure.getMetadata()
                        expfilter = ampExposure.getFilter()
                        expcalib = ampExposure.getCalib()
                    ampDetector = cameraGeom.cast_Amp(
                        ampExposure.getDetector())

                    ampExposure = self.convertIntToFloat(ampExposure)
                    ampExpDataView = ampExposure.Factory(
                        ampExposure, ampDetector.getDiskDataSec())

                    self.saturationDetection(ampExposure, ampDetector)

                    self.overscanCorrection(ampExposure, ampDetector)
                    if calibType in ('flat', 'dark'):
                        self.biasCorrection(ampExpDataView, amp)

                    if False:
                        self.darkCorrection(ampExpDataView, amp)

                    self.updateVariance(ampExpDataView, ampDetector)
                    ampSnapMIList.append(ampExpDataView.getMaskedImage())
                ampMIList.append(self.combineMIList(ampSnapMIList))
            masterFrame = self.combineMIList(ampMIList)
            # Fix saturation too???
            self.fixDefectsAndSat(masterFrame, ampDetector)
            exp = afwImage.ExposureF(masterFrame)
            self.copyMetadata(exp, expmeta, calibType)
            exp.setDetector(ampDetector)
            exp.setWcs(afwImage.Wcs())
            exp.setCalib(expcalib)
            if calibType is 'flat':
                exp.setFilter(expfilter)
            if self.config.doWrite and calibType is not 'flat':
                print "writing file %s" % dataId
                butler.put(exp, calibType, dataId=amp.dataId)
            masterExpList.append(exp)
            dataIdList.append(amp.dataId)
        if self.config.doWrite and calibType is 'flat':
            self.normChipAmps(masterExpList)
            for exp, dataId in zip(masterExpList, dataIdList):
                print "writing flat file %s" % dataId
                butler.put(exp, calibType, dataId)
        return pipeBase.Struct(masterFrameList=masterExpList, )
Beispiel #13
0
 def testConstructor(self):
     copy = afwImage.Wcs(self.wcs.getSkyOrigin(), self.wcs.getPixelOrigin(),
                         self.wcs.getCDMatrix())
def makeCcdMosaic(dir,
                  basename,
                  e,
                  c,
                  aList,
                  imageFactory=afwImage.MaskedImageF,
                  verbose=0):
    """Return an image of all the specified amplifiers, aList, for the given CCD

    E.g. sl = makeCcdMosaic("/lsst/DC3root/rlp1173", "v704897", 0, 3, range(8))
    """

    try:
        aList[0]
    except TypeError:
        aList = [aList]

    for what in ("header", "data"):
        if what == "header":
            bbox = afwGeom.Box2I()
            ampBBox = {}
            wcs = {}
        else:
            ccdImage = imageFactory(bbox.getWidth(), bbox.getHeight())
            ccdImage.set(0)
            ccdImage.setXY0(bbox.getLLC())

        for a in aList:
            filename = os.path.join(
                dir, "IPSD", "output", "sci", "%s-e%d" % (basename, e),
                "%s-e%d-c%03d-a%02d.sci" % (basename, e, c, a))
            if verbose and what == "header":
                print(filename)

            if what == "header":
                md = afwImage.readMetadata(filename + "_img.fits")
                xy0 = afwGeom.Point2I(md.get("CRVAL1A"), md.get("CRVAL2A"))
                xy1 = xy0 + afwGeom.Extent2I(
                    md.get("NAXIS1") - 1,
                    md.get("NAXIS2") - 1)
                bbox.grow(xy0)
                bbox.grow(xy1)

                ampBBox[a] = afwGeom.Box2I(xy0, xy1)
                wcs[a] = afwImage.Wcs(md)
            else:
                try:
                    data = imageFactory(filename + "_img.fits")
                except:
                    data = imageFactory(filename)

                ampImage = ccdImage.Factory(ccdImage, ampBBox[a])
                ampImage[:] = data
                del ampImage

    try:
        ccdImage.getMask()
        if 0 in wcs:
            ccdImage = afwImage.ExposureF(ccdImage, wcs[0])
    except AttributeError:
        pass

    return ccdImage
Beispiel #15
0
 def testConstructor(self):
     copy = afwImage.Wcs(
         self.wcs.getSkyOrigin().getPosition(afwGeom.degrees),
         self.wcs.getPixelOrigin(), self.wcs.getCDMatrix())
Beispiel #16
0
imageSigma = %0.1f
variance   = %0.1f
""" % (coaddPath, numImages, config.imageShape, config.imageSigma,
       config.variance))

    np.random.seed(0)

    coadd = None
    for imInd in range(numImages):
        print("Create exposure %d" % (imInd, ), file=sys.stderr)
        maskedImage = afwTestUtils.makeGaussianNoiseMaskedImage(
            dimensions=config.imageShape,
            sigma=config.imageSigma,
            variance=config.variance)
        # the WCS doesn't matter; the default will do
        wcs = afwImage.Wcs()
        exposure = afwImage.ExposureF(maskedImage, wcs)

        if not coadd:
            print("Create coadd", file=sys.stderr)
            coadd = coaddChiSq.Coadd.fromConfig(bbox=exposure.getBBox(),
                                                wcs=exposure.getWcs(),
                                                config=config.coadd)
            print("badPixelMask=", coadd.getBadPixelMask(), file=sys.stderr)

        coadd.addExposure(exposure)

    print("Save weight map as %s" % (weightPath, ), file=sys.stderr)
    weightMap = coadd.getWeightMap()
    weightMap.writeFits(weightPath)
    coaddExposure = coadd.getCoadd()