1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
|
#pragma once
#include "core/config/ivalue.hh"
#include "core/math/concepts.hh"
namespace config
{
template<math::Arithmetic T>
class Number : public IValue {
public:
explicit Number(T default_value = T(0));
explicit Number(T default_value, T min_value, T max_value);
virtual ~Number(void) = default;
virtual void set(std::string_view value) override;
virtual std::string_view get(void) const override;
T get_value(void) const;
void set_value(T value);
T get_min_value(void) const;
T get_max_value(void) const;
void set_limits(T min_value, T max_value);
private:
T m_value;
T m_min_value;
T m_max_value;
std::string m_string;
};
} // namespace config
namespace config
{
class Int final : public Number<int> {
public:
using Number<int>::Number;
};
class Float final : public Number<float> {
public:
using Number<float>::Number;
};
class Unsigned final : public Number<unsigned int> {
public:
using Number<unsigned int>::Number;
};
class Unsigned64 final : public Number<std::uint64_t> {
public:
using Number<std::uint64_t>::Number;
};
class SizeType final : public Number<std::size_t> {
public:
using Number<std::size_t>::Number;
};
} // namespace config
template<math::Arithmetic T>
inline config::Number<T>::Number(T default_value)
{
m_value = default_value;
m_min_value = std::numeric_limits<T>::lowest();
m_max_value = std::numeric_limits<T>::max();
m_string = std::to_string(default_value);
}
template<math::Arithmetic T>
inline config::Number<T>::Number(T default_value, T min_value, T max_value)
{
m_value = default_value;
m_min_value = min_value;
m_max_value = max_value;
m_string = std::to_string(default_value);
}
template<math::Arithmetic T>
inline void config::Number<T>::set(std::string_view value)
{
T parsed_value;
auto result = std::from_chars(value.data(), value.data() + value.size(), parsed_value);
if(result.ec == std::errc()) {
m_value = std::clamp(parsed_value, m_min_value, m_max_value);
m_string = std::to_string(m_value);
}
}
template<math::Arithmetic T>
inline std::string_view config::Number<T>::get(void) const
{
return m_string;
}
template<math::Arithmetic T>
inline T config::Number<T>::get_value(void) const
{
return m_value;
}
template<math::Arithmetic T>
inline void config::Number<T>::set_value(T value)
{
m_value = std::clamp(value, m_min_value, m_max_value);
m_string = std::to_string(m_value);
}
template<math::Arithmetic T>
inline T config::Number<T>::get_min_value(void) const
{
return m_min_value;
}
template<math::Arithmetic T>
inline T config::Number<T>::get_max_value(void) const
{
return m_max_value;
}
template<math::Arithmetic T>
inline void config::Number<T>::set_limits(T min_value, T max_value)
{
m_min_value = min_value;
m_max_value = max_value;
m_value = std::clamp(m_value, m_min_value, m_max_value);
m_string = std::to_string(m_value);
}
|