20#include "cc_tools_qt/details/ToolsNumericFieldImpl.h" 
   21#include "cc_tools_qt/field/ToolsFloatField.h" 
   23#include "comms/field/FloatValue.h" 
   36template <
typename TField>
 
   37class ToolsFloatFieldImpl : 
public ToolsNumericFieldImpl<cc_tools_qt::field::ToolsFloatField, TField>
 
   39    using Base = ToolsNumericFieldImpl<cc_tools_qt::field::ToolsFloatField, TField>;
 
   41    static_assert(comms::field::isFloatValue<Field>(), 
"Must be of FloatValueField type");
 
   44    using UnderlyingType = 
typename Base::UnderlyingType;
 
   45    using Ptr = 
typename Base::Ptr;
 
   46    using ActPtr = 
typename Base::ActPtr;
 
   47    using SpecialsList = 
typename Base::SpecialsList;
 
   49    explicit ToolsFloatFieldImpl(Field& fieldRef)
 
   54    ToolsFloatFieldImpl(
const ToolsFloatFieldImpl&) = 
default;
 
   55    ToolsFloatFieldImpl(ToolsFloatFieldImpl&&) = 
default;
 
   56    virtual ~ToolsFloatFieldImpl() noexcept = default;
 
   58    ToolsFloatFieldImpl& operator=(const ToolsFloatFieldImpl&) = delete;
 
   61    virtual Ptr cloneImpl()
 override 
   63        return ActPtr(
new ToolsFloatFieldImpl<TField>(Base::field()));
 
   66    virtual bool isNanImpl()
 const override 
   68        return std::isnan(Base::field().getValue());
 
   71    virtual void setNanImpl()
 override 
   73        setFieldValueInternal(std::numeric_limits<typename TField::ValueType>::quiet_NaN());
 
   76    virtual bool isInfImpl()
 const override 
   78        return std::isinf(Base::field().getValue()) && (0 < Base::field().getValue());
 
   81    virtual void setInfImpl()
 override 
   83        setFieldValueInternal(std::numeric_limits<typename TField::ValueType>::infinity());
 
   86    virtual bool isMinusInfImpl()
 const override 
   88        return std::isinf(Base::field().getValue()) && (Base::field().getValue() < 0);
 
   91    virtual void setMinusInfImpl()
 override 
   93        setFieldValueInternal(-std::numeric_limits<typename TField::ValueType>::infinity());
 
   96    virtual double getEpsilonImpl()
 const override 
   98        return static_cast<double>(std::numeric_limits<typename TField::ValueType>::epsilon());
 
  101    virtual const SpecialsList& specialsImpl()
 const override 
  105                Field::hasSpecials(),
 
  110        return specialsInternal(Tag());
 
  113    virtual int decimalsImpl()
 const override 
  115        return Field::displayDecimals();
 
  119    struct HasFeatureTag{};
 
  120    struct NoFeatureTag{};
 
  122    void setFieldValueInternal(
typename TField::ValueType val)
 
  126                Field::hasFixedValue(),
 
  131        setFieldValueInternal(val, Tag());
 
  134    void setFieldValueInternal(
typename TField::ValueType val, HasFeatureTag)
 
  136        Base::field().setValue(val);
 
  139    void setFieldValueInternal([[maybe_unused]] 
typename TField::ValueType val, NoFeatureTag)
 
  141        [[maybe_unused]] 
static constexpr bool Must_not_be_called = 
false;
 
  142        assert(Must_not_be_called);
 
  145    static const SpecialsList& specialsInternal(HasFeatureTag)
 
  147        static const SpecialsList List = createSpecialsList();
 
  151    static const SpecialsList& specialsInternal(NoFeatureTag)
 
  153        static const SpecialsList List;
 
  157    static SpecialsList createSpecialsList()
 
  160        auto mapInfo = Field::specialNamesMap();
 
  161        for (
auto idx = 0U; idx < mapInfo.second; ++idx) {
 
  162            auto& sInfo = mapInfo.first[idx];
 
  163            result.append(qMakePair(sInfo.second, 
static_cast<UnderlyingType
>(sInfo.first)));
 
  170template <
typename TField>
 
  171auto makeFloatField(TField& field)
 
  173    return std::make_unique<ToolsFloatFieldImpl<TField>>(field);