OTB  6.7.0
Orfeo Toolbox
otbDataNode.hxx
Go to the documentation of this file.
1 /*
2  * Copyright (C) 2005-2019 Centre National d'Etudes Spatiales (CNES)
3  *
4  * This file is part of Orfeo Toolbox
5  *
6  * https://www.orfeo-toolbox.org/
7  *
8  * Licensed under the Apache License, Version 2.0 (the "License");
9  * you may not use this file except in compliance with the License.
10  * You may obtain a copy of the License at
11  *
12  * http://www.apache.org/licenses/LICENSE-2.0
13  *
14  * Unless required by applicable law or agreed to in writing, software
15  * distributed under the License is distributed on an "AS IS" BASIS,
16  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17  * See the License for the specific language governing permissions and
18  * limitations under the License.
19  */
20 
21 #ifndef otbDataNode_hxx
22 #define otbDataNode_hxx
23 
24 #include "otbDataNode.h"
25 #include "otbMetaDataKey.h"
26 
27 namespace otb
28 {
29 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
32 {
33  m_NodeType = ROOT;
34  m_NodeId = "";
35  m_Data.valid = false;
36 }
37 
38 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
39 void
42 {
43  m_NodeType = type;
44  m_Data.valid = false;
45 }
46 
47 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
48 void
51 {
52  m_NodeType = FEATURE_POINT;
53  m_Data.point = point;
54  m_Data.valid = true;
55 }
56 
57 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
60 {
61  m_NodeType = FEATURE_LINE;
62  m_Data.line = line;
63  m_Data.valid = true;
64 }
65 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
66 void
69 {
70  m_NodeType = FEATURE_POLYGON;
71  m_Data.exteriorRing = polygon;
72  if (!m_Data.interiorRings)
73  {
74  m_Data.interiorRings = PolygonListType::New();
75  }
76  m_Data.valid = true;
77 }
78 
79 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
80 void
83 {
84  m_NodeType = FEATURE_POLYGON;
85  m_Data.interiorRings = polygonList;
86  if (!m_Data.exteriorRing)
87  {
88  m_Data.exteriorRing = PolygonType::New();
89  }
90  m_Data.valid = true;
91 }
92 
93 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
97 ::GetPoint() const
98 {
99  if (!IsPointFeature())
100  {
101  itkGenericExceptionMacro(<< "Node " << m_NodeId << " is not a point.");
102  }
103  if (!m_Data.valid)
104  {
105  itkGenericExceptionMacro(<< "Invalid point node.");
106  }
107  return m_Data.point;
108 }
109 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
111 ::LinePointerType
113 ::GetLine() const
114 {
115  if (!IsLineFeature())
116  {
117  itkGenericExceptionMacro(<< "Node " << m_NodeId << " is not a line.");
118  }
119  if (!m_Data.valid)
120  {
121  itkGenericExceptionMacro(<< "Invalid line node.");
122  }
123  return m_Data.line;
124 }
125 
126 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
128 ::PolygonPointerType
131 {
132  if (!IsPolygonFeature())
133  {
134  itkGenericExceptionMacro(<< "Node " << m_NodeId << " is not a polygon.");
135  }
136  if (!m_Data.valid || !m_Data.exteriorRing)
137  {
138  itkGenericExceptionMacro(<< "Invalid polygon node.");
139  }
140  return m_Data.exteriorRing;
141 }
142 
143 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
145 ::PolygonListPointerType
148 {
149  if (!IsPolygonFeature())
150  {
151  itkGenericExceptionMacro(<< "Node " << m_NodeId << " is not a polygon.");
152  }
153  if (!m_Data.valid || !m_Data.interiorRings)
154  {
155  itkGenericExceptionMacro(<< "Invalid polygon node.");
156  }
157  return m_Data.interiorRings;
158 }
159 
160 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
161 void
163 ::PrintSelf(std::ostream& os, itk::Indent indent) const
164 {
165  os << indent << this->GetNodeTypeAsString();
166 }
167 
168 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
169 std::string
172 {
173  std::ostringstream oss;
174  switch (m_NodeType)
175  {
176  case ROOT:
177  {
178  oss << "Root (" << m_NodeId << ")";
179  break;
180  }
181  case DOCUMENT:
182  {
183  oss << "Document (" << m_NodeId << ")";
184  break;
185  }
186  case FOLDER:
187  {
188  oss << "Folder (" << m_NodeId << ")";
189  break;
190  }
191  case FEATURE_POINT:
192  {
193  oss << "Point (" << m_NodeId << ") " << m_Data.point;
194  break;
195  }
196  case FEATURE_LINE:
197  {
198  oss << "Line (" << m_NodeId << ") " << m_Data.line->GetVertexList()->Size() << " points";
199  break;
200  }
201  case FEATURE_POLYGON:
202  {
203  oss << "Polygon (" << m_NodeId << ") " << this->GetPolygonExteriorRing()->GetVertexList()->Size() <<
204  " points, " <<
205  this->GetPolygonInteriorRings()->Size() << " interior rings";
206  break;
207  }
208  case FEATURE_MULTIPOINT:
209  {
210  oss << "MultiPoint (" << m_NodeId << ")";
211  break;
212  }
213  case FEATURE_MULTILINE:
214  {
215  oss << "MultiLine (" << m_NodeId << ")";
216  break;
217  }
219  {
220  oss << "MultiPolygon (" << m_NodeId << ")";
221  break;
222  }
223  case FEATURE_COLLECTION:
224  {
225  oss << "Collection (" << m_NodeId << ")";
226  break;
227  }
228  }
229  if (GetMetaDataDictionary().HasKey(MetaDataKey::VectorDataKeywordlistKey))
230  {
232  itk::ExposeMetaData<VectorDataKeywordlist>(GetMetaDataDictionary(), MetaDataKey::VectorDataKeywordlistKey, kwl);
233  oss << "\n -> Metadata: " << kwl;
234  }
235  return oss.str();
236 }
237 /*
238 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
239 void
240 DataNode<TPrecision, VDimension, TValuePrecision>
241 ::SetField(const std::string& key, const std::string& value)
242 {
243  m_FieldMap[key] = value;
244 }
245 */
246 
247 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
248 void
250 ::SetFieldAsString(const std::string& key, const std::string& value)
251 {
253  itk::ExposeMetaData<VectorDataKeywordlist>(this->GetMetaDataDictionary(),
255  kwl);
256  kwl.SetFieldAsString(key, value);
257  itk::EncapsulateMetaData<VectorDataKeywordlist>(this->GetMetaDataDictionary(),
259  kwl);
260 }
261 
262 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
263 void
265 ::SetFieldAsInt(const std::string& key, int value)
266 {
268  itk::ExposeMetaData<VectorDataKeywordlist>(this->GetMetaDataDictionary(),
270  kwl);
271  kwl.SetFieldAsInt(key, value);
272  itk::EncapsulateMetaData<VectorDataKeywordlist>(this->GetMetaDataDictionary(),
274  kwl);
275 }
276 
277 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
278 void
280 ::SetFieldAsDouble(const std::string& key, double value)
281 {
283  itk::ExposeMetaData<VectorDataKeywordlist>(this->GetMetaDataDictionary(),
285  kwl);
286 
287  kwl.SetFieldAsDouble(key, value);
288  itk::EncapsulateMetaData<VectorDataKeywordlist>(this->GetMetaDataDictionary(),
290  kwl);
291 }
292 
293 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
294 double
296 ::GetFieldAsDouble(const std::string& key) const
297 {
298  VectorDataKeywordlist keywordlist;
299  if (HasField(key))
300  {
301  itk::ExposeMetaData<VectorDataKeywordlist>(this->GetMetaDataDictionary(),
303 
304  return keywordlist.GetFieldAsDouble(key);
305  }
306  return 0;
307 }
308 
309 /*
310 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
311 std::string
312 DataNode<TPrecision, VDimension, TValuePrecision>
313 ::GetField(const std::string& key) const
314 {
315  if (HasField(key))
316  {
317  return (*m_FieldMap.find(key)).second;
318  }
319  else
320  {
321  return "Unknown Key";
322  }
323 }*/
324 
325 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
326 std::string
328 ::GetFieldAsString(const std::string& key) const
329 {
330  VectorDataKeywordlist keywordlist;
331  if (HasField(key))
332  {
333  itk::ExposeMetaData<VectorDataKeywordlist>(this->GetMetaDataDictionary(),
335  return keywordlist.GetFieldAsString(key);
336  }
337  return "";
338 }
339 
340 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
341 int
343 ::GetFieldAsInt(const std::string& key) const
344 {
345  VectorDataKeywordlist keywordlist;
346  if (HasField(key))
347  {
348  itk::ExposeMetaData<VectorDataKeywordlist>(this->GetMetaDataDictionary(),
350 
351  return keywordlist.GetFieldAsInt(key);
352  }
353  return 0;
354 }
355 
356 /*
357 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
358 void
359 DataNode<TPrecision, VDimension, TValuePrecision>
360 ::RemoveField(const std::string& key)
361 {
362  m_FieldMap.erase(key);
363 }
364 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
365 bool
366 DataNode<TPrecision, VDimension, TValuePrecision>
367 ::HasField(const std::string& key) const
368 {
369  return (m_FieldMap.find(key)!=m_FieldMap.end());
370 }
371 */
372 
373 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
374 bool
376 ::HasField(const std::string& key) const
377 {
378  VectorDataKeywordlist keywordlist;
379  if (this->GetMetaDataDictionary().HasKey(MetaDataKey::VectorDataKeywordlistKey))
380  {
381  itk::ExposeMetaData<VectorDataKeywordlist>(this->GetMetaDataDictionary(),
383  return keywordlist.HasField(key);
384  }
385  return false;
386 }
387 
388 /*
389 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
390 typename DataNode<TPrecision, VDimension, TValuePrecision>
391 ::FieldType
392 DataNode<TPrecision, VDimension, TValuePrecision>
393 ::GetNthField(unsigned int index) const
394 {
395  if (index<GetNumberOfFields())
396  {
397  FieldMapType::iterator it = m_FieldMap.begin();
398 
399  for (unsigned int i = 0; i<index; ++i)
400  {
401  ++it;
402  }
403  return (*it);
404  }
405  return FieldType("No key","No value");
406 }
407 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
408 unsigned int
409 DataNode<TPrecision, VDimension, TValuePrecision>
410 ::GetNumberOfFields() const
411 {
412  return m_FieldMap.size();
413 }
414 */
415 
416 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
417 void
419 ::CopyFieldList(const DataNode * dataNode)
420 {
421  // The source keywordlist where to get the feature list to copy
423  itk::ExposeMetaData<VectorDataKeywordlist>(dataNode->GetMetaDataDictionary(),
425  srcKwl);
426 
428  itk::ExposeMetaData<VectorDataKeywordlist>(this->GetMetaDataDictionary(),
430  kwl);
431 
432  kwl.CopyFieldList(srcKwl);
433  itk::EncapsulateMetaData<VectorDataKeywordlist>(this->GetMetaDataDictionary(),
435  kwl);
436 }
437 
438 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
439 std::vector<std::string>
442 {
443  VectorDataKeywordlist keywordlist;
444  if (this->GetMetaDataDictionary().HasKey(MetaDataKey::VectorDataKeywordlistKey))
445  {
446  itk::ExposeMetaData<VectorDataKeywordlist>(this->GetMetaDataDictionary(),
448  return keywordlist.GetFieldList();
449  }
450  std::vector<std::string> empty;
451  return empty;
452 }
453 
454 /*
455 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
456 void
457 DataNode<TPrecision, VDimension, TValuePrecision>
458 ::ClearFields()
459 {
460  m_FieldMap.clear();
461 }*/
462 
463 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
464 bool
467 {
468  return m_NodeType == DOCUMENT;
469 }
470 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
471 bool
473 ::IsRoot() const
474 {
475  return m_NodeType == ROOT;
476 }
477 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
478 bool
480 ::IsFolder() const
481 {
482  return m_NodeType == FOLDER;
483 }
484 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
485 bool
488 {
489  return m_NodeType == FEATURE_POINT;
490 }
491 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
492 bool
495 {
496  return m_NodeType == FEATURE_LINE;
497 }
498 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
499 bool
502 {
503  return m_NodeType == FEATURE_POLYGON;
504 }
505 
506 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
507 bool
510 {
511  return m_NodeType == FEATURE_MULTIPOINT;
512 }
513 
514 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
515 bool
518 {
519  return m_NodeType == FEATURE_MULTILINE;
520 }
521 
522 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
523 bool
526 {
527  return m_NodeType == FEATURE_MULTIPOLYGON;
528 }
529 
530 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
531 bool
534 {
535  return m_NodeType == FEATURE_COLLECTION;
536 }
537 
538 
539 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
540 OGRGeometry *
543 {
544  switch(dataNode->GetNodeType())
545  {
546  case FEATURE_POINT:
547  {
548  OGRPoint *ogrPoint = (OGRPoint *) OGRGeometryFactory::createGeometry(wkbPoint);
549  ogrPoint->setX(dataNode->GetPoint()[0]);
550  ogrPoint->setY(dataNode->GetPoint()[1]);
551  return ogrPoint;
552  }
553  break;
554  case FEATURE_LINE:
555  {
556  //Build the ogrObject
557  OGRLineString * ogrLine = (OGRLineString *) OGRGeometryFactory::createGeometry(wkbLineString);
558  VertexListConstPointerType vertexList = dataNode->GetLine()->GetVertexList();
559  typename VertexListType::ConstIterator vIt = vertexList->Begin();
560 
561  while (vIt != vertexList->End())
562  {
563  OGRPoint ogrPoint;
564  ogrPoint.setX(vIt.Value()[0]);
565  ogrPoint.setY(vIt.Value()[1]);
566  if (Dimension > 2)
567  {
568  ogrPoint.setZ(vIt.Value()[2]);
569  }
570  ogrLine->addPoint(&ogrPoint);
571  ++vIt;
572  }
573  return ogrLine;
574  }
575  break;
576  case FEATURE_POLYGON:
577  {
578  OGRPolygon * polygon = (OGRPolygon *) OGRGeometryFactory::createGeometry(wkbPolygon);
579  OGRLinearRing * ogrExternalRing = (OGRLinearRing *) OGRGeometryFactory::createGeometry(wkbLinearRing);
580 
581  VertexListConstPointerType vertexList = dataNode->GetPolygonExteriorRing()->GetVertexList();
582 
583  typename VertexListType::ConstIterator vIt = vertexList->Begin();
584 
585  while (vIt != vertexList->End())
586  {
587  OGRPoint ogrPoint;
588  ogrPoint.setX(vIt.Value()[0]);
589  ogrPoint.setY(vIt.Value()[1]);
590  if ( Dimension > 2)
591  {
592  ogrPoint.setZ(vIt.Value()[2]);
593  }
594 
595  ogrExternalRing->addPoint(&ogrPoint);
596  ++vIt;
597  }
598  polygon->addRing(ogrExternalRing);
599  // Close the polygon
600  polygon->closeRings();
601  OGRGeometryFactory::destroyGeometry(ogrExternalRing);
602  return polygon;
603  }
604  break;
605  default: break;
606  }
607 
608  return nullptr;
609 }
610 
611 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
612 double
615 {
616  // Convert the nodes to OGRGeometries
617  OGRGeometry * dstGeomtery = this->ConvertDataNodeToOGRGeometry(node);
618  OGRGeometry * currentGeometry = this->ConvertDataNodeToOGRGeometry(this);
619 
620  // Compute the distance
621  return currentGeometry->Distance(dstGeomtery);
622 }
623 
624 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
625 double
628 {
629  // Convert Point to point to ogrPoint
630  OGRPoint ogrPointSrc;
631  ogrPointSrc.setX(point[0]);
632  ogrPointSrc.setY(point[1]);
633 
634  // Convert the current datanode to an OGRGeometry
635  OGRGeometry * currentGeometry = this->ConvertDataNodeToOGRGeometry(this);
636 
637  // return the distance
638  return currentGeometry->Distance(&ogrPointSrc);
639 }
640 
641 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
642 bool
644 ::Intersects(const DataNode* node)
645 {
646  // Convert the nodes to OGRGeometries
647  OGRGeometry * dstGeomtery = this->ConvertDataNodeToOGRGeometry(node);
648  OGRGeometry * currentGeometry = this->ConvertDataNodeToOGRGeometry(this);
649 
650  //
651  return currentGeometry->Intersects(dstGeomtery);
652 }
653 
654 template <class TPrecision, unsigned int VDimension, class TValuePrecision>
655 bool
657 ::Within(const DataNode* node)
658 {
659  // Convert the nodes to OGRGeometries
660  OGRGeometry * dstGeomtery = this->ConvertDataNodeToOGRGeometry(node);
661  OGRGeometry * currentGeometry = this->ConvertDataNodeToOGRGeometry(this);
662 
663  //
664  return currentGeometry->Within(dstGeomtery);
665 }
666 
667 
668 } // end namespace otb
669 
670 #endif
bool IsMultiPointFeature() const
bool IsPointFeature() const
bool Within(const DataNode *node)
bool IsLineFeature() const
void SetPolygonInteriorRings(PolygonListType *polygonList)
Definition: otbDataNode.hxx:82
bool HasField(const std::string &key) const
double EuclideanDistanceMetric(const DataNode *node)
OGRGeometry * ConvertDataNodeToOGRGeometry(const DataNode *dataNode)
This class implement a PolyLineParametricPath for which a value can be set. The value is stored in th...
NodeType
Definition: otbDataNode.h:39
OTBOSSIMAdapters_EXPORT char const * VectorDataKeywordlistKey
This class represents a node of data in a vector data hierarchy.
Definition: otbDataNode.h:75
void SetPoint(PointType point)
Definition: otbDataNode.hxx:50
MetaDataDictionary & GetMetaDataDictionary()
This class represent a 2D polygon.
Definition: otbPolygon.h:44
std::string GetNodeTypeAsString() const
std::string GetFieldAsString(const std::string &key) const
VertexListType::ConstPointer VertexListConstPointerType
Definition: otbDataNode.h:102
LinePointerType GetLine() const
std::vector< std::string > GetFieldList() const
void SetFieldAsString(const std::string &key, const std::string &value)
double GetFieldAsDouble(const std::string &key) const
PointType GetPoint() const
Definition: otbDataNode.hxx:97
This class is a generic all-purpose wrapping around an std::vector<itk::SmartPointer<ObjectType> >...
Definition: otbObjectList.h:40
void SetFieldAsDouble(const std::string &key, double value)
bool Intersects(const DataNode *node)
this class handle the metadata of vector data.
void SetPolygonExteriorRing(PolygonType *polygon)
Definition: otbDataNode.hxx:68
bool IsRoot() const
void SetFieldAsInt(const std::string &key, int value)
void SetNodeType(NodeType type)
Definition: otbDataNode.hxx:41
void CopyFieldList(const Self &kwl)
bool IsMultiLineFeature() const
void SetLine(LineType *line)
Definition: otbDataNode.hxx:59
std::vector< std::string > GetFieldList() const
virtual NodeType GetNodeType() const
void SetFieldAsString(const std::string &key, const std::string &value)
std::string GetFieldAsString(const std::string &key) const
int GetFieldAsInt(const std::string &key) const
bool IsFolder() const
bool IsPolygonFeature() const
void PrintSelf(std::ostream &os, itk::Indent indent) const override
bool IsMultiPolygonFeature() const
PolygonListPointerType GetPolygonInteriorRings() const
void SetFieldAsInt(const std::string &key, int value)
int GetFieldAsInt(const std::string &key) const
VectorImageType::PointType PointType
Definition: mvdTypes.h:189
bool IsDocument() const
void SetFieldAsDouble(const std::string &key, double value)
double GetFieldAsDouble(const std::string &key) const
bool HasField(const std::string &key) const
bool IsCollectionFeature() const
void CopyFieldList(const DataNode *dataNode)
PolygonPointerType GetPolygonExteriorRing() const