...
This commit is contained in:
@@ -1,5 +1,7 @@
|
|||||||
cmake_minimum_required(VERSION 3.14)
|
cmake_minimum_required(VERSION 3.14)
|
||||||
|
|
||||||
|
set(QT_CREATOR_SKIP_MAINTENANCE_TOOL_PROVIDER ON)
|
||||||
|
|
||||||
# ******* MOUNT CONTROL COMPONENTS *******
|
# ******* MOUNT CONTROL COMPONENTS *******
|
||||||
|
|
||||||
project(mcc LANGUAGES C CXX Fortran VERSION 0.1)
|
project(mcc LANGUAGES C CXX Fortran VERSION 0.1)
|
||||||
@@ -48,6 +50,7 @@ if(USE_SPDLOG)
|
|||||||
|
|
||||||
find_package(spdlog CONFIG)
|
find_package(spdlog CONFIG)
|
||||||
if(NOT ${spdlog_FOUND})
|
if(NOT ${spdlog_FOUND})
|
||||||
|
message(STATUS "\tfetch spdlog-lib ...")
|
||||||
FetchContent_Declare(
|
FetchContent_Declare(
|
||||||
spdlog
|
spdlog
|
||||||
GIT_REPOSITORY "https://github.com/gabime/spdlog.git"
|
GIT_REPOSITORY "https://github.com/gabime/spdlog.git"
|
||||||
@@ -59,7 +62,7 @@ if(USE_SPDLOG)
|
|||||||
"-DSPDLOG_USE_STD_FORMAT=ON -DSPDLOG_FMT_EXTERNAL=OFF"
|
"-DSPDLOG_USE_STD_FORMAT=ON -DSPDLOG_FMT_EXTERNAL=OFF"
|
||||||
OVERRIDE_FIND_PACKAGE
|
OVERRIDE_FIND_PACKAGE
|
||||||
)
|
)
|
||||||
find_package(spdlog CONFIG)
|
find_package(spdlog REQUIRED CONFIG)
|
||||||
endif()
|
endif()
|
||||||
endif()
|
endif()
|
||||||
|
|
||||||
@@ -171,7 +174,7 @@ if(USE_ASIO)
|
|||||||
|
|
||||||
execute_process(
|
execute_process(
|
||||||
WORKING_DIRECTORY ${asiolib_project_SOURCE_DIR}/asio
|
WORKING_DIRECTORY ${asiolib_project_SOURCE_DIR}/asio
|
||||||
COMMAND ./configure --prefix=${asiolib_project_SOURCE_DIR}
|
COMMAND ./configure --prefix=${asiolib_project_SOURCE_DIR}/asio
|
||||||
)
|
)
|
||||||
|
|
||||||
set(ENV{PKG_CONFIG_PATH} "${asiolib_project_SOURCE_DIR}/asio")
|
set(ENV{PKG_CONFIG_PATH} "${asiolib_project_SOURCE_DIR}/asio")
|
||||||
@@ -250,6 +253,10 @@ if(USE_ASIO)
|
|||||||
target_link_libraries(${PROJECT_NAME} INTERFACE PkgConfig::ASIOLIB)
|
target_link_libraries(${PROJECT_NAME} INTERFACE PkgConfig::ASIOLIB)
|
||||||
endif()
|
endif()
|
||||||
|
|
||||||
|
if(USE_SPDLOG)
|
||||||
|
target_link_libraries(${PROJECT_NAME} INTERFACE spdlog::spdlog)
|
||||||
|
endif()
|
||||||
|
|
||||||
if(BUILD_TESTS)
|
if(BUILD_TESTS)
|
||||||
add_executable(mcc_telemetry_test tests/mcc_telemetry_test.cpp)
|
add_executable(mcc_telemetry_test tests/mcc_telemetry_test.cpp)
|
||||||
target_link_libraries(mcc_telemetry_test PRIVATE ${PROJECT_NAME})
|
target_link_libraries(mcc_telemetry_test PRIVATE ${PROJECT_NAME})
|
||||||
|
|||||||
@@ -968,10 +968,11 @@ concept mcc_movement_controls_c = requires(T t) {
|
|||||||
template <typename T>
|
template <typename T>
|
||||||
concept mcc_mount_status_c = requires {
|
concept mcc_mount_status_c = requires {
|
||||||
[]() {
|
[]() {
|
||||||
[[maybe_unused]] static constexpr std::array arr = {
|
[[maybe_unused]]
|
||||||
T::MOUNT_STATUS_ERROR, T::MOUNT_STATUS_IDLE, T::MOUNT_STATUS_INITIALIZATION,
|
static constexpr std::array arr = {T::MOUNT_STATUS_ERROR, T::MOUNT_STATUS_IDLE,
|
||||||
T::MOUNT_STATUS_ERROR, T::MOUNT_STATUS_STOPPED, T::MOUNT_STATUS_SLEWING,
|
T::MOUNT_STATUS_INITIALIZATION, T::MOUNT_STATUS_STOPPED,
|
||||||
T::MOUNT_STATUS_ADJUSTING, T::MOUNT_STATUS_GUIDING, T::MOUNT_STATUS_TRACKING};
|
T::MOUNT_STATUS_SLEWING, T::MOUNT_STATUS_ADJUSTING,
|
||||||
|
T::MOUNT_STATUS_GUIDING, T::MOUNT_STATUS_TRACKING};
|
||||||
}; // to ensure mount status is compile-time constants
|
}; // to ensure mount status is compile-time constants
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|||||||
@@ -370,14 +370,36 @@ struct MccDeserializer<VT> : MccDeserializerBase {
|
|||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
template <>
|
||||||
|
struct MccDeserializer<MccCoordPairKind> : MccDeserializerBase {
|
||||||
|
static constexpr std::string_view deserializerName{"MCC-COORDPAIR-DESERIALIZER"};
|
||||||
|
|
||||||
|
template <mcc_serialization_params_c ParamsT = mcc_serialization_params_t>
|
||||||
|
error_t operator ()(
|
||||||
|
traits::mcc_input_char_range auto const& input,
|
||||||
|
MccCoordPairKind& value,
|
||||||
|
ParamsT const& params = mcc_serialization_params_t{})
|
||||||
|
{
|
||||||
|
value = MccCoordStrToPairKind(input);
|
||||||
|
|
||||||
|
if (value == MccCoordPairKind::COORDS_KIND_UNKNOWN) {
|
||||||
|
return MccDeserializerErrorCode::ERROR_INVALID_SERIALIZED_VALUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
return MccDeserializerErrorCode::ERROR_OK;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
template <>
|
template <>
|
||||||
struct MccDeserializer<MccSerializedAngleFormatPrec> : MccDeserializerBase {
|
struct MccDeserializer<MccSerializedAngleFormatPrec> : MccDeserializerBase {
|
||||||
static constexpr std::string_view deserializerName{"MCC-ANGLE-FORMAT-PREC-DESERIALIZER"};
|
static constexpr std::string_view deserializerName{"MCC-ANGLE-FORMAT-PREC-DESERIALIZER"};
|
||||||
|
|
||||||
template <mcc_serialization_params_c ParamsT = mcc_serialization_params_t>
|
template <mcc_serialization_params_c ParamsT = mcc_serialization_params_t>
|
||||||
error_t operator()(traits::mcc_input_char_range auto const& input,
|
error_t operator ()(
|
||||||
MccSerializedAngleFormatPrec& value,
|
traits::mcc_input_char_range auto const& input,
|
||||||
ParamsT const& params = mcc_serialization_params_t{})
|
MccSerializedAngleFormatPrec& value,
|
||||||
|
ParamsT const& params = mcc_serialization_params_t{})
|
||||||
{
|
{
|
||||||
// valid format: hour_prec[<params.elem_delim>deg_prec<params.elem_delim>decimals]
|
// valid format: hour_prec[<params.elem_delim>deg_prec<params.elem_delim>decimals]
|
||||||
|
|
||||||
@@ -408,16 +430,17 @@ struct MccDeserializer<MccSerializedAngleFormatPrec> : MccDeserializerBase {
|
|||||||
|
|
||||||
template <>
|
template <>
|
||||||
struct MccDeserializer<MccSerializedCoordPairFormat> : MccDeserializerBase {
|
struct MccDeserializer<MccSerializedCoordPairFormat> : MccDeserializerBase {
|
||||||
static constexpr std::string_view deserializerName{"MCC-COORD-PAIR-FORMAT-DESERIALIZER"};
|
static constexpr std::string_view deserializerName{"MCC-COORDPAIR-FORMAT-DESERIALIZER"};
|
||||||
|
|
||||||
template <mcc_serialization_params_c ParamsT = mcc_serialization_params_t>
|
template <mcc_serialization_params_c ParamsT = mcc_serialization_params_t>
|
||||||
error_t operator()(traits::mcc_input_char_range auto const& input,
|
error_t operator ()(
|
||||||
MccSerializedCoordPairFormat& value,
|
traits::mcc_input_char_range auto const& input,
|
||||||
ParamsT const& params = mcc_serialization_params_t{})
|
MccSerializedCoordPairFormat& value,
|
||||||
|
ParamsT const& params = mcc_serialization_params_t{})
|
||||||
{
|
{
|
||||||
value = MccSerializedCoordPairFormatStrToValue(input);
|
value = MccSerializedCoordPairFormatStrToValue(input);
|
||||||
|
|
||||||
if (value != MccSerializedCoordPairFormat::MCC_SERIALIZED_FORMAT_UNKNOWN){
|
if (value != MccSerializedCoordPairFormat::MCC_SERIALIZED_FORMAT_UNKNOWN) {
|
||||||
return MccDeserializerErrorCode::ERROR_OK;
|
return MccDeserializerErrorCode::ERROR_OK;
|
||||||
} else {
|
} else {
|
||||||
return MccDeserializerErrorCode::ERROR_INVALID_SERIALIZED_VALUE;
|
return MccDeserializerErrorCode::ERROR_INVALID_SERIALIZED_VALUE;
|
||||||
|
|||||||
219
mcc_netserver.h
219
mcc_netserver.h
@@ -37,7 +37,7 @@
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
#include "mcc_generics.h"
|
#include "mcc_concepts.h"
|
||||||
#include "mcc_netserver_endpoint.h"
|
#include "mcc_netserver_endpoint.h"
|
||||||
#include "mcc_netserver_proto.h"
|
#include "mcc_netserver_proto.h"
|
||||||
#include "mcc_traits.h"
|
#include "mcc_traits.h"
|
||||||
@@ -52,9 +52,10 @@ enum class MccGenericMountNetworkServerErrorCode : int {
|
|||||||
ERROR_MOUNT_STOP,
|
ERROR_MOUNT_STOP,
|
||||||
ERROR_MOUNT_SET_TARGET,
|
ERROR_MOUNT_SET_TARGET,
|
||||||
ERROR_MOUNT_GET_TELEMETRY,
|
ERROR_MOUNT_GET_TELEMETRY,
|
||||||
|
ERROR_MOUNT_COORD_TRANSFORM,
|
||||||
ERROR_MOUNT_SLEW,
|
ERROR_MOUNT_SLEW,
|
||||||
ERROR_MOUNT_MOVE,
|
ERROR_MOUNT_MOVE,
|
||||||
ERROR_MOUNT_TRACK
|
ERROR_MOUNT_TRACK,
|
||||||
};
|
};
|
||||||
|
|
||||||
struct MccGenericMountNetworkServerErrorCategory : std::error_category {
|
struct MccGenericMountNetworkServerErrorCategory : std::error_category {
|
||||||
@@ -78,6 +79,8 @@ struct MccGenericMountNetworkServerErrorCategory : std::error_category {
|
|||||||
return "mount set target error";
|
return "mount set target error";
|
||||||
case MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_GET_TELEMETRY:
|
case MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_GET_TELEMETRY:
|
||||||
return "mount get telemetry error";
|
return "mount get telemetry error";
|
||||||
|
case MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_COORD_TRANSFORM:
|
||||||
|
return "coordinate transformation error";
|
||||||
case MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_SLEW:
|
case MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_SLEW:
|
||||||
return "mount slewing error";
|
return "mount slewing error";
|
||||||
case MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_MOVE:
|
case MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_MOVE:
|
||||||
@@ -977,9 +980,9 @@ public:
|
|||||||
}
|
}
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
MccCoordinateSerializer::SerializedCoordFormat _coordFormat{
|
MccSerializedCoordPairFormat _coordFormat{MccSerializedCoordPairFormat::MCC_SERIALIZED_FORMAT_SXGM_HOURDEG};
|
||||||
MccCoordinateSerializer::SerializedCoordFormat::CFMT_SGM};
|
MccSerializedAngleFormatPrec _coordPrec{2, 1, 7};
|
||||||
MccCoordinateSerializer::SexagesimalCoordPrec _coordPrec{2, 1};
|
|
||||||
|
|
||||||
std::function<void()> _stopMountFunc{};
|
std::function<void()> _stopMountFunc{};
|
||||||
|
|
||||||
@@ -1041,44 +1044,51 @@ protected:
|
|||||||
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, MCC_COMMPROTO_KEYWORD_TRACK_STR);
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, MCC_COMMPROTO_KEYWORD_TRACK_STR);
|
||||||
}
|
}
|
||||||
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_COORDFMT_STR)) {
|
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_COORDFMT_STR)) {
|
||||||
auto v = input_msg.template paramValue<MccCoordinateSerializer::SerializedCoordFormat>(0);
|
if (input_msg.paramSize()) { // set operation
|
||||||
if (v) {
|
auto v = input_msg.template paramValue<MccSerializedCoordPairFormat>(0);
|
||||||
_coordFormat = v.value();
|
if (v) {
|
||||||
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, input_msg.byteRepr());
|
_coordFormat = v.value();
|
||||||
} else {
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, input_msg.byteRepr());
|
||||||
err = v.error();
|
} else {
|
||||||
|
err = v.error();
|
||||||
|
}
|
||||||
|
} else { // get operation
|
||||||
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, MCC_COMMPROTO_KEYWORD_COORDFMT_STR,
|
||||||
|
_coordFormat);
|
||||||
}
|
}
|
||||||
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_COORDPREC_STR)) {
|
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_COORDPREC_STR)) {
|
||||||
auto v = input_msg.template paramValue<MccCoordinateSerializer::SexagesimalCoordPrec>(0);
|
if (input_msg.paramSize()) { // set operation
|
||||||
if (v) {
|
auto v = input_msg.template paramValue<MccSerializedAngleFormatPrec>(0);
|
||||||
_coordPrec = v.value();
|
if (v) {
|
||||||
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, input_msg.byteRepr());
|
_coordPrec = v.value();
|
||||||
} else {
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, input_msg.byteRepr());
|
||||||
err = v.error();
|
} else {
|
||||||
|
err = v.error();
|
||||||
|
}
|
||||||
|
} else { // get operation
|
||||||
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, MCC_COMMPROTO_KEYWORD_COORDPREC_STR,
|
||||||
|
_coordPrec);
|
||||||
}
|
}
|
||||||
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_TARGET_STR)) {
|
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_TARGET_STR)) {
|
||||||
// by default return ICRS coordinates
|
impl::MccCoordPairKind pair_kind = impl::MccCoordPairKind::COORDS_KIND_UNKNOWN;
|
||||||
MccCelestialPoint cp{.pair_kind = MccCoordPairKind::COORDS_KIND_RADEC_ICRS};
|
impl::MccSkyPoint sp;
|
||||||
|
|
||||||
auto sz = input_msg.paramSize();
|
auto sz = input_msg.paramSize();
|
||||||
if (sz) { // set or get operation
|
if (sz) { // set or get operation
|
||||||
auto vp = input_msg.template paramValue<MccCoordPairKind>(0); // is it get operation?
|
auto vp = input_msg.template paramValue<impl::MccCoordPairKind>(0); // is it get operation?
|
||||||
if (vp) { // coordinate pair kind is given, it is get operation
|
if (vp) { // coordinate pair kind is given, it is get operation
|
||||||
cp.pair_kind = vp.value();
|
pair_kind = vp.value();
|
||||||
err = coordsFromTelemetryData(*mount_ptr, true, cp);
|
err = coordsFromTelemetryData(mount_ptr, true, pair_kind, sp);
|
||||||
if (!err) {
|
if (!err) {
|
||||||
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, MCC_COMMPROTO_KEYWORD_TARGET_STR,
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, MCC_COMMPROTO_KEYWORD_TARGET_STR,
|
||||||
_coordFormat, _coordPrec, cp);
|
_coordFormat, _coordPrec, sp);
|
||||||
}
|
}
|
||||||
} else { // here a celestial point must be given
|
} else { // here a celestial point must be given
|
||||||
auto vc = input_msg.template paramValue<MccCelestialPoint>(0);
|
auto vc = input_msg.template paramValue<impl::MccSkyPoint>(0);
|
||||||
if (vc) { // set operation
|
if (vc) { // set operation
|
||||||
auto m_err = mount_ptr->setPointingTarget(vc.value());
|
auto m_err = mount_ptr->setPointingTarget(vc.value());
|
||||||
if (m_err) {
|
if (m_err) {
|
||||||
if (m_err) {
|
err = mcc_deduce_err(m_err, MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_SET_TARGET);
|
||||||
err = mcc_deduce_error_code(
|
|
||||||
m_err, MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_SET_TARGET);
|
|
||||||
}
|
|
||||||
} else {
|
} else {
|
||||||
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, input_msg.byteRepr());
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, input_msg.byteRepr());
|
||||||
}
|
}
|
||||||
@@ -1087,42 +1097,38 @@ protected:
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else { // get operation
|
} else { // get operation
|
||||||
err = coordsFromTelemetryData(*mount_ptr, true, cp);
|
err = coordsFromTelemetryData(mount_ptr, true, pair_kind, sp);
|
||||||
if (!err) {
|
if (!err) {
|
||||||
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, MCC_COMMPROTO_KEYWORD_TARGET_STR,
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, MCC_COMMPROTO_KEYWORD_TARGET_STR,
|
||||||
_coordFormat, _coordPrec, cp);
|
_coordFormat, _coordPrec, sp);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_MOUNT_STR)) {
|
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_MOUNT_STR)) {
|
||||||
// by default return ICRS coordinates
|
impl::MccCoordPairKind pair_kind = impl::MccCoordPairKind::COORDS_KIND_UNKNOWN;
|
||||||
MccCelestialPoint cp{.pair_kind = MccCoordPairKind::COORDS_KIND_RADEC_ICRS};
|
impl::MccSkyPoint sp;
|
||||||
|
|
||||||
if (input_msg.paramSize()) { // ccordinate pair kind is given
|
if (input_msg.paramSize()) { // ccordinate pair kind is given
|
||||||
auto vp = input_msg.template paramValue<MccCoordPairKind>(0);
|
auto vp = input_msg.template paramValue<impl::MccCoordPairKind>(0);
|
||||||
if (vp) { // coordinate pair kind is given
|
if (vp) { // coordinate pair kind is given
|
||||||
cp.pair_kind = vp.value();
|
pair_kind = vp.value();
|
||||||
err = coordsFromTelemetryData(*mount_ptr, false, cp);
|
|
||||||
if (!err) {
|
|
||||||
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, MCC_COMMPROTO_KEYWORD_MOUNT_STR,
|
|
||||||
_coordFormat, _coordPrec, cp);
|
|
||||||
}
|
|
||||||
} else { // invalid command!!!
|
} else { // invalid command!!!
|
||||||
err = vp.error();
|
err = vp.error();
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
} else {
|
if (!err) {
|
||||||
err = coordsFromTelemetryData(*mount_ptr, false, cp);
|
err = coordsFromTelemetryData(mount_ptr, false, pair_kind, sp);
|
||||||
if (!err) {
|
if (!err) {
|
||||||
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, MCC_COMMPROTO_KEYWORD_MOUNT_STR,
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, MCC_COMMPROTO_KEYWORD_MOUNT_STR,
|
||||||
_coordFormat, _coordPrec, cp);
|
_coordFormat, _coordPrec, sp);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_TELEMETRY_STR)) {
|
|
||||||
MccTelemetryData tdata;
|
|
||||||
|
|
||||||
// auto t_err = mount_ptr->telemetryData(&tdata);
|
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_TELEMETRY_STR)) {
|
||||||
auto t_err = mount_ptr->waitForTelemetryData(&tdata);
|
typename MountT::telemetry_data_t tdata;
|
||||||
|
|
||||||
|
auto t_err = mount_ptr->telemetryData(&tdata);
|
||||||
if (t_err) {
|
if (t_err) {
|
||||||
err = mcc_deduce_error_code(t_err, MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_GET_TELEMETRY);
|
err = mcc_deduce_error_code(t_err, MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_GET_TELEMETRY);
|
||||||
} else {
|
} else {
|
||||||
@@ -1166,79 +1172,90 @@ protected:
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
std::error_code coordsFromTelemetryData(mcc_generic_mount_c auto& mount,
|
template <mcc_generic_mount_c MountT>
|
||||||
|
std::error_code coordsFromTelemetryData(MountT* mount,
|
||||||
bool target, // true - target coordinates, false - mount coordinates
|
bool target, // true - target coordinates, false - mount coordinates
|
||||||
mcc_celestial_point_c auto& cp)
|
impl::MccCoordPairKind pair_kind,
|
||||||
|
mcc_skypoint_c auto& sp)
|
||||||
{
|
{
|
||||||
MccTelemetryData tdata;
|
typename MountT::telemetry_data_t tdata;
|
||||||
|
|
||||||
auto t_err = mount.waitForTelemetryData(&tdata);
|
auto t_err = mount->telemetryData(&tdata);
|
||||||
// auto t_err = mount.telemetryData(&tdata);
|
|
||||||
if (t_err) {
|
if (t_err) {
|
||||||
return mcc_deduce_error_code(t_err, MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_GET_TELEMETRY);
|
return mcc_deduce_err(t_err, MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_GET_TELEMETRY);
|
||||||
}
|
}
|
||||||
|
|
||||||
mcc_tp2tp(tdata.target.time_point, cp.time_point);
|
auto get_coords = [&]<mcc_coord_pair_c T>(T& cp) {
|
||||||
|
cp.setEpoch(tdata.mountPos.epoch());
|
||||||
|
|
||||||
switch (cp.pair_kind) {
|
if (target) {
|
||||||
case mcc::MccCoordPairKind::COORDS_KIND_RADEC_ICRS:
|
auto err = tdata.targetPos.to(cp);
|
||||||
|
if (err) {
|
||||||
|
return mcc_deduced_err(err, MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_COORD_TRANSFORM);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
auto err = tdata.mountPos.to(cp);
|
||||||
|
if (err) {
|
||||||
|
return mcc_deduced_err(err, MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_COORD_TRANSFORM);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
sp.from(cp);
|
||||||
|
|
||||||
|
return MccGenericMountNetworkServerErrorCode::ERROR_OK;
|
||||||
|
};
|
||||||
|
|
||||||
|
switch (pair_kind) {
|
||||||
|
case impl::MccCoordPairKind::COORDS_KIND_RADEC_ICRS: {
|
||||||
|
impl::MccSkyRADEC_ICRS cp;
|
||||||
|
return get_coords(cp);
|
||||||
|
} break;
|
||||||
|
case impl::MccCoordPairKind::COORDS_KIND_RADEC_OBS: {
|
||||||
|
impl::MccSkyRADEC_OBS cp;
|
||||||
|
return get_coords(cp);
|
||||||
|
} break;
|
||||||
|
case impl::MccCoordPairKind::COORDS_KIND_HADEC_OBS: {
|
||||||
|
impl::MccSkyHADEC_OBS cp;
|
||||||
|
return get_coords(cp);
|
||||||
|
} break;
|
||||||
|
case impl::MccCoordPairKind::COORDS_KIND_RADEC_APP: {
|
||||||
|
impl::MccSkyRADEC_APP cp;
|
||||||
|
return get_coords(cp);
|
||||||
|
} break;
|
||||||
|
case impl::MccCoordPairKind::COORDS_KIND_HADEC_APP: {
|
||||||
|
impl::MccSkyHADEC_APP cp;
|
||||||
|
return get_coords(cp);
|
||||||
|
} break;
|
||||||
|
case impl::MccCoordPairKind::COORDS_KIND_AZZD: {
|
||||||
|
impl::MccSkyAZZD cp;
|
||||||
|
return get_coords(cp);
|
||||||
|
} break;
|
||||||
|
case impl::MccCoordPairKind::COORDS_KIND_AZALT: {
|
||||||
|
impl::MccSkyAZALT cp;
|
||||||
|
return get_coords(cp);
|
||||||
|
} break;
|
||||||
|
case impl::MccCoordPairKind::COORDS_KIND_XY: // interpretated as encoder coordinates
|
||||||
|
case impl::MccCoordPairKind::COORDS_KIND_GENERIC: { // interpretated as encoder coordinates
|
||||||
if (target) {
|
if (target) {
|
||||||
cp.X = tdata.target.RA_ICRS;
|
// WARNING: STILL NOT IMPLEMENTED!!!
|
||||||
cp.Y = tdata.target.DEC_ICRS;
|
|
||||||
mcc_tp2tp(MccCelestialCoordEpoch::J2000_UTC, cp.time_point);
|
|
||||||
} // ??!!!
|
|
||||||
break;
|
|
||||||
case mcc::MccCoordPairKind::COORDS_KIND_RADEC_APP:
|
|
||||||
if (target) {
|
|
||||||
cp.X = tdata.target.RA_APP;
|
|
||||||
cp.Y = tdata.target.DEC_APP;
|
|
||||||
} else {
|
} else {
|
||||||
cp.X = tdata.RA_APP;
|
sp.from(tdata.hwState.XY);
|
||||||
cp.Y = tdata.DEC_APP;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
break;
|
return MccGenericMountNetworkServerErrorCode::ERROR_OK;
|
||||||
case mcc::MccCoordPairKind::COORDS_KIND_HADEC_APP:
|
} break;
|
||||||
|
case impl::MccCoordPairKind::COORDS_KIND_UNKNOWN: { // interpretated as no transformation
|
||||||
if (target) {
|
if (target) {
|
||||||
cp.X = tdata.target.HA;
|
sp = tdata.targetPos;
|
||||||
cp.Y = tdata.target.DEC_APP;
|
|
||||||
} else {
|
} else {
|
||||||
cp.X = tdata.HA;
|
sp = tdata.mountPos;
|
||||||
cp.Y = tdata.DEC_APP;
|
|
||||||
}
|
}
|
||||||
break;
|
}
|
||||||
case mcc::MccCoordPairKind::COORDS_KIND_AZZD:
|
|
||||||
if (target) {
|
|
||||||
cp.X = tdata.target.AZ;
|
|
||||||
cp.Y = tdata.target.ZD;
|
|
||||||
} else {
|
|
||||||
cp.X = tdata.AZ;
|
|
||||||
cp.Y = tdata.ZD;
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case mcc::MccCoordPairKind::COORDS_KIND_AZALT:
|
|
||||||
if (target) {
|
|
||||||
cp.X = tdata.target.AZ;
|
|
||||||
cp.Y = tdata.target.ALT;
|
|
||||||
} else {
|
|
||||||
cp.X = tdata.AZ;
|
|
||||||
cp.Y = tdata.ALT;
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case mcc::MccCoordPairKind::COORDS_KIND_XY:
|
|
||||||
if (target) {
|
|
||||||
cp.X = tdata.target.X;
|
|
||||||
cp.Y = tdata.target.Y;
|
|
||||||
} else {
|
|
||||||
cp.X = tdata.X;
|
|
||||||
cp.Y = tdata.Y;
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
default:
|
default:
|
||||||
return std::make_error_code(std::errc::invalid_argument);
|
return std::make_error_code(std::errc::invalid_argument);
|
||||||
}
|
}
|
||||||
|
|
||||||
return {};
|
return MccGenericMountNetworkServerErrorCode::ERROR_OK;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|||||||
@@ -10,9 +10,9 @@
|
|||||||
#include <string_view>
|
#include <string_view>
|
||||||
|
|
||||||
|
|
||||||
#include "mcc_utils.h"
|
|
||||||
#include "mcc_serializer.h"
|
|
||||||
#include "mcc_deserializer.h"
|
#include "mcc_deserializer.h"
|
||||||
|
#include "mcc_serializer.h"
|
||||||
|
#include "mcc_utils.h"
|
||||||
|
|
||||||
namespace mcc::network
|
namespace mcc::network
|
||||||
{
|
{
|
||||||
@@ -251,10 +251,8 @@ template <mcc::traits::mcc_char_range BYTEREPR_T = std::string_view,
|
|||||||
class MccNetMessage
|
class MccNetMessage
|
||||||
{
|
{
|
||||||
protected:
|
protected:
|
||||||
|
|
||||||
// just a wrapper class to hold MccSerializer<T> specializations
|
// just a wrapper class to hold MccSerializer<T> specializations
|
||||||
struct DefaultSerializer
|
struct DefaultSerializer {
|
||||||
{
|
|
||||||
template <traits::mcc_output_char_range OR, typename T>
|
template <traits::mcc_output_char_range OR, typename T>
|
||||||
auto operator()(OR& bytes, const T& value, mcc_serialization_params_c auto const& pars) const
|
auto operator()(OR& bytes, const T& value, mcc_serialization_params_c auto const& pars) const
|
||||||
{
|
{
|
||||||
@@ -403,7 +401,13 @@ public:
|
|||||||
template <typename T, typename DeserFuncT>
|
template <typename T, typename DeserFuncT>
|
||||||
std::expected<T, std::error_code> paramValue(size_t idx, DeserFuncT&& deser_func) const
|
std::expected<T, std::error_code> paramValue(size_t idx, DeserFuncT&& deser_func) const
|
||||||
{
|
{
|
||||||
static_assert(std::invocable<DeserFuncT, typename decltype(_params)::value_type const&, T&, impl::mcc_serialization_params_t const&>, "INVALID DESERIALIZTION FUNCTION!");
|
static_assert(std::invocable<DeserFuncT, typename decltype(_params)::value_type const&, T&,
|
||||||
|
impl::mcc_serialization_params_t const&>,
|
||||||
|
"INVALID DESERIALIZATION FUNCTION!");
|
||||||
|
static_assert(std::same_as<std::invoke_result_t<DeserFuncT, typename decltype(_params)::value_type const&, T&,
|
||||||
|
impl::mcc_serialization_params_t const&>,
|
||||||
|
std::error_code>,
|
||||||
|
"INVALID DESERIALIZATION FUNCTION!");
|
||||||
|
|
||||||
if (idx >= _params.size()) {
|
if (idx >= _params.size()) {
|
||||||
return std::unexpected{std::make_error_code(std::errc::value_too_large)};
|
return std::unexpected{std::make_error_code(std::errc::value_too_large)};
|
||||||
@@ -422,7 +426,8 @@ public:
|
|||||||
template <typename T>
|
template <typename T>
|
||||||
std::expected<T, std::error_code> paramValue(size_t idx) const
|
std::expected<T, std::error_code> paramValue(size_t idx) const
|
||||||
{
|
{
|
||||||
return paramValue<T>(idx, impl::MccDeserializer<T>{}); // use one of specialization of MccDeserializer templated class
|
return paramValue<T>(
|
||||||
|
idx, impl::MccDeserializer<T>{}); // use one of specialization of MccDeserializer templated class
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -562,13 +567,12 @@ protected:
|
|||||||
|
|
||||||
DefaultSerializer _defaultSerializer{};
|
DefaultSerializer _defaultSerializer{};
|
||||||
|
|
||||||
impl::mcc_serialization_params_t _serializationParams{.seq_delim{MCC_COMMPROTO_PARAMPARAM_DELIM_SEQ}, .elem_delim{MCC_COMMPROTO_RANGEPARAM_DELIM_SEQ}};
|
impl::mcc_serialization_params_t _serializationParams{.seq_delim{MCC_COMMPROTO_PARAMPARAM_DELIM_SEQ},
|
||||||
|
.elem_delim{MCC_COMMPROTO_RANGEPARAM_DELIM_SEQ}};
|
||||||
|
|
||||||
template <typename SerFuncT, typename T, typename... Ts>
|
template <typename SerFuncT, typename T, typename... Ts>
|
||||||
void convertFunc(SerFuncT&& ser_func, std::vector<size_t>& idx, const T& par, const Ts&... pars)
|
void convertFunc(SerFuncT&& ser_func, std::vector<size_t>& idx, const T& par, const Ts&... pars)
|
||||||
requires(!std::same_as<std::remove_cvref_t<SerFuncT>, std::vector<size_t>>)
|
|
||||||
{
|
{
|
||||||
|
|
||||||
if constexpr (std::same_as<T, MccSerializedCoordPairFormat>) {
|
if constexpr (std::same_as<T, MccSerializedCoordPairFormat>) {
|
||||||
_serializationParams.coordpair_format = par;
|
_serializationParams.coordpair_format = par;
|
||||||
} else if constexpr (std::same_as<T, MccSerializedAngleFormatPrec>) {
|
} else if constexpr (std::same_as<T, MccSerializedAngleFormatPrec>) {
|
||||||
@@ -576,8 +580,6 @@ protected:
|
|||||||
} else {
|
} else {
|
||||||
idx.emplace_back(std::distance(_msgBuffer.begin(), _msgBuffer.end()));
|
idx.emplace_back(std::distance(_msgBuffer.begin(), _msgBuffer.end()));
|
||||||
|
|
||||||
// convertFunc(std::forward<SerFuncT>(ser_func), idx, par);
|
|
||||||
|
|
||||||
std::forward<SerFuncT>(ser_func)(_msgBuffer, par, _serializationParams);
|
std::forward<SerFuncT>(ser_func)(_msgBuffer, par, _serializationParams);
|
||||||
|
|
||||||
idx.emplace_back(std::distance(_msgBuffer.begin(), _msgBuffer.end()));
|
idx.emplace_back(std::distance(_msgBuffer.begin(), _msgBuffer.end()));
|
||||||
|
|||||||
@@ -64,7 +64,7 @@ static constexpr MccSerializedAngleFormat MccSerializedAngleFormatStrToValue(R&&
|
|||||||
|
|
||||||
enum class MccSerializedCoordPairFormat {
|
enum class MccSerializedCoordPairFormat {
|
||||||
MCC_SERIALIZED_FORMAT_DEGREES, // both angles are in degrees as floating-point number
|
MCC_SERIALIZED_FORMAT_DEGREES, // both angles are in degrees as floating-point number
|
||||||
MCC_SERIALIZED_FORMAT_SXGM_HOURDEG, // X is in hour and Y is in degree sexagesimal representation
|
MCC_SERIALIZED_FORMAT_SXGM_HOURDEG, // X is in hour (if RA or HA) and Y is in degree sexagesimal representation
|
||||||
MCC_SERIALIZED_FORMAT_SXGM_DEGDEG, // both angles are in sexagesimal degrees
|
MCC_SERIALIZED_FORMAT_SXGM_DEGDEG, // both angles are in sexagesimal degrees
|
||||||
MCC_SERIALIZED_FORMAT_UNKNOWN
|
MCC_SERIALIZED_FORMAT_UNKNOWN
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -228,7 +228,9 @@ struct MccSerializer<VT> : MccSerializerBase {
|
|||||||
VT const& value,
|
VT const& value,
|
||||||
ParamsT const& params = mcc_serialization_params_t{})
|
ParamsT const& params = mcc_serialization_params_t{})
|
||||||
{
|
{
|
||||||
std::vformat_to(std::back_inserter(output), params.systime_format, std::make_format_args(value));
|
// std::vformat_to(std::back_inserter(output), params.systime_format, std::make_format_args(value));
|
||||||
|
auto tp = std::chrono::round<std::chrono::milliseconds>(value);
|
||||||
|
std::vformat_to(std::back_inserter(output), params.systime_format, std::make_format_args(tp));
|
||||||
|
|
||||||
return MccSerializerErrorCode::ERROR_OK;
|
return MccSerializerErrorCode::ERROR_OK;
|
||||||
}
|
}
|
||||||
@@ -249,9 +251,14 @@ struct MccSerializer<VT> : MccSerializerBase {
|
|||||||
std::string sgm;
|
std::string sgm;
|
||||||
|
|
||||||
switch (params.angle_format) {
|
switch (params.angle_format) {
|
||||||
case MccSerializedAngleFormat::MCC_SERIALIZED_FORMAT_DEGREES:
|
case MccSerializedAngleFormat::MCC_SERIALIZED_FORMAT_DEGREES: {
|
||||||
v *= MCC_RADS_TO_DEGRESS;
|
v *= MCC_RADS_TO_DEGRESS;
|
||||||
return MccSerializer<double>{}(output, v, params);
|
std::string_view fmt = "{:." + std::to_string(params.angle_prec.decimals) + "f}";
|
||||||
|
std::vformat_to(std::back_inserter(output), fmt, std::make_format_args(v));
|
||||||
|
|
||||||
|
return MccSerializerErrorCode::ERROR_OK;
|
||||||
|
}
|
||||||
|
// return MccSerializer<double>{}(output, v, params);
|
||||||
case MccSerializedAngleFormat::MCC_SERIALIZED_FORMAT_SXGM_DEGS:
|
case MccSerializedAngleFormat::MCC_SERIALIZED_FORMAT_SXGM_DEGS:
|
||||||
if (params.norm_sxgm) {
|
if (params.norm_sxgm) {
|
||||||
sgm = utils::rad2sxg<true>(v, false, params.angle_prec.deg_prec);
|
sgm = utils::rad2sxg<true>(v, false, params.angle_prec.deg_prec);
|
||||||
@@ -716,6 +723,53 @@ struct MccSerializer<VT> : MccSerializerBase {
|
|||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
template <>
|
||||||
|
struct MccSerializer<MccSerializedCoordPairFormat> : MccSerializerBase {
|
||||||
|
constexpr static std::string_view serializerName{"MCC-COORDPAIR-FORMAT-SERIALIZER"};
|
||||||
|
|
||||||
|
template <mcc_serialization_params_c ParamsT = mcc_serialization_params_t>
|
||||||
|
error_t operator()(traits::mcc_output_char_range auto& output,
|
||||||
|
MccSerializedCoordPairFormat const& value,
|
||||||
|
ParamsT const& params = mcc_serialization_params_t{})
|
||||||
|
{
|
||||||
|
std::ranges::copy(MccSerializedCoordPairFormatToStr(value), std::back_inserter(output));
|
||||||
|
|
||||||
|
return MccSerializerErrorCode::ERROR_OK;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
template <>
|
||||||
|
struct MccSerializer<MccSerializedAngleFormatPrec> : MccSerializerBase {
|
||||||
|
constexpr static std::string_view serializerName{"MCC-ANGLE-FORMAT-PREC-SERIALIZER"};
|
||||||
|
|
||||||
|
template <mcc_serialization_params_c ParamsT = mcc_serialization_params_t>
|
||||||
|
error_t operator()(traits::mcc_output_char_range auto& output,
|
||||||
|
MccSerializedAngleFormatPrec const& value,
|
||||||
|
ParamsT const& params = mcc_serialization_params_t{})
|
||||||
|
{
|
||||||
|
auto err = MccSerializer<decltype(value.hour_prec)>{}(output, value.hour_prec, params);
|
||||||
|
if (!err) {
|
||||||
|
auto err = MccSerializer<decltype(value.deg_prec)>{}(output, value.deg_prec, params);
|
||||||
|
if (!err) {
|
||||||
|
auto err = MccSerializer<decltype(value.decimals)>{}(output, value.decimals, params);
|
||||||
|
if (err) {
|
||||||
|
return mcc_deduced_err(err, MccSerializerErrorCode::ERROR_UNDERLYING_SERIALIZER);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
return mcc_deduced_err(err, MccSerializerErrorCode::ERROR_UNDERLYING_SERIALIZER);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
return mcc_deduced_err(err, MccSerializerErrorCode::ERROR_UNDERLYING_SERIALIZER);
|
||||||
|
}
|
||||||
|
|
||||||
|
return MccSerializerErrorCode::ERROR_OK;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
static_assert(mcc_serializer_c<MccSerializer<MccAngle>>, "!!!");
|
static_assert(mcc_serializer_c<MccSerializer<MccAngle>>, "!!!");
|
||||||
|
|
||||||
} // namespace mcc::impl
|
} // namespace mcc::impl
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
#include <print>
|
|
||||||
#include <list>
|
#include <list>
|
||||||
|
#include <print>
|
||||||
|
|
||||||
#include <mcc_netserver_proto.h>
|
#include <mcc_netserver_proto.h>
|
||||||
|
|
||||||
@@ -24,7 +24,7 @@ int main()
|
|||||||
msg2_t msg2("ACK", 12.43298042, "EEE", std::chrono::seconds(10), vd);
|
msg2_t msg2("ACK", 12.43298042, "EEE", std::chrono::seconds(10), vd);
|
||||||
// msg2_t msg2("ACK");
|
// msg2_t msg2("ACK");
|
||||||
|
|
||||||
std::println("msg.bytes = <{}>",msg2.byteRepr());
|
std::println("msg.bytes = <{}>", msg2.byteRepr());
|
||||||
std::println("msg.key = <{}>", msg2.keyword());
|
std::println("msg.key = <{}>", msg2.keyword());
|
||||||
std::println("msg.par[1] = <{}>", msg2.param(1));
|
std::println("msg.par[1] = <{}>", msg2.param(1));
|
||||||
std::println("msg.par[2] = <{}>", msg2.param(2));
|
std::println("msg.par[2] = <{}>", msg2.param(2));
|
||||||
@@ -58,16 +58,20 @@ int main()
|
|||||||
|
|
||||||
mcc::impl::MccSkyPoint spt(mcc::impl::MccSkyRADEC_APP{"10:00:00.0"_hms, 12.098687_degs});
|
mcc::impl::MccSkyPoint spt(mcc::impl::MccSkyRADEC_APP{"10:00:00.0"_hms, 12.098687_degs});
|
||||||
|
|
||||||
msg2.construct("ACK", "MOUNT", spt);
|
msg2.construct("ACK", "MOUNT", mcc::MccSerializedAngleFormatPrec{3, 2}, spt);
|
||||||
std::println("msg2.bytes = <{}>", msg2.byteRepr());
|
std::println("msg2.bytes = <{}>", msg2.byteRepr());
|
||||||
|
|
||||||
auto spt_d = msg2.paramValue<mcc::impl::MccSkyPoint>(1);
|
auto spt_d = msg2.paramValue<mcc::impl::MccSkyPoint>(1);
|
||||||
|
|
||||||
if (spt_d){
|
if (spt_d) {
|
||||||
std::println("msg2.parvalue(1).epoch() = {}", spt_d->epoch().MJD()+mcc::MCC_MJD_ZERO);
|
std::println("msg2.parvalue(1).pairKind() = {}", MccCoordPairKindToStr(spt_d->pairKind()));
|
||||||
|
std::println("msg2.parvalue(1).epoch() = {}", spt_d->epoch().MJD() + mcc::MCC_MJD_ZERO);
|
||||||
} else {
|
} else {
|
||||||
std::println("cannot deserialize MccSkyPoint value!");
|
std::println("cannot deserialize MccSkyPoint value!");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
msg2.construct("ACK", "MOUNT", mcc::MccSerializedCoordPairFormat::MCC_SERIALIZED_FORMAT_DEGREES, spt);
|
||||||
|
std::println("msg2.bytes = <{}>", msg2.byteRepr());
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user