Line data Source code
1 : /****************************************************************************** 2 : * 3 : * Project: S-101 driver 4 : * Purpose: Implements OGRS101Reader 5 : * Author: Even Rouault <even dot rouault at spatialys.com> 6 : * 7 : ****************************************************************************** 8 : * Copyright (c) 2026, Even Rouault <even dot rouault at spatialys.com> 9 : * 10 : * SPDX-License-Identifier: MIT 11 : ****************************************************************************/ 12 : 13 : #include "ogr_s101.h" 14 : #include "ogrs101readerconstants.h" 15 : #include "ogrs101readerconstants.h" 16 : 17 : #include <memory> 18 : 19 : /************************************************************************/ 20 : /* CreateInformationTypeFeatureDefn() */ 21 : /************************************************************************/ 22 : 23 : /** Create the feature definition for the informationType layer. 24 : */ 25 266 : bool OGRS101Reader::CreateInformationTypeFeatureDefn() 26 : { 27 266 : if (m_oInformationTypeRecordIndex.GetCount() != 0) 28 : { 29 : m_poFeatureDefnInformationType = 30 178 : OGRFeatureDefnRefCountedPtr::makeInstance("informationType"); 31 178 : m_poFeatureDefnInformationType->SetGeomType(wkbNone); 32 : { 33 356 : OGRFieldDefn oFieldDefn(OGR_FIELD_NAME_RECORD_ID, OFTInteger); 34 178 : m_poFeatureDefnInformationType->AddFieldDefn(&oFieldDefn); 35 : } 36 : { 37 356 : OGRFieldDefn oFieldDefn(OGR_FIELD_NAME_RECORD_VERSION, OFTInteger); 38 178 : m_poFeatureDefnInformationType->AddFieldDefn(&oFieldDefn); 39 : } 40 : { 41 356 : OGRFieldDefn oFieldDefn(OGR_FIELD_NAME_INFORMATION_TYPE, OFTString); 42 178 : m_poFeatureDefnInformationType->AddFieldDefn(&oFieldDefn); 43 : } 44 : 45 : // Scan the properties of the information type record 46 356 : if (!InferFeatureDefn( 47 178 : m_oInformationTypeRecordIndex, IRID_FIELD, ATTR_FIELD, 48 : /* anRecordIdx = */ {}, *m_poFeatureDefnInformationType, 49 178 : m_oMapFieldDomains)) 50 : { 51 9 : return false; 52 : } 53 : 54 : // Scan the properties of the association of one information record to 55 : // another related information type record. 56 338 : if (!InferFeatureDefn( 57 169 : m_oInformationTypeRecordIndex, IRID_FIELD, INAS_FIELD, 58 : /* anRecordIdx = */ {}, *m_poFeatureDefnInformationType, 59 169 : m_oMapFieldDomains)) 60 : { 61 0 : return false; 62 : } 63 : } 64 : 65 257 : return true; 66 : } 67 : 68 : /************************************************************************/ 69 : /* FillFeatureInformationType() */ 70 : /************************************************************************/ 71 : 72 : /** Fill the content of the provided feature from the identified record 73 : * of m_oInformationTypeRecordIndex. 74 : */ 75 399 : bool OGRS101Reader::FillFeatureInformationType(const DDFRecordIndex &oIndex, 76 : int iRecord, 77 : OGRFeature &oFeature) const 78 : { 79 399 : const auto poRecord = oIndex.GetByIndex(iRecord); 80 399 : CPLAssert(poRecord); 81 : 82 : // Numeric Information Type Code 83 399 : constexpr const char *NITC_SUBFIELD = "NITC"; 84 : const InfoTypeCode nNITC( 85 399 : poRecord->GetIntSubfield(IRID_FIELD, 0, NITC_SUBFIELD, 0)); 86 399 : const auto oIter = m_informationTypeCodes.find(nNITC); 87 399 : if (oIter != m_informationTypeCodes.end()) 88 : { 89 398 : oFeature.SetField(OGR_FIELD_NAME_INFORMATION_TYPE, 90 398 : oIter->second.c_str()); 91 : } 92 1 : else if (!EMIT_ERROR_OR_WARNING( 93 : CPLSPrintf("Unknown value %d for NITC subfield of IRID field.", 94 : static_cast<int>(nNITC)))) 95 : { 96 0 : return false; 97 : } 98 : else 99 : { 100 1 : oFeature.SetField( 101 : OGR_FIELD_NAME_INFORMATION_TYPE, 102 : CPLSPrintf("informationTypeCode%d", static_cast<int>(nNITC))); 103 : } 104 : 105 : // An IRID record might have a ATTR field, a INAS field (thus pointing 106 : // to another IRID record), both or none... 107 798 : return FillFeatureAttributes(oIndex, iRecord, ATTR_FIELD, oFeature) && 108 798 : FillFeatureAttributes(oIndex, iRecord, INAS_FIELD, oFeature); 109 : }