23 Support for displaying cameraGeom objects.
26 __all__ = [
'prepareWcsData',
'plotFocalPlane',
'makeImageFromAmp',
'calcRawCcdBBox',
'makeImageFromCcd',
27 'FakeImageDataSource',
'ButlerImage',
'rawCallback',
'overlayCcdBoxes',
28 'showAmp',
'showCcd',
'getCcdInCamBBoxList',
'getCameraImageBBox',
29 'makeImageFromCamera',
'showCamera',
'makeFocalPlaneWcs',
'findAmp']
44 from ._rotateBBoxBy90
import rotateBBoxBy90
45 from ._assembleImage
import assembleAmplifierImage, assembleAmplifierRawImage
46 from ._cameraGeom
import FIELD_ANGLE, FOCAL_PLANE
57 """Put Wcs from an Amp image into CCD coordinates
61 wcs : `lsst.afw.geom.SkyWcs`
62 The WCS object to start from.
63 amp : `lsst.afw.table.AmpInfoRecord`
66 Is the image to which the WCS refers trimmed of non-imaging pixels?
70 ampWcs : `lsst.afw.geom.SkyWcs`
74 ampBox = amp.getRawDataBBox()
76 ampBox = amp.getRawBBox()
81 trim_shift = ampBox.getMin() - amp.getBBox().getMin()
82 wcs = wcs.copyAtShiftedPixelOrigin(
lsst.geom.Extent2D(-trim_shift.getX(), -trim_shift.getY()))
84 offset = amp.getRawXYOffset()
88 def plotFocalPlane(camera, fieldSizeDeg_x=0, fieldSizeDeg_y=None, dx=0.1, dy=0.1, figsize=(10., 10.),
89 useIds=
False, showFig=
True, savePath=
None):
90 """Make a plot of the focal plane along with a set points that sample
95 camera : `lsst.afw.cameraGeom.Camera`
97 fieldSizeDeg_x : `float`
98 Amount of the field to sample in x in degrees
99 fieldSizeDeg_y : `float` or `None`
100 Amount of the field to sample in y in degrees
102 Spacing of sample points in x in degrees
104 Spacing of sample points in y in degrees
105 figsize : `tuple` containing two `float`
106 Matplotlib style tuple indicating the size of the figure in inches
108 Label detectors by name, not id?
110 Display the figure on the screen?
111 savePath : `str` or `None`
112 If not `None`, save a copy of the figure to this name.
115 from matplotlib.patches
import Polygon
116 from matplotlib.collections
import PatchCollection
117 import matplotlib.pyplot
as plt
120 "Can't run plotFocalPlane: matplotlib has not been set up")
123 if fieldSizeDeg_y
is None:
124 fieldSizeDeg_y = fieldSizeDeg_x
126 field_gridx, field_gridy = numpy.meshgrid(
127 numpy.arange(0., fieldSizeDeg_x + dx, dx) - fieldSizeDeg_x/2.,
128 numpy.arange(0., fieldSizeDeg_y + dy, dy) - fieldSizeDeg_y/2.)
129 field_gridx, field_gridy = field_gridx.flatten(), field_gridy.flatten()
131 field_gridx, field_gridy = [], []
139 for x, y
in zip(field_gridx, field_gridy)]
140 posFocalPlaneList = camera.transform(posFieldAngleList, FIELD_ANGLE, FOCAL_PLANE)
141 for posFocalPlane
in posFocalPlaneList:
142 xs.append(posFocalPlane.getX())
143 ys.append(posFocalPlane.getY())
144 dets = camera.findDetectors(posFocalPlane, FOCAL_PLANE)
150 colorMap = {DetectorType.SCIENCE:
'b', DetectorType.FOCUS:
'y',
151 DetectorType.GUIDER:
'g', DetectorType.WAVEFRONT:
'r'}
155 plt.figure(figsize=figsize)
160 corners = [(c.getX(), c.getY())
for c
in det.getCorners(FOCAL_PLANE)]
161 for corner
in corners:
162 xvals.append(corner[0])
163 yvals.append(corner[1])
164 colors.append(colorMap[det.getType()])
165 patches.append(Polygon(corners,
True))
166 center = det.getOrientation().getFpPosition()
167 ax.text(center.getX(), center.getY(), det.getId()
if useIds
else det.getName(),
168 horizontalalignment=
'center', size=6)
170 patchCollection = PatchCollection(patches, alpha=0.6, facecolor=colors)
171 ax.add_collection(patchCollection)
172 ax.scatter(xs, ys, s=10, alpha=.7, linewidths=0., c=pcolors)
173 ax.set_xlim(
min(xvals) -
abs(0.1*
min(xvals)),
175 ax.set_ylim(
min(yvals) -
abs(0.1*
min(yvals)),
177 ax.set_xlabel(
'Focal Plane X (mm)')
178 ax.set_ylabel(
'Focal Plane Y (mm)')
179 if savePath
is not None:
180 plt.savefig(savePath)
185 def makeImageFromAmp(amp, imValue=None, imageFactory=afwImage.ImageU, markSize=10, markValue=0,
186 scaleGain=lambda gain: (gain*1000)//10):
187 """Make an image from an amp object.
189 Since images are integer images by default, the gain needs to be scaled to
190 give enough dynamic range to see variation from amp to amp.
191 The scaling algorithm is assignable.
195 amp : `lsst.afw.table.AmpInfoRecord`
196 Amp record to use for constructing the raw amp image.
197 imValue : `float` or `None`
198 Value to assign to the constructed image, or scaleGain(gain) if `None`.
199 imageFactory : callable like `lsst.afw.image.Image`
200 Type of image to construct.
202 Size of mark at read corner in pixels.
204 Value of pixels in the read corner mark.
206 The function by which to scale the gain (must take a single argument).
210 ampImage : `lsst.afw.image`
211 An untrimmed amp image, of the type produced by ``imageFactory``.
213 bbox = amp.getRawBBox()
214 dbbox = amp.getRawDataBBox()
215 img = imageFactory(bbox)
217 img.set(int(scaleGain(amp.getGain())))
222 if amp.getReadoutCorner() == afwCameraGeom.ReadoutCorner.LL:
223 markbbox.include(dbbox.getMin())
225 elif amp.getReadoutCorner() == afwCameraGeom.ReadoutCorner.LR:
227 markbbox.include(cornerPoint)
229 elif amp.getReadoutCorner() == afwCameraGeom.ReadoutCorner.UR:
231 markbbox.include(cornerPoint)
233 elif amp.getReadoutCorner() == afwCameraGeom.ReadoutCorner.UL:
235 markbbox.include(cornerPoint)
238 raise RuntimeError(
"Could not set readout corner")
239 mimg = imageFactory(img, markbbox)
245 """Calculate the raw ccd bounding box.
249 ccd : `lsst.afw.cameraGeom.Detector`
250 Detector for which to calculate the un-trimmed bounding box.
254 bbox : `lsst.geom.Box2I` or `None`
255 Bounding box of the un-trimmed Detector, or `None` if there is not enough
256 information to calculate raw BBox.
260 tbbox = amp.getRawBBox()
261 tbbox.shift(amp.getRawXYOffset())
266 def makeImageFromCcd(ccd, isTrimmed=True, showAmpGain=True, imageFactory=afwImage.ImageU, rcMarkSize=10,
268 """Make an Image of a CCD.
272 ccd : `lsst.afw.cameraGeom.Detector`
273 Detector to use in making the image.
275 Assemble a trimmed Detector image.
277 Use the per-amp gain to color the pixels in the image?
278 imageFactory : callable like `lsst.afw.image.Image`
279 Image type to generate.
281 Size of the mark to make in the amp images at the read corner.
283 Bin the image by this factor in both dimensions.
287 image : `lsst.afw.image.Image`
288 Image of the Detector (type returned by ``imageFactory``).
299 amp, imageFactory=imageFactory, markSize=rcMarkSize))
302 imageFactory=imageFactory, markSize=rcMarkSize))
305 if len(ampImages) > 0:
306 ccdImage = imageFactory(bbox)
307 for ampImage, amp
in zip(ampImages, ccd):
315 "Cannot create untrimmed CCD without amps with raw information")
316 ccdImage = imageFactory(ccd.getBBox())
322 """A class to retrieve synthetic images for display by the show* methods
327 Should amps be trimmed?
331 The value of any pixels that lie outside the CCDs.
333 Color the amp segments with the gain of the amp?
335 Size of the side of the box used to mark the read corner.
337 Value to assign the read corner mark.
338 ampImValue : `float` or `None`
339 Value to assign to amps; scaleGain(gain) is used if `None`.
341 Function to scale the gain by.
343 def __init__(self, isTrimmed=True, verbose=False, background=numpy.nan,
344 showAmpGain=True, markSize=10, markValue=0,
345 ampImValue=None, scaleGain=lambda gain: (gain*1000)//10):
356 """Return a CCD image for the detector and the (possibly updated) Detector.
360 det : `lsst.afw.cameraGeom.Detector`
361 Detector to use for making the image.
362 imageFactory : callable like `lsst.afw.image.Image`
363 Image constructor for making the image.
365 Bin the image by this factor in both dimensions.
369 ccdImage : `lsst.afw.image.Image`
370 The constructed image.
373 imageFactory=imageFactory, binSize=binSize)
377 """Return an amp segment image.
381 amp : `lsst.afw.table.AmpInfoTable`
382 AmpInfoTable for this amp.
383 imageFactory : callable like `lsst.afw.image.Image`
384 Image constructor for making the image.
388 ampImage : `lsst.afw.image.Image`
389 The constructed image.
395 ampImage = ampImage.Factory(ampImage, amp.getRawDataBBox())
400 """A class to return an Image of a given Ccd using the butler.
404 butler : `lsst.daf.persistence.Butler` or `None`
405 The butler to use. If `None`, an empty image is returned.
407 The type of image to read (e.g. raw, bias, flat, calexp).
409 If true, the showCamera command expects to be given trimmed images.
411 Be chatty (in particular, log any error messages from the butler)?
413 The value of any pixels that lie outside the CCDs.
415 A function called with (image, ccd, butler) for every image, which
416 returns the image to be displayed (e.g. rawCallback). The image must
417 be of the correct size, allowing for the value of isTrimmed.
419 Passed to the butler.
421 Passed to the butler.
425 You can define a short named function as a callback::
427 def callback(im, ccd, imageSource):
428 return cameraGeom.utils.rawCallback(im, ccd, imageSource, correctGain=True)
431 isTrimmed=True, verbose=False, background=numpy.nan,
432 callback=None, *args, **kwargs):
433 super(ButlerImage, self).
__init__(*args)
443 def _prepareImage(self, ccd, im, binSize, allowRotate=True):
449 im, ccd.getOrientation().getNQuarter())
453 def getCcdImage(self, ccd, imageFactory=afwImage.ImageF, binSize=1, asMaskedImage=False):
454 """Return an image of the specified ccd, and also the (possibly updated) ccd"""
456 log = _LOG.getChild(
"ButlerImage")
464 if self.
butlerbutler
is not None:
466 for dataId
in [dict(detector=ccd.getId()), dict(ccd=ccd.getId()), dict(ccd=ccd.getName())]:
469 except FitsError
as e:
470 err = IOError(e.args[0].split(
'\n')[0])
472 except Exception
as e:
477 ccd = im.getDetector()
482 im = im.getMaskedImage()
484 im = im.getMaskedImage().getImage()
488 print(f
"Reading {ccd.getId()}: {err}")
490 log.warning(
"Reading %s: %s", ccd.getId(), err)
493 return self.
_prepareImage_prepareImage(ccd, imageFactory(*bbox.getDimensions()), binSize), ccd
495 if self.
typetype ==
"raw":
496 if hasattr(im,
'convertF'):
498 if False and self.
callbackcallback
is None:
504 im = self.
callbackcallback(im, ccd, imageSource=self)
505 except Exception
as e:
507 log.error(
"callback failed: %s", e)
508 im = imageFactory(*bbox.getDimensions())
512 return self.
_prepareImage_prepareImage(ccd, im, binSize, allowRotate=allowRotate), ccd
516 correctGain=False, subtractBias=False, convertToFloat=False, obeyNQuarter=True):
517 """A callback function that may or may not subtract bias/correct gain/trim
522 im : `lsst.afw.image.Image` or `lsst.afw.image.MaskedImage` or `lsst.afw.image.Exposure`
523 An image of a chip, ready to be binned and maybe rotated.
524 ccd : `lsst.afw.cameraGeom.Detector` or `None`
525 The Detector; if `None` assume that im is an exposure and extract its Detector.
526 imageSource : `FakeImageDataSource` or `None`
527 Source to get ccd images. Must have a `getCcdImage()` method.
529 Correct each amplifier for its gain?
530 subtractBias : `bool`
531 Subtract the bias from each amplifier?
532 convertToFloat : `bool`
533 Convert ``im`` to floating point if possible.
534 obeyNQuarter : `bool`
535 Obey nQuarter from the Detector (default: True)
539 image : `lsst.afw.image.Image` like
540 The constructed image (type returned by ``im.Factory``).
544 If imageSource is derived from ButlerImage, imageSource.butler is available.
547 ccd = im.getDetector()
548 if hasattr(im,
"getMaskedImage"):
549 im = im.getMaskedImage()
550 if convertToFloat
and hasattr(im,
"convertF"):
553 isTrimmed = imageSource.isTrimmed
562 data = im[a.getRawDataBBox()]
567 bias = im[a.getRawHorizontalOverscanBBox()]
572 ampImages.append(data)
574 ccdImage = im.Factory(bbox)
575 for ampImage, amp
in zip(ampImages, ccd):
582 nQuarter = ccd.getOrientation().getNQuarter()
589 isTrimmed=False, ccdOrigin=(0, 0), display=
None, binSize=1):
590 """Overlay bounding boxes on an image display.
594 ccd : `lsst.afw.cameraGeom.Detector`
595 Detector to iterate for the amp bounding boxes.
596 untrimmedCcdBbox : `lsst.geom.Box2I` or `None`
597 Bounding box of the un-trimmed Detector.
599 number of 90 degree rotations to apply to the bounding boxes (used for rotated chips).
601 Is the Detector image over which the boxes are layed trimmed?
602 ccdOrigin : `tuple` of `float`
603 Detector origin relative to the parent origin if in a larger pixel grid.
604 display : `lsst.afw.display.Display`
605 Image display to display on.
607 Bin the image by this factor in both dimensions.
612 - Entire detector GREEN
613 - All data for amp GREEN
614 - HorizontalPrescan YELLOW
615 - HorizontalOverscan RED
617 - VerticalOverscan MAGENTA
618 - VerticalOverscan MAGENTA
621 raise RuntimeError(
"Please specify a display")
623 if untrimmedCcdBbox
is None:
625 untrimmedCcdBbox = ccd.getBBox()
628 for a
in ccd.getAmplifiers():
629 bbox = a.getRawBBox()
630 untrimmedCcdBbox.include(bbox)
632 with display.Buffering():
633 ccdDim = untrimmedCcdBbox.getDimensions()
637 ampbbox = amp.getBBox()
639 ampbbox = amp.getRawBBox()
643 displayUtils.drawBBox(ampbbox, origin=ccdOrigin, borderWidth=0.49,
644 display=display, bin=binSize)
647 for bbox, ctype
in ((amp.getRawHorizontalOverscanBBox(), afwDisplay.RED),
648 (amp.getRawDataBBox(), afwDisplay.BLUE),
649 (amp.getRawVerticalOverscanBBox(),
651 (amp.getRawPrescanBBox(), afwDisplay.YELLOW)):
654 displayUtils.drawBBox(bbox, origin=ccdOrigin, borderWidth=0.49, ctype=ctype,
655 display=display, bin=binSize)
657 xc, yc = ((ampbbox.getMin()[0] + ampbbox.getMax()[0])//2,
658 (ampbbox.getMin()[1] + ampbbox.getMax()[1])//2)
671 ccdHeight = ccdBbox.getHeight()
672 ccdWidth = ccdBbox.getWidth()
676 xc, yc = 0.5*ccdHeight + c*xc + s*yc, 0.5*ccdWidth + -s*xc + c*yc
681 display.dot(str(amp.getName()), xc/binSize,
682 yc/binSize, textAngle=nQuarter*90)
684 displayUtils.drawBBox(ccdBbox, origin=ccdOrigin,
685 borderWidth=0.49, ctype=afwDisplay.MAGENTA, display=display, bin=binSize)
688 def showAmp(amp, imageSource=FakeImageDataSource(isTrimmed=
False), display=
None, overlay=
True,
689 imageFactory=afwImage.ImageU):
690 """Show an amp in an image display.
694 amp : `lsst.afw.tables.AmpInfoRecord`
695 Amp record to use in display.
696 imageSource : `FakeImageDataSource` or `None`
697 Source for getting the amp image. Must have a ``getAmpImage()`` method.
698 display : `lsst.afw.display.Display`
699 Image display to use.
701 Overlay bounding boxes?
702 imageFactory : callable like `lsst.afw.image.Image`
703 Type of image to display (only used if ampImage is `None`).
706 display = _getDisplayFromDisplayOrFrame(display)
708 ampImage = imageSource.getAmpImage(amp, imageFactory=imageFactory)
709 ampImSize = ampImage.getDimensions()
710 title = amp.getName()
711 display.mtv(ampImage, title=title)
713 with display.Buffering():
714 if ampImSize == amp.getRawBBox().getDimensions():
715 bboxes = [(amp.getRawBBox(), 0.49, afwDisplay.GREEN), ]
716 xy0 = bboxes[0][0].getMin()
718 (amp.getRawHorizontalOverscanBBox(), 0.49, afwDisplay.RED))
719 bboxes.append((amp.getRawDataBBox(), 0.49, afwDisplay.BLUE))
720 bboxes.append((amp.getRawPrescanBBox(),
721 0.49, afwDisplay.YELLOW))
722 bboxes.append((amp.getRawVerticalOverscanBBox(),
723 0.49, afwDisplay.MAGENTA))
725 bboxes = [(amp.getBBox(), 0.49,
None), ]
726 xy0 = bboxes[0][0].getMin()
728 for bbox, borderWidth, ctype
in bboxes:
733 displayUtils.drawBBox(
734 bbox, borderWidth=borderWidth, ctype=ctype, display=display)
737 def showCcd(ccd, imageSource=FakeImageDataSource(), display=
None, overlay=
True,
738 imageFactory=afwImage.ImageF, binSize=1, inCameraCoords=
False):
739 """Show a CCD on display.
743 ccd : `lsst.afw.cameraGeom.Detector`
744 Detector to use in display.
745 imageSource : `FakeImageDataSource` or `None`
746 Source to get ccd images. Must have a ``getCcdImage()`` method.
747 display : `lsst.afw.display.Display`
748 image display to use.
750 Show amp bounding boxes on the displayed image?
751 imageFactory : callable like `lsst.afw.image.Image`
752 The image factory to use in generating the images.
754 Bin the image by this factor in both dimensions.
755 inCameraCoords : `bool`
756 Show the Detector in camera coordinates?
758 display = _getDisplayFromDisplayOrFrame(display)
762 ccdImage, ccd = imageSource.getCcdImage(
763 ccd, imageFactory=imageFactory, binSize=binSize)
765 ccdBbox = ccdImage.getBBox()
766 if ccdBbox.getDimensions() == ccd.getBBox().getDimensions():
772 nQuarter = ccd.getOrientation().getNQuarter()
774 title = ccd.getName()
779 display.mtv(ccdImage, title=title)
783 ccdOrigin, display, binSize)
789 """Get the bounding boxes of a list of Detectors within a camera sized pixel grid
793 ccdList : `lsst.afw.cameraGeom.Detector`
796 Bin the image by this factor in both dimensions.
797 pixelSize_o : `float`
798 Size of the pixel in mm.
800 Origin of the camera pixel grid in pixels.
804 boxList : `list` [`lsst.geom.Box2I`]
805 A list of bounding boxes in camera pixel coordinates.
809 if not pixelSize_o == ccd.getPixelSize():
811 "Cameras with detectors with different pixel scales are not currently supported")
814 for corner
in ccd.getCorners(FOCAL_PLANE):
815 dbbox.include(corner)
817 nQuarter = ccd.getOrientation().getNQuarter()
818 cbbox = ccd.getBBox()
819 ex = cbbox.getDimensions().getX()//binSize
820 ey = cbbox.getDimensions().getY()//binSize
825 int(llc.getY()//pixelSize_o.getY()/binSize)))
827 -int(origin.getY())//binSize))
833 """Get the bounding box of a camera sized image in pixels
837 camBbox : `lsst.geom.Box2D`
838 Camera bounding box in focal plane coordinates (mm).
840 Size of a detector pixel in mm.
842 Buffer around edge of image in pixels.
846 box : `lsst.geom.Box2I`
847 The resulting bounding box.
850 int(camBbox.getMinY()//pixelSize.getY()))
852 int(camBbox.getMaxY()//pixelSize.getY()))
854 retBox.grow(bufferSize)
859 imageSource=FakeImageDataSource(), imageFactory=afwImage.ImageU, binSize=1):
860 """Make an Image of a Camera.
862 Put each detector's image in the correct location and orientation on the
863 focal plane. The input images can be binned to an integer fraction of their
868 camera : `lsst.afw.cameraGeom.Camera`
869 Camera object to use to make the image.
870 detectorNameList : `list` [`str`]
871 List of detector names from ``camera`` to use in building the image.
872 Use all Detectors if `None`.
874 Value to use where there is no Detector.
876 Size of border in binned pixels to make around the camera image.
877 imageSource : `FakeImageDataSource` or `None`
878 Source to get ccd images. Must have a ``getCcdImage()`` method.
879 imageFactory : callable like `lsst.afw.image.Image`
880 Type of image to build.
882 Bin the image by this factor in both dimensions.
886 image : `lsst.afw.image.Image`
887 Image of the entire camera.
889 log = _LOG.getChild(
"makeImageFromCamera")
891 if detectorNameList
is None:
894 ccdList = [camera[name]
for name
in detectorNameList]
896 if detectorNameList
is None:
897 camBbox = camera.getFpBBox()
900 for detName
in detectorNameList:
901 for corner
in camera[detName].getCorners(FOCAL_PLANE):
902 camBbox.include(corner)
904 pixelSize_o = camera[
next(camera.getNameIter())].getPixelSize()
906 origin = camBbox.getMin()
908 camIm = imageFactory(int(math.ceil(camBbox.getDimensions().getX()/binSize)),
909 int(math.ceil(camBbox.getDimensions().getY()/binSize)))
910 camIm[:] = imageSource.background
912 assert imageSource.isTrimmed,
"isTrimmed is False isn't supported by getCcdInCamBBoxList"
915 for det, bbox
in zip(ccdList, boxList):
916 im = imageSource.getCcdImage(det, imageFactory, binSize)[0]
920 imView = camIm.Factory(camIm, bbox, afwImage.LOCAL)
924 log.error(
"Unable to fit image for detector \"%s\" into image of camera: %s",
930 def showCamera(camera, imageSource=FakeImageDataSource(), imageFactory=afwImage.ImageF,
931 detectorNameList=
None, binSize=10, bufferSize=10, overlay=
True, title=
"",
932 showWcs=
None, ctype=afwDisplay.GREEN, textSize=1.25, originAtCenter=
True, display=
None,
934 """Show a Camera on display, with the specified display.
936 The rotation of the sensors is snapped to the nearest multiple of 90 deg.
937 Also note that the pixel size is constant over the image array. The lower
938 left corner (LLC) of each sensor amp is snapped to the LLC of the pixel
939 containing the LLC of the image.
943 camera : `lsst.afw.cameraGeom.Camera`
944 Camera object to use to make the image.
945 imageSource : `FakeImageDataSource` or `None`
946 Source to get ccd images. Must have a ``getCcdImage()`` method.
947 imageFactory : `lsst.afw.image.Image`
948 Type of image to make
949 detectorNameList : `list` [`str`] or `None`
950 List of detector names from `camera` to use in building the image.
951 Use all Detectors if `None`.
953 Bin the image by this factor in both dimensions.
955 Size of border in binned pixels to make around the camera image.
957 Overlay Detector IDs and boundaries?
959 Title to use in display.
961 Include a WCS in the display?
962 ctype : `lsst.afw.display.COLOR` or `str`
963 Color to use when drawing Detector boundaries.
965 Size of detector labels
966 originAtCenter : `bool`
967 Put origin of the camera WCS at the center of the image?
968 If `False`, the origin will be at the lower left.
969 display : `lsst.afw.display`
970 Image display on which to display.
972 All remaining keyword arguments are passed to makeImageFromCamera
976 image : `lsst.afw.image.Image`
979 display = _getDisplayFromDisplayOrFrame(display)
983 cameraImage =
makeImageFromCamera(camera, detectorNameList=detectorNameList, bufferSize=bufferSize,
984 imageSource=imageSource, imageFactory=imageFactory, binSize=binSize,
987 if detectorNameList
is None:
988 ccdList = [camera[name]
for name
in camera.getNameIter()]
990 ccdList = [camera[name]
for name
in detectorNameList]
992 if detectorNameList
is None:
993 camBbox = camera.getFpBBox()
996 for detName
in detectorNameList:
997 for corner
in camera[detName].getCorners(FOCAL_PLANE):
998 camBbox.include(corner)
999 pixelSize = ccdList[0].getPixelSize()
1004 cameraImage.getBBox()).getCenter()
1013 title = camera.getName()
1014 display.mtv(cameraImage, title=title, wcs=wcs)
1017 with display.Buffering():
1019 camBbox, pixelSize, bufferSize*binSize)
1021 ccdList, binSize, pixelSize, camBbox.getMin())
1022 for bbox, ccd
in zip(bboxList, ccdList):
1023 nQuarter = ccd.getOrientation().getNQuarter()
1026 displayUtils.drawBBox(
1027 bbox, borderWidth=0.5, ctype=ctype, display=display)
1028 dims = bbox.getDimensions()
1029 display.dot(ccd.getName(), bbox.getMinX() + dims.getX()/2, bbox.getMinY() + dims.getY()/2,
1030 ctype=ctype, size=textSize, textAngle=nQuarter*90)
1036 """Make a WCS for the focal plane geometry
1037 (i.e. one that returns positions in "mm")
1042 Size of the image pixels in physical units
1043 referencePixel : `lsst.geom.Point2D`
1044 Pixel for origin of WCS
1049 Wcs object for mapping between pixels and focal plane.
1052 if referencePixel
is None:
1055 md.set(
"CRPIX%d"%(i + 1), referencePixel[i])
1056 md.set(
"CRVAL%d"%(i + 1), 0.)
1057 md.set(
"CDELT1", pixelSize[0])
1058 md.set(
"CDELT2", pixelSize[1])
1059 md.set(
"CTYPE1",
"CAMERA_X")
1060 md.set(
"CTYPE2",
"CAMERA_Y")
1061 md.set(
"CUNIT1",
"mm")
1062 md.set(
"CUNIT2",
"mm")
1068 """Find the Amp with the specified pixel position within the composite
1072 ccd : `lsst.afw.cameraGeom.Detector`
1073 Detector to look in.
1074 pixelPosition : `lsst.geom.Point2I`
1075 The pixel position to find the amp for.
1079 `lsst.afw.table.AmpInfoCatalog`
1080 Amp record in which ``pixelPosition`` falls or `None` if no Amp found.
1083 if amp.getBBox().
contains(pixelPosition):
def __init__(self, butler=None, type="raw", isTrimmed=True, verbose=False, background=numpy.nan, callback=None, *args, **kwargs)
def _prepareImage(self, ccd, im, binSize, allowRotate=True)
def getCcdImage(self, ccd, imageFactory=afwImage.ImageF, binSize=1, asMaskedImage=False)
def getAmpImage(self, amp, imageFactory)
def __init__(self, isTrimmed=True, verbose=False, background=numpy.nan, showAmpGain=True, markSize=10, markValue=0, ampImValue=None, scaleGain=lambda gain:(gain *1000)//10)
def getCcdImage(self, det, imageFactory, binSize)
Class for storing generic metadata.
A floating-point coordinate rectangle geometry.
An integer coordinate rectangle.
static Log getLogger(Log const &logger)
Reports attempts to exceed implementation-defined length limits for some classes.
def assembleAmplifierRawImage(destImage, rawImage, amplifier)
def assembleAmplifierImage(destImage, rawImage, amplifier)
def rotateBBoxBy90(bbox, n90, dimensions)
def makeFocalPlaneWcs(pixelSize, referencePixel)
def plotFocalPlane(camera, fieldSizeDeg_x=0, fieldSizeDeg_y=None, dx=0.1, dy=0.1, figsize=(10., 10.), useIds=False, showFig=True, savePath=None)
def showAmp(amp, imageSource=FakeImageDataSource(isTrimmed=False), display=None, overlay=True, imageFactory=afwImage.ImageU)
def makeImageFromCcd(ccd, isTrimmed=True, showAmpGain=True, imageFactory=afwImage.ImageU, rcMarkSize=10, binSize=1)
def makeImageFromCamera(camera, detectorNameList=None, background=numpy.nan, bufferSize=10, imageSource=FakeImageDataSource(), imageFactory=afwImage.ImageU, binSize=1)
def overlayCcdBoxes(ccd, untrimmedCcdBbox=None, nQuarter=0, isTrimmed=False, ccdOrigin=(0, 0), display=None, binSize=1)
def findAmp(ccd, pixelPosition)
def makeImageFromAmp(amp, imValue=None, imageFactory=afwImage.ImageU, markSize=10, markValue=0, scaleGain=lambda gain:(gain *1000)//10)
def prepareWcsData(wcs, amp, isTrimmed=True)
def getCcdInCamBBoxList(ccdList, binSize, pixelSize_o, origin)
def rawCallback(im, ccd=None, imageSource=None, correctGain=False, subtractBias=False, convertToFloat=False, obeyNQuarter=True)
def getCameraImageBBox(camBbox, pixelSize, bufferSize)
def showCcd(ccd, imageSource=FakeImageDataSource(), display=None, overlay=True, imageFactory=afwImage.ImageF, binSize=1, inCameraCoords=False)
def showCamera(camera, imageSource=FakeImageDataSource(), imageFactory=afwImage.ImageF, detectorNameList=None, binSize=10, bufferSize=10, overlay=True, title="", showWcs=None, ctype=afwDisplay.GREEN, textSize=1.25, originAtCenter=True, display=None, **kwargs)
std::shared_ptr< SkyWcs > makeSkyWcs(daf::base::PropertySet &metadata, bool strip=false)
Construct a SkyWcs from FITS keywords.
std::shared_ptr< SkyWcs > makeFlippedWcs(SkyWcs const &wcs, bool flipLR, bool flipTB, lsst::geom::Point2D const ¢er)
Return a copy of a FITS-WCS with pixel positions flipped around a specified center.
Backwards-compatibility support for depersisting the old Calib (FluxMag0/FluxMag0Err) objects.
Statistics makeStatistics(lsst::afw::image::Image< Pixel > const &img, lsst::afw::image::Mask< image::MaskPixel > const &msk, int const flags, StatisticsControl const &sctrl=StatisticsControl())
Handle a watered-down front-end to the constructor (no variance)
std::shared_ptr< ImageT > rotateImageBy90(ImageT const &image, int nQuarter)
Rotate an image by an integral number of quarter turns.
std::shared_ptr< ImageT > binImage(ImageT const &inImage, int const binX, int const binY, lsst::afw::math::Property const flags=lsst::afw::math::MEAN)
Angle abs(Angle const &a)