def offsetFocalFieldAngle(self, pupilOffset=None, focalFieldAngleOffset=None, beam=None): """Offset the focal plane field angle and/or pupil position of a beam. Compute new telescope, camera rotator and CBP positions and thus update beam info. Parameters ---------- pupilOffset : pair of `float` (optional) Offset of the position of the specified beam on the :ref:`telescope pupil <lsst.cbp.pupil_position>` (x, y mm); defaults to (0, 0). focalFieldAngleOffset : pair of `float` (optional) Offset of the :ref:`focal plane field angle <lsst.cbp.focal_plane_field_angle>` of the specified beam (x, y mm); defaults to (0, 0). beam : `int` or `str` (optional) Name or index of beam; defaults to self.maskInfo.defaultBeam. """ beamInfo = self[beam] if pupilOffset is None: pupilOffset = (0, 0) pupilOffset = Extent2D(*pupilOffset) if focalFieldAngleOffset is None: focalFieldAngleOffset = (0, 0) focalFieldAngleOffset = Extent2D(*focalFieldAngleOffset) newPupilPos = beamInfo.pupilPos + pupilOffset newFocalFieldAngle = beamInfo.focalFieldAngle + focalFieldAngleOffset self.setFocalFieldAngle(pupilPos=newPupilPos, focalFieldAngle=newFocalFieldAngle, beam=beam)
def test_Box2D_repr(self): from lsst.geom import Box2D, Point2D, Extent2D print(repr(Box2D())) self.assertEqual(eval(repr(Box2D())), Box2D()) self.assertEqual( eval(repr(Box2D(Point2D(1.0, 2.0), Extent2D(3.0, 4.0)))), Box2D(Point2D(1.0, 2.0), Extent2D(3.0, 4.0)))
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 __init__(self, config, maskInfo, cameraGeom): self.config = config self.maskInfo = maskInfo self.cameraGeom = cameraGeom self._fieldAngleToFocalPlane = cameraGeom.getTransform( FIELD_ANGLE, FOCAL_PLANE) # amount to add to default hole position to compute telescope rotator angle (pixels); # I found that a wide range of values works, with (1, 0) comfortably in that range self._holeDelta = Extent2D(1, 0) self._telAzAlt = SpherePoint(np.nan, np.nan, radians) self._telRot = np.nan * radians self._cbpAzAlt = SpherePoint(np.nan, np.nan, radians)
def offsetDetectorPos(self, pupilOffset=None, detectorOffset=None, beam=None): """Offset the detector position and/or pupil position of a beam. Compute new telescope, camera rotator and CBP positions and thus update beam info. Parameters ---------- pupilOffset : pair of `float` (optional) Offset of the position of the specified beam on the :ref:`telescope pupil <lsst.cbp.pupil_position>` (x, y mm); defaults to (0, 0). detectorOffset : pair of `float` (optional) Offset of the position of the specified spot on the detector it is presently on (x, y pixels); defaults to (0, 0). beam : `int` or `str` (optional) Name or index of beam; defaults to self.maskInfo.defaultBeam. """ beamInfo = self[beam] if not beamInfo.isOnDetector: raise RuntimeError("This beam is not on a detector") if pupilOffset is None: pupilOffset = (0, 0) pupilOffset = Extent2D(*pupilOffset) if detectorOffset is None: detectorOffset = (0, 0) detectorOffset = Extent2D(*detectorOffset) newPupilPos = beamInfo.pupilPos + pupilOffset newDetectorPos = beamInfo.detectorPos + detectorOffset self.setDetectorPos(pupilPos=newPupilPos, detectorPos=newDetectorPos, detector=beamInfo.detectorName, beam=beam)
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 _computeCameraRotatorAngle(self, telAzAlt, cbpAzAlt): """Compute the internal camera rotator angle needed for a given telescope and CBP pointing. Parameters ---------- telAzAlt : `lsst.geom.SpherePoint` Telescope internal azimuth and altitude. cbpAzAlt : `lsst.geom.SpherePoint` CBP internal azimuth and altitude. Returns ------- rotatorAangle : `lsst.geom.Angle` Internal camera rotator angle. """ # Compute focal plane position, ignoring self._telRot, # for two holes separated by x in the CBP equidistant from the center. # Compute the angle that would make the spots line up # with the x axis in the focal plane. ctrHolePos = Point2D(0, 0) holeDelta = Extent2D(*coordUtils.getFlippedPos( self._holeDelta, flipX=self.config.cbpFlipX)) holePos1 = ctrHolePos - holeDelta holePos2 = ctrHolePos + holeDelta pupilUnitVector1 = self._computeTelPupilUnitVectorFromHolePos( holePos1, telAzAlt=telAzAlt, cbpAzAlt=cbpAzAlt) pupilUnitVector2 = self._computeTelPupilUnitVectorFromHolePos( holePos2, telAzAlt=telAzAlt, cbpAzAlt=cbpAzAlt) # Rotation is done in a right-handed system, regardless of telFlipX pupilFieldAngle1 = coordUtils.vectorToFieldAngle(pupilUnitVector1, flipX=False) pupilFieldAngle2 = coordUtils.vectorToFieldAngle(pupilUnitVector2, flipX=False) focalPlane1 = self._fieldAngleToFocalPlane.applyForward( Point2D(*pupilFieldAngle1)) focalPlane2 = self._fieldAngleToFocalPlane.applyForward( Point2D(*pupilFieldAngle2)) deltaFocalPlane = np.subtract(focalPlane2, focalPlane1) return -math.atan2(deltaFocalPlane[1], deltaFocalPlane[0]) * radians
def setUp(self): np.random.seed(6) matrix = np.random.randn(2, 2) vector = np.random.randn(2) self.transform = AffineTransform(LinearTransform(matrix), Extent2D(vector))
def setUp(self): """Constructs a CCD with two amplifiers and prepares for ISR""" np.random.seed(12345) baseValue = 100.0 gain = 1.0 readNoise = 123456789.0 saturation = 987654321.0 height = 234 imageSize = Extent2I(123, height) overscanSize = Extent2I(16, height) self.sigma = 1.234 # Set up the various regions overscan1 = Box2I(Point2I(0, 0), overscanSize) image1 = Box2I(Point2I(overscanSize[0], 0), imageSize) image2 = Box2I(Point2I(overscanSize[0] + imageSize[0], 0), imageSize) overscan2 = Box2I(Point2I(overscanSize[0] + 2 * imageSize[0], 0), overscanSize) leftBox = Box2I( overscan1.getMin(), Extent2I(overscan1.getWidth() + image1.getWidth(), height)) rightBox = Box2I( image2.getMin(), Extent2I(image2.getWidth() + overscan2.getWidth(), height)) target1 = Box2I(Point2I(0, 0), imageSize) target2 = Box2I(Point2I(image1.getWidth(), 0), imageSize) # Set the pixels exposure = ExposureF( Box2I(Point2I(0, 0), Extent2I(imageSize[0] * 2 + overscanSize[0] * 2, height))) yy = np.arange(0, height, 1, dtype=np.float32) leftImage = ExposureF(exposure, leftBox) leftImage.image.array[:] = baseValue + yy[:, np.newaxis] rightImage = ExposureF(exposure, rightBox) rightImage.image.array[:] = baseValue - yy[:, np.newaxis] leftOverscan = ExposureF(exposure, overscan1) leftOverscan.image.array += np.random.normal( 0.0, self.sigma, leftOverscan.image.array.shape) rightOverscan = ExposureF(exposure, overscan2) rightOverscan.image.array += np.random.normal( 0.0, self.sigma, leftOverscan.image.array.shape) exposure.mask.array[:] = 0.0 exposure.variance.array[:] = np.nan # Construct the detectors amp1 = makeAmplifier("left", target1, image1, overscan1, gain, readNoise, saturation) amp2 = makeAmplifier("right", target2, image2, overscan2, gain, readNoise, saturation) ccdBox = Box2I(Point2I(0, 0), Extent2I(image1.getWidth() + image2.getWidth(), height)) camBuilder = cameraGeom.Camera.Builder("fakeCam") detBuilder = camBuilder.add("detector", 1) detBuilder.setSerial("det1") detBuilder.setBBox(ccdBox) detBuilder.setPixelSize(Extent2D(1.0, 1.0)) detBuilder.setOrientation(cameraGeom.Orientation()) detBuilder.append(amp1) detBuilder.append(amp2) cam = camBuilder.finish() exposure.setDetector(cam.get('detector')) header = PropertyList() header.add("EXPTIME", 0.0) exposure.getInfo().setVisitInfo(VisitInfo(header)) self.exposure = exposure self.config = IsrTask.ConfigClass() # Disable everything we don't care about self.config.doBias = False self.config.doDark = False self.config.doFlat = False self.config.doFringe = False self.config.doDefect = False self.config.doWrite = False self.config.expectWcs = False self.config.doLinearize = False self.config.doCrosstalk = False self.config.doBrighterFatter = False self.config.doAttachTransmissionCurve = False self.config.doAssembleCcd = False self.config.doNanMasking = False self.config.doInterpolate = False self.config.maskNegativeVariance = False # This runs on mocks. # Set the things that match our test setup self.config.overscan.fitType = "CHEB" self.config.overscan.order = 1 self.config.doEmpiricalReadNoise = True self.task = IsrTask(config=self.config)