gmlhandler.cpp

来自「支持各种栅格图像和矢量图像读取的库」· C++ 代码 · 共 303 行

CPP
303
字号
/********************************************************************** * $Id: gmlhandler.cpp 10646 2007-01-18 02:38:10Z warmerdam $ * * Project:  GML Reader * Purpose:  Implementation of GMLHandler class. * Author:   Frank Warmerdam, warmerdam@pobox.com * ********************************************************************** * Copyright (c) 2002, Frank Warmerdam * * Permission is hereby granted, free of charge, to any person obtaining a * copy of this software and associated documentation files (the "Software"), * to deal in the Software without restriction, including without limitation * the rights to use, copy, modify, merge, publish, distribute, sublicense, * and/or sell copies of the Software, and to permit persons to whom the * Software is furnished to do so, subject to the following conditions: *  * The above copyright notice and this permission notice shall be included * in all copies or substantial portions of the Software. *  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER  * DEALINGS IN THE SOFTWARE. ****************************************************************************/#include <ctype.h>#include "gmlreaderp.h"#include "cpl_conv.h"#define MAX_TOKEN_SIZE  1000/************************************************************************//*                             GMLHandler()                             *//************************************************************************/GMLHandler::GMLHandler( GMLReader *poReader ){    m_poReader = poReader;    m_pszCurField = NULL;    m_pszGeometry = NULL;    m_nGeomAlloc = m_nGeomLen = 0;}/************************************************************************//*                            ~GMLHandler()                             *//************************************************************************/GMLHandler::~GMLHandler(){    CPLFree( m_pszCurField );    CPLFree( m_pszGeometry );}/************************************************************************//*                            startElement()                            *//************************************************************************/void GMLHandler::startElement(const XMLCh* const    uri,                              const XMLCh* const    localname,                              const XMLCh* const    qname,                              const Attributes& attrs ){    char        szElementName[MAX_TOKEN_SIZE];    GMLReadState *poState = m_poReader->GetState();    tr_strcpy( szElementName, localname );/* -------------------------------------------------------------------- *//*      If we are in the midst of collecting a feature attribute        *//*      value, then this must be a complex attribute which we don't     *//*      try to collect for now, so just terminate the field             *//*      collection.                                                     *//* -------------------------------------------------------------------- */    if( m_pszCurField != NULL )    {        CPLFree( m_pszCurField );        m_pszCurField = NULL;    }/* -------------------------------------------------------------------- *//*      If we are collecting geometry, or if we determine this is a     *//*      geometry element then append to the geometry info.              *//* -------------------------------------------------------------------- */    if( m_pszGeometry != NULL         || IsGeometryElement( szElementName ) )    {        int nLNLen = tr_strlen( localname );        /* should save attributes too! */        if( m_pszGeometry == NULL )            m_nGeometryDepth = poState->m_nPathLength;                if( m_nGeomLen + nLNLen + 4 > m_nGeomAlloc )        {            m_nGeomAlloc = (int) (m_nGeomAlloc * 1.3 + nLNLen + 1000);            m_pszGeometry = (char *)                 CPLRealloc( m_pszGeometry, m_nGeomAlloc);        }        strcpy( m_pszGeometry+m_nGeomLen, "<" );        tr_strcpy( m_pszGeometry+m_nGeomLen+1, localname );        strcat( m_pszGeometry+m_nGeomLen+nLNLen+1, ">" );        m_nGeomLen += strlen(m_pszGeometry+m_nGeomLen);    }    /* -------------------------------------------------------------------- *//*      Is it a feature?  If so push a whole new state, and return.     *//* -------------------------------------------------------------------- */    else if( m_poReader->IsFeatureElement( szElementName ) )    {        m_poReader->PushFeature( szElementName, attrs );        return;    }/* -------------------------------------------------------------------- *//*      If it is (or at least potentially is) a simple attribute,       *//*      then start collecting it.                                       *//* -------------------------------------------------------------------- */    else if( m_poReader->IsAttributeElement( szElementName ) )    {        CPLFree( m_pszCurField );        m_pszCurField = CPLStrdup("");    }/* -------------------------------------------------------------------- *//*      Push the element onto the current state's path.                 *//* -------------------------------------------------------------------- */    poState->PushPath( szElementName );}/************************************************************************//*                             endElement()                             *//************************************************************************/void GMLHandler::endElement(const   XMLCh* const    uri,                            const   XMLCh* const    localname,                            const   XMLCh* const    qname ){    char        szElementName[MAX_TOKEN_SIZE];    GMLReadState *poState = m_poReader->GetState();    tr_strcpy( szElementName, localname );/* -------------------------------------------------------------------- *//*      Is this closing off an attribute value?  We assume so if        *//*      we are collecting an attribute value and got to this point.     *//*      We don't bother validating that the closing tag matches the     *//*      opening tag.                                                    *//* -------------------------------------------------------------------- */    if( m_pszCurField != NULL )    {        CPLAssert( poState->m_poFeature != NULL );                m_poReader->SetFeatureProperty( szElementName, m_pszCurField );        CPLFree( m_pszCurField );        m_pszCurField = NULL;    }/* -------------------------------------------------------------------- *//*      If we are collecting Geometry than store it, and consider if    *//*      this is the end of the geometry.                                *//* -------------------------------------------------------------------- */    if( m_pszGeometry != NULL )    {        int nLNLen = tr_strlen( localname );        /* should save attributes too! */        if( m_nGeomLen + nLNLen + 4 > m_nGeomAlloc )        {            m_nGeomAlloc = (int) (m_nGeomAlloc * 1.3 + nLNLen + 1000);            m_pszGeometry = (char *)                 CPLRealloc( m_pszGeometry, m_nGeomAlloc);        }        strcat( m_pszGeometry+m_nGeomLen, "</" );        tr_strcpy( m_pszGeometry+m_nGeomLen+2, localname );        strcat( m_pszGeometry+m_nGeomLen+nLNLen+2, ">" );        m_nGeomLen += strlen(m_pszGeometry+m_nGeomLen);        if( poState->m_nPathLength == m_nGeometryDepth+1 )        {            if( poState->m_poFeature != NULL )                poState->m_poFeature->SetGeometryDirectly( m_pszGeometry );            else                CPLFree( m_pszGeometry );            m_pszGeometry = NULL;            m_nGeomAlloc = m_nGeomLen = 0;        }    }/* -------------------------------------------------------------------- *//*      If we are collecting a feature, and this element tag matches    *//*      element name for the class, then we have finished the           *//*      feature, and we pop the feature read state.                     *//* -------------------------------------------------------------------- */    if( poState->m_poFeature != NULL        && EQUAL(szElementName,                 poState->m_poFeature->GetClass()->GetElementName()) )    {        m_poReader->PopState();    }/* -------------------------------------------------------------------- *//*      Otherwise, we just pop the element off the local read states    *//*      element stack.                                                  *//* -------------------------------------------------------------------- */    else    {        if( EQUAL(szElementName,poState->GetLastComponent()) )            poState->PopPath();        else        {            CPLAssert( FALSE );        }    }}/************************************************************************//*                             characters()                             *//************************************************************************/void GMLHandler::characters(const XMLCh* const chars_in,                                const unsigned int length ){    const XMLCh *chars = chars_in;    if( m_pszCurField != NULL )    {        int     nCurFieldLength = strlen(m_pszCurField);        while( *chars == ' ' || *chars == 10 || *chars == 13 || *chars == '\t')            chars++;                m_pszCurField = (char *)             CPLRealloc( m_pszCurField,                         nCurFieldLength+tr_strlen(chars)+1 );        tr_strcpy( m_pszCurField + nCurFieldLength, chars );    }    else if( m_pszGeometry != NULL )    {        // Ignore white space        while( *chars == ' ' || *chars == 10 || *chars == 13 || *chars == '\t')            chars++;                int nCharsLen = tr_strlen( chars );        if( m_nGeomLen + nCharsLen + 4 > m_nGeomAlloc )        {            m_nGeomAlloc = (int) (m_nGeomAlloc * 1.3 + nCharsLen + 1000);            m_pszGeometry = (char *)                 CPLRealloc( m_pszGeometry, m_nGeomAlloc);        }        tr_strcpy( m_pszGeometry+m_nGeomLen, chars );        m_nGeomLen += strlen(m_pszGeometry+m_nGeomLen);    }}/************************************************************************//*                             fatalError()                             *//************************************************************************/void GMLHandler::fatalError( const SAXParseException &exception){    char *pszErrorMessage;    pszErrorMessage = tr_strdup( exception.getMessage() );    CPLError( CE_Failure, CPLE_AppDefined,               "XML Parsing Error: %s\n",               pszErrorMessage );    CPLFree( pszErrorMessage );}/************************************************************************//*                         IsGeometryElement()                          *//************************************************************************/int GMLHandler::IsGeometryElement( const char *pszElement ){    return EQUAL(pszElement,"Polygon")         || EQUAL(pszElement,"MultiPolygon")         || EQUAL(pszElement,"MultiPoint")         || EQUAL(pszElement,"MultiLineString")         || EQUAL(pszElement,"GeometryCollection")         || EQUAL(pszElement,"Point")         || EQUAL(pszElement,"LineString");}

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?