cc_tools_qt
Common Environment for Protocol Analysis.
Loading...
Searching...
No Matches
ToolsIntFieldImpl.h
1//
2// Copyright 2014 - 2025 (C). Alex Robenko. All rights reserved.
3//
4
5// This file is free software: you can redistribute it and/or modify
6// it under the terms of the GNU General Public License as published by
7// the Free Software Foundation, either version 3 of the License, or
8// (at your option) any later version.
9//
10// This program is distributed in the hope that it will be useful,
11// but WITHOUT ANY WARRANTY; without even the implied warranty of
12// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13// GNU General Public License for more details.
14//
15// You should have received a copy of the GNU General Public License
16// along with this program. If not, see <http://www.gnu.org/licenses/>.
17
18
19#pragma once
20
21#include "cc_tools_qt/details/ToolsNumericFieldImpl.h"
22#include "cc_tools_qt/field/ToolsIntField.h"
23
24#include "comms/field/IntValue.h"
25
26#include <cstdint>
27#include <cassert>
28#include <memory>
29#include <type_traits>
30
31namespace cc_tools_qt
32{
33
34namespace details
35{
36
37template <typename TField>
38class ToolsIntFieldImpl : public ToolsNumericFieldImpl<cc_tools_qt::field::ToolsIntField, TField>
39{
40 using Base = ToolsNumericFieldImpl<cc_tools_qt::field::ToolsIntField, TField>;
41 using Field = TField;
42 static_assert(comms::field::isIntValue<Field>(), "Must be of comms::field::IntValue type");
43
44public:
45
46 using UnderlyingType = typename Base::UnderlyingType;
47 using Ptr = typename Base::Ptr;
48 using ActPtr = typename Base::ActPtr;
49 using SpecialsList = typename Base::SpecialsList;
50
51 explicit ToolsIntFieldImpl(Field& fieldRef)
52 : Base(fieldRef)
53 {
54 }
55
56 ToolsIntFieldImpl(const ToolsIntFieldImpl&) = default;
57 ToolsIntFieldImpl(ToolsIntFieldImpl&&) = default;
58 virtual ~ToolsIntFieldImpl() noexcept = default;
59
60 ToolsIntFieldImpl& operator=(const ToolsIntFieldImpl&) = delete;
61
62protected:
63 virtual UnderlyingType minValueImpl() const override
64 {
65 return std::numeric_limits<typename Field::ValueType>::min();
66 }
67
68 virtual UnderlyingType maxValueImpl() const override
69 {
70 return std::numeric_limits<typename Field::ValueType>::max();
71 }
72
73 virtual double getScaledImpl() const override
74 {
75 return Base::field().template scaleAs<double>();
76 }
77
78 virtual void setScaledImpl(double value) override
79 {
80 using Tag =
81 std::conditional_t<
82 Field::hasFixedValue(),
83 NoFeatureTag,
84 HasFeatureTag
85 >;
86
87 setScaledInternal(value, Tag());
88 }
89
90 virtual double scaleValueImpl(UnderlyingType value) const override
91 {
92 using Tag =
93 std::conditional_t<
94 Field::hasFixedValue(),
95 NoFeatureTag,
96 HasFeatureTag
97 >;
98 return scaleValueInternal(value, Tag());
99 }
100
101 virtual bool isSignedImpl() const override
102 {
103 return std::is_signed<typename Field::ValueType>::value;
104 }
105
106 virtual std::size_t valueTypeSizeImpl() const override
107 {
108 return sizeof(typename Field::ValueType);
109 }
110
111 virtual Ptr cloneImpl() override
112 {
113 return ActPtr(new ToolsIntFieldImpl<TField>(Base::field()));
114 }
115
116 virtual const SpecialsList& specialsImpl() const override
117 {
118 using Tag =
119 std::conditional_t<
120 Field::hasSpecials(),
121 HasFeatureTag,
122 NoFeatureTag
123 >;
124
125 return specialsInternal(Tag());
126 }
127
128 virtual int scaledDecimalsImpl() const override
129 {
130 using Tag =
131 std::conditional_t<
132 Field::hasScaling(),
133 HasFeatureTag,
134 NoFeatureTag
135 >;
136
137 return scaledDecimalsInternal(Tag());
138 }
139
140 virtual UnderlyingType getDisplayValueImpl() const override
141 {
142 return static_cast<UnderlyingType>(Base::field().getDisplayValue());
143 }
144
145 virtual void setDisplayValueImpl(UnderlyingType value) override
146 {
147 using Tag =
148 std::conditional_t<
149 Field::hasFixedValue(),
150 NoFeatureTag,
151 HasFeatureTag
152 >;
153
154 setDisplayValueInternal(value, Tag());
155 }
156
157private:
158 struct HasFeatureTag{};
159 struct NoFeatureTag{};
160
161 static const SpecialsList& specialsInternal(HasFeatureTag)
162 {
163 static const SpecialsList List = createSpecialsList();
164 return List;
165 }
166
167 static const SpecialsList& specialsInternal(NoFeatureTag)
168 {
169 static const SpecialsList List;
170 return List;
171 }
172
173 static int scaledDecimalsInternal(HasFeatureTag)
174 {
175 return Field::displayDecimals();
176 }
177
178 static int scaledDecimalsInternal(NoFeatureTag)
179 {
180 return 0;
181 }
182
183 static SpecialsList createSpecialsList()
184 {
185 SpecialsList result;
186 auto mapInfo = Field::specialNamesMap();
187 for (auto idx = 0U; idx < mapInfo.second; ++idx) {
188 auto& sInfo = mapInfo.first[idx];
189 result.append(qMakePair(sInfo.second, static_cast<UnderlyingType>(sInfo.first)));
190 }
191
192 return result;
193 }
194
195 void setScaledInternal(double value, HasFeatureTag)
196 {
197 Base::field().setScaled(value);
198 }
199
200 void setScaledInternal([[maybe_unused]] double value, NoFeatureTag)
201 {
202 [[maybe_unused]] static constexpr bool Must_not_be_called = false;
203 assert(Must_not_be_called);
204 }
205
206 static double scaleValueInternal(UnderlyingType value, HasFeatureTag)
207 {
208 Field fieldTmp;
209 fieldTmp.setValue(value);
210 return fieldTmp.template scaleAs<double>();
211 }
212
213 static double scaleValueInternal([[maybe_unused]] UnderlyingType value, NoFeatureTag)
214 {
215 [[maybe_unused]] static constexpr bool Must_not_be_called = false;
216 assert(Must_not_be_called);
217 return 0.0;
218 }
219
220 void setDisplayValueInternal(UnderlyingType value, HasFeatureTag)
221 {
222 Base::field().setDisplayValue(value);
223 }
224
225 void setDisplayValueInternal([[maybe_unused]] UnderlyingType value, NoFeatureTag)
226 {
227 [[maybe_unused]] static constexpr bool Must_not_be_called = false;
228 assert(Must_not_be_called);
229 }
230
231};
232
233template <typename TField>
234auto makeIntField(TField& field)
235{
236 return std::make_unique<ToolsIntFieldImpl<TField>>(field);
237}
238
239} // namespace details
240
241} // namespace cc_tools_qt
Main namespace for all classes / functions of the shared library.