Trax3 3.1.0
trax track library
Loading...
Searching...
No Matches
SpatSupportXML.h
1// trax track library
2// AD 2014
3//
4// "You are too clever to be mentally ill."
5//
6// The Indelicates
7//
8// Copyright (c) 2025 Trend Redaktions- und Verlagsgesellschaft mbH
9// Copyright (c) 2019 Marc-Michael Horstmann
10//
11// Permission is hereby granted to any person obtaining a copy of this software
12// and associated source code (the "Software"), to use, view, and study the
13// Software for personal or internal business purposes, subject to the following
14// conditions:
15//
16// 1. Redistribution, modification, sublicensing, or commercial use of the
17// Software is NOT permitted without prior written consent from the copyright
18// holder.
19//
20// 2. The Software is provided "AS IS", without warranty of any kind, express
21// or implied.
22//
23// 3. All copies of the Software must retain this license notice.
24//
25// For further information, please contact: horstmann.marc@trendverlag.de
26
27#pragma once
28
29#include "common/Helpers.h"
30#include <boost/property_tree/ptree.hpp>
31
32
33namespace spat{
34
35 template<typename> struct Box;
36 template<typename,typename> struct Frame;
37 template<typename> struct Position;
38 template<typename> struct Position2D;
39 template<typename> struct Rect;
40 template<typename> struct Vector;
41 template<typename,typename> struct VectorBundle;
42 template<typename,typename> struct VectorBundle2;
43
50 namespace ptreesupport{
51
55 template<typename Valtype>
56 boost::property_tree::ptree& operator << ( boost::property_tree::ptree& opt, const Position<Valtype>& p );
57 template<typename Valtype>
58 boost::property_tree::ptree& operator >> ( boost::property_tree::ptree& ipt, Position<Valtype>& p );
59 template<typename Valtype>
60 boost::property_tree::ptree& operator << ( boost::property_tree::ptree& opt, const Position2D<Valtype>& p );
61 template<typename Valtype>
62 boost::property_tree::ptree& operator >> ( boost::property_tree::ptree& ipt, Position2D<Valtype>& p );
63 template<typename Valtype>
64 boost::property_tree::ptree& operator << ( boost::property_tree::ptree& opt, const Vector<Valtype>& v );
65 template<typename Valtype>
66 boost::property_tree::ptree& operator >> ( boost::property_tree::ptree& ipt, Vector<Valtype>& v );
67 template<typename Valtype,typename ValtypeT>
68 boost::property_tree::ptree& operator << ( boost::property_tree::ptree& opt, const VectorBundle<Valtype,ValtypeT>& vb );
69 template<typename Valtype,typename ValtypeT>
70 boost::property_tree::ptree& operator >> ( boost::property_tree::ptree& ipt, VectorBundle<Valtype,ValtypeT>& vb );
71 template<typename Valtype,typename ValtypeT>
72 boost::property_tree::ptree& operator << ( boost::property_tree::ptree& opt, const VectorBundle2<Valtype,ValtypeT>& vb2 );
73 template<typename Valtype,typename ValtypeT>
74 boost::property_tree::ptree& operator >> ( boost::property_tree::ptree& ipt, VectorBundle2<Valtype,ValtypeT>& vb2 );
75 template<typename Valtype,typename ValtypeT>
76 boost::property_tree::ptree& operator << ( boost::property_tree::ptree& opt, const Frame<Valtype,ValtypeT>& f );
77 template<typename Valtype,typename ValtypeT>
78 boost::property_tree::ptree& operator >> ( boost::property_tree::ptree& ipt, Frame<Valtype,ValtypeT>& f );
79 template<typename Valtype>
80 boost::property_tree::ptree& operator << ( boost::property_tree::ptree& pt, const Box<Valtype>& section );
81 template<typename Valtype>
82 boost::property_tree::ptree& operator << ( boost::property_tree::ptree& pt, const Rect<Valtype>& rect );
84
85
92 template<typename Valtype> inline
93 void ReadPosition( const boost::property_tree::ptree& pt, Position<Valtype>& position ){
94 position.x = common::DealDenormalizedNumbers(pt.get( "<xmlattr>.x", Valtype{0} ));
95 position.y = common::DealDenormalizedNumbers(pt.get( "<xmlattr>.y", Valtype{0} ));
96 position.z = common::DealDenormalizedNumbers(pt.get( "<xmlattr>.z", Valtype{0} ));
97 }
98
99 template<typename Valtype> inline
100 bool FindPosition( const boost::property_tree::ptree& pt, Position<Valtype>& position ){
101 auto iter = pt.find( "Position" );
102 if( iter == pt.not_found() )
103 return false;
104
105 ReadPosition( iter->second, position );
106 return true;
107 }
108
109 template<typename Valtype> inline
110 void ReadPosition2D( const boost::property_tree::ptree& pt, Position2D<Valtype>& position ){
111 position.x = common::DealDenormalizedNumbers(pt.get( "<xmlattr>.x", Valtype{0} ));
112 position.y = common::DealDenormalizedNumbers(pt.get( "<xmlattr>.y", Valtype{0} ));
113 }
114
115 template<typename Valtype> inline
116 void ReadVector( const boost::property_tree::ptree& pt, Vector<Valtype>& vector ){
117 vector.dx = common::DealDenormalizedNumbers(pt.get( "<xmlattr>.dx", Valtype{1} ));
118 vector.dy = common::DealDenormalizedNumbers(pt.get( "<xmlattr>.dy", Valtype{0} ));
119 vector.dz = common::DealDenormalizedNumbers(pt.get( "<xmlattr>.dz", Valtype{0} ));
120 }
121
122 template<typename Valtype> inline
123 bool FindVector( const boost::property_tree::ptree& pt, Vector<Valtype>& vector ){
124 const auto iter = pt.find( "Vector" );
125 if( iter == pt.not_found() )
126 return false;
127
128 ReadVector( iter->second, vector );
129 return true;
130 }
131
132 template<typename Valtype,typename ValtypeT> inline
133 void ReadFrame( const boost::property_tree::ptree& pt, Frame<Valtype,ValtypeT>& frame ){
134 frame.Init();
135
136 auto iter = pt.begin();
137
138 if( iter == pt.end() ||
139 iter->first != "Position" )
140 return;
141 ReadPosition( iter->second, frame.P );
142
143 if( ++iter == pt.end() ||
144 iter->first != "Vector" )
145 return;
146 ReadVector( iter->second, frame.T );
147
148 if( ++iter == pt.end() ||
149 iter->first != "Vector" )
150 return;
151 ReadVector( iter->second, frame.N );
152
153 if( ++iter == pt.end() ||
154 iter->first != "Vector" )
155 return;
156 ReadVector( iter->second, frame.B );
157 }
158
159 template<typename Valtype,typename ValtypeT> inline
160 bool FindFrame( const boost::property_tree::ptree& pt, Frame<Valtype,ValtypeT>& frame ){
161 const auto iter = pt.find( "Frame" );
162 if( iter == pt.not_found() )
163 return false;
164
165 ReadFrame( iter->second, frame );
166 return true;
167 }
168
169 template<typename Valtype,typename ValtypeT> inline
170 void ReadVectorBundle( const boost::property_tree::ptree& pt, VectorBundle<Valtype,ValtypeT>& VectorBundle ){
172
173 auto iter = pt.begin();
174
175 if( iter == pt.end() ||
176 iter->first != "Position" )
177 return;
178 ReadPosition( iter->second, VectorBundle.P );
179
180 if( ++iter == pt.end() ||
181 iter->first != "Vector" )
182 return;
183 ReadVector( iter->second, VectorBundle.T );
184 }
185
186 template<typename Valtype,typename ValtypeT> inline
187 void ReadVectorBundle2( const boost::property_tree::ptree& pt, VectorBundle2<Valtype,ValtypeT>& VectorBundle2 ){
189
190 auto iter = pt.begin();
191
192 if( iter == pt.end() ||
193 iter->first != "Position" )
194 return;
195 ReadPosition( iter->second, VectorBundle2.P );
196
197 if( ++iter == pt.end() ||
198 iter->first != "Vector" )
199 return;
200 ReadVector( iter->second, VectorBundle2.T );
201
202 if( ++iter == pt.end() ||
203 iter->first != "Vector" )
204 return;
205 ReadVector( iter->second, VectorBundle2.N );
206 }
207
208 template<typename Valtype> inline
209 void ReadRect( const boost::property_tree::ptree& pt, Rect<Valtype>& rect ){
210 rect.Left( common::DealDenormalizedNumbers(pt.get( "<xmlattr>.left", Valtype{0} )) );
211 rect.Top( common::DealDenormalizedNumbers(pt.get( "<xmlattr>.top", Valtype{0} )) );
212 rect.Right( common::DealDenormalizedNumbers(pt.get( "<xmlattr>.right", Valtype{0} )) );
213 rect.Bottom( common::DealDenormalizedNumbers(pt.get( "<xmlattr>.bottom", Valtype{0} )) );
214 }
215
216 template<typename Valtype> inline
217 void ReadArea( const boost::property_tree::ptree& pt, Box<Valtype>& area ){
218 area.NearX( common::DealDenormalizedNumbers(pt.get( "<xmlattr>.xnear", Valtype{0} )) );
219 area.NearY( common::DealDenormalizedNumbers(pt.get( "<xmlattr>.ynear", Valtype{0} )) );
220 area.NearZ( common::DealDenormalizedNumbers(pt.get( "<xmlattr>.znear", Valtype{0} )) );
221 area.FarX( common::DealDenormalizedNumbers(pt.get( "<xmlattr>.xfar", Valtype{0} )) );
222 area.FarY( common::DealDenormalizedNumbers(pt.get( "<xmlattr>.yfar", Valtype{0} )) );
223 area.FarZ( common::DealDenormalizedNumbers(pt.get( "<xmlattr>.zfar", Valtype{0} )) );
224 }
225
226 template<typename Valtype> inline
227 bool FindArea( const boost::property_tree::ptree& pt, Box<Valtype>& area ){
228 auto iter = pt.find( "Area" );
229 if( iter == pt.not_found() )
230 return false;
231
232 ReadArea( iter->second, area );
233 return true;
234 }
236
237 template<typename Valtype>
238 boost::property_tree::ptree& operator << ( boost::property_tree::ptree& opt, const Position<Valtype>& p ){
239 boost::property_tree::ptree ptPosition;
240 ptPosition.add( "<xmlattr>.x", p.x );
241 ptPosition.add( "<xmlattr>.y", p.y );
242 ptPosition.add( "<xmlattr>.z", p.z );
243 opt.add_child( "Position", ptPosition );
244 return opt;
245 }
246
247 template<typename Valtype>
248 boost::property_tree::ptree& operator >> ( boost::property_tree::ptree& ipt, Position<Valtype>& p ){
249 for( auto iter = ipt.begin(); iter != ipt.end(); ++iter ){
250 if( (*iter).first == "Position" ){
251 p.x = common::DealDenormalizedNumbers((*iter).second.get( "<xmlattr>.x", Valtype{0} ));
252 p.y = common::DealDenormalizedNumbers((*iter).second.get( "<xmlattr>.y", Valtype{0} ));
253 p.z = common::DealDenormalizedNumbers((*iter).second.get( "<xmlattr>.z", Valtype{0} ));
254
255 ipt.erase( iter );
256 return ipt;
257 }
258 }
259
260 assert( !"Syntax error: no Position tag!" );
261 return ipt;
262 }
263
264 template<typename Valtype>
265 boost::property_tree::ptree& operator << ( boost::property_tree::ptree& opt, const Position2D<Valtype>& p ){
266 boost::property_tree::ptree ptPosition;
267 ptPosition.add( "<xmlattr>.x", p.x );
268 ptPosition.add( "<xmlattr>.y", p.y );
269 opt.add_child( "Position2D", ptPosition );
270 return opt;
271 }
272
273 template<typename Valtype>
274 boost::property_tree::ptree& operator >> ( boost::property_tree::ptree& ipt, Position2D<Valtype>& p ){
275 for( auto iter = ipt.begin(); iter != ipt.end(); ++iter ){
276 if( (*iter).first == "Position2D" ){
277 p.x = common::DealDenormalizedNumbers((*iter).second.get( "<xmlattr>.x", Valtype{0} ));
278 p.y = common::DealDenormalizedNumbers((*iter).second.get( "<xmlattr>.y", Valtype{0} ));
279
280 ipt.erase( iter );
281 return ipt;
282 }
283 }
284
285 assert( !"Syntax error: no Position tag!" );
286 return ipt;
287 }
288
289 template<typename Valtype>
290 boost::property_tree::ptree& operator << ( boost::property_tree::ptree& opt, const Vector<Valtype>& v ){
291 boost::property_tree::ptree ptVector;
292 ptVector.add( "<xmlattr>.dx", v.dx );
293 ptVector.add( "<xmlattr>.dy", v.dy );
294 ptVector.add( "<xmlattr>.dz", v.dz );
295 opt.add_child( "Vector", ptVector );
296 return opt;
297 }
298
299 template<typename Valtype>
300 boost::property_tree::ptree& operator >> ( boost::property_tree::ptree& ipt, Vector<Valtype>& v ){
301 for( auto iter = ipt.begin(); iter != ipt.end(); ++iter ){
302 if( (*iter).first == "Vector" ){
303 v.dx = common::DealDenormalizedNumbers((*iter).second.get( "<xmlattr>.dx", Valtype{1} ));
304 v.dy = common::DealDenormalizedNumbers((*iter).second.get( "<xmlattr>.dy", Valtype{0} ));
305 v.dz = common::DealDenormalizedNumbers((*iter).second.get( "<xmlattr>.dz", Valtype{0} ));
306
307 ipt.erase( iter );
308 return ipt;
309 }
310 }
311
312 assert( !"Syntax error: no Vector tag!" );
313 return ipt;
314 }
315
316 template<typename Valtype,typename ValtypeT>
317 boost::property_tree::ptree& operator << ( boost::property_tree::ptree& opt, const VectorBundle<Valtype,ValtypeT>& vb ){
318 boost::property_tree::ptree ptVectorBundle;
319 ptVectorBundle << vb.P << vb.T;
320 opt.add_child( "VectorBundle", ptVectorBundle );
321 return opt;
322 }
323
324 template<typename Valtype,typename ValtypeT>
325 boost::property_tree::ptree& operator >> ( boost::property_tree::ptree& ipt, VectorBundle<Valtype,ValtypeT>& vb ){
326 for( auto iter = ipt.begin(); iter != ipt.end(); ++iter ){
327 if( (*iter).first == "VectorBundle" )
328 {
329 (*iter).second >> vb.P >> vb.T;
330 ipt.erase( iter );
331 return ipt;
332 }
333 }
334
335 assert( !"Syntax error: no VectorBundle tag!" );
336 return ipt;
337 }
338
339 template<typename Valtype,typename ValtypeT>
340 boost::property_tree::ptree& operator << ( boost::property_tree::ptree& opt, const VectorBundle2<Valtype,ValtypeT>& vb2 ){
341 boost::property_tree::ptree ptVectorBundle2;
342 ptVectorBundle2 << vb2.P << vb2.T << vb2.N;
343 opt.add_child( "VectorBundle2", ptVectorBundle2 );
344 return opt;
345 }
346
347 template<typename Valtype,typename ValtypeT>
348 boost::property_tree::ptree& operator >> ( boost::property_tree::ptree& ipt, VectorBundle2<Valtype,ValtypeT>& vb2 ){
349 for( auto iter = ipt.begin(); iter != ipt.end(); ++iter ){
350 if( (*iter).first == "VectorBundle2" )
351 {
352 (*iter).second >> vb2.P >> vb2.T >> vb2.N;
353 ipt.erase( iter );
354 return ipt;
355 }
356 }
357
358 assert( !"Syntax error: no VectorBundle2 tag!" );
359 return ipt;
360 }
361
362 template<typename Valtype,typename ValtypeT>
363 boost::property_tree::ptree& operator << ( boost::property_tree::ptree& opt, const Frame<Valtype,ValtypeT>& f ){
364 boost::property_tree::ptree ptFrame;
365 ptFrame << f.P << f.T << f.N << f.B;
366 opt.add_child( "Frame", ptFrame );
367 return opt;
368 }
369
370 template<typename Valtype,typename ValtypeT>
371 boost::property_tree::ptree& operator >> ( boost::property_tree::ptree& ipt, Frame<Valtype,ValtypeT>& f ){
372 for( auto iter = ipt.begin(); iter != ipt.end(); ++iter ){
373 if( (*iter).first == "Frame" )
374 {
375 (*iter).second >> f.P >> f.T >> f.N >> f.B;
376 ipt.erase( iter );
377 return ipt;
378 }
379 }
380
381 assert( !"Syntax error: no Frame tag!" );
382 return ipt;
383 }
384
385 template<typename Valtype>
386 boost::property_tree::ptree& operator << ( boost::property_tree::ptree& pt, const Box<Valtype>& area ){
387 boost::property_tree::ptree ptArea;
388
389 ptArea.add( "<xmlattr>.xnear", area.NearX() );
390 ptArea.add( "<xmlattr>.xfar", area.FarX() );
391 ptArea.add( "<xmlattr>.ynear", area.NearY() );
392 ptArea.add( "<xmlattr>.yfar", area.FarY() );
393 ptArea.add( "<xmlattr>.znear", area.NearZ() );
394 ptArea.add( "<xmlattr>.zfar", area.FarZ() );
395
396 pt.add_child( "Area", ptArea );
397 return pt;
398 }
399
400 template<typename Valtype>
401 boost::property_tree::ptree& operator << ( boost::property_tree::ptree& pt, const Rect<Valtype>& rect ){
402 boost::property_tree::ptree ptRect;
403
404 ptRect.add( "<xmlattr>.left", rect.Left() );
405 ptRect.add( "<xmlattr>.top", rect.Top() );
406 ptRect.add( "<xmlattr>.right", rect.Right() );
407 ptRect.add( "<xmlattr>.bottom", rect.Bottom() );
408
409 pt.add_child( "Rect", ptRect );
410 return pt;
411 }
412
413 } // namespace ptreesupport
414}
415
Valtype DealDenormalizedNumbers(Valtype val)
Make too small numbers zero.
Definition Helpers.h:151
ptree operator support
Definition SpatSupportXML.h:50
The namespace provides classes and methods for spatial computations.
Definition Box.h:32
Axis aligned box.
Definition Box.h:41
Valtype NearY() const noexcept
Definition Box.h:339
Valtype NearX() const noexcept
Definition Box.h:334
Valtype FarX() const noexcept
Definition Box.h:349
Valtype FarY() const noexcept
Definition Box.h:354
Valtype NearZ() const noexcept
Definition Box.h:344
Valtype FarZ() const noexcept
Definition Box.h:359
A Frame ("TNBFrame") describes a location in 3d space and an orientation using a right handed coordin...
Definition Frame.h:52
Vector< ValtypeT > B
Binormal axis or z-axis.
Definition Frame.h:56
Frame & Init() noexcept
Initializes the Frame structure to position (or zero) and the vectors to standard right-handed orthog...
Definition Frame.h:611
Position< Valtype > P
Point in 3D space.
Definition Frame.h:53
Vector< ValtypeT > N
Normal axis or y-axis.
Definition Frame.h:55
Vector< ValtypeT > T
Tangential axis or x-axis.
Definition Frame.h:54
Implements a 2D - position in cartesian coordinates.
Definition Position2D.h:45
Valtype x
cartesian x coordinate
Definition Position2D.h:48
Valtype y
cartesian y coordinate
Definition Position2D.h:49
Implements a 3D - position in cartesian coordinates.
Definition Position.h:46
Valtype y
cartesian y coordinate.
Definition Position.h:50
Valtype z
cartesian z coordinate.
Definition Position.h:51
Valtype x
cartesian x coordinate.
Definition Position.h:49
Axis aligned rectangle.
Definition Rect.h:41
Valtype Left() const noexcept
Definition Rect.h:285
Valtype Top() const noexcept
Definition Rect.h:290
Valtype Bottom() const noexcept
Definition Rect.h:300
Valtype Right() const noexcept
Definition Rect.h:295
Implements a tangential space bundle.
Definition VectorBundle2.h:43
Vector< ValtypeT > T
Tangent vector or x-axis.
Definition VectorBundle2.h:45
VectorBundle2 & Init() noexcept
Initializes the VectorBundle2 structure to position zero and the vectors to standard right-handed uni...
Definition VectorBundle2.h:316
Vector< ValtypeT > N
Normal axis or y-axis.
Definition VectorBundle2.h:46
Position< Valtype > P
Base space postion.
Definition VectorBundle2.h:44
Implements a Vector bundle.
Definition VectorBundle.h:42
VectorBundle & Init() noexcept
Initializes the VectorBundle structure to position zero and the ex Vector.
Definition VectorBundle.h:233
Position< Valtype > P
Base space postion.
Definition VectorBundle.h:43
Vector< ValtypeT > T
Tangent vector or x-axis.
Definition VectorBundle.h:44
Implements a 3D - vector in cartesian coordinates.
Definition Vector.h:48
Valtype dy
cartesian y component.
Definition Vector.h:52
Valtype dx
cartesian x component.
Definition Vector.h:51
Valtype dz
cartesian z component.
Definition Vector.h:53