OGRGeometry* GML_BuildOGRGeometryFromList(const CPLXMLNode* const * papsGeometry, int bTryToMakeMultipolygons, int bInvertAxisOrderIfLatLong, const char* pszDefaultSRSName, int bConsiderEPSGAsURN, int bGetSecondaryGeometryOption, void* hCacheSRS, int bFaceHoleNegative) { OGRGeometry* poGeom = NULL; int i; OGRGeometryCollection* poCollection = NULL; for(i=0;papsGeometry[i] != NULL;i++) { OGRGeometry* poSubGeom = GML2OGRGeometry_XMLNode( papsGeometry[i], bGetSecondaryGeometryOption, 0, 0, FALSE, TRUE, bFaceHoleNegative ); if (poSubGeom) { if (poGeom == NULL) poGeom = poSubGeom; else { if (poCollection == NULL) { if (bTryToMakeMultipolygons && wkbFlatten(poGeom->getGeometryType()) == wkbPolygon && wkbFlatten(poSubGeom->getGeometryType()) == wkbPolygon) { OGRGeometryCollection* poGeomColl = new OGRMultiPolygon(); poGeomColl->addGeometryDirectly(poGeom); poGeomColl->addGeometryDirectly(poSubGeom); poGeom = poGeomColl; } else if (bTryToMakeMultipolygons && wkbFlatten(poGeom->getGeometryType()) == wkbMultiPolygon && wkbFlatten(poSubGeom->getGeometryType()) == wkbPolygon) { OGRGeometryCollection* poGeomColl = (OGRGeometryCollection* )poGeom; poGeomColl->addGeometryDirectly(poSubGeom); } else if (bTryToMakeMultipolygons && wkbFlatten(poGeom->getGeometryType()) == wkbMultiPolygon && wkbFlatten(poSubGeom->getGeometryType()) == wkbMultiPolygon) { OGRGeometryCollection* poGeomColl = (OGRGeometryCollection* )poGeom; OGRGeometryCollection* poGeomColl2 = (OGRGeometryCollection* )poSubGeom; int nCount = poGeomColl2->getNumGeometries(); int i; for(i=0;i<nCount;i++) { poGeomColl->addGeometry(poGeomColl2->getGeometryRef(i)); } delete poSubGeom; } else if (bTryToMakeMultipolygons && wkbFlatten(poGeom->getGeometryType()) == wkbMultiPolygon) { delete poGeom; delete poSubGeom; return GML_BuildOGRGeometryFromList(papsGeometry, FALSE, bInvertAxisOrderIfLatLong, pszDefaultSRSName, bConsiderEPSGAsURN, bGetSecondaryGeometryOption, hCacheSRS); } else { poCollection = new OGRGeometryCollection(); poCollection->addGeometryDirectly(poGeom); poGeom = poCollection; } } if (poCollection != NULL) { poCollection->addGeometryDirectly(poSubGeom); } } } } if( poGeom == NULL ) return NULL; std::string osWork; const char* pszSRSName = GML_ExtractSrsNameFromGeometry(papsGeometry, osWork, bConsiderEPSGAsURN); const char* pszNameLookup = pszSRSName; if( pszNameLookup == NULL ) pszNameLookup = pszDefaultSRSName; if (pszNameLookup != NULL) { SRSCache* poSRSCache = (SRSCache*)hCacheSRS; SRSDesc& oSRSDesc = poSRSCache->Get(pszNameLookup); poGeom->assignSpatialReference(oSRSDesc.poSRS); if (oSRSDesc.bAxisInvert && bInvertAxisOrderIfLatLong) poGeom->swapXY(); } return poGeom; }
OGRGeometry* GML_BuildOGRGeometryFromList(const CPLXMLNode* const * papsGeometry, int bTryToMakeMultipolygons, int bInvertAxisOrderIfLatLong, const char* pszDefaultSRSName, int bConsiderEPSGAsURN, int bGetSecondaryGeometryOption, void* hCacheSRS) { OGRGeometry* poGeom = NULL; int i; OGRGeometryCollection* poCollection = NULL; for(i=0;papsGeometry[i] != NULL;i++) { OGRGeometry* poSubGeom = GML2OGRGeometry_XMLNode( papsGeometry[i], bGetSecondaryGeometryOption ); if (poSubGeom) { if (poGeom == NULL) poGeom = poSubGeom; else { if (poCollection == NULL) { if (bTryToMakeMultipolygons && wkbFlatten(poGeom->getGeometryType()) == wkbPolygon && wkbFlatten(poSubGeom->getGeometryType()) == wkbPolygon) { OGRGeometryCollection* poGeomColl = new OGRMultiPolygon(); poGeomColl->addGeometryDirectly(poGeom); poGeomColl->addGeometryDirectly(poSubGeom); poGeom = poGeomColl; } else if (bTryToMakeMultipolygons && wkbFlatten(poGeom->getGeometryType()) == wkbMultiPolygon && wkbFlatten(poSubGeom->getGeometryType()) == wkbPolygon) { OGRGeometryCollection* poGeomColl = (OGRGeometryCollection* )poGeom; poGeomColl->addGeometryDirectly(poSubGeom); } else if (bTryToMakeMultipolygons && wkbFlatten(poGeom->getGeometryType()) == wkbMultiPolygon && wkbFlatten(poSubGeom->getGeometryType()) == wkbMultiPolygon) { OGRGeometryCollection* poGeomColl = (OGRGeometryCollection* )poGeom; OGRGeometryCollection* poGeomColl2 = (OGRGeometryCollection* )poSubGeom; int nCount = poGeomColl2->getNumGeometries(); int i; for(i=0;i<nCount;i++) { poGeomColl->addGeometry(poGeomColl2->getGeometryRef(i)); } delete poSubGeom; } else if (bTryToMakeMultipolygons && wkbFlatten(poGeom->getGeometryType()) == wkbMultiPolygon) { delete poGeom; delete poSubGeom; return GML_BuildOGRGeometryFromList(papsGeometry, FALSE, bInvertAxisOrderIfLatLong, pszDefaultSRSName, bConsiderEPSGAsURN, bGetSecondaryGeometryOption, hCacheSRS); } else { poCollection = new OGRGeometryCollection(); poCollection->addGeometryDirectly(poGeom); poGeom = poCollection; } } if (poCollection != NULL) { poCollection->addGeometryDirectly(poSubGeom); } } } } if ( poGeom != NULL && bInvertAxisOrderIfLatLong ) { std::string osWork; const char* pszSRSName = GML_ExtractSrsNameFromGeometry(papsGeometry, osWork, bConsiderEPSGAsURN); const char* pszNameLookup = pszSRSName ? pszSRSName : pszDefaultSRSName; if (pszNameLookup != NULL) { SRSCache* poSRSCache = (SRSCache*)hCacheSRS; int bSwap; if (strcmp(poSRSCache->osLastSRSName.c_str(), pszNameLookup) == 0) { bSwap = poSRSCache->bAxisInvertLastSRSName; } else { bSwap = GML_IsSRSLatLongOrder(pszNameLookup); poSRSCache->osLastSRSName = pszNameLookup; poSRSCache->bAxisInvertLastSRSName= bSwap; } if (bSwap) poGeom->swapXY(); } } return poGeom; }
OGRFeature *OGRGMLLayer::GetNextFeature() { GMLFeature *poGMLFeature = NULL; OGRGeometry *poGeom = NULL; if (bWriter) { CPLError(CE_Failure, CPLE_NotSupported, "Cannot read features when writing a GML file"); return NULL; } if( iNextGMLId == 0 ) ResetReading(); /* ==================================================================== */ /* Loop till we find and translate a feature meeting all our */ /* requirements. */ /* ==================================================================== */ while( TRUE ) { /* -------------------------------------------------------------------- */ /* Cleanup last feature, and get a new raw gml feature. */ /* -------------------------------------------------------------------- */ if( poGMLFeature != NULL ) delete poGMLFeature; if( poGeom != NULL ) { delete poGeom; poGeom = NULL; } poGMLFeature = poDS->GetReader()->NextFeature(); if( poGMLFeature == NULL ) return NULL; /* -------------------------------------------------------------------- */ /* Is it of the proper feature class? */ /* -------------------------------------------------------------------- */ // We count reading low level GML features as a feature read for // work checking purposes, though at least we didn't necessary // have to turn it into an OGRFeature. m_nFeaturesRead++; if( poGMLFeature->GetClass() != poFClass ) continue; /* -------------------------------------------------------------------- */ /* Extract the fid: */ /* -Assumes the fids are non-negative integers with an optional */ /* prefix */ /* -If a prefix differs from the prefix of the first feature from */ /* the poDS then the fids from the poDS are ignored and are */ /* assigned serially thereafter */ /* -------------------------------------------------------------------- */ int nFID = -1; const char * pszGML_FID = poGMLFeature->GetFID(); if( bInvalidFIDFound ) { nFID = iNextGMLId++; } else if( pszGML_FID == NULL ) { bInvalidFIDFound = TRUE; nFID = iNextGMLId++; } else if( iNextGMLId == 0 ) { int i = strlen( pszGML_FID )-1, j = 0; while( i >= 0 && pszGML_FID[i] >= '0' && pszGML_FID[i] <= '9' && j<8) i--, j++; /* i points the last character of the fid */ if( i >= 0 && j < 8 && pszFIDPrefix == NULL) { pszFIDPrefix = (char *) CPLMalloc(i+2); pszFIDPrefix[i+1] = '\0'; strncpy(pszFIDPrefix, pszGML_FID, i+1); } /* pszFIDPrefix now contains the prefix or NULL if no prefix is found */ if( j < 8 && sscanf(pszGML_FID+i+1, "%d", &nFID)==1) { if( iNextGMLId <= nFID ) iNextGMLId = nFID + 1; } else { bInvalidFIDFound = TRUE; nFID = iNextGMLId++; } } else if( iNextGMLId != 0 ) { const char* pszFIDPrefix_notnull = pszFIDPrefix; if (pszFIDPrefix_notnull == NULL) pszFIDPrefix_notnull = ""; int nLenPrefix = strlen(pszFIDPrefix_notnull); if( strncmp(pszGML_FID, pszFIDPrefix_notnull, nLenPrefix) == 0 && strlen(pszGML_FID+nLenPrefix) <= 9 && sscanf(pszGML_FID+nLenPrefix, "%d", &nFID) == 1 ) { /* fid with the prefix. Using its numerical part */ if( iNextGMLId < nFID ) iNextGMLId = nFID + 1; } else { /* fid without the aforementioned prefix or a valid numerical part */ bInvalidFIDFound = TRUE; nFID = iNextGMLId++; } } /* -------------------------------------------------------------------- */ /* Does it satisfy the spatial query, if there is one? */ /* -------------------------------------------------------------------- */ char** papszGeometryList = poGMLFeature->GetGeometryList(); if( papszGeometryList != NULL ) { const char* pszSRSName = poDS->GetGlobalSRSName(); poGeom = GML_BuildOGRGeometryFromList(papszGeometryList, TRUE, m_bInvertAxisOrderIfLatLong, pszSRSName); if (poGeom != NULL && poSRS != NULL) poGeom->assignSpatialReference(poSRS); // We assume the createFromGML() function would have already // reported the error. if( poGeom == NULL ) { delete poGMLFeature; return NULL; } if( m_poFilterGeom != NULL && !FilterGeometry( poGeom ) ) continue; } /* -------------------------------------------------------------------- */ /* Convert the whole feature into an OGRFeature. */ /* -------------------------------------------------------------------- */ int iField; int iDstField = 0; OGRFeature *poOGRFeature = new OGRFeature( GetLayerDefn() ); poOGRFeature->SetFID( nFID ); if (poDS->ExposeGMLId()) { if (pszGML_FID) poOGRFeature->SetField( iDstField, pszGML_FID ); iDstField ++; } for( iField = 0; iField < poFClass->GetPropertyCount(); iField++, iDstField ++ ) { const GMLProperty *psGMLProperty = poGMLFeature->GetProperty( iField ); if( psGMLProperty == NULL || psGMLProperty->nSubProperties == 0 ) continue; switch( poFClass->GetProperty(iField)->GetType() ) { case GMLPT_Real: { poOGRFeature->SetField( iDstField, CPLAtof(psGMLProperty->papszSubProperties[0]) ); } break; case GMLPT_IntegerList: { int nCount = psGMLProperty->nSubProperties; int *panIntList = (int *) CPLMalloc(sizeof(int) * nCount ); int i; for( i = 0; i < nCount; i++ ) panIntList[i] = atoi(psGMLProperty->papszSubProperties[i]); poOGRFeature->SetField( iDstField, nCount, panIntList ); CPLFree( panIntList ); } break; case GMLPT_RealList: { int nCount = psGMLProperty->nSubProperties; double *padfList = (double *)CPLMalloc(sizeof(double)*nCount); int i; for( i = 0; i < nCount; i++ ) padfList[i] = CPLAtof(psGMLProperty->papszSubProperties[i]); poOGRFeature->SetField( iDstField, nCount, padfList ); CPLFree( padfList ); } break; case GMLPT_StringList: { poOGRFeature->SetField( iDstField, psGMLProperty->papszSubProperties ); } break; default: poOGRFeature->SetField( iDstField, psGMLProperty->papszSubProperties[0] ); break; } } /* -------------------------------------------------------------------- */ /* Test against the attribute query. */ /* -------------------------------------------------------------------- */ if( m_poAttrQuery != NULL && !m_poAttrQuery->Evaluate( poOGRFeature ) ) { delete poOGRFeature; continue; } /* -------------------------------------------------------------------- */ /* Wow, we got our desired feature. Return it. */ /* -------------------------------------------------------------------- */ delete poGMLFeature; poOGRFeature->SetGeometryDirectly( poGeom ); return poOGRFeature; } return NULL; }
OGRGeometry* GML_BuildOGRGeometryFromList(char** papszGeometryList, int bTryToMakeMultipolygons, int bInvertAxisOrderIfLatLong, const char* pszDefaultSRSName) { OGRGeometry* poGeom = NULL; if( papszGeometryList != NULL ) { char** papszIter = papszGeometryList; OGRGeometryCollection* poCollection = NULL; while(*papszIter) { OGRGeometry* poSubGeom = OGRGeometryFactory::createFromGML( *papszIter ); if (poSubGeom) { if (poGeom == NULL) poGeom = poSubGeom; else { if (poCollection == NULL) { if (bTryToMakeMultipolygons && wkbFlatten(poGeom->getGeometryType()) == wkbPolygon && wkbFlatten(poSubGeom->getGeometryType()) == wkbPolygon) { OGRGeometryCollection* poGeomColl = new OGRMultiPolygon(); poGeomColl->addGeometryDirectly(poGeom); poGeomColl->addGeometryDirectly(poSubGeom); poGeom = poGeomColl; } else if (bTryToMakeMultipolygons && wkbFlatten(poGeom->getGeometryType()) == wkbMultiPolygon && wkbFlatten(poSubGeom->getGeometryType()) == wkbPolygon) { OGRGeometryCollection* poGeomColl = (OGRGeometryCollection* )poGeom; poGeomColl->addGeometryDirectly(poSubGeom); } else if (bTryToMakeMultipolygons && wkbFlatten(poGeom->getGeometryType()) == wkbMultiPolygon && wkbFlatten(poSubGeom->getGeometryType()) == wkbMultiPolygon) { OGRGeometryCollection* poGeomColl = (OGRGeometryCollection* )poGeom; OGRGeometryCollection* poGeomColl2 = (OGRGeometryCollection* )poSubGeom; int nCount = poGeomColl2->getNumGeometries(); int i; for(i=0;i<nCount;i++) { poGeomColl->addGeometry(poGeomColl2->getGeometryRef(i)); } delete poSubGeom; } else if (bTryToMakeMultipolygons && wkbFlatten(poGeom->getGeometryType()) == wkbMultiPolygon) { delete poGeom; delete poSubGeom; return GML_BuildOGRGeometryFromList(papszGeometryList, FALSE, bInvertAxisOrderIfLatLong, pszDefaultSRSName); } else { poCollection = new OGRGeometryCollection(); poCollection->addGeometryDirectly(poGeom); poGeom = poCollection; } } if (poCollection != NULL) { poCollection->addGeometryDirectly(poSubGeom); } } } papszIter ++; } } if (bInvertAxisOrderIfLatLong) { char* pszSRSName = GML_ExtractSrsNameFromGeometry(papszGeometryList); if (GML_IsSRSLatLongOrder(pszSRSName ? pszSRSName : pszDefaultSRSName)) poGeom->swapXY(); CPLFree(pszSRSName); } return poGeom; }
OGRFeature *OGRGMLLayer::GetNextFeature() { if (bWriter) { CPLError(CE_Failure, CPLE_NotSupported, "Cannot read features when writing a GML file"); return NULL; } if( poDS->GetLastReadLayer() != this ) { if( poDS->GetReadMode() != INTERLEAVED_LAYERS ) ResetReading(); poDS->SetLastReadLayer(this); } /* ==================================================================== */ /* Loop till we find and translate a feature meeting all our */ /* requirements. */ /* ==================================================================== */ while( true ) { GMLFeature *poGMLFeature = NULL; OGRGeometry *poGeom = NULL; poGMLFeature = poDS->PeekStoredGMLFeature(); if (poGMLFeature != NULL) poDS->SetStoredGMLFeature(NULL); else { poGMLFeature = poDS->GetReader()->NextFeature(); if( poGMLFeature == NULL ) return NULL; // We count reading low level GML features as a feature read for // work checking purposes, though at least we didn't necessary // have to turn it into an OGRFeature. m_nFeaturesRead++; } /* -------------------------------------------------------------------- */ /* Is it of the proper feature class? */ /* -------------------------------------------------------------------- */ if( poGMLFeature->GetClass() != poFClass ) { if( poDS->GetReadMode() == INTERLEAVED_LAYERS || (poDS->GetReadMode() == SEQUENTIAL_LAYERS && iNextGMLId != 0) ) { CPLAssert(poDS->PeekStoredGMLFeature() == NULL); poDS->SetStoredGMLFeature(poGMLFeature); return NULL; } else { delete poGMLFeature; continue; } } /* -------------------------------------------------------------------- */ /* Extract the fid: */ /* -Assumes the fids are non-negative integers with an optional */ /* prefix */ /* -If a prefix differs from the prefix of the first feature from */ /* the poDS then the fids from the poDS are ignored and are */ /* assigned serially thereafter */ /* -------------------------------------------------------------------- */ GIntBig nFID = -1; const char * pszGML_FID = poGMLFeature->GetFID(); if( bInvalidFIDFound ) { nFID = iNextGMLId++; } else if( pszGML_FID == NULL ) { bInvalidFIDFound = true; nFID = iNextGMLId++; } else if( iNextGMLId == 0 ) { int j = 0; int i = static_cast<int>(strlen( pszGML_FID ))-1; while( i >= 0 && pszGML_FID[i] >= '0' && pszGML_FID[i] <= '9' && j<20) i--, j++; /* i points the last character of the fid */ if( i >= 0 && j < 20 && pszFIDPrefix == NULL) { pszFIDPrefix = (char *) CPLMalloc(i+2); pszFIDPrefix[i+1] = '\0'; strncpy(pszFIDPrefix, pszGML_FID, i+1); } /* pszFIDPrefix now contains the prefix or NULL if no prefix is found */ if( j < 20 && sscanf(pszGML_FID+i+1, CPL_FRMT_GIB, &nFID)==1) { if( iNextGMLId <= nFID ) iNextGMLId = nFID + 1; } else { bInvalidFIDFound = true; nFID = iNextGMLId++; } } else if( iNextGMLId != 0 ) { const char* pszFIDPrefix_notnull = pszFIDPrefix; if (pszFIDPrefix_notnull == NULL) pszFIDPrefix_notnull = ""; int nLenPrefix = static_cast<int>(strlen(pszFIDPrefix_notnull)); if( strncmp(pszGML_FID, pszFIDPrefix_notnull, nLenPrefix) == 0 && strlen(pszGML_FID+nLenPrefix) < 20 && sscanf(pszGML_FID+nLenPrefix, CPL_FRMT_GIB, &nFID) == 1 ) { /* fid with the prefix. Using its numerical part */ if( iNextGMLId < nFID ) iNextGMLId = nFID + 1; } else { /* fid without the aforementioned prefix or a valid numerical part */ bInvalidFIDFound = true; nFID = iNextGMLId++; } } /* -------------------------------------------------------------------- */ /* Does it satisfy the spatial query, if there is one? */ /* -------------------------------------------------------------------- */ OGRGeometry** papoGeometries = NULL; const CPLXMLNode* const * papsGeometry = poGMLFeature->GetGeometryList(); if( poFeatureDefn->GetGeomFieldCount() > 1 ) { papoGeometries = (OGRGeometry**) CPLCalloc( poFeatureDefn->GetGeomFieldCount(), sizeof(OGRGeometry*) ); const char* pszSRSName = poDS->GetGlobalSRSName(); for( int i=0; i < poFeatureDefn->GetGeomFieldCount(); i++ ) { const CPLXMLNode* psGeom = poGMLFeature->GetGeometryRef(i); if( psGeom != NULL ) { const CPLXMLNode* myGeometryList[2]; myGeometryList[0] = psGeom; myGeometryList[1] = NULL; poGeom = GML_BuildOGRGeometryFromList(myGeometryList, true, poDS->GetInvertAxisOrderIfLatLong(), pszSRSName, poDS->GetConsiderEPSGAsURN(), poDS->GetSecondaryGeometryOption(), hCacheSRS, bFaceHoleNegative ); /* Do geometry type changes if needed to match layer geometry type */ if (poGeom != NULL) { papoGeometries[i] = OGRGeometryFactory::forceTo(poGeom, poFeatureDefn->GetGeomFieldDefn(i)->GetType()); poGeom = NULL; } else // We assume the createFromGML() function would have already // reported the error. { for( i=0; i < poFeatureDefn->GetGeomFieldCount(); i++) { delete papoGeometries[i]; } CPLFree(papoGeometries); delete poGMLFeature; return NULL; } } } if( m_poFilterGeom != NULL && m_iGeomFieldFilter >= 0 && m_iGeomFieldFilter < poFeatureDefn->GetGeomFieldCount() && papoGeometries[m_iGeomFieldFilter] && !FilterGeometry( papoGeometries[m_iGeomFieldFilter] ) ) { for( int i=0; i < poFeatureDefn->GetGeomFieldCount(); i++ ) { delete papoGeometries[i]; } CPLFree(papoGeometries); delete poGMLFeature; continue; } } else if (papsGeometry[0] != NULL) { const char* pszSRSName = poDS->GetGlobalSRSName(); poGeom = GML_BuildOGRGeometryFromList(papsGeometry, true, poDS->GetInvertAxisOrderIfLatLong(), pszSRSName, poDS->GetConsiderEPSGAsURN(), poDS->GetSecondaryGeometryOption(), hCacheSRS, bFaceHoleNegative ); /* Do geometry type changes if needed to match layer geometry type */ if (poGeom != NULL) { poGeom = OGRGeometryFactory::forceTo(poGeom, GetGeomType()); } else // We assume the createFromGML() function would have already // reported the error. { delete poGMLFeature; return NULL; } if( m_poFilterGeom != NULL && !FilterGeometry( poGeom ) ) { delete poGMLFeature; delete poGeom; continue; } } /* -------------------------------------------------------------------- */ /* Convert the whole feature into an OGRFeature. */ /* -------------------------------------------------------------------- */ int iField; int iDstField = 0; OGRFeature *poOGRFeature = new OGRFeature( poFeatureDefn ); poOGRFeature->SetFID( nFID ); if (poDS->ExposeId()) { if (pszGML_FID) poOGRFeature->SetField( iDstField, pszGML_FID ); iDstField ++; } int nPropertyCount = poFClass->GetPropertyCount(); for( iField = 0; iField < nPropertyCount; iField++, iDstField ++ ) { const GMLProperty *psGMLProperty = poGMLFeature->GetProperty( iField ); if( psGMLProperty == NULL || psGMLProperty->nSubProperties == 0 ) continue; switch( poFClass->GetProperty(iField)->GetType() ) { case GMLPT_Real: { poOGRFeature->SetField( iDstField, CPLAtof(psGMLProperty->papszSubProperties[0]) ); } break; case GMLPT_IntegerList: { int nCount = psGMLProperty->nSubProperties; int *panIntList = (int *) CPLMalloc(sizeof(int) * nCount ); for( int i = 0; i < nCount; i++ ) panIntList[i] = atoi(psGMLProperty->papszSubProperties[i]); poOGRFeature->SetField( iDstField, nCount, panIntList ); CPLFree( panIntList ); } break; case GMLPT_Integer64List: { int nCount = psGMLProperty->nSubProperties; GIntBig *panIntList = (GIntBig *) CPLMalloc(sizeof(GIntBig) * nCount ); for( int i = 0; i < nCount; i++ ) panIntList[i] = CPLAtoGIntBig(psGMLProperty->papszSubProperties[i]); poOGRFeature->SetField( iDstField, nCount, panIntList ); CPLFree( panIntList ); } break; case GMLPT_RealList: { int nCount = psGMLProperty->nSubProperties; double *padfList = (double *)CPLMalloc(sizeof(double)*nCount); for( int i = 0; i < nCount; i++ ) padfList[i] = CPLAtof(psGMLProperty->papszSubProperties[i]); poOGRFeature->SetField( iDstField, nCount, padfList ); CPLFree( padfList ); } break; case GMLPT_StringList: case GMLPT_FeaturePropertyList: { poOGRFeature->SetField( iDstField, psGMLProperty->papszSubProperties ); } break; case GMLPT_Boolean: { if( strcmp(psGMLProperty->papszSubProperties[0], "true") == 0 || strcmp(psGMLProperty->papszSubProperties[0], "1") == 0 ) { poOGRFeature->SetField( iDstField, 1); } else if( strcmp(psGMLProperty->papszSubProperties[0], "false") == 0 || strcmp(psGMLProperty->papszSubProperties[0], "0") == 0 ) { poOGRFeature->SetField( iDstField, 0); } else poOGRFeature->SetField( iDstField, psGMLProperty->papszSubProperties[0] ); break; } case GMLPT_BooleanList: { int nCount = psGMLProperty->nSubProperties; int *panIntList = (int *) CPLMalloc(sizeof(int) * nCount ); for( int i = 0; i < nCount; i++ ) { panIntList[i] = ( strcmp(psGMLProperty->papszSubProperties[i], "true") == 0 || strcmp(psGMLProperty->papszSubProperties[i], "1") == 0 ); } poOGRFeature->SetField( iDstField, nCount, panIntList ); CPLFree( panIntList ); break; } default: poOGRFeature->SetField( iDstField, psGMLProperty->papszSubProperties[0] ); break; } } delete poGMLFeature; poGMLFeature = NULL; /* Assign the geometry before the attribute filter because */ /* the attribute filter may use a special field like OGR_GEOMETRY */ if( papoGeometries != NULL ) { for( int i=0; i < poFeatureDefn->GetGeomFieldCount(); i++ ) { poOGRFeature->SetGeomFieldDirectly( i, papoGeometries[i] ); } CPLFree(papoGeometries); papoGeometries = NULL; } else poOGRFeature->SetGeometryDirectly( poGeom ); /* Assign SRS */ for( int i=0; i < poFeatureDefn->GetGeomFieldCount(); i++ ) { poGeom = poOGRFeature->GetGeomFieldRef(i); if( poGeom != NULL ) { OGRSpatialReference* poSRS = poFeatureDefn->GetGeomFieldDefn(i)->GetSpatialRef(); if (poSRS != NULL) poGeom->assignSpatialReference(poSRS); } } /* -------------------------------------------------------------------- */ /* Test against the attribute query. */ /* -------------------------------------------------------------------- */ if( m_poAttrQuery != NULL && !m_poAttrQuery->Evaluate( poOGRFeature ) ) { delete poOGRFeature; continue; } /* -------------------------------------------------------------------- */ /* Wow, we got our desired feature. Return it. */ /* -------------------------------------------------------------------- */ return poOGRFeature; } return NULL; }