Example #1
0
int GMLReader::PrescanForSchema( int bGetExtents )

{
    GMLFeature  *poFeature;

    if( m_pszFilename == NULL )
        return FALSE;

    SetClassListLocked( FALSE );

    ClearClasses();
    if( !SetupParser() )
        return FALSE;

    while( (poFeature = NextFeature()) != NULL )
    {
        GMLFeatureClass *poClass = poFeature->GetClass();

        if( poClass->GetFeatureCount() == -1 )
            poClass->SetFeatureCount( 1 );
        else
            poClass->SetFeatureCount( poClass->GetFeatureCount() + 1 );

#ifdef SUPPORT_GEOMETRY
        if( bGetExtents )
        {
            OGRGeometry *poGeometry = NULL;

            if( poFeature->GetGeometry() != NULL 
                && strlen(poFeature->GetGeometry()) != 0 )
            {
                poGeometry = OGRGeometryFactory::createFromGML( 
                    poFeature->GetGeometry() );
            }

            if( poGeometry != NULL )
            {
                double  dfXMin, dfXMax, dfYMin, dfYMax;
                OGREnvelope sEnvelope;

                poGeometry->getEnvelope( &sEnvelope );
                delete poGeometry;
                if( poClass->GetExtents(&dfXMin, &dfXMax, &dfYMin, &dfYMax) )
                {
                    dfXMin = MIN(dfXMin,sEnvelope.MinX);
                    dfXMax = MAX(dfXMax,sEnvelope.MaxX);
                    dfYMin = MIN(dfYMin,sEnvelope.MinY);
                    dfYMax = MAX(dfYMax,sEnvelope.MaxY);
                }
                else
                {
                    dfXMin = sEnvelope.MinX;
                    dfXMax = sEnvelope.MaxX;
                    dfYMin = sEnvelope.MinY;
                    dfYMax = sEnvelope.MaxY;
                }

                poClass->SetExtents( dfXMin, dfXMax, dfYMin, dfYMax );
            }
#endif /* def SUPPORT_GEOMETRY */
        }
        
        delete poFeature;
    }

    CleanupParser();

    return GetClassCount() > 0;
}
Example #2
0
int GMLReader::LoadClasses( const char *pszFile )

{
    // Add logic later to determine reasonable default schema file. 
    if( pszFile == NULL )
        return FALSE;

/* -------------------------------------------------------------------- */
/*      Load the raw XML file.                                          */
/* -------------------------------------------------------------------- */
    FILE       *fp;
    int         nLength;
    char        *pszWholeText;

    fp = VSIFOpen( pszFile, "rb" );

    if( fp == NULL )
    {
        CPLError( CE_Failure, CPLE_OpenFailed, 
                  "Failed to open file %s.", pszFile );
        return FALSE;
    }

    VSIFSeek( fp, 0, SEEK_END );
    nLength = VSIFTell( fp );
    VSIFSeek( fp, 0, SEEK_SET );

    pszWholeText = (char *) VSIMalloc(nLength+1);
    if( pszWholeText == NULL )
    {
        CPLError( CE_Failure, CPLE_AppDefined, 
                  "Failed to allocate %d byte buffer for %s,\n"
                  "is this really a GMLFeatureClassList file?",
                  nLength, pszFile );
        VSIFClose( fp );
        return FALSE;
    }
    
    if( VSIFRead( pszWholeText, nLength, 1, fp ) != 1 )
    {
        VSIFree( pszWholeText );
        VSIFClose( fp );
        CPLError( CE_Failure, CPLE_AppDefined, 
                  "Read failed on %s.", pszFile );
        return FALSE;
    }
    pszWholeText[nLength] = '\0';

    VSIFClose( fp );

    if( strstr( pszWholeText, "<GMLFeatureClassList>" ) == NULL )
    {
        VSIFree( pszWholeText );
        CPLError( CE_Failure, CPLE_AppDefined, 
                  "File %s does not contain a GMLFeatureClassList tree.",
                  pszFile );
        return FALSE;
    }

/* -------------------------------------------------------------------- */
/*      Convert to XML parse tree.                                      */
/* -------------------------------------------------------------------- */
    CPLXMLNode *psRoot;

    psRoot = CPLParseXMLString( pszWholeText );
    VSIFree( pszWholeText );

    // We assume parser will report errors via CPL.
    if( psRoot == NULL )
        return FALSE;

    if( psRoot->eType != CXT_Element 
        || !EQUAL(psRoot->pszValue,"GMLFeatureClassList") )
    {
        CPLDestroyXMLNode(psRoot);
        CPLError( CE_Failure, CPLE_AppDefined, 
                  "File %s is not a GMLFeatureClassList document.",
                  pszFile );
        return FALSE;
    }

/* -------------------------------------------------------------------- */
/*      Extract feature classes for all definitions found.              */
/* -------------------------------------------------------------------- */
    CPLXMLNode *psThis;

    for( psThis = psRoot->psChild; psThis != NULL; psThis = psThis->psNext )
    {
        if( psThis->eType == CXT_Element 
            && EQUAL(psThis->pszValue,"GMLFeatureClass") )
        {
            GMLFeatureClass   *poClass;

            poClass = new GMLFeatureClass();

            if( !poClass->InitializeFromXML( psThis ) )
            {
                delete poClass;
                CPLDestroyXMLNode( psRoot );
                return FALSE;
            }

            poClass->SetSchemaLocked( TRUE );

            AddClass( poClass );
        }
    }

    CPLDestroyXMLNode( psRoot );
    
    SetClassListLocked( TRUE );

    return TRUE;
}
Example #3
0
int GMLReader::ReArrangeTemplateClasses ( GFSTemplateList *pCC )
{
/* rearranging the final FeatureClass list [SEQUENTIAL] */
    int m_nSavedClassCount = GetClassCount();

/* saving the previous FeatureClass list */
    GMLFeatureClass **m_papoSavedClass = (GMLFeatureClass **)
                    CPLMalloc( sizeof(void*) * m_nSavedClassCount );
    int clIdx;
    for (clIdx = 0; clIdx < GetClassCount(); clIdx++)
    {
    /* tranferring any previous FeatureClass */
        m_papoSavedClass[clIdx] = m_papoClass[clIdx];
    }

/* cleaning the previous FeatureClass list */
    SetClassListLocked( FALSE );
    CPLFree( m_papoClass );
    m_nClassCount = 0;
    m_papoClass = NULL;

    GFSTemplateItem *pItem = pCC->GetFirst();
    while ( pItem != NULL )
    {
    /*
    * re-inserting any required FeatureClassup
    * accordingly to actual SEQUENTIAL layout
    */
        GMLFeatureClass* poClass = NULL;
        for( int iClass = 0; iClass < m_nSavedClassCount; iClass++ )
        {
            GMLFeatureClass* poItem = m_papoSavedClass[iClass];
            if( EQUAL(poItem->GetName(), pItem->GetName() ))
            {
                poClass = poItem;
                break;
            }
        }
        if (poClass != NULL)
        {
            if (poClass->GetFeatureCount() > 0)
                AddClass( poClass );
        }
        pItem = pItem->GetNext();
    }
    SetClassListLocked( TRUE );

/* destroying the saved List and any unused FeatureClass */
    for( int iClass = 0; iClass < m_nSavedClassCount; iClass++ )
    {
        int bUnused = TRUE;
        GMLFeatureClass* poClass = m_papoSavedClass[iClass];
        for( int iClass2 = 0; iClass2 < m_nClassCount; iClass2++ )
        {
            if (m_papoClass[iClass2] == poClass)
            {
                bUnused = FALSE;
                break;
            }
        }
        if ( bUnused == TRUE )
            delete poClass;
    }
    CPLFree( m_papoSavedClass );
    return 1;
}
Example #4
0
int GMLReader::ParseXSD( const char *pszFile )

{
    if( pszFile == NULL )
        return FALSE;

/* -------------------------------------------------------------------- */
/*      Load the raw XML file.                                          */
/* -------------------------------------------------------------------- */
    CPLXMLNode *psXSDTree = CPLParseXMLFile( pszFile );
    
    if( psXSDTree == NULL )
        return FALSE;

/* -------------------------------------------------------------------- */
/*      Strip off any namespace qualifiers.                             */
/* -------------------------------------------------------------------- */
    CPLStripXMLNamespace( psXSDTree, NULL, TRUE );

/* -------------------------------------------------------------------- */
/*      Find <schema> root element.                                     */
/* -------------------------------------------------------------------- */
    CPLXMLNode *psSchemaNode = CPLGetXMLNode( psXSDTree, "=schema" );
    if( psSchemaNode == NULL )
    {
        CPLDestroyXMLNode( psXSDTree );
        return FALSE;
    }

/* ==================================================================== */
/*      Process each feature class definition.                          */
/* ==================================================================== */
    CPLXMLNode *psThis;
    int         bIsLevel0 = TRUE;

    for( psThis = psSchemaNode->psChild; 
         psThis != NULL; psThis = psThis->psNext )
    {
/* -------------------------------------------------------------------- */
/*      Check for <xs:element> node.                                    */
/* -------------------------------------------------------------------- */
        if( psThis->eType != CXT_Element 
            || !EQUAL(psThis->pszValue,"element") )
            continue;

/* -------------------------------------------------------------------- */
/*      Check the substitution group.                                   */
/* -------------------------------------------------------------------- */
        const char *pszSubGroup = 
            StripNS(CPLGetXMLValue(psThis,"substitutionGroup",""));

        // Old OGR produced elements for the feature collection.
        if( EQUAL(pszSubGroup, "_FeatureCollection") )
            continue;

        if( !EQUAL(pszSubGroup, "_Feature") )
        {
            bIsLevel0 = FALSE;
            break;
        }
        
/* -------------------------------------------------------------------- */
/*      Get name                                                        */
/* -------------------------------------------------------------------- */
        const char *pszName;

        pszName = CPLGetXMLValue( psThis, "name", NULL );
        if( pszName == NULL )
        {
            bIsLevel0 = FALSE;
            break;
        }

/* -------------------------------------------------------------------- */
/*      Get type and verify relationship with name.                     */
/* -------------------------------------------------------------------- */
        const char *pszType;

        pszType = CPLGetXMLValue( psThis, "type", NULL );
        if( strstr( pszType, ":" ) != NULL )
            pszType = strstr( pszType, ":" ) + 1; 
        if( pszType == NULL || !EQUALN(pszType,pszName,strlen(pszName)) 
            || !(EQUAL(pszType+strlen(pszName),"_Type") ||
                    EQUAL(pszType+strlen(pszName),"Type")) )
        {
            bIsLevel0 = FALSE;
            break;
        }

/* -------------------------------------------------------------------- */
/*      The very next element should be the corresponding               */
/*      complexType declaration for the element.                        */
/* -------------------------------------------------------------------- */
        psThis = psThis->psNext;
        while( psThis != NULL && psThis->eType == CXT_Comment )
            psThis = psThis->psNext;

        if( psThis == NULL 
            || psThis->eType != CXT_Element
            || !EQUAL(psThis->pszValue,"complexType") 
            || !EQUAL(CPLGetXMLValue(psThis,"name",""),pszType) )
        {
            bIsLevel0 = FALSE;
            break;
        }

/* -------------------------------------------------------------------- */
/*      Grab the sequence of extensions greatgrandchild.                */
/* -------------------------------------------------------------------- */
        CPLXMLNode *psAttrSeq = 
            CPLGetXMLNode( psThis, 
                           "complexContent.extension.sequence" );

        if( psAttrSeq == NULL )
        {
            bIsLevel0 = FALSE;
            break;
        }

/* -------------------------------------------------------------------- */
/*      We are pretty sure this going to be a valid Feature class       */
/*      now, so create it.                                              */
/* -------------------------------------------------------------------- */
        GMLFeatureClass *poClass = new GMLFeatureClass( pszName );

/* -------------------------------------------------------------------- */
/*      Loop over each of the attribute elements being defined for      */
/*      this feature class.                                             */
/* -------------------------------------------------------------------- */
        CPLXMLNode *psAttrDef;

        for( psAttrDef = psAttrSeq->psChild; 
             psAttrDef != NULL; 
             psAttrDef = psAttrDef->psNext )
        {
            if( !EQUAL(psAttrDef->pszValue,"element") )
                continue;

            // For now we skip geometries .. fixup later.
            if( CPLGetXMLNode( psAttrDef, "simpleType" ) == NULL )
                continue;

            GMLPropertyDefn *poProp = new GMLPropertyDefn( 
                CPLGetXMLValue( psAttrDef, "name", "unnamed" ),
                CPLGetXMLValue( psAttrDef, "name", "unnamed" ) );

            const char *pszBase = 
                StripNS( CPLGetXMLValue( psAttrDef, 
                                         "simpleType.restriction.base", "" ));

            if( EQUAL(pszBase,"decimal") )
            {
                poProp->SetType( GMLPT_Real );
                const char *pszWidth = 
                    CPLGetXMLValue( psAttrDef, 
                              "simpleType.restriction.totalDigits.value", "0" );
                const char *pszPrecision = 
                    CPLGetXMLValue( psAttrDef, 
                              "simpleType.restriction.fractionDigits.value", "0" );
                poProp->SetWidth( atoi(pszWidth) );
                poProp->SetPrecision( atoi(pszPrecision) );
            }
            
            else if( EQUAL(pszBase,"float") 
                     || EQUAL(pszBase,"double") )
                poProp->SetType( GMLPT_Real );

            else if( EQUAL(pszBase,"integer") )
            {
                poProp->SetType( GMLPT_Integer );
                const char *pszWidth = 
                    CPLGetXMLValue( psAttrDef, 
                              "simpleType.restriction.totalDigits.value", "0" );
                poProp->SetWidth( atoi(pszWidth) );
            }

            else if( EQUAL(pszBase,"string") )
            {
                poProp->SetType( GMLPT_String );
                const char *pszWidth = 
                    CPLGetXMLValue( psAttrDef, 
                              "simpleType.restriction.maxLength.value", "0" );
                poProp->SetWidth( atoi(pszWidth) );
            }

            else
                poProp->SetType( GMLPT_Untyped );

            poClass->AddProperty( poProp );
        }

/* -------------------------------------------------------------------- */
/*      Class complete, add to reader class list.                       */
/* -------------------------------------------------------------------- */
        poClass->SetSchemaLocked( TRUE );

        AddClass( poClass );
    }

    CPLDestroyXMLNode( psXSDTree );

    if( m_nClassCount > 0 )
    {
        SetClassListLocked( TRUE );
        return TRUE;
    }
    else
        return FALSE;
}
int NASReader::PrescanForSchema( int bGetExtents )

{
    GMLFeature  *poFeature;

    if( m_pszFilename == NULL )
        return FALSE;

    SetClassListLocked( FALSE );

    ClearClasses();
    if( !SetupParser() )
        return FALSE;

    while( (poFeature = NextFeature()) != NULL )
    {
        GMLFeatureClass *poClass = poFeature->GetClass();

        if( poClass->GetFeatureCount() == -1 )
            poClass->SetFeatureCount( 1 );
        else
            poClass->SetFeatureCount( poClass->GetFeatureCount() + 1 );

#ifdef SUPPORT_GEOMETRY
        if( bGetExtents )
        {
            OGRGeometry *poGeometry = NULL;

            if( poFeature->GetGeometry() != NULL 
                && strlen(poFeature->GetGeometry()) != 0 )
            {
                poGeometry = (OGRGeometry *) OGR_G_CreateFromGML( 
                    poFeature->GetGeometry() );
            }

            if( poGeometry != NULL )
            {
                double  dfXMin, dfXMax, dfYMin, dfYMax;
                OGREnvelope sEnvelope;
                OGRwkbGeometryType eGType = (OGRwkbGeometryType) 
                    poClass->GetGeometryType();

                // Merge geometry type into layer.
                if( poClass->GetFeatureCount() == 1 && eGType == wkbUnknown )
                    eGType = wkbNone;

                poClass->SetGeometryType( 
                    (int) OGRMergeGeometryTypes(
                        eGType, poGeometry->getGeometryType() ) );

                // merge extents.
                poGeometry->getEnvelope( &sEnvelope );
                delete poGeometry;
                if( poClass->GetExtents(&dfXMin, &dfXMax, &dfYMin, &dfYMax) )
                {
                    dfXMin = MIN(dfXMin,sEnvelope.MinX);
                    dfXMax = MAX(dfXMax,sEnvelope.MaxX);
                    dfYMin = MIN(dfYMin,sEnvelope.MinY);
                    dfYMax = MAX(dfYMax,sEnvelope.MaxY);
                }
                else
                {
                    dfXMin = sEnvelope.MinX;
                    dfXMax = sEnvelope.MaxX;
                    dfYMin = sEnvelope.MinY;
                    dfYMax = sEnvelope.MaxY;
                }

                poClass->SetExtents( dfXMin, dfXMax, dfYMin, dfYMax );
            }
            else 
            {
                if( poClass->GetGeometryType() == (int) wkbUnknown 
                    && poClass->GetFeatureCount() == 1 )
                    poClass->SetGeometryType( wkbNone );
            }
#endif /* def SUPPORT_GEOMETRY */
        }
        
        delete poFeature;
    }

    CleanupParser();

    return GetClassCount() > 0;
}
Example #6
0
int NASReader::PrescanForSchema( int bGetExtents )

{
    GMLFeature  *poFeature;

    if( m_pszFilename == NULL )
        return FALSE;

    SetClassListLocked( FALSE );

    ClearClasses();
    if( !SetupParser() )
        return FALSE;

    std::string osWork;

    while( (poFeature = NextFeature()) != NULL )
    {
        GMLFeatureClass *poClass = poFeature->GetClass();

        if( poClass->GetFeatureCount() == -1 )
            poClass->SetFeatureCount( 1 );
        else
            poClass->SetFeatureCount( poClass->GetFeatureCount() + 1 );

#ifdef SUPPORT_GEOMETRY
        if( bGetExtents )
        {
            OGRGeometry *poGeometry = NULL;

            const CPLXMLNode* const * papsGeometry = poFeature->GetGeometryList();
            if( papsGeometry[0] != NULL )
            {
                poGeometry = (OGRGeometry*) OGR_G_CreateFromGMLTree(papsGeometry[0]);
            }

            if( poGeometry != NULL )
            {
                double  dfXMin, dfXMax, dfYMin, dfYMax;
                OGREnvelope sEnvelope;
                OGRwkbGeometryType eGType = (OGRwkbGeometryType) 
                    poClass->GetGeometryType();

                // Merge SRSName into layer.
                const char* pszSRSName = GML_ExtractSrsNameFromGeometry(papsGeometry, osWork, FALSE);
//                if (pszSRSName != NULL)
//                    m_bCanUseGlobalSRSName = FALSE;
                poClass->MergeSRSName(pszSRSName);

                // Merge geometry type into layer.
                if( poClass->GetFeatureCount() == 1 && eGType == wkbUnknown )
                    eGType = wkbNone;

                poClass->SetGeometryType( 
                    (int) OGRMergeGeometryTypes(
                        eGType, poGeometry->getGeometryType() ) );

                // merge extents.
                poGeometry->getEnvelope( &sEnvelope );
                delete poGeometry;
                if( poClass->GetExtents(&dfXMin, &dfXMax, &dfYMin, &dfYMax) )
                {
                    dfXMin = MIN(dfXMin,sEnvelope.MinX);
                    dfXMax = MAX(dfXMax,sEnvelope.MaxX);
                    dfYMin = MIN(dfYMin,sEnvelope.MinY);
                    dfYMax = MAX(dfYMax,sEnvelope.MaxY);
                }
                else
                {
                    dfXMin = sEnvelope.MinX;
                    dfXMax = sEnvelope.MaxX;
                    dfYMin = sEnvelope.MinY;
                    dfYMax = sEnvelope.MaxY;
                }

                poClass->SetExtents( dfXMin, dfXMax, dfYMin, dfYMax );
            }
            else 
            {
                if( poClass->GetGeometryType() == (int) wkbUnknown 
                    && poClass->GetFeatureCount() == 1 )
                    poClass->SetGeometryType( wkbNone );
            }
#endif /* def SUPPORT_GEOMETRY */
        }
        
        delete poFeature;
    }

    CleanupParser();

    return GetClassCount() > 0;
}