As part of this analysis, we have added the capability to simulate wavelength-dependent surface brightness profiles to the open source galaxy simulation package GalSim, which is being used in the GREAT3 shape measurement data challenge. The new chromatic API makes it convenient to simulate both the effects of chromatic PSFs and chromatic galaxies (also referred to as galaxies with color gradients).

As an example, a simulation of a bulge+disk galaxy convolved with an atmospheric PSF and observed in the r-band might look like:

    import galsim

    # load bulge, disk spectra into galsim.SED objects
    bulge_spectrum = galsim.SED('early_type_spec.dat')
    disk_spectrum = galsim.SED('late_type_spec.dat')
    # define the bulge and the disk as separable products of a spatial profile
    # and an SED.
    bulge = galsim.deVaucouleurs(flux=0.1, half_light_radius=0.4) * bulge_spectrum
    disk = galsim.Exponential(flux=0.2, half_light_radius=0.7) * disk_spectrum
    # Add them together!
    galaxy = bulge + disk

    # Make a chromatic PSF by transforming a fiducial monochromatic PSF at 500 nm
    psf_500 = galsim.Kolmogorov(fwhm=0.67) # fiducial PSF
    # galsim.ChromaticAtmosphere adds differential chromatic refraction and
    # chromatic seeing to the fiducial PSF.
    psf = galsim.ChromaticAtmosphere(psf_500, 500, zenith_angle=30*galsim.degrees)

    # Convolve galaxy profile and PSF together.
    final = galsim.Convolve(galaxy, psf)

    # Need a filter bandpass to draw through.
    bandpass = galsim.Bandpass('rband.dat')
    # Draw the image!
    image = final.drawImage(bandpass)

For Euclid, the PSF is chromatic primarily due to the diffraction limit. If this were the only contribution to the PSF, then the chromatic effect would be . When combined with telescope jitter and the modulation transfer function from the CCD, however, the Euclid PSF will actually scale approximately like . This effect is also convenient to implement in GalSim:

    # Again, we'll apply a wavelength dependent transformation to a
    # monochromatic fiducial PSF.
    aperture_diameter = 1.2 # meters
    central_wavelength = 750e-9 # meters
    lam_over_diam = central_wavelength / aperture_diam * galsim.radians / galsim.arcsec
    psf_750 = galsim.Airy(lam_over_diam=lam_over_diam)
    # galsim.ChromaticObject chromaticizes the fiducial PSF so that
    # .dilate() can accept a function of wavelength as its argument.
    psf_Euclid = galsim.ChromaticObject(psf_750).dilate(lambda w: (w/750)**0.6)