/** \file \brief Graybody implementation. \who \kpr */ #include "mutils/nmath.h" #include "Detector.h" #include "Graybody.h" namespace mu = mutils; namespace manticore { /// Detector support. namespace graybody { /// Parameters required by flux(). struct FluxData { double Th, ///< Core temperature. Sigmah, ///< Core mass surface density. Tc, ///< Halo temperature. Sigmac; ///< Halo surface density. const Detector *d; ///< Detector instance. const Graybody *g; ///< Graybody instance. /// Single-temperature graybody intensity method. double (Graybody::*I)(double, double, double) const; /// Two-temperature graybody intensity method. double (Graybody::*I2)(double, double, double, double, double) const; }; extern "C" { /// Flux density integrand (one-component). /// \param[in] nu Frequency (Hz). /// \param[in] fd FluxData instance. double flux(double nu, void *fd) { auto &p = *static_cast(fd); return (p.g->*(p.I))(nu, p.Th, p.Sigmah) * p.d->response(nu); } /// Flux density integrand (two-component). /// \param[in] nu Frequency (Hz). /// \param[in] fd FluxData instance. double flux2(double nu, void *fd) { auto &p = *static_cast(fd); return (p.g->*(p.I2))(nu, p.Tc, p.Sigmac, p.Th, p.Sigmah) * p.d->response(nu); } } // extern "C" } // namescape graybody double Graybody::Itot(double (Graybody::*I)(double, double, double) const, double T, double Sigma, const Detector *detect, double sr) const { graybody::FluxData fd = {T, Sigma, 0.0, 0.0, detect, this, I, nullptr}; std::pair freqRange = detect->freqRange(); return sr * mu::kgauss_r(graybody::flux, &fd, freqRange.first, freqRange.second, err_); } double Graybody::Itot2( double (Graybody::*I)(double, double, double, double, double) const, double Tc, double Sigmac, double Th, double Sigmah, const Detector *detect, double sr) const { std::pair freqRange = detect->freqRange(); graybody::FluxData fd = {Th, Sigmah, Tc, Sigmac, detect, this, nullptr, I}; return sr * mu::kgauss_r(graybody::flux2, &fd, freqRange.first, freqRange.second, err_); } } // namespace manticore