swift
datarefs.h
Go to the documentation of this file.
1 // SPDX-FileCopyrightText: Copyright (C) 2013 swift Project Community / Contributors
2 // SPDX-License-Identifier: GPL-3.0-or-later OR LicenseRef-swift-pilot-client-1
3 
4 #ifndef SWIFT_SIM_XSWIFTBUS_DATAREFS_H
5 #define SWIFT_SIM_XSWIFTBUS_DATAREFS_H
6 
8 
9 #include <XPLM/XPLMDataAccess.h>
10 #include <XPLM/XPLMUtilities.h>
11 
12 #include <array>
13 #include <cassert>
14 #include <string>
15 
16 // Avoid checking large auto-generated header with cppcheck
17 #ifndef CPPCHECK
18 # include "datarefs.inc"
19 #endif
20 
21 namespace XSwiftBus
22 {
23 
25  class DataRefImpl
26  {
27  public:
28  DataRefImpl(char const *name) : m_ref(XPLMFindDataRef(name))
29  {
30  if (!m_ref)
31  {
32  XPLMDebugString("Missing dataref:");
33  XPLMDebugString(name);
34  XPLMDebugString("\n");
35  }
36  }
37 
38  bool isValid() const { return m_ref; }
39 
40  template <typename T>
41  void implSet(T);
42 
43  template <typename T>
44  T implGet() const;
45 
46  private:
47  XPLMDataRef m_ref;
48  };
49 
51  class ArrayDataRefImpl
52  {
53  public:
54  ArrayDataRefImpl(char const *name, int size) : m_ref(XPLMFindDataRef(name)), m_size(size)
55  {
56  if (!m_ref)
57  {
58  XPLMDebugString("Missing dataref:");
59  XPLMDebugString(name);
60  XPLMDebugString("\n");
61  }
62  }
63 
64  bool isValid() const { return m_ref; }
65 
66  template <typename T>
67  void implSetAll(T *const);
68 
69  template <typename T>
70  void implGetAll(T *) const;
71 
72  template <typename T>
73  void implSetAt(int index, T);
74 
75  template <typename T>
76  T implGetAt(int index) const;
77 
78  private:
79  XPLMDataRef m_ref;
80  int const m_size;
81  };
82 
88  template <class DataRefTraits>
89  class DataRef : private DataRefImpl
90  {
91  static_assert(!DataRefTraits::is_array, "this is an array dataref");
92 
93  public:
95  DataRef() : DataRefImpl(DataRefTraits::name()) {}
96 
98  using TraitsType = DataRefTraits;
99 
101  using DataRefType = typename DataRefTraits::type;
102 
104  void set(DataRefType d)
105  {
106  static_assert(DataRefTraits::writable, "read-only dataref");
107  DataRefImpl::implSet(d);
108  }
109 
111  void setAsInt(int d) { this->set(static_cast<DataRefType>(d)); }
112 
114  void setAsDouble(double d) { this->set(static_cast<DataRefType>(d)); }
115 
117  DataRefType get() const { return DataRefImpl::implGet<DataRefType>(); }
118 
119  using DataRefImpl::isValid;
120  };
121 
127  template <class DataRefTraits>
128  class ArrayDataRef : private ArrayDataRefImpl
129  {
130  static_assert(DataRefTraits::is_array, "not an array dataref");
131 
132  public:
134  ArrayDataRef() : ArrayDataRefImpl(DataRefTraits::name(), DataRefTraits::size) {}
135 
137  using TraitsType = DataRefTraits;
138 
140  using DataRefType = typename DataRefTraits::type;
141 
143  static constexpr auto DataRefSize = DataRefTraits::size;
144 
146  void setAll(std::array<DataRefType, DataRefSize> const &a)
147  {
148  static_assert(DataRefTraits::writable, "read-only dataref");
149  ArrayDataRefImpl::implSetAll<DataRefType>(a.data());
150  }
151 
153  std::array<DataRefType, DataRefSize> getAll() const
154  {
155  std::array<DataRefType, DataRefSize> result;
156  ArrayDataRefImpl::implGetAll<DataRefType>(result.data());
157  return result;
158  }
159 
161  void setAt(int index, DataRefType d)
162  {
163  static_assert(DataRefTraits::writable, "read-only dataref");
164  ArrayDataRefImpl::implSetAt(index, d);
165  }
166 
168  DataRefType getAt(int index) const { return ArrayDataRefImpl::implGetAt<DataRefType>(index); }
169 
170  using ArrayDataRefImpl::isValid;
171  };
172 
178  template <class DataRefTraits>
180  {
181  static_assert(DataRefTraits::is_array, "not an array dataref");
182 
183  public:
185  StringDataRef() : m_ref(XPLMFindDataRef(DataRefTraits::name()))
186  {
187  if (!m_ref)
188  {
189  XPLMDebugString("Missing dataref:");
190  XPLMDebugString(DataRefTraits::name());
191  XPLMDebugString("\n");
192  }
193  }
194 
196  bool isValid() const { return m_ref; }
197 
199  void set(std::string const &s) { setSubstr(0, s); }
200 
202  std::string get() const { return getSubstr(0, DataRefTraits::size); }
203 
205  void setSubstr(size_t offset, std::string const &s)
206  {
207  static_assert(DataRefTraits::writable, "read-only dataref");
208  assert((s.size() + 1) <= (DataRefTraits::size - offset));
209  XPLMSetDatab(m_ref, (void *)s.c_str(), (int)offset, (int)s.size() + 1);
210  }
211 
213  std::string getSubstr(size_t offset, size_t size) const
214  {
215  std::string s(size, 0);
216  XPLMGetDatab(m_ref, &s[0], (int)offset, (int)size);
217  size = s.find(char(0));
218  if (size != std::string::npos) s.resize(size);
219  return s;
220  }
221 
222  private:
223  XPLMDataRef m_ref;
224  };
225 
226  template <>
227  inline void DataRefImpl::implSet<int>(int d)
228  {
229  XPLMSetDatai(m_ref, d);
230  }
231  template <>
232  inline void DataRefImpl::implSet<float>(float d)
233  {
234  XPLMSetDataf(m_ref, d);
235  }
236  template <>
237  inline void DataRefImpl::implSet<double>(double d)
238  {
239  XPLMSetDatad(m_ref, d);
240  }
241  template <>
242  inline int DataRefImpl::implGet<int>() const
243  {
244  return XPLMGetDatai(m_ref);
245  }
246  template <>
247  inline float DataRefImpl::implGet<float>() const
248  {
249  return XPLMGetDataf(m_ref);
250  }
251  template <>
252  inline double DataRefImpl::implGet<double>() const
253  {
254  return XPLMGetDatad(m_ref);
255  }
256 
257  template <>
258  inline void ArrayDataRefImpl::implSetAll(int const *v)
259  {
260  XPLMSetDatavi(m_ref, const_cast<int *>(v), 0, m_size);
261  }
262  template <>
263  inline void ArrayDataRefImpl::implSetAll(float const *v)
264  {
265  XPLMSetDatavf(m_ref, const_cast<float *>(v), 0, m_size);
266  }
267  template <>
268  inline void ArrayDataRefImpl::implGetAll(int *v) const
269  {
270  XPLMGetDatavi(m_ref, &v[0], 0, m_size);
271  }
272  template <>
273  inline void ArrayDataRefImpl::implGetAll(float *v) const
274  {
275  XPLMGetDatavf(m_ref, &v[0], 0, m_size);
276  }
277 
278  template <>
279  inline void ArrayDataRefImpl::implSetAt<int>(int i, int d)
280  {
281  assert(i <= m_size);
282  XPLMSetDatavi(m_ref, &d, i, 1);
283  }
284  template <>
285  inline void ArrayDataRefImpl::implSetAt<float>(int i, float d)
286  {
287  assert(i <= m_size);
288  XPLMSetDatavf(m_ref, &d, i, 1);
289  }
290  template <>
291  inline int ArrayDataRefImpl::implGetAt<int>(int i) const
292  {
293  assert(i <= m_size);
294  int d;
295  XPLMGetDatavi(m_ref, &d, i, 1);
296  return d;
297  }
298  template <>
299  inline float ArrayDataRefImpl::implGetAt<float>(int i) const
300  {
301  assert(i <= m_size);
302  float d;
303  XPLMGetDatavf(m_ref, &d, i, 1);
304  return d;
305  }
306 
307 } // namespace XSwiftBus
308 
309 #endif // SWIFT_SIM_XSWIFTBUS_DATAREFS_H
Class providing access to a single X-Plane array dataref.
Definition: datarefs.h:129
static constexpr auto DataRefSize
Array dataref size.
Definition: datarefs.h:143
std::array< DataRefType, DataRefSize > getAll() const
Get the value of the whole array.
Definition: datarefs.h:153
void setAt(int index, DataRefType d)
Set the value of a single element (if it is writable)
Definition: datarefs.h:161
void setAll(std::array< DataRefType, DataRefSize > const &a)
Set the value of the whole array (if it is writable)
Definition: datarefs.h:146
ArrayDataRef()
Constructor.
Definition: datarefs.h:134
DataRefType getAt(int index) const
Get the value of a single element.
Definition: datarefs.h:168
typename DataRefTraits::type DataRefType
Dataref type.
Definition: datarefs.h:140
DataRefTraits TraitsType
Traits type.
Definition: datarefs.h:137
Class providing access to a single X-Plane dataref.
Definition: datarefs.h:90
void set(DataRefType d)
Set the value of the dataref (if it is writable)
Definition: datarefs.h:104
void setAsDouble(double d)
Set as integer, avoids cast warnings such as "possible loss of data".
Definition: datarefs.h:114
void setAsInt(int d)
Set as integer, avoids cast warnings such as "possible loss of data".
Definition: datarefs.h:111
typename DataRefTraits::type DataRefType
Dataref type.
Definition: datarefs.h:101
DataRefTraits TraitsType
Traits type.
Definition: datarefs.h:98
DataRef()
Constructor.
Definition: datarefs.h:95
DataRefType get() const
Get the value of the dataref.
Definition: datarefs.h:117
Class providing access to a single X-Plane string dataref.
Definition: datarefs.h:180
void set(std::string const &s)
Set the value of the whole string (if it is writable)
Definition: datarefs.h:199
std::string getSubstr(size_t offset, size_t size) const
Get the value of part of the string.
Definition: datarefs.h:213
StringDataRef()
Constructor.
Definition: datarefs.h:185
bool isValid() const
True if the dataref exists.
Definition: datarefs.h:196
void setSubstr(size_t offset, std::string const &s)
Set the value of part of the string (if it is writable)
Definition: datarefs.h:205
std::string get() const
Get the value of the whole string.
Definition: datarefs.h:202
Plugin loaded by X-Plane which publishes a DBus service.
Definition: command.h:14