10double SkyRenderer::flux(
double mag)
const
16 return pow(10.0, (z - mag) * k / 2.5);
19int SkyRenderer::addToPixel(
INDI::CCDChip *chip,
int x,
int y,
int val)
21 int const nwidth = chip->
getSubW();
22 int const nheight = chip->
getSubH();
27 if (x < 0 || x >= nwidth || y < 0 || y >= nheight)
33 int newval =
static_cast<int>(pt[0]) + val;
36 if (newval > m_MaxPix)
38 if (newval < m_MinPix)
40 pt[0] =
static_cast<uint16_t
>(newval);
49 int const subX = chip->
getSubX();
50 int const subY = chip->
getSubY();
51 int const subW = chip->
getSubW() + subX;
52 int const subH = chip->
getSubH() + subY;
54 if (x < subX || x > subW || y < subY || y > subH)
57 float const totalFlux =
static_cast<float>(flux(mag) * exp_s);
64 float effectiveSeeing = m_Cfg.
seeing;
67 float const cx = chip->
getXRes() / 2.0f;
68 float const cy = chip->
getYRes() / 2.0f;
69 float const dx = (x - cx) / cx;
70 float const dy = (y - cy) / cy;
73 float const tiltOffset = m_Cfg.
tiltLR * dx + m_Cfg.
tiltTB * dy;
74 effectiveSeeing += tiltOffset;
75 if (effectiveSeeing < 0.5f)
76 effectiveSeeing = 0.5f;
79 int const boxsizey =
static_cast<int>(3.0f * effectiveSeeing / m_ImageScaleY) + 1;
81 float const sigma = effectiveSeeing / (2.0f * std::sqrt(2.0f * std::log(2.0f)));
82 float const norm = 1.0f / (sigma * std::sqrt(2.0f *
float(
M_PI)));
83 float const inv2sig2 = 1.0f / (2.0f * sigma * sigma);
89 float const fracX = x -
static_cast<int>(x);
90 float const fracY = y -
static_cast<int>(y);
92 for (
int sy = -boxsizey; sy <= boxsizey; sy++)
94 for (
int sx = -boxsizey; sx <= boxsizey; sx++)
96 float const ddx = m_ImageScaleX * (sx - fracX);
97 float const ddy = m_ImageScaleY * (sy - fracY);
98 float const dc2 = ddx * ddx + ddy * ddy;
99 float const fa = norm * std::exp(-dc2 * inv2sig2);
100 int const fp =
static_cast<int>(fa * totalFlux);
104 static_cast<int>(x) + sx,
105 static_cast<int>(y) + sy, fp) != 0)
118 int const nx = chip->
getSubW();
119 int const ny = chip->
getSubH();
122 for (
int y = 0; y < ny; y++)
123 for (
int x = 0; x < nx; x++)
125 int newval =
static_cast<int>(buf[y * nx + x]) + bias + (random() % maxNoise);
126 if (newval > m_Cfg.
maxVal)
128 buf[y * nx + x] =
static_cast<uint16_t
>(newval);
132void SkyRenderer::drawSkyGlow(
INDI::CCDChip *chip,
float exp_s)
134 float const skyflux =
static_cast<float>(flux(m_Cfg.
skyGlow)) * exp_s;
136 int const nwidth = chip->
getSubW();
137 int const nheight = chip->
getSubH();
141 float const vig = std::min(nwidth, nheight) * m_ImageScaleX;
142 float const invVig2 = 1.0f / (vig * vig);
144 for (
int y = 0; y < nheight; y++)
146 float const sy = nheight / 2.0f - y;
148 for (
int x = 0; x < nwidth; x++)
150 float const sx = nwidth / 2.0f - x;
152 float const dc2 = sx * sx * m_ImageScaleX * m_ImageScaleX
153 + sy * sy * m_ImageScaleY * m_ImageScaleY;
155 float const fa = std::exp(-2.0f * 0.7f * dc2 * invVig2);
157 float fp = (pt[0] + skyflux) * fa;
159 if (fp > m_Cfg.
maxVal) fp =
static_cast<float>(m_Cfg.
maxVal);
160 if (fp < pt[0]) fp = pt[0];
161 if (fp > m_MaxPix) m_MaxPix =
static_cast<int>(fp);
162 if (fp < m_MinPix) m_MinPix =
static_cast<int>(fp);
164 pt[0] =
static_cast<uint16_t
>(fp);
173 double dec_j2000_deg,
174 double focal_length_mm,
178 double minSearchRadiusArcmin)
184 m_ImageScaleX =
static_cast<float>((chip->
getPixelSizeX() / focal_length_mm) * 206.3);
185 m_ImageScaleY =
static_cast<float>((chip->
getPixelSizeY() / focal_length_mm) * 206.3);
188 double const theta = rotation_deg * (
M_PI / 180.0);
189 double const pprx = focal_length_mm / chip->
getPixelSizeX() * 1000.0;
190 double const ppry = focal_length_mm / chip->
getPixelSizeY() * 1000.0;
192 double const pa = pprx * std::cos(theta);
193 double const pb = ppry * std::sin(theta);
194 double const pd = -pprx * std::sin(theta);
195 double const pe = ppry * std::cos(theta);
196 double const pc = chip->
getXRes() / 2.0;
197 double const pf = chip->
getYRes() / 2.0;
198 double const ccdW = chip->
getXRes();
201 double const rar = ra_j2000_deg * (
M_PI / 180.0);
202 double const decr = dec_j2000_deg * (
M_PI / 180.0);
205 double radius = std::sqrt(
206 m_ImageScaleX * m_ImageScaleX * chip->
getXRes() / 2.0 * chip->
getXRes() / 2.0 +
207 m_ImageScaleY * m_ImageScaleY * chip->
getYRes() / 2.0 * chip->
getYRes() / 2.0) / 60.0;
208 if (minSearchRadiusArcmin > 0 && radius < minSearchRadiusArcmin)
209 radius = minSearchRadiusArcmin;
227 snprintf(gsccmd,
sizeof(gsccmd),
228 "gsc -c %8.6f %+8.6f -r %4.1f -m 0 %4.2f -n 3000",
234 FILE *pp = popen(gsccmd,
"r");
239 while (fgets(line,
sizeof(line), pp) !=
nullptr)
241 char id[20], plate[6], ob[6];
242 float ra,
dec, pose, mag, mage, dist;
245 int rc = sscanf(line,
"%10s %f %f %f %f %f %d %d %4s %2s %f %d",
246 id, &
ra, &
dec, &pose, &mag, &mage,
247 &band, &c, plate, ob, &dist, &dir);
251 double const srar =
ra * (
M_PI / 180.0);
252 double const sdecr =
dec * (
M_PI / 180.0);
254 double const denom = cos(decr) * cos(sdecr) * cos(srar - rar)
255 + sin(decr) * sin(sdecr);
259 double const sx = cos(sdecr) * sin(srar - rar) / denom;
260 double const sy = (sin(decr) * cos(sdecr) * cos(srar - rar)
261 - cos(decr) * sin(sdecr)) / denom;
264 double const ccdx = ccdW - (pa * sx + pb * sy + pc);
265 double const ccdy = pd * sx + pe * sy + pf;
268 static_cast<float>(ccdx),
269 static_cast<float>(ccdy),
280 drawSkyGlow(chip, exposure_s);
The CCDChip class provides functionality of a CCD Chip within a CCD.
int getSubX() const
getSubX Get the starting left coordinates (X) of the frame.
int getSubY() const
getSubY Get the starting top coordinates (Y) of the frame.
float getPixelSizeY() const
getPixelSizeY Get vertical pixel size in microns.
int getSubH() const
getSubH Get the height of the frame
float getPixelSizeX() const
getPixelSizeX Get horizontal pixel size in microns.
int getXRes() const
getXRes Get the horizontal resolution in pixels of the CCD Chip.
uint8_t * getFrameBuffer()
getFrameBuffer Get raw frame buffer of the CCD chip.
int getSubW() const
getSubW Get the width of the frame
int getFrameBufferSize() const
getFrameBufferSize Get allocated frame buffer size to hold the CCD image frame.
int getYRes() const
Get the vertical resolution in pixels of the CCD Chip.
int renderFrame(INDI::CCDChip *chip, double ra_j2000_deg, double dec_j2000_deg, double focal_length_mm, double rotation_deg, float exposure_s, bool renderStars=true, double minSearchRadiusArcmin=0)
void applyReadoutNoise(INDI::CCDChip *chip, int bias, int maxNoise)
int drawImageStar(INDI::CCDChip *, float mag, float x, float y, float exp_s)
double range360(double r)
range360 Limits an angle to be between 0-360 degrees.
double rangeDec(double decdegrees)
rangeDec Limits declination value to be in -90 to 90 range.
Implementations for common driver routines.