components concepts - beta version stage

This commit is contained in:
Timur A. Fatkhullin 2025-07-10 18:18:30 +03:00
parent 4d13c86e3d
commit fe61ccf0ec
3 changed files with 112 additions and 123 deletions

View File

@ -6,8 +6,8 @@
// #include <atomic>
#include <chrono>
#include <concepts>
#include <cstdint>
// #include <concepts>
// #include <cstdint>
#include <functional>
#include <string_view>
#include "spdlog/sinks/null_sink.h"
@ -17,90 +17,12 @@
#include "mcc_spdlog.h"
#include "mcc_traits.h"
// #include "mount_astrom.h"
#include "mcc_mount_pz.h"
// #include "mcc_mount_pz.h"
#include "mcc_mount_concepts.h"
namespace mcc
{
/* BASIC DATA DEFINITIONS */
// meteo parameters (e.g. to compute refraction)
struct MccMountMeteo {
typedef double temp_t;
typedef double humid_t;
typedef double press_t;
temp_t temperature; // Temperature in C
humid_t humidity; // humidity in % ([0.0, 1.0])
press_t pressure; // atmospheric presure in hPa=mB
};
// mount site geographical location
struct MccMountSiteInfo {
typedef MccAngle mnt_site_coord_t;
typedef MccAngle mnt_site_elev_t;
mnt_site_coord_t latitude{"00:00:00.0"_dms}; //
mnt_site_coord_t longitude{0.0}; // positive to the East
mnt_site_elev_t elevation{0.0}; // in meters
std::string_view name{"ALL-ZERO"}; // just a human-readable name
};
// mount current telemetry: time, position and related quantities
struct MccMountTelemetry {
typedef double mnt_coord_t;
typedef double mnt_speed_t;
typedef double time_point_t;
// time-related
std::chrono::system_clock::time_point utc;
time_point_t mjd; // modified Julian date
time_point_t ut1;
time_point_t tt;
time_point_t siderTime; // sideral time (in radians)
// apparent target (user-input) current coordinates (in radians)
mnt_coord_t tagRA, tagDEC;
mnt_coord_t tagHA;
mnt_coord_t tagAZ, tagZD;
mnt_coord_t tagPA; // paralactic angle
// encoder-measured current mount coordinates (in radians)
mnt_coord_t mntRA, mntDEC;
mnt_coord_t mntHA;
mnt_coord_t mntAZ, mntZD;
mnt_coord_t mntPA;
// encoder-measured (non-corrected for PCS) current mount position and moving speed (in radians, radians/s)
// X - HA, Y - DEC for equatorial-type mount; X - AZ, Y - ZD for horizontal-type one
mnt_coord_t mntPosX, mntPosY;
mnt_speed_t mntSpeedX, mntSpeedY;
// current refraction coefficient (for tagZD)
mnt_coord_t currRefr;
// PCS (pointing correction system) corrections
// X - HA, Y - DEC for equatorial-type mount; X - AZ, Y - ZD for horizontal-type one
mnt_coord_t pcsX, pcsY;
};
// mount construction type (only the most common ones)
enum class MccMountType : uint8_t { GERMAN_TYPE, FORK_TYPE, CROSSAXIS_TYPE, ALTAZ_TYPE };
template <MccMountType TYPE>
static constexpr std::string_view MccMountTypeStr = TYPE == MccMountType::GERMAN_TYPE ? "GERMAN"
: TYPE == MccMountType::FORK_TYPE ? "FORK"
: TYPE == MccMountType::CROSSAXIS_TYPE ? "CROSSAXIS"
: TYPE == MccMountType::ALTAZ_TYPE ? "ALTAZ"
: "UNKNOWN";
// mount configuration
@ -109,17 +31,6 @@ struct MccMountConfig {
static constexpr MccMountType mountType = MOUNT_TYPE;
virtual ~MccMountConfig() = default;
// astrom::MccLeapSeconds leapSeconds;
// astrom::MccIersBulletinA iersBulletinA;
MccMountSiteInfo siteInfo{.latitude = 0.0, .longitude = 0.0, .elevation = 0.0, .name{"ALL-ZERO"}};
// template <typename ComponentT, typename... CompCtorArgTs>
// auto update(this auto&& self, CompCtorArgTs... comp_ctor_args)
// {
// return std::forward<decltype(self)>(self).updateImpl(std::forward<CompCtorArgTs>(comp_ctor_args)...);
// }
};
@ -133,7 +44,7 @@ concept mcc_mountconfig_c = requires(T t) { []<MccMountType MOUNT_TYPE>(MccMount
} // namespace traits
template <traits::mcc_mountconfig_c MOUNT_CONFIG, std::derived_from<MccMountTelemetry> MOUNT_TELEMETRY>
template <traits::mcc_mountconfig_c MOUNT_CONFIG, traits::mcc_mount_telemetry_c MOUNT_TELEMETRY>
class MccMount : public fsm::MccFiniteStateMachine, public utils::MccSpdlogLogger
{
public:
@ -141,6 +52,7 @@ public:
typedef MOUNT_CONFIG mount_config_t;
typedef MOUNT_TELEMETRY mount_telemetry_t;
typedef typename mount_telemetry_t::mount_telemetry_data_t mount_telemetry_data_t;
struct slew_param_t {
MccCoordPairKind kind; // input coordinates type
@ -194,67 +106,96 @@ public:
mount_config_t mountConfig() const
{
return _mountConfig;
// return _mountConfig.load();
}
mount_telemetry_t mountTelemetry() const
mount_telemetry_data_t mountTelemetry() const
{
return _mountTelemetry;
// return _mountTelemetry.load();
return _mountTelemetry.data();
}
/* prohibited zone related public methods */
template <std::derived_from<MccProhibitedZone> ZT, std::derived_from<MccProhibitedZone>... ZTs>
template <traits::mcc_prohibited_zone_c ZT, traits::mcc_prohibited_zone_c... ZTs>
size_t pzAddZone(ZT zone, ZTs... zones)
{
static constexpr auto pi2 = std::numbers::pi / 2.0;
_pzRequestFunc.emplace_back([zone = std::move(zone), this]() {
mount_telemetry_t data = _mountTelemetry.load();
auto zone_ptr = std::make_shared<ZT>(std::move(zone));
if constexpr (ZT::preferedCoordKind == MccCoordPairKind::COORDS_KIND_AZALT) {
return zone.request(MccAngleAZ(data.tagAZ), MccAngleALT(pi2 - data.tagZD));
} else if constexpr (ZT::preferedCoordKind == MccCoordPairKind::COORDS_KIND_AZZD) {
return zone.request(MccAngleAZ(data.tagAZ), MccAngleZD(data.tagZD));
} else if constexpr (ZT::preferedCoordKind == MccCoordPairKind::COORDS_KIND_RADEC_APP) {
return zone.request(MccAngleRA_APP(data.tagRA), MccAngleDEC_APP(data.tagDEC));
} else if constexpr (ZT::preferedCoordKind == MccCoordPairKind::COORDS_KIND_HADEC_APP) {
return zone.request(MccAngleHA_APP(data.tagHA), MccAngleDEC_APP(data.tagDEC));
} else if constexpr (ZT::preferedCoordKind == MccCoordPairKind::COORDS_KIND_RADEC_ICRS) {
return zone.request(MccAngleRA_APP(data.tagRA), MccAngleDEC_APP(data.tagDEC));
} else if constexpr (ZT::preferedCoordKind == MccCoordPairKind::COORDS_KIND_XY) {
return zone.request(MccAngleX(data.mntPosX), MccAngleY(data.mntPosY));
} else {
static_assert(false, "UNKNOWN COORDINATE SYSTEM!!!");
}
});
if constexpr (ZT::preferedCoordKind == MccCoordPairKind::COORDS_KIND_AZALT) { // azimuth and altitude
_pzInZoneFunc.emplace_back([zone_ptr, this]() {
auto tmry_data = _mountTelemetry();
return zone_ptr->inZone(tmry_data.mntAZ, tmry_data.mntALT, tmry_data.utc);
});
_pzTimeToFunc.emplace_back([zone_ptr, this]() {
auto tmry_data = _mountTelemetry();
return zone_ptr->timeTo(tmry_data.mntAZ, tmry_data.mntALT, tmry_data.utc);
});
_pzTimeFromFunc.emplace_back([zone_ptr, this]() {
auto tmry_data = _mountTelemetry();
return zone_ptr->timeFrom(tmry_data.mntAZ, tmry_data.mntALT, tmry_data.utc);
});
} else if constexpr (ZT::preferedCoordKind ==
MccCoordPairKind::COORDS_KIND_AZZD) { // azimuth and zenithal distance
_pzInZoneFunc.emplace_back([zone_ptr, this]() {
auto tmry_data = _mountTelemetry();
return zone_ptr->inZone(tmry_data.mntAZ, pi2 - tmry_data.mntALT, tmry_data.utc);
});
_pzTimeToFunc.emplace_back([zone_ptr, this]() {
auto tmry_data = _mountTelemetry();
return zone_ptr->timeTo(tmry_data.mntAZ, pi2 - tmry_data.mntALT, tmry_data.utc);
});
_pzTimeFromFunc.emplace_back([zone_ptr, this]() {
auto tmry_data = _mountTelemetry();
return zone_ptr->timeFrom(tmry_data.mntAZ, pi2 - tmry_data.mntALT, tmry_data.utc);
});
} else if constexpr (ZT::preferedCoordKind == MccCoordPairKind::COORDS_KIND_RADEC_APP) {
} else if constexpr (ZT::preferedCoordKind == MccCoordPairKind::COORDS_KIND_HADEC_APP) {
} else if constexpr (ZT::preferedCoordKind == MccCoordPairKind::COORDS_KIND_RADEC_ICRS) {
} else if constexpr (ZT::preferedCoordKind == MccCoordPairKind::COORDS_KIND_XY) {
} else {
static_assert(false, "UNKNOWN COORDINATE SYSTEM!!!");
}
if constexpr (sizeof...(ZTs)) {
psAddZone(std::move(zones)...);
}
return _pzRequestFunc.size();
return _pzInZoneFunc.size();
}
void pzClearZone()
{
_pzRequestFunc.clear();
_pzInZoneFunc.clear();
_pzTimeToFunc.clear();
_pzTimeFromFunc.clear();
}
protected:
// std::atomic<mount_config_t> _mountConfig;
// std::atomic<mount_telemetry_t> _mountTelemetry;
mount_config_t _mountConfig;
mount_telemetry_t _mountTelemetry;
typedef std::chrono::duration<double> pz_duration_t;
// a type to which the result of calling prohibited zone class methods 'timeTo' and 'timeFrom' will be converted
typedef std::chrono::duration<double> pz_duration_t; // seconds as floating-point number
std::vector<std::function<bool()>> _pzInZoneFunc{};
std::vector<std::function<pz_duration_t()>> _pzTimeToFunc{};
std::vector<std::function<pz_duration_t()>> _pzTimeFromFunc{};
std::vector<std::function<MccProhibitedZone::pz_request_t()>> _pzRequestFunc{};
}; // end of MccMount class

View File

@ -4,6 +4,7 @@
#include <concepts>
#include "mcc_mount_coord.h"
#include "mcc_traits.h"
@ -213,6 +214,48 @@ concept mcc_mount_telemetry_c = requires(T t, const T t_const) {
/* MOUNT PROHIBITED ZONE */
template <typename T>
concept mcc_prohibited_zone_c = std::movable<T> && requires(T t, const T t_const) {
typename T::coord_t;
typename T::time_point_t;
// the type 'T' must define static constexpr member of type MccCoordPairKind
// to declarate type of coordinate pair used to describe the zone.
// This coordinate pair must be used as input in the class methods.
requires requires {
requires std::same_as<decltype(T::zoneCoordPairKind), const MccCoordPairKind>;
[]() {
constexpr MccCoordPairKind val = T::zoneCoordPairKind;
}(); // to ensure that 'zoneCoordPairKind' can be used at compile-time context
};
// return a name of the zone
{ t_const.name() } -> mcc_formattable;
// check if given coordinates are in the zone at given time point
{
t.inZone(std::declval<typename T::coord_t>(), std::declval<typename T::coord_t>(),
std::declval<typename T::time_point_t>())
} -> std::convertible_to<bool>;
// for given coordinates and time the method computes a time to reach the zone
{
t.timeTo(std::declval<typename T::coord_t>(), std::declval<typename T::coord_t>(),
std::declval<typename T::time_point_t>())
} -> mcc_time_duration_c;
// for given coordinates and time the method computes a time to exit from the zone
{
t.timeFrom(std::declval<typename T::coord_t>(), std::declval<typename T::coord_t>(),
std::declval<typename T::time_point_t>())
} -> mcc_time_duration_c;
};
/* MOUNT GENERIC CONFIGURATION */
template <typename T>
@ -221,4 +264,7 @@ concept mcc_mount_config_c = requires(T t) {
{ t.pec() } -> mcc_mount_pec_c;
{ t.hardware() } -> mcc_mount_hardware_c;
};
} // namespace mcc::traits

View File

@ -185,6 +185,8 @@ public:
std::lock_guard lock{_updateMutex};
_data = std::move(current_data);
return TEL_ERROR_OK;
}
mount_telemetry_data_t data(this auto&& self)