Beispiel #1
0
OGRErr OGRDXFWriterLayer::WritePOINT( OGRFeature *poFeature )

{
    WriteValue( 0, "POINT" );
    WriteCore( poFeature );
    WriteValue( 100, "AcDbEntity" );
    WriteValue( 100, "AcDbPoint" );

    // Write style pen color
    OGRStyleTool *poTool = nullptr;
    OGRStyleMgr oSM;
    if( poFeature->GetStyleString() != nullptr )
    {
        oSM.InitFromFeature( poFeature );

        if( oSM.GetPartCount() > 0 )
            poTool = oSM.GetPart(0);
    }
    if( poTool && poTool->GetType() == OGRSTCPen )
    {
        OGRStylePen *poPen = (OGRStylePen *) poTool;
        GBool  bDefault;

        if( poPen->Color(bDefault) != nullptr && !bDefault )
            WriteValue( 62, ColorStringToDXFColor( poPen->Color(bDefault) ) );
    }
    delete poTool;

    OGRPoint *poPoint = poFeature->GetGeometryRef()->toPoint();

    WriteValue( 10, poPoint->getX() );
    if( !WriteValue( 20, poPoint->getY() ) )
        return OGRERR_FAILURE;

    if( poPoint->getGeometryType() == wkbPoint25D )
    {
        if( !WriteValue( 30, poPoint->getZ() ) )
            return OGRERR_FAILURE;
    }

    return OGRERR_NONE;
}
Beispiel #2
0
void kml2styletable (
    OGRStyleTable * poOgrStyleTable,
    StylePtr poKmlStyle )
{


    /***** no reason to add it if it don't have an id *****/

    if ( poKmlStyle->has_id (  ) ) {

        OGRStyleMgr *poOgrSM = new OGRStyleMgr ( poOgrStyleTable );

        poOgrSM->InitStyleString ( NULL );

        /***** read the style *****/

        kml2stylestring ( poKmlStyle, poOgrSM );

        /***** add the style to the style table *****/

        const std::string oName = poKmlStyle->get_id (  );


        poOgrSM->AddStyle ( CPLString (  ).Printf ( "@%s",
                                                    oName.c_str (  ) ), NULL );

        /***** cleanup the style manager *****/

        delete poOgrSM;
    }

    else {
        CPLError ( CE_Failure, CPLE_AppDefined,
                   "ERROR Parseing kml Style: No id" );
    }

    return;
}
Beispiel #3
0
void addstylestring2kml (
    const char *pszStyleString,
    StylePtr poKmlStyle,
    KmlFactory * poKmlFactory,
    PlacemarkPtr poKmlPlacemark,
    OGRFeature * poOgrFeat )
{

    LineStylePtr poKmlLineStyle = NULL;
    PolyStylePtr poKmlPolyStyle = NULL;
    IconStylePtr poKmlIconStyle = NULL;
    LabelStylePtr poKmlLabelStyle = NULL;
    
    /***** just bail now if stylestring is empty *****/

    if ( !pszStyleString || !*pszStyleString ) {
        return;
    }

    /***** create and init a style mamager with the style string *****/

    OGRStyleMgr *poOgrSM = new OGRStyleMgr;

    poOgrSM->InitStyleString ( pszStyleString );

    /***** loop though the style parts *****/

    int i;

    for ( i = 0; i < poOgrSM->GetPartCount ( NULL ); i++ ) {
        OGRStyleTool *poOgrST = poOgrSM->GetPart ( i, NULL );

        if ( !poOgrST ) {
            continue;
        }
        
        switch ( poOgrST->GetType (  ) ) {
        case OGRSTCPen:
            {
                GBool nullcheck;

                poKmlLineStyle = poKmlFactory->CreateLineStyle (  );

                OGRStylePen *poStylePen = ( OGRStylePen * ) poOgrST;

                /***** pen color *****/

                int nR,
                    nG,
                    nB,
                    nA;

                const char *pszcolor = poStylePen->Color ( nullcheck );

                if ( !nullcheck
                     && poStylePen->GetRGBFromString ( pszcolor, nR, nG, nB, nA ) ) {
                    poKmlLineStyle->set_color ( Color32 ( nA, nB, nG, nR ) );
                }
                double dfWidth = poStylePen->Width ( nullcheck );

                if ( nullcheck )
                    dfWidth = 1.0;

                poKmlLineStyle->set_width ( dfWidth );
                
                break;
            }
        case OGRSTCBrush:
            {
                GBool nullcheck;

                poKmlPolyStyle = poKmlFactory->CreatePolyStyle (  );

                OGRStyleBrush *poStyleBrush = ( OGRStyleBrush * ) poOgrST;

                /***** brush color *****/

                int nR,
                    nG,
                    nB,
                    nA;

                const char *pszcolor = poStyleBrush->ForeColor ( nullcheck );

                if ( !nullcheck
                     && poStyleBrush->GetRGBFromString ( pszcolor, nR, nG, nB, nA ) ) {
                    poKmlPolyStyle->set_color ( Color32 ( nA, nB, nG, nR ) );
                }
                

                break;
            }
        case OGRSTCSymbol:
            {
                GBool nullcheck;
                GBool nullcheck2;

                OGRStyleSymbol *poStyleSymbol = ( OGRStyleSymbol * ) poOgrST;

                /***** id (kml icon) *****/

                const char *pszId = poStyleSymbol->Id ( nullcheck );

                if ( !nullcheck ) {
                    if ( !poKmlIconStyle)
                        poKmlIconStyle = poKmlFactory->CreateIconStyle (  );

                    /***** split it at the ,'s *****/

                    char **papszTokens =
                        CSLTokenizeString2 ( pszId, ",",
                                             CSLT_HONOURSTRINGS | CSLT_STRIPLEADSPACES |
                                             CSLT_STRIPENDSPACES );

                    if ( papszTokens ) {

                        /***** for lack of a better solution just take the first one *****/
                        //todo come up with a better idea

                        if ( papszTokens[0] ) {
                            IconStyleIconPtr poKmlIcon =
                                poKmlFactory->CreateIconStyleIcon (  );
                            poKmlIcon->set_href ( papszTokens[0] );
                            poKmlIconStyle->set_icon ( poKmlIcon );
                        }

                        CSLDestroy ( papszTokens );

                    }


                }

                /***** heading *****/

                double heading = poStyleSymbol->Angle ( nullcheck );

                if ( !nullcheck ) {
                    if ( !poKmlIconStyle)
                        poKmlIconStyle = poKmlFactory->CreateIconStyle (  );
                    poKmlIconStyle->set_heading ( heading );
                }

                /***** scale *****/

                double dfScale = poStyleSymbol->Size ( nullcheck );

                if ( !nullcheck ) {
                    if ( !poKmlIconStyle)
                        poKmlIconStyle = poKmlFactory->CreateIconStyle (  );

                    poKmlIconStyle->set_scale ( dfScale );
                }

                /***** color *****/

                int nR,
                    nG,
                    nB,
                    nA;

                const char *pszcolor = poStyleSymbol->Color ( nullcheck );

                if ( !nullcheck && poOgrST->GetRGBFromString ( pszcolor, nR, nG, nB, nA ) ) {
                    poKmlIconStyle->set_color ( Color32 ( nA, nB, nG, nR ) );
                }

                /***** hotspot *****/

                double dfDx = poStyleSymbol->SpacingX ( nullcheck );
                double dfDy = poStyleSymbol->SpacingY ( nullcheck2 );

                if ( !nullcheck && !nullcheck2 ) {
                    if ( !poKmlIconStyle)
                        poKmlIconStyle = poKmlFactory->CreateIconStyle (  );

                    HotSpotPtr poKmlHotSpot = poKmlFactory->CreateHotSpot (  );

                    poKmlHotSpot->set_x ( dfDx );
                    poKmlHotSpot->set_y ( dfDy );

                    poKmlIconStyle->set_hotspot ( poKmlHotSpot );
                }
                
                break;
            }
        case OGRSTCLabel:
            {
                GBool nullcheck;
                GBool nullcheck2;
                
                poKmlLabelStyle = poKmlFactory->CreateLabelStyle (  );

                OGRStyleLabel *poStyleLabel = ( OGRStyleLabel * ) poOgrST;

                /***** color *****/

                int nR,
                    nG,
                    nB,
                    nA;

                const char *pszcolor = poStyleLabel->ForeColor ( nullcheck );

                if ( !nullcheck
                     && poStyleLabel->GetRGBFromString ( pszcolor, nR, nG, nB, nA ) ) {
                    poKmlLabelStyle->set_color ( Color32 ( nA, nB, nG, nR ) );
                }

                /***** scale *****/

                double dfScale = poStyleLabel->Stretch ( nullcheck );

                if ( !nullcheck ) {
                    dfScale /= 100.0;
                    poKmlLabelStyle->set_scale ( dfScale );
                }
                
                /***** heading *****/

                double heading = poStyleLabel->Angle ( nullcheck );

                if ( !nullcheck ) {
                    if ( !poKmlIconStyle) {
                        poKmlIconStyle = poKmlFactory->CreateIconStyle (  );
                        IconStyleIconPtr poKmlIcon = poKmlFactory->CreateIconStyleIcon (  );
                        poKmlIconStyle->set_icon ( poKmlIcon );
                    }
                    
                    poKmlIconStyle->set_heading ( heading );
                }

                /***** hotspot *****/

                double dfDx = poStyleLabel->SpacingX ( nullcheck );
                double dfDy = poStyleLabel->SpacingY ( nullcheck2 );

                if ( !nullcheck && !nullcheck2 ) {
                    if ( !poKmlIconStyle) {
                        poKmlIconStyle = poKmlFactory->CreateIconStyle (  );
                        IconStyleIconPtr poKmlIcon = poKmlFactory->CreateIconStyleIcon (  );
                        poKmlIconStyle->set_icon ( poKmlIcon );
                    }
                    
                    HotSpotPtr poKmlHotSpot = poKmlFactory->CreateHotSpot (  );

                    poKmlHotSpot->set_x ( dfDx );
                    poKmlHotSpot->set_y ( dfDy );

                    poKmlIconStyle->set_hotspot ( poKmlHotSpot );
                }

                /***** label text *****/

                const char *pszText = poStyleLabel->TextString ( nullcheck );

                if ( !nullcheck ) {
                    if ( poKmlPlacemark ) {

                        poKmlPlacemark->set_name( pszText );
                    }
                }
                    
                break;
            }
        case OGRSTCNone:
        default:
            break;
        }

        delete poOgrST;
    }

    if ( poKmlLineStyle )
        poKmlStyle->set_linestyle ( poKmlLineStyle );

    if ( poKmlPolyStyle )
        poKmlStyle->set_polystyle ( poKmlPolyStyle );

    if ( poKmlIconStyle )
        poKmlStyle->set_iconstyle ( poKmlIconStyle );

    if ( poKmlLabelStyle )
        poKmlStyle->set_labelstyle ( poKmlLabelStyle );
    
    delete poOgrSM;
}
Beispiel #4
0
void kml2stylestring (
    StylePtr poKmlStyle,
    OGRStyleMgr * poOgrSM )

{

    OGRStyleMgr * poOgrNewSM ;
    OGRStyleTool *poOgrST = NULL;
    OGRStyleTool *poOgrTmpST = NULL;
    int i;

    poOgrNewSM = new OGRStyleMgr( NULL );
    
    /***** linestyle / pen *****/

    if ( poKmlStyle->has_linestyle (  ) ) {

        poOgrNewSM->InitStyleString ( NULL );
        
        LineStylePtr poKmlLineStyle = poKmlStyle->get_linestyle (  );

        poOgrTmpST = NULL;
        for ( i = 0; i < poOgrSM->GetPartCount ( NULL ); i++ ) {
            poOgrST = poOgrSM->GetPart ( i, NULL );

            if ( !poOgrST )
                continue;
        
            if ( poOgrST->GetType ( ) == OGRSTCPen ) {
                poOgrTmpST = poOgrST;
            }
            else {
                poOgrNewSM->AddPart ( poOgrST );
                delete poOgrST;
            }
        }
        
        OGRStylePen *poOgrStylePen = kml2pen ( poKmlLineStyle,
                                               ( OGRStylePen *) poOgrTmpST);
        
        poOgrNewSM->AddPart ( poOgrStylePen );

        delete poOgrStylePen;
        poOgrSM->InitStyleString ( poOgrNewSM->GetStyleString(NULL) );
        
    }

    /***** polystyle / brush *****/

    if ( poKmlStyle->has_polystyle (  ) ) {

        poOgrNewSM->InitStyleString ( NULL );

        PolyStylePtr poKmlPolyStyle = poKmlStyle->get_polystyle (  );

        poOgrTmpST = NULL;
        for ( i = 0; i < poOgrSM->GetPartCount ( NULL ); i++ ) {
            poOgrST = poOgrSM->GetPart ( i, NULL );

            if ( !poOgrST )
                continue;
        
            if ( poOgrST->GetType ( ) == OGRSTCBrush ) {
                poOgrTmpST = poOgrST;
            }
            else {
                poOgrNewSM->AddPart ( poOgrST );
                delete poOgrST;
            }
        }

        OGRStyleBrush *poOgrStyleBrush = kml2brush ( poKmlPolyStyle,
                                                     ( OGRStyleBrush *) poOgrTmpST );

        poOgrNewSM->AddPart ( poOgrStyleBrush );

        delete poOgrStyleBrush;
        poOgrSM->InitStyleString ( poOgrNewSM->GetStyleString(NULL) );

    }

    /***** iconstyle / symbol *****/

    if ( poKmlStyle->has_iconstyle (  ) ) {
        
        poOgrNewSM->InitStyleString ( NULL );

        IconStylePtr poKmlIconStyle = poKmlStyle->get_iconstyle (  );

        poOgrTmpST = NULL;
        for ( i = 0; i < poOgrSM->GetPartCount ( NULL ); i++ ) {
            poOgrST = poOgrSM->GetPart ( i, NULL );

            if ( !poOgrST )
                continue;
        
            if ( poOgrST->GetType ( ) == OGRSTCSymbol ) {
                poOgrTmpST = poOgrST;
            }
            else {
                poOgrNewSM->AddPart ( poOgrST );
                delete poOgrST;
            }
        }

        OGRStyleSymbol *poOgrStyleSymbol = kml2symbol ( poKmlIconStyle,
                                                     ( OGRStyleSymbol *) poOgrTmpST );

        poOgrNewSM->AddPart ( poOgrStyleSymbol );

        delete poOgrStyleSymbol;
        poOgrSM->InitStyleString ( poOgrNewSM->GetStyleString(NULL) );

    }

    /***** labelstyle / label *****/

    if ( poKmlStyle->has_labelstyle (  ) ) {
        
        poOgrNewSM->InitStyleString ( NULL );

        LabelStylePtr poKmlLabelStyle = poKmlStyle->get_labelstyle (  );

        poOgrTmpST = NULL;
        for ( i = 0; i < poOgrSM->GetPartCount ( NULL ); i++ ) {
            poOgrST = poOgrSM->GetPart ( i, NULL );

            if ( !poOgrST )
                continue;
        
            if ( poOgrST->GetType ( ) == OGRSTCLabel ) {
                poOgrTmpST = poOgrST;
            }
            else {
                poOgrNewSM->AddPart ( poOgrST );
                delete poOgrST;
            }
        }

        OGRStyleLabel *poOgrStyleLabel = kml2label ( poKmlLabelStyle,
                                                     ( OGRStyleLabel *) poOgrTmpST );

        poOgrNewSM->AddPart ( poOgrStyleLabel );

        delete poOgrStyleLabel;
        poOgrSM->InitStyleString ( poOgrNewSM->GetStyleString(NULL) );

    }

    delete poOgrNewSM;

}
OGRErr OGRJMLWriterLayer::ICreateFeature( OGRFeature *poFeature )

{
    /* Finish column declaration if we haven't yet created a feature */
    if( !bFeaturesWritten )
    {
        if( bAddOGRStyleField && poFeatureDefn->GetFieldIndex("OGR_STYLE") < 0 )
        {
            WriteColumnDeclaration( "OGR_STYLE", "STRING" );
        }
        if( bAddRGBField && poFeatureDefn->GetFieldIndex("R_G_B") < 0 )
        {
            WriteColumnDeclaration( "R_G_B", "STRING" );
        }
        VSIFPrintfL(fp, "</ColumnDefinitions>\n</JCSGMLInputTemplate>\n<featureCollection>\n");
        bFeaturesWritten = TRUE;
    }

    if( bClassicGML )
        VSIFPrintfL(fp, "   <featureMember>\n");
    VSIFPrintfL(fp, "     <feature>\n");

    /* Add geometry */
    VSIFPrintfL(fp, "          <geometry>\n");
    OGRGeometry* poGeom = poFeature->GetGeometryRef();
    if( poGeom != NULL )
    {
        char* pszGML = poGeom->exportToGML();
        VSIFPrintfL(fp, "                %s\n", pszGML);
        CPLFree(pszGML);
    }
    else
    {
        VSIFPrintfL(fp, "                %s\n",
                    "<gml:MultiGeometry></gml:MultiGeometry>");
    }
    VSIFPrintfL(fp, "          </geometry>\n");

    /* Add fields */
    for(int i=0;i<poFeature->GetFieldCount();i++)
    {
        char* pszName = OGRGetXML_UTF8_EscapedString(
                                poFeatureDefn->GetFieldDefn(i)->GetNameRef() );
        if( bClassicGML )
            VSIFPrintfL(fp, "          <%s>", pszName);
        else
            VSIFPrintfL(fp, "          <property name=\"%s\">", pszName);
        if( poFeature->IsFieldSet(i) )
        {
            OGRFieldType eType = poFeatureDefn->GetFieldDefn(i)->GetType();
            if( eType == OFTString )
            {
                char* pszValue = OGRGetXML_UTF8_EscapedString(
                                            poFeature->GetFieldAsString(i) );
                VSIFPrintfL(fp, "%s", pszValue);
                CPLFree(pszValue);
            }
            else if( eType == OFTDateTime )
            {
                int nYear, nMonth, nDay, nHour, nMinute, nTZFlag;
                float fSecond;
                poFeature->GetFieldAsDateTime(i, &nYear, &nMonth, &nDay,
                                            &nHour, &nMinute, &fSecond, &nTZFlag);
                /* When writing time zone, OpenJUMP expects .XXX seconds */
                /* to be written */
                if( nTZFlag > 1 || OGR_GET_MS(fSecond) != 0 )
                    VSIFPrintfL(fp, "%04d-%02d-%02dT%02d:%02d:%06.3f",
                                nYear, nMonth, nDay,
                                nHour, nMinute, fSecond);
                else
                    VSIFPrintfL(fp, "%04d-%02d-%02dT%02d:%02d:%02d",
                                nYear, nMonth, nDay,
                                nHour, nMinute, (int)fSecond);
                if( nTZFlag > 1 )
                {
                    int nOffset = (nTZFlag - 100) * 15;
                    int nHours = (int) (nOffset / 60);  // round towards zero
                    int nMinutes = ABS(nOffset - nHours * 60);

                    if( nOffset < 0 )
                    {
                        VSIFPrintfL(fp, "-" );
                        nHours = ABS(nHours);
                    }
                    else
                        VSIFPrintfL(fp, "+" );

                    VSIFPrintfL(fp, "%02d%02d", nHours, nMinutes );
                }
            }
            else
            {
                VSIFPrintfL(fp, "%s", poFeature->GetFieldAsString(i));
            }
        }
        if( bClassicGML )
            VSIFPrintfL(fp, "</%s>\n", pszName);
        else
            VSIFPrintfL(fp, "</property>\n");
        CPLFree(pszName);
    }

    /* Add OGR_STYLE from feature style string (if asked) */
    if( bAddOGRStyleField && poFeatureDefn->GetFieldIndex("OGR_STYLE") < 0 )
    {
        if( bClassicGML )
            VSIFPrintfL(fp, "          <OGR_STYLE>");
        else
            VSIFPrintfL(fp, "          <property name=\"%s\">", "OGR_STYLE");
        if( poFeature->GetStyleString() != NULL )
        {
            char* pszValue = OGRGetXML_UTF8_EscapedString( poFeature->GetStyleString() );
            VSIFPrintfL(fp, "%s", pszValue);
            CPLFree(pszValue);
        }
        if( bClassicGML )
            VSIFPrintfL(fp, "</OGR_STYLE>\n");
        else
            VSIFPrintfL(fp, "</property>\n");
    }
    
    /* Derive R_G_B field from feature style string */
    if( bAddRGBField && poFeatureDefn->GetFieldIndex("R_G_B") < 0 )
    {
        if( bClassicGML )
            VSIFPrintfL(fp, "          <R_G_B>");
        else
            VSIFPrintfL(fp, "          <property name=\"%s\">", "R_G_B");
        if( poFeature->GetStyleString() != NULL )
        {
            OGRGeometry* poGeom = poFeature->GetGeometryRef();
            OGRwkbGeometryType eGeomType =
                poGeom ? wkbFlatten(poGeom->getGeometryType()) : wkbUnknown;
            OGRStyleMgr oMgr;
            oMgr.InitFromFeature(poFeature);
            for(int i=0;i<oMgr.GetPartCount();i++)
            {
                OGRStyleTool* poTool = oMgr.GetPart(i);
                if( poTool != NULL )
                {
                    const char* pszColor = NULL;
                    if( poTool->GetType() == OGRSTCPen &&
                        eGeomType != wkbPolygon && eGeomType != wkbMultiPolygon )
                    {
                        GBool bIsNull;
                        pszColor = ((OGRStylePen*)poTool)->Color(bIsNull);
                        if( bIsNull ) pszColor = NULL;
                    }
                    else if( poTool->GetType() == OGRSTCBrush )
                    {
                        GBool bIsNull;
                        pszColor = ((OGRStyleBrush*)poTool)->ForeColor(bIsNull);
                        if( bIsNull ) pszColor = NULL;
                    }
                    int R, G, B, A;
                    if( pszColor != NULL &&
                        poTool->GetRGBFromString(pszColor, R, G, B, A) && A != 0 )
                    {
                        VSIFPrintfL(fp, "%02X%02X%02X", R, G, B);
                    }
                    delete poTool;
                }
            }
        }
        if( bClassicGML )
            VSIFPrintfL(fp, "</R_G_B>\n");
        else
            VSIFPrintfL(fp, "</property>\n");
    }

    VSIFPrintfL(fp, "     </feature>\n");
    if( bClassicGML )
        VSIFPrintfL(fp, "   </featureMember>\n");

    poFeature->SetFID(nNextFID ++);

    return OGRERR_NONE;
}
void kml2featurestyle (
    FeaturePtr poKmlFeature,
    OGRLIBKMLDataSource * poOgrDS,
    OGRLayer * poOgrLayer,
    OGRFeature * poOgrFeat )
{

    /***** does the placemark have a style url? *****/

    if (    poKmlFeature->has_styleurl (  ) ) {

        const string poKmlStyleUrl = poKmlFeature->get_styleurl (  );

        /***** is the name in the layer style table *****/

        char *pszUrl = CPLStrdup ( poKmlStyleUrl.c_str (  ) );

        OGRStyleTable *poOgrSTBLLayer;
        const char *pszTest = NULL;

        /***** is it a layer style ? *****/

        if ( *pszUrl == '#'
             && ( poOgrSTBLLayer = poOgrLayer->GetStyleTable (  ) ) != NULL )
        {
             pszTest = poOgrSTBLLayer->Find ( pszUrl + 1 );
        }

        if ( pszTest ) {

            /***** should we resolve the style *****/

            const char *pszResolve = CPLGetConfigOption ( "LIBKML_RESOLVE_STYLE", "no" );

            if (CPLTestBool(pszResolve)) {

                poOgrFeat->SetStyleString ( pszTest );
            }

            else {

                *pszUrl = '@';

                poOgrFeat->SetStyleString( pszUrl );

            }

        }

        /***** is it a dataset style? *****/

        else {

            int nPathLen = static_cast<int>(strlen ( poOgrDS->GetStylePath (  ) ));

            if (    nPathLen == 0
                 || EQUALN ( pszUrl, poOgrDS->GetStylePath (  ), nPathLen ))
            {

                /***** should we resolve the style *****/

                const char *pszResolve = CPLGetConfigOption ( "LIBKML_RESOLVE_STYLE", "no" );

                if ( CPLTestBool(pszResolve)
                     && ( poOgrSTBLLayer = poOgrDS->GetStyleTable (  ) ) != NULL
                     && ( pszTest = poOgrSTBLLayer->Find ( pszUrl + nPathLen + 1) ) != NULL
                   )
                {

                    poOgrFeat->SetStyleString ( pszTest );
                }

                else {

                    pszUrl[nPathLen] = '@';
                    poOgrFeat->SetStyleString ( pszUrl + nPathLen );
                }

            }

            /**** its someplace else *****/

            else {

                const char *pszFetch = CPLGetConfigOption ( "LIBKML_EXTERNAL_STYLE", "no" );

                if ( CPLTestBool(pszFetch) ) {

                    /***** load up the style table *****/

                    char *pszUrlTmp = CPLStrdup(pszUrl);
                    char *pszPound = strchr(pszUrlTmp, '#');
                    if (pszPound != NULL) {
                        *pszPound = '\0';
                    }

                    /***** try it as a url then a file *****/

                    VSILFILE *fp = NULL;

                    if (    (fp = VSIFOpenL( CPLFormFilename( "/vsicurl/",
                                                              pszUrlTmp,
                                                              NULL),
                                             "r" )) != NULL
                        ||  (fp = VSIFOpenL( pszUrlTmp, "r" )) != NULL )
                    {

                        char szbuf[1025];
                        std::string oStyle = "";

                        /***** loop, read and copy to a string *****/

                        size_t nRead;

                        do {

                            nRead = VSIFReadL(szbuf, 1, sizeof(szbuf) - 1, fp);

                            if (nRead == 0)
                                break;

                            /***** copy buf to the string *****/

                            szbuf[nRead] = '\0';
                            oStyle.append( szbuf );

                        } while (!VSIFEofL(fp));

                        VSIFCloseL(fp);

                        /***** parse the kml into the ds style table *****/

                        if ( poOgrDS->ParseIntoStyleTable (&oStyle, pszUrlTmp)) {

                            kml2featurestyle (poKmlFeature,
                                              poOgrDS,
                                              poOgrLayer,
                                              poOgrFeat );
                        }

                        else {

                            /***** if failed just store the url *****/

                            poOgrFeat->SetStyleString ( pszUrl );
                        }
                    }
                    CPLFree(pszUrlTmp);
                }

                else {

                    poOgrFeat->SetStyleString ( pszUrl );
                }
            }

        }
        CPLFree ( pszUrl );

    }

    /***** does the placemark have a style selector *****/

   if ( poKmlFeature->has_styleselector (  ) ) {

        StyleSelectorPtr poKmlStyleSelector =
            poKmlFeature->get_styleselector (  );

        /***** is the style a style? *****/

        if ( poKmlStyleSelector->IsA ( kmldom::Type_Style ) ) {
            StylePtr poKmlStyle = AsStyle ( poKmlStyleSelector );

            OGRStyleMgr *poOgrSM = new OGRStyleMgr;

            /***** if were resolving style the feature *****/
            /***** might already have styling to add too *****/

            const char *pszResolve = CPLGetConfigOption ( "LIBKML_RESOLVE_STYLE", "no" );
            if (CPLTestBool(pszResolve)) {
                 poOgrSM->InitFromFeature ( poOgrFeat );
            }
            else {

                /***** if featyurestyle gets a name tool this needs changed to the above *****/

                poOgrSM->InitStyleString ( NULL );
            }

            /***** read the style *****/

            kml2stylestring ( poKmlStyle, poOgrSM );

            /***** add the style to the feature *****/

            poOgrFeat->SetStyleString(poOgrSM->GetStyleString(NULL));

            delete poOgrSM;
        }

        /***** is the style a stylemap? *****/

        else if ( poKmlStyleSelector->IsA ( kmldom::Type_StyleMap ) ) {
            /* todo need to figure out what to do with a style map */
        }


    }
}
Beispiel #7
0
OGRErr OGRDXFWriterLayer::WritePOLYLINE( OGRFeature *poFeature,
                                         const OGRGeometry *poGeom )

{
/* -------------------------------------------------------------------- */
/*      For now we handle multilinestrings by writing a series of       */
/*      entities.                                                       */
/* -------------------------------------------------------------------- */
    if( poGeom == nullptr )
        poGeom = poFeature->GetGeometryRef();

    if ( poGeom->IsEmpty() )
    {
        return OGRERR_NONE;
    }

    if( wkbFlatten(poGeom->getGeometryType()) == wkbMultiPolygon
        || wkbFlatten(poGeom->getGeometryType()) == wkbMultiLineString )
    {
        const OGRGeometryCollection *poGC = poGeom->toGeometryCollection();
        OGRErr eErr = OGRERR_NONE;
        for( auto&& poMember: *poGC )
        {
            eErr = WritePOLYLINE( poFeature, poMember );
            if( eErr != OGRERR_NONE )
                break;
        }

        return eErr;
    }

/* -------------------------------------------------------------------- */
/*      Polygons are written with on entity per ring.                   */
/* -------------------------------------------------------------------- */
    if( wkbFlatten(poGeom->getGeometryType()) == wkbPolygon
        || wkbFlatten(poGeom->getGeometryType()) == wkbTriangle)
    {
        const OGRPolygon *poPoly = poGeom->toPolygon();
        OGRErr eErr = OGRERR_NONE;
        for( auto&& poRing: *poPoly )
        {
            eErr = WritePOLYLINE( poFeature, poRing );
            if( eErr != OGRERR_NONE )
                break;
        }

        return eErr;
    }

/* -------------------------------------------------------------------- */
/*      Do we now have a geometry we can work with?                     */
/* -------------------------------------------------------------------- */
    if( wkbFlatten(poGeom->getGeometryType()) != wkbLineString )
        return OGRERR_UNSUPPORTED_GEOMETRY_TYPE;

    const OGRLineString *poLS = poGeom->toLineString();

/* -------------------------------------------------------------------- */
/*      Write as a lightweight polygon,                                 */
/*       or as POLYLINE if the line contains different heights          */
/* -------------------------------------------------------------------- */
    int bHasDifferentZ = FALSE;
    if( poLS->getGeometryType() == wkbLineString25D )
    {
        double z0 = poLS->getZ(0);
        for( int iVert = 0; iVert < poLS->getNumPoints(); iVert++ )
        {
            if (z0 != poLS->getZ(iVert))
            {
                bHasDifferentZ = TRUE;
                break;
            }
        }
    }

    WriteValue( 0, bHasDifferentZ ? "POLYLINE" : "LWPOLYLINE" );
    WriteCore( poFeature );
    WriteValue( 100, "AcDbEntity" );
    if( bHasDifferentZ )
    {
        WriteValue( 100, "AcDb3dPolyline" );
        WriteValue( 10, 0.0 );
        WriteValue( 20, 0.0 );
        WriteValue( 30, 0.0 );
    }
    else
        WriteValue( 100, "AcDbPolyline" );
    if( EQUAL( poGeom->getGeometryName(), "LINEARRING" ) )
        WriteValue( 70, 1 + (bHasDifferentZ ? 8 : 0) );
    else
        WriteValue( 70, 0 + (bHasDifferentZ ? 8 : 0) );
    if( !bHasDifferentZ )
        WriteValue( 90, poLS->getNumPoints() );
    else
        WriteValue( 66, "1" );  // Vertex Flag

/* -------------------------------------------------------------------- */
/*      Do we have styling information?                                 */
/* -------------------------------------------------------------------- */
    OGRStyleTool *poTool = nullptr;
    OGRStyleMgr oSM;

    if( poFeature->GetStyleString() != nullptr )
    {
        oSM.InitFromFeature( poFeature );

        if( oSM.GetPartCount() > 0 )
            poTool = oSM.GetPart(0);
    }

/* -------------------------------------------------------------------- */
/*      Handle a PEN tool to control drawing color and width.           */
/*      Perhaps one day also dottedness, etc.                           */
/* -------------------------------------------------------------------- */
    if( poTool && poTool->GetType() == OGRSTCPen )
    {
        OGRStylePen *poPen = (OGRStylePen *) poTool;
        GBool bDefault;

        if( poPen->Color(bDefault) != nullptr && !bDefault )
            WriteValue( 62, ColorStringToDXFColor( poPen->Color(bDefault) ) );

        // we want to fetch the width in ground units.
        poPen->SetUnit( OGRSTUGround, 1.0 );
        const double dfWidth = poPen->Width(bDefault);

        if( !bDefault )
            WriteValue( 370, (int) floor(dfWidth * 100 + 0.5) );
    }

/* -------------------------------------------------------------------- */
/*      Do we have a Linetype for the feature?                          */
/* -------------------------------------------------------------------- */
    CPLString osLineType = poFeature->GetFieldAsString( "Linetype" );
    double dfLineTypeScale = 0.0;

    bool bGotLinetype = false;

    if( !osLineType.empty() )
    {
        std::vector<double> adfLineType =
            poDS->oHeaderDS.LookupLineType( osLineType );

        if( adfLineType.empty() && oNewLineTypes.count(osLineType) > 0 )
            adfLineType = oNewLineTypes[osLineType];

        if( !adfLineType.empty() )
        {
            bGotLinetype = true;
            WriteValue( 6, osLineType );

            // If the given linetype is proportional to the linetype data
            // in the style string, then apply a linetype scale
            if( poTool != nullptr && poTool->GetType() == OGRSTCPen )
            {
                std::vector<double> adfDefinition = PrepareLineTypeDefinition(
                    static_cast<OGRStylePen *>( poTool ) );
                
                if( !adfDefinition.empty() )
                {
                    dfLineTypeScale = IsLineTypeProportional( adfLineType,
                        adfDefinition );

                    if( dfLineTypeScale != 0.0 && 
                        fabs( dfLineTypeScale - 1.0 ) > 1e-4 )
                    {
                        WriteValue( 48, dfLineTypeScale );
                    }
                }
            }
        }
    }

    if( !bGotLinetype && poTool != nullptr && poTool->GetType() == OGRSTCPen )
    {
        std::vector<double> adfDefinition = PrepareLineTypeDefinition(
            static_cast<OGRStylePen *>( poTool ) );

        if( !adfDefinition.empty() )
        {
            // Is this definition already created and named?
            for( const auto& oPair : poDS->oHeaderDS.GetLineTypeTable() )
            {
                dfLineTypeScale = IsLineTypeProportional( oPair.second,
                    adfDefinition );
                if( dfLineTypeScale != 0.0 )
                {
                    osLineType = oPair.first;
                    break;
                }
            }

            if( dfLineTypeScale == 0.0 )
            {
                for( const auto& oPair : oNewLineTypes )
                {
                    dfLineTypeScale = IsLineTypeProportional( oPair.second,
                        adfDefinition );
                    if( dfLineTypeScale != 0.0 )
                    {
                        osLineType = oPair.first;
                        break;
                    }
                }
            }

            // If not, create an automatic name for it.
            if( osLineType == "" )
            {
                dfLineTypeScale = 1.0;
                do
                {
                    osLineType.Printf( "AutoLineType-%d", nNextAutoID++ );
                }
                while( poDS->oHeaderDS.LookupLineType(osLineType).size() > 0 );
            }

            // If it isn't already defined, add it now.
            if( poDS->oHeaderDS.LookupLineType( osLineType ).empty() &&
                oNewLineTypes.count( osLineType ) == 0 )
            {
                oNewLineTypes[osLineType] = adfDefinition;
            }

            WriteValue( 6, osLineType );

            if( dfLineTypeScale != 0.0 && fabs( dfLineTypeScale - 1.0 ) > 1e-4 )
            {
                WriteValue( 48, dfLineTypeScale );
            }
        }
    }

/* -------------------------------------------------------------------- */
/*      Write the vertices                                              */
/* -------------------------------------------------------------------- */

    if( !bHasDifferentZ && poLS->getGeometryType() == wkbLineString25D )
    {
     // if LWPOLYLINE with Z write it only once
        if( !WriteValue( 38, poLS->getZ(0) ) )
            return OGRERR_FAILURE;
    }

    for( int iVert = 0; iVert < poLS->getNumPoints(); iVert++ )
    {
        if( bHasDifferentZ )
        {
            WriteValue( 0, "VERTEX" );
            WriteValue( 100, "AcDbEntity" );
            WriteValue( 100, "AcDbVertex" );
            WriteValue( 100, "AcDb3dPolylineVertex" );
            WriteCore( poFeature );
        }
        WriteValue( 10, poLS->getX(iVert) );
        if( !WriteValue( 20, poLS->getY(iVert) ) )
            return OGRERR_FAILURE;

        if( bHasDifferentZ )
        {
            if( !WriteValue( 30 , poLS->getZ(iVert) ) )
                return OGRERR_FAILURE;
            WriteValue( 70, 32 );
        }
    }

    if( bHasDifferentZ )
    {
        WriteValue( 0, "SEQEND" );
        WriteCore( poFeature );
        WriteValue( 100, "AcDbEntity" );
    }

    delete poTool;

    return OGRERR_NONE;

#ifdef notdef
/* -------------------------------------------------------------------- */
/*      Alternate unmaintained implementation as a polyline entity.     */
/* -------------------------------------------------------------------- */
    WriteValue( 0, "POLYLINE" );
    WriteCore( poFeature );
    WriteValue( 100, "AcDbEntity" );
    WriteValue( 100, "AcDbPolyline" );
    if( EQUAL( poGeom->getGeometryName(), "LINEARRING" ) )
        WriteValue( 70, 1 );
    else
        WriteValue( 70, 0 );
    WriteValue( 66, "1" );

    for( int iVert = 0; iVert < poLS->getNumPoints(); iVert++ )
    {
        WriteValue( 0, "VERTEX" );
        WriteValue( 8, "0" );
        WriteValue( 10, poLS->getX(iVert) );
        if( !WriteValue( 20, poLS->getY(iVert) ) )
            return OGRERR_FAILURE;

        if( poLS->getGeometryType() == wkbLineString25D )
        {
            if( !WriteValue( 30, poLS->getZ(iVert) ) )
                return OGRERR_FAILURE;
        }
    }

    WriteValue( 0, "SEQEND" );
    WriteValue( 8, "0" );

    return OGRERR_NONE;
#endif
}
Beispiel #8
0
OGRErr OGRDXFWriterLayer::WriteTEXT( OGRFeature *poFeature )

{
    WriteValue( 0, "MTEXT" );
    WriteCore( poFeature );
    WriteValue( 100, "AcDbEntity" );
    WriteValue( 100, "AcDbMText" );

/* -------------------------------------------------------------------- */
/*      Do we have styling information?                                 */
/* -------------------------------------------------------------------- */
    OGRStyleTool *poTool = nullptr;
    OGRStyleMgr oSM;

    if( poFeature->GetStyleString() != nullptr )
    {
        oSM.InitFromFeature( poFeature );

        if( oSM.GetPartCount() > 0 )
            poTool = oSM.GetPart(0);
    }

/* ==================================================================== */
/*      Process the LABEL tool.                                         */
/* ==================================================================== */
    double dfDx = 0.0;
    double dfDy = 0.0;

    if( poTool && poTool->GetType() == OGRSTCLabel )
    {
        OGRStyleLabel *poLabel = (OGRStyleLabel *) poTool;
        GBool  bDefault;

/* -------------------------------------------------------------------- */
/*      Color                                                           */
/* -------------------------------------------------------------------- */
        if( poLabel->ForeColor(bDefault) != nullptr && !bDefault )
            WriteValue( 62, ColorStringToDXFColor(
                            poLabel->ForeColor(bDefault) ) );

/* -------------------------------------------------------------------- */
/*      Angle                                                           */
/* -------------------------------------------------------------------- */
        const double dfAngle = poLabel->Angle(bDefault);

        if( !bDefault )
            WriteValue( 50, dfAngle );

/* -------------------------------------------------------------------- */
/*      Height - We need to fetch this in georeferenced units - I'm     */
/*      doubt the default translation mechanism will be much good.      */
/* -------------------------------------------------------------------- */
        poTool->SetUnit( OGRSTUGround );
        const double dfHeight = poLabel->Size(bDefault);

        if( !bDefault )
            WriteValue( 40, dfHeight );

/* -------------------------------------------------------------------- */
/*      Anchor / Attachment Point                                       */
/* -------------------------------------------------------------------- */
        const int nAnchor = poLabel->Anchor(bDefault);

        if( !bDefault )
        {
            const static int anAnchorMap[] =
                { -1, 7, 8, 9, 4, 5, 6, 1, 2, 3, 7, 8, 9 };

            if( nAnchor > 0 && nAnchor < 13 )
                WriteValue( 71, anAnchorMap[nAnchor] );
        }

/* -------------------------------------------------------------------- */
/*      Offset                                                          */
/* -------------------------------------------------------------------- */
        dfDx = poLabel->SpacingX(bDefault);
        dfDy = poLabel->SpacingY(bDefault);

/* -------------------------------------------------------------------- */
/*      Escape the text, and convert to ISO8859.                        */
/* -------------------------------------------------------------------- */
        const char *pszText = poLabel->TextString( bDefault );

        if( pszText != nullptr && !bDefault )
        {
            CPLString osEscaped = TextEscape( pszText );
            while( osEscaped.size() > 250 )
            {
                WriteValue( 3, osEscaped.substr( 0, 250 ).c_str() );
                osEscaped.erase( 0, 250 );
            }
            WriteValue( 1, osEscaped );
        }

/* -------------------------------------------------------------------- */
/*      Store the text style in the map.                                */
/* -------------------------------------------------------------------- */
        std::map<CPLString, CPLString> oTextStyleDef =
            PrepareTextStyleDefinition( poLabel );
        CPLString osStyleName;

        for( const auto& oPair: oNewTextStyles )
        {
            if( oPair.second == oTextStyleDef )
            {
                osStyleName = oPair.first;
                break;
            }
        }

        if( osStyleName == "" )
        {

            do
            {
                osStyleName.Printf( "AutoTextStyle-%d", nNextAutoID++ );
            }
            while( poDS->oHeaderDS.TextStyleExists( osStyleName ) );

            oNewTextStyles[osStyleName] = oTextStyleDef;
        }

        WriteValue( 7, osStyleName );
    }

    delete poTool;

/* -------------------------------------------------------------------- */
/*      Write the location.                                             */
/* -------------------------------------------------------------------- */
    OGRPoint *poPoint = poFeature->GetGeometryRef()->toPoint();

    WriteValue( 10, poPoint->getX() + dfDx );
    if( !WriteValue( 20, poPoint->getY() + dfDy ) )
        return OGRERR_FAILURE;

    if( poPoint->getGeometryType() == wkbPoint25D )
    {
        if( !WriteValue( 30, poPoint->getZ() ) )
            return OGRERR_FAILURE;
    }

    return OGRERR_NONE;
}
Beispiel #9
0
OGRErr OGRDXFWriterLayer::WriteHATCH( OGRFeature *poFeature,
                                      OGRGeometry *poGeom )

{
/* -------------------------------------------------------------------- */
/*      For now we handle multipolygons by writing a series of          */
/*      entities.                                                       */
/* -------------------------------------------------------------------- */
    if( poGeom == nullptr )
        poGeom = poFeature->GetGeometryRef();

    if ( poGeom->IsEmpty() )
    {
        return OGRERR_NONE;
    }

    if( wkbFlatten(poGeom->getGeometryType()) == wkbMultiPolygon )
    {
        OGRErr eErr = OGRERR_NONE;
        for( auto&& poMember: poGeom->toMultiPolygon() )
        {
            eErr = WriteHATCH( poFeature, poMember );
            if( eErr != OGRERR_NONE )
                break;
        }

        return eErr;
    }

/* -------------------------------------------------------------------- */
/*      Do we now have a geometry we can work with?                     */
/* -------------------------------------------------------------------- */
    if( wkbFlatten(poGeom->getGeometryType()) != wkbPolygon &&
        wkbFlatten(poGeom->getGeometryType()) != wkbTriangle )
    {
        return OGRERR_UNSUPPORTED_GEOMETRY_TYPE;
    }

/* -------------------------------------------------------------------- */
/*      Write as a hatch.                                               */
/* -------------------------------------------------------------------- */
    WriteValue( 0, "HATCH" );
    WriteCore( poFeature );
    WriteValue( 100, "AcDbEntity" );
    WriteValue( 100, "AcDbHatch" );

    // Figure out "average" elevation
    OGREnvelope3D oEnv;
    poGeom->getEnvelope( &oEnv );
    WriteValue( 10, 0 ); // elevation point X = 0
    WriteValue( 20, 0 ); // elevation point Y = 0
    // elevation point Z = constant elevation
    WriteValue( 30, oEnv.MinZ + ( oEnv.MaxZ - oEnv.MinZ ) / 2 );

    WriteValue(210, 0 ); // extrusion direction X
    WriteValue(220, 0 ); // extrusion direction Y
    WriteValue(230,1.0); // extrusion direction Z

    WriteValue( 2, "SOLID" ); // fill pattern
    WriteValue( 70, 1 ); // solid fill
    WriteValue( 71, 0 ); // associativity

/* -------------------------------------------------------------------- */
/*      Do we have styling information?                                 */
/* -------------------------------------------------------------------- */
    OGRStyleTool *poTool = nullptr;
    OGRStyleMgr oSM;

    if( poFeature->GetStyleString() != nullptr )
    {
        oSM.InitFromFeature( poFeature );

        if( oSM.GetPartCount() > 0 )
            poTool = oSM.GetPart(0);
    }
    // Write style brush fore color
    if( poTool && poTool->GetType() == OGRSTCBrush )
    {
        OGRStyleBrush *poBrush = (OGRStyleBrush *) poTool;
        GBool  bDefault;

        if( poBrush->ForeColor(bDefault) != nullptr && !bDefault )
            WriteValue( 62, ColorStringToDXFColor( poBrush->ForeColor(bDefault) ) );
    }
    delete poTool;

/* -------------------------------------------------------------------- */
/*      Handle a PEN tool to control drawing color and width.           */
/*      Perhaps one day also dottedness, etc.                           */
/* -------------------------------------------------------------------- */
#ifdef notdef
    if( poTool && poTool->GetType() == OGRSTCPen )
    {
        OGRStylePen *poPen = (OGRStylePen *) poTool;
        GBool  bDefault;

        if( poPen->Color(bDefault) != NULL && !bDefault )
            WriteValue( 62, ColorStringToDXFColor( poPen->Color(bDefault) ) );

        double dfWidthInMM = poPen->Width(bDefault);

        if( !bDefault )
            WriteValue( 370, (int) floor(dfWidthInMM * 100 + 0.5) );
    }

/* -------------------------------------------------------------------- */
/*      Do we have a Linetype for the feature?                          */
/* -------------------------------------------------------------------- */
    CPLString osLineType = poFeature->GetFieldAsString( "Linetype" );

    if( !osLineType.empty()
        && (poDS->oHeaderDS.LookupLineType( osLineType ) != NULL
            || oNewLineTypes.count(osLineType) > 0 ) )
    {
        // Already define -> just reference it.
        WriteValue( 6, osLineType );
    }
    else if( poTool != NULL && poTool->GetType() == OGRSTCPen )
    {
        CPLString osDefinition = PrepareLineTypeDefinition( poFeature,
                                                            poTool );

        if( osDefinition != "" && osLineType == "" )
        {
            // Is this definition already created and named?
            std::map<CPLString,CPLString>::iterator it;

            for( it = oNewLineTypes.begin();
                 it != oNewLineTypes.end();
                 it++ )
            {
                if( (*it).second == osDefinition )
                {
                    osLineType = (*it).first;
                    break;
                }
            }

            // create an automatic name for it.
            if( osLineType == "" )
            {
                do
                {
                    osLineType.Printf( "AutoLineType-%d", nNextAutoID++ );
                }
                while( poDS->oHeaderDS.LookupLineType(osLineType) != NULL );
            }
        }

        // If it isn't already defined, add it now.
        if( osDefinition != "" && oNewLineTypes.count(osLineType) == 0 )
        {
            oNewLineTypes[osLineType] = osDefinition;
            WriteValue( 6, osLineType );
        }
    }
    delete poTool;
#endif

/* -------------------------------------------------------------------- */
/*      Process the loops (rings).                                      */
/* -------------------------------------------------------------------- */
    OGRPolygon *poPoly = poGeom->toPolygon();

    WriteValue( 91, poPoly->getNumInteriorRings() + 1 );

    for( auto&& poLR: *poPoly )
    {
        WriteValue( 92, 2 ); // Polyline
        WriteValue( 72, 0 ); // has bulge
        WriteValue( 73, 1 ); // is closed
        WriteValue( 93, poLR->getNumPoints() );

        for( int iVert = 0; iVert < poLR->getNumPoints(); iVert++ )
        {
            WriteValue( 10, poLR->getX(iVert) );
            WriteValue( 20, poLR->getY(iVert) );
        }

        WriteValue( 97, 0 ); // 0 source boundary objects
    }

    WriteValue( 75, 0 ); // hatch style = Hatch "odd parity" area (Normal style)
    WriteValue( 76, 1 ); // hatch pattern type = predefined
    WriteValue( 98, 0 ); // 0 seed points

    return OGRERR_NONE;

#ifdef notdef
/* -------------------------------------------------------------------- */
/*      Alternate unmaintained implementation as a polyline entity.     */
/* -------------------------------------------------------------------- */
    WriteValue( 0, "POLYLINE" );
    WriteCore( poFeature );
    WriteValue( 100, "AcDbEntity" );
    WriteValue( 100, "AcDbPolyline" );
    if( EQUAL( poGeom->getGeometryName(), "LINEARRING" ) )
        WriteValue( 70, 1 );
    else
        WriteValue( 70, 0 );
    WriteValue( 66, "1" );

    for( int iVert = 0; iVert < poLS->getNumPoints(); iVert++ )
    {
        WriteValue( 0, "VERTEX" );
        WriteValue( 8, "0" );
        WriteValue( 10, poLS->getX(iVert) );
        if( !WriteValue( 20, poLS->getY(iVert) ) )
            return OGRERR_FAILURE;

        if( poLS->getGeometryType() == wkbLineString25D )
        {
            if( !WriteValue( 30, poLS->getZ(iVert) ) )
                return OGRERR_FAILURE;
        }
    }

    WriteValue( 0, "SEQEND" );
    WriteValue( 8, "0" );

    return OGRERR_NONE;
#endif
}
Beispiel #10
0
OGRErr OGRDXFWriterLayer::WriteINSERT( OGRFeature *poFeature )

{
    WriteValue( 0, "INSERT" );
    WriteCore( poFeature );
    WriteValue( 100, "AcDbEntity" );
    WriteValue( 100, "AcDbBlockReference" );
    WriteValue( 2, poFeature->GetFieldAsString("BlockName") );

    // Write style symbol color
    OGRStyleTool *poTool = nullptr;
    OGRStyleMgr oSM;
    if( poFeature->GetStyleString() != nullptr )
    {
        oSM.InitFromFeature( poFeature );

        if( oSM.GetPartCount() > 0 )
            poTool = oSM.GetPart(0);
    }
    if( poTool && poTool->GetType() == OGRSTCSymbol )
    {
        OGRStyleSymbol *poSymbol = (OGRStyleSymbol *) poTool;
        GBool bDefault;

        if( poSymbol->Color(bDefault) != nullptr && !bDefault )
            WriteValue( 62, ColorStringToDXFColor( poSymbol->Color(bDefault) ) );
    }
    delete poTool;

/* -------------------------------------------------------------------- */
/*      Write location in OCS.                                          */
/* -------------------------------------------------------------------- */
    int nCoordCount = 0;
    const double *padfCoords =
        poFeature->GetFieldAsDoubleList( "BlockOCSCoords", &nCoordCount );

    if( nCoordCount == 3 )
    {
        WriteValue( 10, padfCoords[0] );
        WriteValue( 20, padfCoords[1] );
        if( !WriteValue( 30, padfCoords[2] ) )
            return OGRERR_FAILURE;
    }
    else
    {
        // We don't have an OCS; we will just assume that the location of
        // the geometry (in WCS) is the correct insertion point.
        OGRPoint *poPoint = poFeature->GetGeometryRef()->toPoint();

        WriteValue( 10, poPoint->getX() );
        if( !WriteValue( 20, poPoint->getY() ) )
            return OGRERR_FAILURE;

        if( poPoint->getGeometryType() == wkbPoint25D )
        {
            if( !WriteValue( 30, poPoint->getZ() ) )
                return OGRERR_FAILURE;
        }
    }

/* -------------------------------------------------------------------- */
/*      Write scaling.                                                  */
/* -------------------------------------------------------------------- */
    int nScaleCount = 0;
    const double *padfScale =
        poFeature->GetFieldAsDoubleList( "BlockScale", &nScaleCount );

    if( nScaleCount == 3 )
    {
        WriteValue( 41, padfScale[0] );
        WriteValue( 42, padfScale[1] );
        WriteValue( 43, padfScale[2] );
    }

/* -------------------------------------------------------------------- */
/*      Write rotation.                                                 */
/* -------------------------------------------------------------------- */
    const double dfAngle = poFeature->GetFieldAsDouble( "BlockAngle" );

    if( dfAngle != 0.0 )
    {
        WriteValue( 50, dfAngle ); // degrees
    }

/* -------------------------------------------------------------------- */
/*      Write OCS normal vector.                                        */
/* -------------------------------------------------------------------- */
    int nOCSCount = 0;
    const double *padfOCS =
        poFeature->GetFieldAsDoubleList( "BlockOCSNormal", &nOCSCount );

    if( nOCSCount == 3 )
    {
        WriteValue( 210, padfOCS[0] );
        WriteValue( 220, padfOCS[1] );
        WriteValue( 230, padfOCS[2] );
    }

    return OGRERR_NONE;
}
Beispiel #11
0
OGRErr OGRDXFWriterLayer::WritePOLYLINE( OGRFeature *poFeature,
                                         OGRGeometry *poGeom )

{
/* -------------------------------------------------------------------- */
/*      For now we handle multilinestrings by writing a series of       */
/*      entities.                                                       */
/* -------------------------------------------------------------------- */
    if( poGeom == NULL )
        poGeom = poFeature->GetGeometryRef();

    if ( poGeom->IsEmpty() )
    {
        return OGRERR_NONE;
    }
            
    if( wkbFlatten(poGeom->getGeometryType()) == wkbMultiPolygon 
        || wkbFlatten(poGeom->getGeometryType()) == wkbMultiLineString )
    {
        OGRGeometryCollection *poGC = (OGRGeometryCollection *) poGeom;
        int iGeom;
        OGRErr eErr = OGRERR_NONE;

        for( iGeom = 0; 
             eErr == OGRERR_NONE && iGeom < poGC->getNumGeometries(); 
             iGeom++ )
        {
            eErr = WritePOLYLINE( poFeature, poGC->getGeometryRef( iGeom ) );
        }

        return eErr;
    }

/* -------------------------------------------------------------------- */
/*      Polygons are written with on entity per ring.                   */
/* -------------------------------------------------------------------- */
    if( wkbFlatten(poGeom->getGeometryType()) == wkbPolygon )
    {
        OGRPolygon *poPoly = (OGRPolygon *) poGeom;
        int iGeom;
        OGRErr eErr;

        eErr = WritePOLYLINE( poFeature, poPoly->getExteriorRing() );
        for( iGeom = 0; 
             eErr == OGRERR_NONE && iGeom < poPoly->getNumInteriorRings(); 
             iGeom++ )
        {
            eErr = WritePOLYLINE( poFeature, poPoly->getInteriorRing(iGeom) );
        }

        return eErr;
    }

/* -------------------------------------------------------------------- */
/*      Do we now have a geometry we can work with?                     */
/* -------------------------------------------------------------------- */
    if( wkbFlatten(poGeom->getGeometryType()) != wkbLineString )
        return OGRERR_UNSUPPORTED_GEOMETRY_TYPE;

    OGRLineString *poLS = (OGRLineString *) poGeom;

/* -------------------------------------------------------------------- */
/*      Write as a lightweight polygon,                                 */
/*       or as POLYLINE if the line contains different heights          */
/* -------------------------------------------------------------------- */
    int bHasDifferentZ = FALSE;
    if( poLS->getGeometryType() == wkbLineString25D )
    {
        double z0 = poLS->getZ(0);
        for( int iVert = 0; iVert < poLS->getNumPoints(); iVert++ )
        {
            if (z0 != poLS->getZ(iVert))
            {
                bHasDifferentZ = TRUE;
                break;
            }
        }
    }

    WriteValue( 0, bHasDifferentZ ? "POLYLINE" : "LWPOLYLINE" );
    WriteCore( poFeature );
    WriteValue( 100, "AcDbEntity" );
    if( bHasDifferentZ )
    {
        WriteValue( 100, "AcDb3dPolyline" );
        WriteValue( 10, 0.0 );
        WriteValue( 20, 0.0 );
        WriteValue( 30, 0.0 );
    }
    else
        WriteValue( 100, "AcDbPolyline" );
    if( EQUAL( poGeom->getGeometryName(), "LINEARRING" ) )
        WriteValue( 70, 1 + (bHasDifferentZ ? 8 : 0) );
    else
        WriteValue( 70, 0 + (bHasDifferentZ ? 8 : 0) );
    if( !bHasDifferentZ )
        WriteValue( 90, poLS->getNumPoints() );
    else
        WriteValue( 66, "1" );  // Vertex Flag

/* -------------------------------------------------------------------- */
/*      Do we have styling information?                                 */
/* -------------------------------------------------------------------- */
    OGRStyleTool *poTool = NULL;
    OGRStyleMgr oSM;

    if( poFeature->GetStyleString() != NULL )
    {
        oSM.InitFromFeature( poFeature );

        if( oSM.GetPartCount() > 0 )
            poTool = oSM.GetPart(0);
    }

/* -------------------------------------------------------------------- */
/*      Handle a PEN tool to control drawing color and width.           */
/*      Perhaps one day also dottedness, etc.                           */
/* -------------------------------------------------------------------- */
    if( poTool && poTool->GetType() == OGRSTCPen )
    {
        OGRStylePen *poPen = (OGRStylePen *) poTool;
        GBool  bDefault;

        if( poPen->Color(bDefault) != NULL && !bDefault )
            WriteValue( 62, ColorStringToDXFColor( poPen->Color(bDefault) ) );

        // we want to fetch the width in ground units. 
        poPen->SetUnit( OGRSTUGround, 1.0 );
        double dfWidth = poPen->Width(bDefault);

        if( !bDefault )
            WriteValue( 370, (int) floor(dfWidth * 100 + 0.5) );
    }

/* -------------------------------------------------------------------- */
/*      Do we have a Linetype for the feature?                          */
/* -------------------------------------------------------------------- */
    CPLString osLineType = poFeature->GetFieldAsString( "Linetype" );

    if( osLineType.size() > 0 
        && (poDS->oHeaderDS.LookupLineType( osLineType ) != NULL 
            || oNewLineTypes.count(osLineType) > 0 ) )
    {
        // Already define -> just reference it.
        WriteValue( 6, osLineType );
    }
    else if( poTool != NULL && poTool->GetType() == OGRSTCPen )
    {
        CPLString osDefinition = PrepareLineTypeDefinition( poFeature, 
                                                            poTool );

        if( osDefinition != "" && osLineType == "" )
        {
            // Is this definition already created and named?
            std::map<CPLString,CPLString>::iterator it;

            for( it = oNewLineTypes.begin();
                 it != oNewLineTypes.end();
                 it++ )
            {
                if( (*it).second == osDefinition )
                {
                    osLineType = (*it).first;
                    break;
                }
            }

            // create an automatic name for it.
            if( osLineType == "" )
            {
                do 
                { 
                    osLineType.Printf( "AutoLineType-%d", nNextAutoID++ );
                }
                while( poDS->oHeaderDS.LookupLineType(osLineType) != NULL );
            }
        }

        // If it isn't already defined, add it now.
        if( osDefinition != "" && oNewLineTypes.count(osLineType) == 0 )
        {
            oNewLineTypes[osLineType] = osDefinition;
            WriteValue( 6, osLineType );
        }
    }

/* -------------------------------------------------------------------- */
/*      Write the vertices                                              */
/* -------------------------------------------------------------------- */

    if( !bHasDifferentZ && poLS->getGeometryType() == wkbLineString25D )
    {
     // if LWPOLYLINE with Z write it only once
        if( !WriteValue( 38, poLS->getZ(0) ) )
            return OGRERR_FAILURE;
    }

    int iVert;

    for( iVert = 0; iVert < poLS->getNumPoints(); iVert++ )
    {
        if( bHasDifferentZ ) 
        {
            WriteValue( 0, "VERTEX" );
            WriteValue( 100, "AcDbEntity" );
            WriteValue( 100, "AcDbVertex" );
            WriteValue( 100, "AcDb3dPolylineVertex" );
            WriteCore( poFeature );
        }
        WriteValue( 10, poLS->getX(iVert) );
        if( !WriteValue( 20, poLS->getY(iVert) ) ) 
            return OGRERR_FAILURE;

        if( bHasDifferentZ )
        {
            if( !WriteValue( 30 , poLS->getZ(iVert) ) )
                return OGRERR_FAILURE;
            WriteValue( 70, 32 );
        }
    }

    if( bHasDifferentZ )
    {
        WriteValue( 0, "SEQEND" );
        WriteCore( poFeature );
        WriteValue( 100, "AcDbEntity" );
    }
    
    delete poTool;

    return OGRERR_NONE;

#ifdef notdef
/* -------------------------------------------------------------------- */
/*      Alternate unmaintained implementation as a polyline entity.     */
/* -------------------------------------------------------------------- */
    WriteValue( 0, "POLYLINE" );
    WriteCore( poFeature );
    WriteValue( 100, "AcDbEntity" );
    WriteValue( 100, "AcDbPolyline" );
    if( EQUAL( poGeom->getGeometryName(), "LINEARRING" ) )
        WriteValue( 70, 1 );
    else
        WriteValue( 70, 0 );
    WriteValue( 66, "1" );

    int iVert;

    for( iVert = 0; iVert < poLS->getNumPoints(); iVert++ )
    {
        WriteValue( 0, "VERTEX" );
        WriteValue( 8, "0" );
        WriteValue( 10, poLS->getX(iVert) );
        if( !WriteValue( 20, poLS->getY(iVert) ) ) 
            return OGRERR_FAILURE;

        if( poLS->getGeometryType() == wkbLineString25D )
        {
            if( !WriteValue( 30, poLS->getZ(iVert) ) )
                return OGRERR_FAILURE;
        }
    }

    WriteValue( 0, "SEQEND" );
    WriteValue( 8, "0" );
    
    return OGRERR_NONE;
#endif
}
Beispiel #12
0
OGRErr OGRDXFWriterLayer::WriteTEXT( OGRFeature *poFeature )

{
    WriteValue( 0, "MTEXT" );
    WriteCore( poFeature );
    WriteValue( 100, "AcDbEntity" );
    WriteValue( 100, "AcDbMText" );

/* -------------------------------------------------------------------- */
/*      Do we have styling information?                                 */
/* -------------------------------------------------------------------- */
    OGRStyleTool *poTool = NULL;
    OGRStyleMgr oSM;

    if( poFeature->GetStyleString() != NULL )
    {
        oSM.InitFromFeature( poFeature );

        if( oSM.GetPartCount() > 0 )
            poTool = oSM.GetPart(0);
    }

/* ==================================================================== */
/*      Process the LABEL tool.                                         */
/* ==================================================================== */
    if( poTool && poTool->GetType() == OGRSTCLabel )
    {
        OGRStyleLabel *poLabel = (OGRStyleLabel *) poTool;
        GBool  bDefault;

/* -------------------------------------------------------------------- */
/*      Color                                                           */
/* -------------------------------------------------------------------- */
        if( poLabel->ForeColor(bDefault) != NULL && !bDefault )
            WriteValue( 62, ColorStringToDXFColor( 
                            poLabel->ForeColor(bDefault) ) );

/* -------------------------------------------------------------------- */
/*      Angle                                                           */
/* -------------------------------------------------------------------- */
        double dfAngle = poLabel->Angle(bDefault);

        // The DXF2000 reference says this is in radians, but in files
        // I see it seems to be in degrees. Perhaps this is version dependent?
        if( !bDefault )
            WriteValue( 50, dfAngle );

/* -------------------------------------------------------------------- */
/*      Height - We need to fetch this in georeferenced units - I'm     */
/*      doubt the default translation mechanism will be much good.      */
/* -------------------------------------------------------------------- */
        poTool->SetUnit( OGRSTUGround );
        double dfHeight = poLabel->Size(bDefault);

        if( !bDefault )
            WriteValue( 40, dfHeight );

/* -------------------------------------------------------------------- */
/*      Anchor / Attachment Point                                       */
/* -------------------------------------------------------------------- */
        int nAnchor = poLabel->Anchor(bDefault);
        
        if( !bDefault )
        {
            const static int anAnchorMap[] = 
                { -1, 7, 8, 9, 4, 5, 6, 1, 2, 3, 7, 8, 9 };

            if( nAnchor > 0 && nAnchor < 13 )
                WriteValue( 71, anAnchorMap[nAnchor] );
        }

/* -------------------------------------------------------------------- */
/*      Escape the text, and convert to ISO8859.                        */
/* -------------------------------------------------------------------- */
        const char *pszText = poLabel->TextString( bDefault );

        if( pszText != NULL && !bDefault )
        {
            CPLString osEscaped = TextEscape( pszText );
            WriteValue( 1, osEscaped );
        }
    }

    delete poTool;

/* -------------------------------------------------------------------- */
/*      Write the location.                                             */
/* -------------------------------------------------------------------- */
    OGRPoint *poPoint = (OGRPoint *) poFeature->GetGeometryRef();

    WriteValue( 10, poPoint->getX() );
    if( !WriteValue( 20, poPoint->getY() ) ) 
        return OGRERR_FAILURE;

    if( poPoint->getGeometryType() == wkbPoint25D )
    {
        if( !WriteValue( 30, poPoint->getZ() ) )
            return OGRERR_FAILURE;
    }
    
    return OGRERR_NONE;

}
Beispiel #13
0
OGRErr OGRDXFWriterLayer::WriteINSERT( OGRFeature *poFeature )

{
    WriteValue( 0, "INSERT" );
    WriteCore( poFeature );
    WriteValue( 100, "AcDbEntity" );
    WriteValue( 100, "AcDbBlockReference" );
    WriteValue( 2, poFeature->GetFieldAsString("BlockName") );

    // Write style symbol color
    OGRStyleTool *poTool = NULL;
    OGRStyleMgr oSM;
    if( poFeature->GetStyleString() != NULL )
    {
        oSM.InitFromFeature( poFeature );

        if( oSM.GetPartCount() > 0 )
            poTool = oSM.GetPart(0);
    }
    if( poTool && poTool->GetType() == OGRSTCSymbol )
    {
        OGRStyleSymbol *poSymbol = (OGRStyleSymbol *) poTool;
        GBool  bDefault;

        if( poSymbol->Color(bDefault) != NULL && !bDefault )
            WriteValue( 62, ColorStringToDXFColor( poSymbol->Color(bDefault) ) );
    }
    delete poTool;
    
/* -------------------------------------------------------------------- */
/*      Write location.                                                 */
/* -------------------------------------------------------------------- */
    OGRPoint *poPoint = (OGRPoint *) poFeature->GetGeometryRef();

    WriteValue( 10, poPoint->getX() );
    if( !WriteValue( 20, poPoint->getY() ) ) 
        return OGRERR_FAILURE;

    if( poPoint->getGeometryType() == wkbPoint25D )
    {
        if( !WriteValue( 30, poPoint->getZ() ) )
            return OGRERR_FAILURE;
    }
    
/* -------------------------------------------------------------------- */
/*      Write scaling.                                                  */
/* -------------------------------------------------------------------- */
    int nScaleCount;
    const double *padfScale = 
        poFeature->GetFieldAsDoubleList( "BlockScale", &nScaleCount );

    if( nScaleCount == 3 )
    {
        WriteValue( 41, padfScale[0] );
        WriteValue( 42, padfScale[1] );
        WriteValue( 43, padfScale[2] );
    }

/* -------------------------------------------------------------------- */
/*      Write rotation.                                                 */
/* -------------------------------------------------------------------- */
    double dfAngle = poFeature->GetFieldAsDouble( "BlockAngle" );

    if( dfAngle != 0.0 )
    {
        WriteValue( 50, dfAngle ); // degrees
    }

    return OGRERR_NONE;
}
OGRErr OGRDXFWriterLayer::WriteHATCH( OGRFeature *poFeature,
                                      OGRGeometry *poGeom )

{
/* -------------------------------------------------------------------- */
/*      For now we handle multipolygons by writing a series of          */
/*      entities.                                                       */
/* -------------------------------------------------------------------- */
    if( poGeom == NULL )
        poGeom = poFeature->GetGeometryRef();

    if ( poGeom->IsEmpty() )
    {
        return OGRERR_NONE;
    }
            
    if( wkbFlatten(poGeom->getGeometryType()) == wkbMultiPolygon )
    {
        OGRGeometryCollection *poGC = (OGRGeometryCollection *) poGeom;
        int iGeom;
        OGRErr eErr = OGRERR_NONE;

        for( iGeom = 0; 
             eErr == OGRERR_NONE && iGeom < poGC->getNumGeometries(); 
             iGeom++ )
        {
            eErr = WriteHATCH( poFeature, poGC->getGeometryRef( iGeom ) );
        }

        return eErr;
    }

/* -------------------------------------------------------------------- */
/*      Do we now have a geometry we can work with?                     */
/* -------------------------------------------------------------------- */
    if( wkbFlatten(poGeom->getGeometryType()) != wkbPolygon )
        return OGRERR_UNSUPPORTED_GEOMETRY_TYPE;

/* -------------------------------------------------------------------- */
/*      Write as a hatch.                                               */
/* -------------------------------------------------------------------- */
    WriteValue( 0, "HATCH" );
    WriteCore( poFeature );
    WriteValue( 100, "AcDbEntity" );
    WriteValue( 100, "AcDbHatch" );
    WriteValue( 2, "SOLID" ); // fill pattern
    WriteValue( 70, 1 ); // solid fill
    WriteValue( 71, 0 ); // associativity 

/* -------------------------------------------------------------------- */
/*      Do we have styling information?                                 */
/* -------------------------------------------------------------------- */
    OGRStyleTool *poTool = NULL;
    OGRStyleMgr oSM;

    if( poFeature->GetStyleString() != NULL )
    {
        oSM.InitFromFeature( poFeature );

        if( oSM.GetPartCount() > 0 )
            poTool = oSM.GetPart(0);
    }

/* -------------------------------------------------------------------- */
/*      Handle a PEN tool to control drawing color and width.           */
/*      Perhaps one day also dottedness, etc.                           */
/* -------------------------------------------------------------------- */
#ifdef notdef
    if( poTool && poTool->GetType() == OGRSTCPen )
    {
        OGRStylePen *poPen = (OGRStylePen *) poTool;
        GBool  bDefault;

        if( poPen->Color(bDefault) != NULL && !bDefault )
            WriteValue( 62, ColorStringToDXFColor( poPen->Color(bDefault) ) );
        
        double dfWidthInMM = poPen->Width(bDefault);

        if( !bDefault )
            WriteValue( 370, (int) floor(dfWidthInMM * 100 + 0.5) );
    }

/* -------------------------------------------------------------------- */
/*      Do we have a Linetype for the feature?                          */
/* -------------------------------------------------------------------- */
    CPLString osLineType = poFeature->GetFieldAsString( "Linetype" );

    if( osLineType.size() > 0 
        && (poDS->oHeaderDS.LookupLineType( osLineType ) != NULL 
            || oNewLineTypes.count(osLineType) > 0 ) )
    {
        // Already define -> just reference it.
        WriteValue( 6, osLineType );
    }
    else if( poTool != NULL && poTool->GetType() == OGRSTCPen )
    {
        CPLString osDefinition = PrepareLineTypeDefinition( poFeature, 
                                                            poTool );

        if( osDefinition != "" && osLineType == "" )
        {
            // Is this definition already created and named?
            std::map<CPLString,CPLString>::iterator it;

            for( it = oNewLineTypes.begin();
                 it != oNewLineTypes.end();
                 it++ )
            {
                if( (*it).second == osDefinition )
                {
                    osLineType = (*it).first;
                    break;
                }
            }

            // create an automatic name for it.
            if( osLineType == "" )
            {
                do 
                { 
                    osLineType.Printf( "AutoLineType-%d", nNextAutoID++ );
                }
                while( poDS->oHeaderDS.LookupLineType(osLineType) != NULL );
            }
        }

        // If it isn't already defined, add it now.
        if( osDefinition != "" && oNewLineTypes.count(osLineType) == 0 )
        {
            oNewLineTypes[osLineType] = osDefinition;
            WriteValue( 6, osLineType );
        }
    }
    delete poTool;
#endif

/* -------------------------------------------------------------------- */
/*      Process the loops (rings).                                      */
/* -------------------------------------------------------------------- */
    OGRPolygon *poPoly = (OGRPolygon *) poGeom;

    WriteValue( 91, poPoly->getNumInteriorRings() + 1 );

    for( int iRing = -1; iRing < poPoly->getNumInteriorRings(); iRing++ )
    {
        OGRLinearRing *poLR;

        if( iRing == -1 )
            poLR = poPoly->getExteriorRing();
        else
            poLR = poPoly->getInteriorRing( iRing );

        WriteValue( 92, 2 ); // Polyline
        WriteValue( 72, 0 ); // has bulge
        WriteValue( 73, 1 ); // is closed
        WriteValue( 93, poLR->getNumPoints() );
        
        for( int iVert = 0; iVert < poLR->getNumPoints(); iVert++ )
        {
            WriteValue( 10, poLR->getX(iVert) );
            WriteValue( 20, poLR->getY(iVert) );
        }
    }
    
    return OGRERR_NONE;

#ifdef notdef
/* -------------------------------------------------------------------- */
/*      Alternate unmaintained implementation as a polyline entity.     */
/* -------------------------------------------------------------------- */
    WriteValue( 0, "POLYLINE" );
    WriteCore( poFeature );
    WriteValue( 100, "AcDbEntity" );
    WriteValue( 100, "AcDbPolyline" );
    if( EQUAL( poGeom->getGeometryName(), "LINEARRING" ) )
        WriteValue( 70, 1 );
    else
        WriteValue( 70, 0 );
    WriteValue( 66, "1" );

    int iVert;

    for( iVert = 0; iVert < poLS->getNumPoints(); iVert++ )
    {
        WriteValue( 0, "VERTEX" );
        WriteValue( 8, "0" );
        WriteValue( 10, poLS->getX(iVert) );
        if( !WriteValue( 20, poLS->getY(iVert) ) ) 
            return OGRERR_FAILURE;

        if( poLS->getGeometryType() == wkbLineString25D )
        {
            if( !WriteValue( 30, poLS->getZ(iVert) ) )
                return OGRERR_FAILURE;
        }
    }

    WriteValue( 0, "SEQEND" );
    WriteValue( 8, "0" );
    
    return OGRERR_NONE;
#endif
}
Beispiel #15
0
OGRErr OGRKMLLayer::ICreateFeature( OGRFeature* poFeature )
{
    CPLAssert( NULL != poFeature );
    CPLAssert( NULL != poDS_ );

    if( !bWriter_ )
        return OGRERR_FAILURE;

    if( bClosedForWriting )
    {
        CPLError(CE_Failure, CPLE_NotSupported,
                 "Interleaved feature adding to different layers is not supported");
        return OGRERR_FAILURE;
    }

    VSILFILE *fp = poDS_->GetOutputFP();
    CPLAssert( NULL != fp );

    if( poDS_->GetLayerCount() == 1 && nWroteFeatureCount_ == 0 )
    {
        CPLString osRet = WriteSchema();
        if( osRet.size() )
            VSIFPrintfL( fp, "%s", osRet.c_str() );
        bSchemaWritten_ = TRUE;

        VSIFPrintfL( fp, "<Folder><name>%s</name>\n", pszName_);
    }

    VSIFPrintfL( fp, "  <Placemark>\n" );

    if( poFeature->GetFID() == OGRNullFID )
        poFeature->SetFID( iNextKMLId_++ );

    // Find and write the name element
    if (NULL != poDS_->GetNameField())
    {
        for( int iField = 0; iField < poFeatureDefn_->GetFieldCount(); iField++ )
        {
            OGRFieldDefn *poField = poFeatureDefn_->GetFieldDefn( iField );

            if( poFeature->IsFieldSet( iField )
                && EQUAL(poField->GetNameRef(), poDS_->GetNameField()) )
            {
                const char *pszRaw = poFeature->GetFieldAsString( iField );
                while( *pszRaw == ' ' )
                    pszRaw++;

                char *pszEscaped = OGRGetXML_UTF8_EscapedString( pszRaw );

                VSIFPrintfL( fp, "\t<name>%s</name>\n", pszEscaped);
                CPLFree( pszEscaped );
            }
        }
    }

    if (NULL != poDS_->GetDescriptionField())
    {
        for( int iField = 0; iField < poFeatureDefn_->GetFieldCount(); iField++ )
        {
            OGRFieldDefn *poField = poFeatureDefn_->GetFieldDefn( iField );

            if( poFeature->IsFieldSet( iField )
                && EQUAL(poField->GetNameRef(), poDS_->GetDescriptionField()) )
            {
                const char *pszRaw = poFeature->GetFieldAsString( iField );
                while( *pszRaw == ' ' )
                    pszRaw++;

                char *pszEscaped = OGRGetXML_UTF8_EscapedString( pszRaw );

                VSIFPrintfL( fp, "\t<description>%s</description>\n", pszEscaped);
                CPLFree( pszEscaped );
            }
        }
    }

    OGRwkbGeometryType eGeomType = wkbNone;
    if (poFeature->GetGeometryRef() != NULL)
        eGeomType = wkbFlatten(poFeature->GetGeometryRef()->getGeometryType());
    if ( wkbPolygon == eGeomType
         || wkbMultiPolygon == eGeomType
         || wkbLineString == eGeomType
         || wkbMultiLineString == eGeomType )
    {
        OGRStylePen *poPen = NULL;
        OGRStyleMgr oSM;

        if( poFeature->GetStyleString() != NULL )
        {
            oSM.InitFromFeature( poFeature );

            int i;
            for(i=0; i<oSM.GetPartCount();i++)
            {
                OGRStyleTool *poTool = oSM.GetPart(i);
                if (poTool && poTool->GetType() == OGRSTCPen )
                {
                    poPen = (OGRStylePen*) poTool;
                    break;
                }
                delete poTool;
            }
        }

        VSIFPrintfL( fp, "\t<Style>");
        if( poPen != NULL )
        {
            GBool  bDefault;
            int    bHasWidth = FALSE;

            /* Require width to be returned in pixel */
            poPen->SetUnit(OGRSTUPixel);
            double fW = poPen->Width(bDefault);
            if( bDefault )
                fW = 1;
            else
                bHasWidth = TRUE;
            const char* pszColor = poPen->Color(bDefault);
            int nColorLen = static_cast<int>(CPLStrnlen(pszColor, 10));
            if( pszColor != NULL && pszColor[0] == '#' && !bDefault && nColorLen >= 7)
            {
                char acColor[9] = {0};
                /* Order of KML color is aabbggrr, whereas OGR color is #rrggbb[aa] ! */
                if(nColorLen == 9)
                {
                    acColor[0] = pszColor[7]; /* A */
                    acColor[1] = pszColor[8];
                }
                else
                {
                    acColor[0] = 'F';
                    acColor[1] = 'F';
                }
                acColor[2] = pszColor[5]; /* B */
                acColor[3] = pszColor[6];
                acColor[4] = pszColor[3]; /* G */
                acColor[5] = pszColor[4];
                acColor[6] = pszColor[1]; /* R */
                acColor[7] = pszColor[2];
                VSIFPrintfL( fp, "<LineStyle><color>%s</color>", acColor);
                if (bHasWidth)
                    VSIFPrintfL( fp, "<width>%g</width>", fW);
                VSIFPrintfL( fp, "</LineStyle>");
            }
            else
                VSIFPrintfL( fp, "<LineStyle><color>ff0000ff</color></LineStyle>");
        }
        else
            VSIFPrintfL( fp, "<LineStyle><color>ff0000ff</color></LineStyle>");
        delete poPen;
        //If we're dealing with a polygon, add a line style that will stand out a bit
        VSIFPrintfL( fp, "<PolyStyle><fill>0</fill></PolyStyle></Style>\n" );
    }

    int bHasFoundOtherField = FALSE;

    // Write all fields as SchemaData
    for( int iField = 0; iField < poFeatureDefn_->GetFieldCount(); iField++ )
    {
        OGRFieldDefn *poField = poFeatureDefn_->GetFieldDefn( iField );

        if( poFeature->IsFieldSet( iField ))
        {
            if (NULL != poDS_->GetNameField() &&
                EQUAL(poField->GetNameRef(), poDS_->GetNameField()) )
                continue;

            if (NULL != poDS_->GetDescriptionField() &&
                EQUAL(poField->GetNameRef(), poDS_->GetDescriptionField()) )
                continue;

            if (!bHasFoundOtherField)
            {
                VSIFPrintfL( fp, "\t<ExtendedData><SchemaData schemaUrl=\"#%s\">\n", pszName_ );
                bHasFoundOtherField = TRUE;
            }
            const char *pszRaw = poFeature->GetFieldAsString( iField );

            while( *pszRaw == ' ' )
                pszRaw++;

            char *pszEscaped;
            if (poFeatureDefn_->GetFieldDefn(iField)->GetType() == OFTReal)
            {
                pszEscaped = CPLStrdup( pszRaw );
            }
            else
            {
                pszEscaped = OGRGetXML_UTF8_EscapedString( pszRaw );
            }

            VSIFPrintfL( fp, "\t\t<SimpleData name=\"%s\">%s</SimpleData>\n",
                        poField->GetNameRef(), pszEscaped);

            CPLFree( pszEscaped );
        }
    }

    if (bHasFoundOtherField)
    {
        VSIFPrintfL( fp, "\t</SchemaData></ExtendedData>\n" );
    }

    // Write out Geometry - for now it isn't indented properly.
    if( poFeature->GetGeometryRef() != NULL )
    {
        char* pszGeometry = NULL;
        OGREnvelope sGeomBounds;
        OGRGeometry* poWGS84Geom;

        if (NULL != poCT_)
        {
            poWGS84Geom = poFeature->GetGeometryRef()->clone();
            poWGS84Geom->transform( poCT_ );
        }
        else
        {
            poWGS84Geom = poFeature->GetGeometryRef();
        }

        // TODO - porting
        // pszGeometry = poFeature->GetGeometryRef()->exportToKML();
        pszGeometry =
            OGR_G_ExportToKML( (OGRGeometryH)poWGS84Geom,
                               poDS_->GetAltitudeMode());

        VSIFPrintfL( fp, "      %s\n", pszGeometry );
        CPLFree( pszGeometry );

        poWGS84Geom->getEnvelope( &sGeomBounds );
        poDS_->GrowExtents( &sGeomBounds );

        if (NULL != poCT_)
        {
            delete poWGS84Geom;
        }
    }

    VSIFPrintfL( fp, "  </Placemark>\n" );
    nWroteFeatureCount_++;
    return OGRERR_NONE;
}