def run(self, sources, skyMap, tractInfo, patchInfo, includeDeblend=True): """Set is-primary and related flags on sources @param[in,out] sources a SourceTable - reads centroid fields and an nChild field - writes is-patch-inner, is-tract-inner and is-primary flags @param[in] skyMap sky tessellation object (subclass of lsst.skymap.BaseSkyMap) @param[in] tractInfo tract object (subclass of lsst.skymap.TractInfo) @param[in] patchInfo patch object (subclass of lsst.skymap.PatchInfo) @param[in] includeDeblend include deblend information in isPrimary? """ nChildKey = None if includeDeblend: nChildKey = self.schema.find(self.config.nChildKeyName).key # set inner flags for each source and set primary flags for sources with no children # (or all sources if deblend info not available) innerFloatBBox = Box2D(patchInfo.getInnerBBox()) # When the centroider fails, we can still fall back to the peak, but we don't trust # that quite as much - so we use a slightly smaller box for the patch comparison. # That's trickier for the tract comparison, so we just use the peak without extra # care there. shrunkInnerFloatBBox = Box2D(innerFloatBBox) shrunkInnerFloatBBox.grow(-1) pseudoFilterKeys = [] for filt in self.config.pseudoFilterList: try: pseudoFilterKeys.append(self.schema.find("merge_peak_%s" % filt).getKey()) except Exception: self.log.warn("merge_peak is not set for pseudo-filter %s" % filt) tractId = tractInfo.getId() for source in sources: centroidPos = source.getCentroid() if numpy.any(numpy.isnan(centroidPos)): continue if source.getCentroidFlag(): # Use a slightly smaller box to guard against bad centroids (see above) isPatchInner = shrunkInnerFloatBBox.contains(centroidPos) else: isPatchInner = innerFloatBBox.contains(centroidPos) source.setFlag(self.isPatchInnerKey, isPatchInner) skyPos = source.getCoord() sourceInnerTractId = skyMap.findTract(skyPos).getId() isTractInner = sourceInnerTractId == tractId source.setFlag(self.isTractInnerKey, isTractInner) if nChildKey is None or source.get(nChildKey) == 0: for pseudoFilterKey in pseudoFilterKeys: if source.get(pseudoFilterKey): isPseudo = True break else: isPseudo = False source.setFlag(self.isPrimaryKey, isPatchInner and isTractInner and not isPseudo)
def setUp(self): # Test geometry: # # -100,99 99,99 # +--------------------+ # |AAAAAAAAAACCCCCDDDDD| A == only in epoch A # |AAAAAAAAAACCCCCDDDDD| B == only in epoch B # |AAAAAAAAAACCCCCDDDDD| C == in both epoch A and epoch B # |AAAAAAAAAACCCCCDDDDD| D == in epoch A; in B's bbox but outside its ValidPolygon # |AAAAAAAAAACCCCCDDDDD| # | BBBBBBBBBB| All WCSs have the same CRVAL and CD. # | BBBBBBBBBB| # | BBBBBBBBBB| Coadd has CRPIX=(0, 0) # | BBBBBBBBBB| Epoch A has CRPIX=(0, -50) # | BBBBBBBBBB| Epoch B has CRPIX=(-50, 0) # +--------------------+ # -100,-100 99,-100 # self.rng = np.random.RandomState(50) crval = SpherePoint(45.0, 45.0, degrees) cdMatrix = makeCdMatrix(scale=5E-5 * degrees, flipX=True) self.wcsCoadd = makeSkyWcs(crpix=Point2D(0.0, 0.0), crval=crval, cdMatrix=cdMatrix) self.wcsA = makeSkyWcs(crpix=Point2D(0.0, -50.0), crval=crval, cdMatrix=cdMatrix) self.wcsB = makeSkyWcs(crpix=Point2D(-50.0, 0.0), crval=crval, cdMatrix=cdMatrix) self.bboxCoadd = Box2I(Point2I(-100, -100), Point2I(99, 99)) self.bboxA = Box2I(Point2I(-100, -50), Point2I(99, 49)) self.bboxB = Box2I(Point2I(-50, -100), Point2I(49, 99)) self.polygonA = None polygonD = Polygon(Box2D(Box2I(Point2I(0, 0), Point2I(49, 99)))) self.polygonB, = polygonD.symDifference(Polygon(Box2D(self.bboxB))) self.curveA = makeRandomTransmissionCurve(self.rng) self.curveB = makeRandomTransmissionCurve(self.rng) self.weightA = 0.6 self.weightB = 0.2 schema = ExposureTable.makeMinimalSchema() weightKey = schema.addField("weight", type=float, doc="relative weight of image in Coadd") catalog = ExposureCatalog(schema) recordA = catalog.addNew() recordA[weightKey] = self.weightA recordA.setWcs(self.wcsA) recordA.setValidPolygon(self.polygonA) recordA.setBBox(self.bboxA) recordA.setTransmissionCurve(self.curveA) recordB = catalog.addNew() recordB[weightKey] = self.weightB recordB.setWcs(self.wcsB) recordB.setValidPolygon(self.polygonB) recordB.setBBox(self.bboxB) recordB.setTransmissionCurve(self.curveB) self.curveCoadd = makeCoaddTransmissionCurve(self.wcsCoadd, catalog)
def testReadOldTanFits(self): """Test reading a FITS file containing data for an lsst::afw::image::TanWcs That file was made using the same metadata follows (like self.metadata without the distortion) """ tanMetadata = PropertyList() # the following was fit using CreateWcsWithSip from meas_astrom # and is valid over this bbox: (minimum=(0, 0), maximum=(3030, 3030)) # This same metadata was used to create testdata/oldTanSipwWs.fits for name, value in ( ("RADESYS", "ICRS"), ("CTYPE1", "RA---TAN"), ("CTYPE2", "DEC--TAN"), ("CRPIX1", 1531.1824767147), ("CRPIX2", 1531.1824767147), ("CRVAL1", 43.035511801383), ("CRVAL2", 44.305697682784), ("CUNIT1", "deg"), ("CUNIT2", "deg"), ("CD1_1", 0.00027493991598151), ("CD1_2", -3.2758487104158e-06), ("CD2_1", 3.2301310675830e-06), ("CD2_2", 0.00027493937506632), ): tanMetadata.set(name, value) dataDir = os.path.join(os.path.split(__file__)[0], "data") filePath = os.path.join(dataDir, "oldTanWcs.fits") wcsFromFits = SkyWcs.readFits(filePath) wcsFromMetadata = makeSkyWcs(tanMetadata) bbox = Box2D(Point2D(-1000, -1000), Extent2D(3000, 3000)) self.assertWcsAlmostEqualOverBBox(wcsFromFits, wcsFromMetadata, bbox)
def checkMakeFlippedWcs(self, skyWcs, skyAtol=1e-7 * arcseconds): """Check makeFlippedWcs on the provided WCS """ # make an arbitrary bbox, but one that includes zero in one axis # and does not include zero in the other axis # the center of the bbox is used as the center of flipping # and the corners of the bbox are the input positions that are tested bbox = Box2D(Point2D(-100, 1000), Extent2D(2000, 1501)) # dict of (isRight, isTop): position minPos = bbox.getMin() maxPos = bbox.getMax() center = bbox.getCenter() cornerDict = { (False, False): minPos, (False, True): Point2D(minPos[0], maxPos[1]), (True, False): Point2D(maxPos[0], minPos[1]), (True, True): maxPos, } for flipLR, flipTB in itertools.product((False, True), (False, True)): flippedWcs = makeFlippedWcs(wcs=skyWcs, flipLR=flipLR, flipTB=flipTB, center=center) # the center is unchanged self.assertSpherePointsAlmostEqual(skyWcs.pixelToSky(center), flippedWcs.pixelToSky(center), maxSep=skyAtol) for isR, isT in itertools.product((False, True), (False, True)): origPos = cornerDict[(isR, isT)] flippedPos = cornerDict[(isR ^ flipLR, isT ^ flipTB)] self.assertSpherePointsAlmostEqual( skyWcs.pixelToSky(origPos), flippedWcs.pixelToSky(flippedPos), maxSep=skyAtol)
def testAgainstAstropyWcs(self): skyWcs = makeSkyWcs(self.metadata, strip=False) header = makeLimitedFitsHeader(self.metadata) astropyWcs = astropy.wcs.WCS(header) bbox = Box2D(Point2D(-1000, -1000), Extent2D(3000, 3000)) self.assertSkyWcsAstropyWcsAlmostEqual(skyWcs=skyWcs, astropyWcs=astropyWcs, bbox=bbox)
def testBasics(self): """Test construction of a discrete sky map """ butler = Butler(inputs=self.inPath, outputs={ 'root': self.outPath, 'mode': 'rw' }) coordList = [] # list of sky coords of all corners of all calexp for dataId in ( dict(visit=1, filter="g"), dict(visit=2, filter="g"), dict(visit=3, filter="r"), ): # TODO: pybind11 remove `immediate=True` once DM-9112 is resolved rawImage = butler.get("raw", dataId, immediate=True) # fake calexp by simply copying raw data; the task just cares about its bounding box # (which is slightly larger for raw, but that doesn't matter for this test) calexp = rawImage butler.put(calexp, "calexp", dataId) calexpWcs = calexp.getWcs() calexpBoxD = Box2D(calexp.getBBox()) coordList += [ calexpWcs.pixelToSky(corner) for corner in calexpBoxD.getCorners() ] # use the calexp to make a sky map retVal = MakeDiscreteSkyMapTask.parseAndRun( args=[self.inPath, "--output", self.outPath, "--id", "filter=g^r"], config=self.config, doReturnResults=True, ) self.assertEqual(len(retVal.resultList), 1) skyMap = retVal.resultList[0].result.skyMap self.assertEqual(type(skyMap), DiscreteSkyMap) self.assertEqual(len(skyMap), 1) tractInfo = skyMap[0] self.assertEqual(tractInfo.getId(), 0) self.assertEqual(tractInfo.getNumPatches(), Extent2I(3, 3)) tractWcs = tractInfo.getWcs() tractBoxD = Box2D(tractInfo.getBBox()) for skyPoint in coordList: self.assertTrue(tractBoxD.contains(tractWcs.skyToPixel(skyPoint)))
def makeRandomPoint(self, *args, **kwds): """Draw a random Point2D within a Box2I. All arguments are forwarded directly to the Box2I constructor, allowing the caller to pass a fully-constructed Box2I, a (Point2I, Point2I) pair, or a (Point2I, Extent2I) pair. """ bboxD = Box2D(Box2I(*args, **kwds)) return bboxD.getMin() + Extent2D(bboxD.getWidth() * self.rng.rand(), bboxD.getHeight() * self.rng.rand())
def testReadOldTanSipFits(self): """Test reading a FITS file containing data for an lsst::afw::image::TanWcs That file was made using the same metadata as this test """ dataDir = os.path.join(os.path.split(__file__)[0], "data") filePath = os.path.join(dataDir, "oldTanSipWcs.fits") wcsFromFits = SkyWcs.readFits(filePath) wcsFromMetadata = makeSkyWcs(self.metadata) bbox = Box2D(Point2D(-1000, -1000), Extent2D(3000, 3000)) self.assertWcsAlmostEqualOverBBox(wcsFromFits, wcsFromMetadata, bbox)
def extractCtorArgs(md): wcs = makeSkyWcs(makePropertyListFromDict(md)) kwds = { "pixelToIwc": getPixelToIntermediateWorldCoords(wcs), "bbox": Box2D(Box2I(Point2I(0, 0), Extent2I(md["NAXES1"], md["NAXES2"]))), "crpix": Point2D(md["CRPIX1"] - 1.0, md["CRPIX2"] - 1.0), # -1 for LSST vs. FITS conventions "cd": np.array([[md["CD1_1"], md["CD1_2"]], [md["CD2_1"], md["CD2_2"]]]), } return kwds
def __init__(self, detectorList): """!Construct a DetectorCollection @param[in] detectorList a sequence of detectors in index order """ self._idDetectorDict = dict((d.getId(), d) for d in detectorList) self._nameDetectorDict = dict((d.getName(), d) for d in detectorList) self._fpBBox = Box2D() for detector in detectorList: for corner in detector.getCorners(FOCAL_PLANE): self._fpBBox.include(corner) if len(self._idDetectorDict) < len(detectorList): raise RuntimeError("Detector IDs are not unique") if len(self._nameDetectorDict) < len(detectorList): raise RuntimeError("Detector names are not unique")
def createMatchMetadata(exposure, border=0): """Create metadata required for unpersisting a match list @param[in] exposure exposure for which to create metadata @param[in] border number of pixels by which to grow the bbox in all directions @return metadata about the field (a daf_base PropertyList) """ bboxd = Box2D(exposure.getBBox()) bboxd.grow(border) wcs = getDistortedWcs(exposure.getInfo()) ctrCoord = wcs.pixelToSky(bboxd.getCenter()).toIcrs() approxRadius = max( ctrCoord.angularSeparation(wcs.pixelToSky(pp).toIcrs()) for pp in bboxd.getCorners()) return MatchMetadata(ctrCoord, approxRadius, exposure.getFilter().getName())
def assertSkyWcsAstropyWcsAlmostEqual(self, skyWcs, astropyWcs, bbox, pixAtol=1e-4, skyAtol=1e-4 * arcseconds, checkRoundTrip=True): """Assert that a SkyWcs and the corresponding astropy.wcs.WCS agree over a specified bounding box """ bbox = Box2D(bbox) center = bbox.getCenter() xArr = bbox.getMinX(), center[0], bbox.getMaxX() yArr = bbox.getMinY(), center[1], bbox.getMaxY() pixPosList = [Point2D(x, y) for x, y in itertools.product(xArr, yArr)] # pixelToSky skyPosList = skyWcs.pixelToSky(pixPosList) astropySkyPosList = self.astropyPixelsToSky(astropyWcs=astropyWcs, pixPosList=pixPosList) self.assertSpherePointListsAlmostEqual(skyPosList, astropySkyPosList, maxSep=skyAtol) if not checkRoundTrip: return # astropy round trip astropyPixPosRoundTrip = self.astropySkyToPixels( astropyWcs=astropyWcs, skyPosList=astropySkyPosList) self.assertPairListsAlmostEqual(pixPosList, astropyPixPosRoundTrip, maxDiff=pixAtol) # SkyWcs round trip pixPosListRoundTrip = skyWcs.skyToPixel(skyPosList) self.assertPairListsAlmostEqual(pixPosList, pixPosListRoundTrip, maxDiff=pixAtol) # skyToPixel astropy vs SkyWcs astropyPixPosList2 = self.astropySkyToPixels(astropyWcs=astropyWcs, skyPosList=skyPosList) self.assertPairListsAlmostEqual(pixPosListRoundTrip, astropyPixPosList2, maxDiff=pixAtol)
def makeSkyPolygonFromBBox(bbox, wcs): """Make an on-sky polygon from a bbox and a SkyWcs Parameters ---------- bbox : `lsst.afw.geom.Box2I` or `lsst.afw.geom.Box2D` Bounding box of region, in pixel coordinates wcs : `lsst.afw.geom.SkyWcs` Celestial WCS Returns ------- polygon : `lsst.sphgeom.ConvexPolygon` On-sky region """ pixelPoints = Box2D(bbox).getCorners() skyPoints = wcs.pixelToSky(pixelPoints) return ConvexPolygon.convexHull([sp.getVector() for sp in skyPoints])
def testReadV1Catalog(self): testDir = os.path.dirname(__file__) v1CatalogPath = os.path.join( testDir, "data", "exposure_catalog_v1.fits") catV1 = lsst.afw.table.ExposureCatalog.readFits(v1CatalogPath) self.assertEqual(self.cat[0].get(self.ka), catV1[0].get(self.ka)) self.assertEqual(self.cat[0].get(self.kb), catV1[0].get(self.kb)) self.comparePsfs(self.cat[0].getPsf(), catV1[0].getPsf()) bbox = Box2D(Point2D(0, 0), Extent2D(2000, 2000)) self.assertWcsAlmostEqualOverBBox(self.cat[0].getWcs(), catV1[0].getWcs(), bbox) self.assertEqual(self.cat[1].get(self.ka), catV1[1].get(self.ka)) self.assertEqual(self.cat[1].get(self.kb), catV1[1].get(self.kb)) self.assertEqual(self.cat[1].getWcs(), catV1[1].getWcs()) self.assertIsNone(self.cat[1].getPsf()) self.assertIsNone(self.cat[1].getPhotoCalib()) self.assertEqual(self.cat[0].getPhotoCalib(), catV1[0].getPhotoCalib()) self.assertIsNone(catV1[0].getVisitInfo()) self.assertIsNone(catV1[1].getVisitInfo())
def testAgainstAstropyWcs(self): bbox = Box2D(Point2D(-1000, -1000), Extent2D(2000, 2000)) for crval, orientation, flipX, projection in itertools.product( self.crvalList, self.orientationList, (False, True), ("TAN", "STG", "CEA", "AIT")): cdMatrix = makeCdMatrix(scale=self.scale, orientation=orientation, flipX=flipX) metadata = makeSimpleWcsMetadata(crpix=self.crpix, crval=crval, cdMatrix=cdMatrix, projection=projection) header = makeLimitedFitsHeader(metadata) astropyWcs = astropy.wcs.WCS(header) skyWcs = makeSkyWcs(crpix=self.crpix, crval=crval, cdMatrix=cdMatrix, projection=projection) # Most projections only seem to agree to within 1e-4 in the round trip test self.assertSkyWcsAstropyWcsAlmostEqual(skyWcs=skyWcs, astropyWcs=astropyWcs, bbox=bbox)
def drawOnePoint(self, mask_array, dim, wcs, xy0, skyInfo): x = numpy.random.random() * (dim[0] - 1) y = numpy.random.random() * (dim[0] - 1) value = mask_array[y, x] radec = wcs.pixelToSky(x + xy0.getX(), y + xy0.getY()) xy = wcs.skyToPixel(radec) # inner patch innerFloatBBox = Box2D(skyInfo.patchInfo.getInnerBBox()) isPatchInner = innerFloatBBox.contains(xy) # inner tract sourceInnerTractId = skyInfo.skyMap.findTract(radec).getId() isTractInner = sourceInnerTractId == skyInfo.tractInfo.getId() ra = radec.getLongitude().asDegrees() dec = radec.getLatitude().asDegrees() return ra, dec, value, isPatchInner, isTractInner
def checkTanWcs(self, crval, orientation, flipX): """Construct a pure TAN SkyWcs and check that it operates as specified Parameters ---------- crval : `lsst.afw.geom.SpherePoint` Desired reference sky position. Must not be at either pole. orientation : `lsst.afw.geom.Angle` Position angle of focal plane +Y, measured from N through E. At 0 degrees, +Y is along N and +X is along E/W if flipX false/true At 90 degrees, +Y is along E and +X is along S/N if flipX false/true flipX : `bool` Flip x axis? See `orientation` for details. Returns ------- wcs : `lsst.afw.geom.SkyWcs` The generated pure TAN SkyWcs """ cdMatrix = makeCdMatrix(scale=self.scale, orientation=orientation, flipX=flipX) wcs = makeSkyWcs(crpix=self.crpix, crval=crval, cdMatrix=cdMatrix) self.checkPersistence(wcs, bbox=self.bbox) self.checkMakeFlippedWcs(wcs) self.assertTrue(wcs.isFits) self.assertEqual(wcs.isFlipped, bool(flipX)) xoffAng = 0 * degrees if flipX else 180 * degrees pixelList = [ Point2D(self.crpix[0], self.crpix[1]), Point2D(self.crpix[0] + 1, self.crpix[1]), Point2D(self.crpix[0], self.crpix[1] + 1), ] skyList = wcs.pixelToSky(pixelList) # check pixels to sky predSkyList = [ crval, crval.offset(xoffAng - orientation, self.scale), crval.offset(90 * degrees - orientation, self.scale), ] self.assertSpherePointListsAlmostEqual(predSkyList, skyList) self.assertSpherePointListsAlmostEqual(predSkyList, wcs.pixelToSky(pixelList)) for pixel, predSky in zip(pixelList, predSkyList): self.assertSpherePointsAlmostEqual(predSky, wcs.pixelToSky(pixel)) self.assertSpherePointsAlmostEqual( predSky, wcs.pixelToSky(pixel[0], pixel[1])) # check sky to pixels self.assertPairListsAlmostEqual(pixelList, wcs.skyToPixel(skyList)) self.assertPairListsAlmostEqual(pixelList, wcs.skyToPixel(skyList)) for pixel, sky in zip(pixelList, skyList): self.assertPairsAlmostEqual(pixel, wcs.skyToPixel(sky)) # self.assertPairsAlmostEqual(pixel, wcs.skyToPixel(sky[0], sky[1])) # check CRVAL round trip self.assertSpherePointsAlmostEqual(wcs.getSkyOrigin(), crval, maxSep=self.tinyAngle) crpix = wcs.getPixelOrigin() self.assertPairsAlmostEqual(crpix, self.crpix, maxDiff=self.tinyPixels) self.assertFloatsAlmostEqual(wcs.getCdMatrix(), cdMatrix) pixelScale = wcs.getPixelScale() self.assertAnglesAlmostEqual(self.scale, pixelScale, maxDiff=self.tinyAngle) pixelScale = wcs.getPixelScale(self.crpix) self.assertAnglesAlmostEqual(self.scale, pixelScale, maxDiff=self.tinyAngle) # check that getFitsMetadata can operate at high precision # and has axis order RA, Dec fitsMetadata = wcs.getFitsMetadata(True) self.assertEqual(fitsMetadata.get("CTYPE1")[0:4], "RA--") self.assertEqual(fitsMetadata.get("CTYPE2")[0:4], "DEC-") # Compute a WCS with the pixel origin shifted by an arbitrary amount # The resulting sky origin should not change offset = Extent2D(500, -322) # arbitrary shiftedWcs = wcs.copyAtShiftedPixelOrigin(offset) self.assertTrue(shiftedWcs.isFits) predShiftedPixelOrigin = self.crpix + offset self.assertPairsAlmostEqual(shiftedWcs.getPixelOrigin(), predShiftedPixelOrigin, maxDiff=self.tinyPixels) self.assertSpherePointsAlmostEqual(shiftedWcs.getSkyOrigin(), crval, maxSep=self.tinyAngle) shiftedPixelList = [p + offset for p in pixelList] shiftedSkyList = shiftedWcs.pixelToSky(shiftedPixelList) self.assertSpherePointListsAlmostEqual(skyList, shiftedSkyList, maxSep=self.tinyAngle) # Check that the shifted WCS can be round tripped as FITS metadata shiftedMetadata = shiftedWcs.getFitsMetadata(precise=True) shiftedWcsCopy = makeSkyWcs(shiftedMetadata) shiftedBBox = Box2D(predShiftedPixelOrigin, predShiftedPixelOrigin + Extent2I(2000, 2000)) self.assertWcsAlmostEqualOverBBox(shiftedWcs, shiftedWcsCopy, shiftedBBox) wcsCopy = SkyWcs.readString(wcs.writeString()) self.assertTrue(wcsCopy.isFits) return wcs
def testSampleAt(self): """Test the behavior of TransmissionCurve.sampleAt on the subclass returned by makeCoaddTransmissionCurve. """ wavelengths = np.linspace(4000, 7000, 200) # Points in coadd coordinates in each of the distinct regions point0 = self.makeRandomPoint(Point2I(-100, -100), Point2I(-1, -1)) pointA = self.makeRandomPoint(Point2I(-100, 0), Point2I(-1, 99)) pointB = self.makeRandomPoint(Point2I(0, -100), Point2I(99, -1)) pointC = self.makeRandomPoint(Point2I(0, 0), Point2I(49, 99)) pointD = self.makeRandomPoint(Point2I(50, 0), Point2I(99, 99)) points = [point0, pointA, pointB, pointC, pointD] # The same points, in sky coordinates coords = [self.wcsCoadd.pixelToSky(point) for point in points] # The same points, in Epoch A's coordinates point0A, pointAA, pointBA, pointCA, pointDA = [ self.wcsA.skyToPixel(coord) for coord in coords ] self.assertFalse(Box2D(self.bboxA).contains(point0A)) self.assertTrue(Box2D(self.bboxA).contains(pointAA)) self.assertFalse(Box2D(self.bboxA).contains(pointBA)) self.assertTrue(Box2D(self.bboxA).contains(pointCA)) self.assertTrue(Box2D(self.bboxA).contains(pointDA)) # The same points, in Epoch B's coordinates point0B, pointAB, pointBB, pointCB, pointDB = [ self.wcsB.skyToPixel(coord) for coord in coords ] self.assertFalse(Box2D(self.bboxB).contains(point0B)) self.assertFalse(Box2D(self.bboxB).contains(pointAB)) self.assertTrue(Box2D(self.bboxB).contains(pointBB)) self.assertTrue(Box2D(self.bboxB).contains(pointCB)) self.assertTrue(Box2D(self.bboxB).contains(pointDB)) self.assertTrue(self.polygonB.contains(pointBB)) self.assertTrue(self.polygonB.contains(pointCB)) self.assertFalse(self.polygonB.contains(pointDB)) # Test that we can't compute throughputs in region 0 (where there are no inputs) self.assertRaises(InvalidParameterError, self.curveCoadd.sampleAt, point0, wavelengths) # Test throughputs in region A (only Epoch A contributes) throughputA1 = self.curveCoadd.sampleAt(pointA, wavelengths) throughputA2 = self.curveA.sampleAt(pointAA, wavelengths) self.assertFloatsAlmostEqual(throughputA1, throughputA2) # Test throughputs in region B (only Epoch B contributes) throughputB1 = self.curveCoadd.sampleAt(pointB, wavelengths) throughputB2 = self.curveB.sampleAt(pointBB, wavelengths) self.assertFloatsAlmostEqual(throughputB1, throughputB2) # Test throughputs in region C (both epochs contribute) throughputC1 = self.curveCoadd.sampleAt(pointC, wavelengths) throughputC2 = self.curveA.sampleAt(pointCA, wavelengths) throughputC3 = self.curveB.sampleAt(pointCB, wavelengths) self.assertFloatsAlmostEqual(throughputC1, throughputC2 * 0.75 + throughputC3 * 0.25) # Test throughputs in region D (only Epoch A contributes) throughputD1 = self.curveCoadd.sampleAt(pointD, wavelengths) throughputD2 = self.curveA.sampleAt(pointDA, wavelengths) self.assertFloatsAlmostEqual(throughputD1, throughputD2)
def setUp(self): metadata = PropertyList() # the following was fit using CreateWcsWithSip from meas_astrom # and is valid over this bbox: (minimum=(0, 0), maximum=(3030, 3030)) # This same metadata was used to create testdata/oldTanSipwWs.fits for name, value in ( ("RADESYS", "ICRS"), ("CTYPE1", "RA---TAN-SIP"), ("CTYPE2", "DEC--TAN-SIP"), ("CRPIX1", 1531.1824767147), ("CRPIX2", 1531.1824767147), ("CRVAL1", 43.035511801383), ("CRVAL2", 44.305697682784), ("CUNIT1", "deg"), ("CUNIT2", "deg"), ("CD1_1", 0.00027493991598151), ("CD1_2", -3.2758487104158e-06), ("CD2_1", 3.2301310675830e-06), ("CD2_2", 0.00027493937506632), ("A_ORDER", 5), ("A_0_2", -1.7769487466972e-09), ("A_0_3", 5.3745894718340e-13), ("A_0_4", -7.2921116596880e-17), ("A_0_5", 8.6947236956136e-21), ("A_1_1", 5.4246387438098e-08), ("A_1_2", -1.5689083084641e-12), ("A_1_3", 1.2424130500997e-16), ("A_1_4", 3.9982572658006e-20), ("A_2_0", 4.9268299826160e-08), ("A_2_1", 1.6365657558495e-12), ("A_2_2", 1.1976983061953e-16), ("A_2_3", -1.7262037266467e-19), ("A_3_0", -5.9235031179999e-13), ("A_3_1", -3.4444326387310e-16), ("A_3_2", 1.4377441160800e-19), ("A_4_0", 1.8736407845095e-16), ("A_4_1", 2.9213314172884e-20), ("A_5_0", -5.3601346091084e-20), ("B_ORDER", 5), ("B_0_2", 4.9268299822979e-08), ("B_0_3", -5.9235032026906e-13), ("B_0_4", 1.8736407776035e-16), ("B_0_5", -5.3601341373220e-20), ("B_1_1", 5.4246387435453e-08), ("B_1_2", 1.6365657531115e-12), ("B_1_3", -3.4444326228808e-16), ("B_1_4", 2.9213312399941e-20), ("B_2_0", -1.7769487494962e-09), ("B_2_1", -1.5689082999319e-12), ("B_2_2", 1.1976983393279e-16), ("B_2_3", 1.4377441169892e-19), ("B_3_0", 5.3745894237186e-13), ("B_3_1", 1.2424130479929e-16), ("B_3_2", -1.7262036838229e-19), ("B_4_0", -7.2921117326608e-17), ("B_4_1", 3.9982566975450e-20), ("B_5_0", 8.6947240592408e-21), ("AP_ORDER", 6), ("AP_0_0", -5.4343024221207e-11), ("AP_0_1", 5.5722265946666e-12), ("AP_0_2", 1.7769484042400e-09), ("AP_0_3", -5.3773609554820e-13), ("AP_0_4", 7.3035278852156e-17), ("AP_0_5", -8.7151153799062e-21), ("AP_0_6", 3.2535945427624e-27), ("AP_1_0", -3.8944805432871e-12), ("AP_1_1", -5.4246388067582e-08), ("AP_1_2", 1.5741716194971e-12), ("AP_1_3", -1.2447067748187e-16), ("AP_1_4", -3.9960260822306e-20), ("AP_1_5", 1.1297941471380e-26), ("AP_2_0", -4.9268299293185e-08), ("AP_2_1", -1.6256111849359e-12), ("AP_2_2", -1.1973373130440e-16), ("AP_2_3", 1.7266948205700e-19), ("AP_2_4", -3.7059606160753e-26), ("AP_3_0", 5.9710911995811e-13), ("AP_3_1", 3.4464427650041e-16), ("AP_3_2", -1.4381853884204e-19), ("AP_3_3", -7.6527426974322e-27), ("AP_4_0", -1.8748435698960e-16), ("AP_4_1", -2.9267280226373e-20), ("AP_4_2", 4.8004317051259e-26), ("AP_5_0", 5.3657330221120e-20), ("AP_5_1", -1.6904065766661e-27), ("AP_6_0", -1.9484495120493e-26), ("BP_ORDER", 6), ("BP_0_0", -5.4291220607725e-11), ("BP_0_1", -3.8944871307931e-12), ("BP_0_2", -4.9268299290361e-08), ("BP_0_3", 5.9710912831833e-13), ("BP_0_4", -1.8748435594265e-16), ("BP_0_5", 5.3657325543368e-20), ("BP_0_6", -1.9484577299247e-26), ("BP_1_0", 5.5722051513577e-12), ("BP_1_1", -5.4246388065000e-08), ("BP_1_2", -1.6256111821465e-12), ("BP_1_3", 3.4464427499767e-16), ("BP_1_4", -2.9267278448109e-20), ("BP_1_5", -1.6904244067295e-27), ("BP_2_0", 1.7769484069376e-09), ("BP_2_1", 1.5741716110182e-12), ("BP_2_2", -1.1973373446176e-16), ("BP_2_3", -1.4381853893526e-19), ("BP_2_4", 4.8004294492911e-26), ("BP_3_0", -5.3773609074713e-13), ("BP_3_1", -1.2447067726801e-16), ("BP_3_2", 1.7266947774875e-19), ("BP_3_3", -7.6527556667042e-27), ("BP_4_0", 7.3035279660505e-17), ("BP_4_1", -3.9960255158200e-20), ("BP_4_2", -3.7059659675039e-26), ("BP_5_0", -8.7151157361284e-21), ("BP_5_1", 1.1297944388060e-26), ("BP_6_0", 3.2535788867488e-27), ): metadata.set(name, value) self.metadata = metadata self.bbox = Box2D(Point2D(-1000, -1000), Extent2D(3000, 3000))