osgEarth 2.1.1

/home/cube/sources/osgearth/src/osgEarthDrivers/kml/KML_Geometry.cpp

Go to the documentation of this file.
00001 /* -*-c++-*- */
00002 /* osgEarth - Dynamic map generation toolkit for OpenSceneGraph
00003  * Copyright 2008-2010 Pelican Mapping
00004  * http://osgearth.org
00005  *
00006  * osgEarth is free software; you can redistribute it and/or modify
00007  * it under the terms of the GNU Lesser General Public License as published by
00008  * the Free Software Foundation; either version 2 of the License, or
00009  * (at your option) any later version.
00010  *
00011  * This program is distributed in the hope that it will be useful,
00012  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00013  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00014  * GNU Lesser General Public License for more details.
00015  *
00016  * You should have received a copy of the GNU Lesser General Public License
00017  * along with this program.  If not, see <http://www.gnu.org/licenses/>
00018  */
00019 #include "KML_Geometry"
00020 #include "KML_Point"
00021 #include "KML_LineString"
00022 #include "KML_LinearRing"
00023 #include "KML_Polygon"
00024 #include "KML_MultiGeometry"
00025 #include "KML_Model"
00026 #include <osgEarth/StringUtils>
00027 
00028 void 
00029 KML_Geometry::build( const Config& parentConf, KMLContext& cx, Style& style)
00030 {
00031     const ConfigSet& children = parentConf.children();
00032     for( ConfigSet::const_iterator i = children.begin(); i != children.end(); ++i )
00033     {
00034         buildChild( *i, cx, style );
00035     }
00036 }
00037 
00038 void
00039 KML_Geometry::buildChild( const Config& conf, KMLContext& cx, Style& style)
00040 {
00041     if ( conf.key() == "point" )
00042     {
00043         KML_Point g;
00044         g.parseStyle(conf, cx, style);
00045         g.parseCoords(conf, cx);
00046         _geom = g._geom.get();
00047     }
00048     else if ( conf.key() == "linestring" )
00049     {
00050         KML_LineString g;
00051         g.parseStyle(conf, cx, style);
00052         g.parseCoords(conf, cx);
00053         _geom = g._geom.get();
00054     }
00055     else if ( conf.key() == "linearring" )
00056     {
00057         KML_LinearRing g;
00058         g.parseStyle(conf, cx, style);
00059         g.parseCoords(conf, cx);
00060         _geom = g._geom.get();
00061     }
00062     else if ( conf.key() == "polygon" || conf.key() == "gx:latlonquad" )
00063     {
00064         KML_Polygon g;
00065         g.parseStyle(conf, cx, style);
00066         g.parseCoords(conf, cx);
00067         _geom = g._geom.get();
00068     }
00069     else if ( conf.key() == "multigeometry" )
00070     {
00071         KML_MultiGeometry g;
00072         g.parseStyle(conf, cx, style);
00073         g.parseCoords(conf, cx);
00074         const ConfigSet& mgChildren = conf.children();
00075         
00076         for( ConfigSet::const_iterator i = mgChildren.begin(); i != mgChildren.end(); ++i )
00077         {
00078             const Config& mgChild = *i;
00079             Style subStyle = style;
00080             KML_Geometry subGeom;
00081             subGeom.parseStyle( mgChild, cx, subStyle );
00082             subGeom.buildChild( mgChild, cx, style );
00083             if ( subGeom._geom.valid() )
00084                 dynamic_cast<MultiGeometry*>(g._geom.get())->getComponents().push_back( subGeom._geom.get() );
00085         }
00086         //g.parseCoords(conf.child("multigeometry"), cx);
00087         _geom = g._geom.get();
00088     }
00089     else if ( conf.key() == "model" )
00090     {
00091         KML_Model g;
00092         g.parseStyle(conf, cx, style);
00093         g.parseCoords(conf, cx);
00094         _geom = g._geom.get();
00095     }
00096 }
00097 
00098 void
00099 KML_Geometry::parseCoords( const Config& conf, KMLContext& cx )
00100 {
00101     const Config& coords = conf.child("coordinates");
00102     StringVector tuples;
00103     StringTokenizer( coords.value(), tuples, " ", "", false, true );
00104     for( StringVector::const_iterator s=tuples.begin(); s != tuples.end(); ++s )
00105     {
00106         StringVector parts;
00107         StringTokenizer( *s, parts, ",", "", false, true );
00108         if ( parts.size() >= 2 )
00109         {
00110             osg::Vec3d point;
00111             point.x() = as<double>( parts[0], 0.0 );
00112             point.y() = as<double>( parts[1], 0.0 );
00113             if ( parts.size() >= 3 ) {
00114                 point.z() = as<double>( parts[2], 0.0 );
00115             }
00116             _geom->push_back(point);
00117         }
00118     }
00119 }
00120 
00121 void
00122 KML_Geometry::parseStyle( const Config& conf, KMLContext& cx, Style& style )
00123 {
00124     _extrude = conf.value("extrude") == "1";
00125     _tessellate = conf.value("tessellate") == "1";
00126 
00127     std::string am = conf.value("altitudemode");
00128 
00129     // clampToGround is the default. We will be draping the geometry UNLESS tessellate is
00130     // set to true.
00131     if ( (am.empty() || am == "clampToGround") && _tessellate )
00132     {
00133         AltitudeSymbol* af = style.getOrCreate<AltitudeSymbol>();
00134         af->clamping() = AltitudeSymbol::CLAMP_TO_TERRAIN;
00135         _extrude = false;
00136     }
00137 
00138     // "relativeToGround" means the coordinates' Z values are relative to the Z of the
00139     // terrain at that point. NOTE: GE flattens rooftops in this mode when extrude=1,
00140     // which seems wrong..
00141     else if ( am == "relativeToGround" )
00142     {
00143         AltitudeSymbol* af = style.getOrCreate<AltitudeSymbol>();
00144         af->clamping() = AltitudeSymbol::CLAMP_RELATIVE_TO_TERRAIN;
00145     }
00146 
00147     // "absolute" means to treat the Z values as-is
00148     else if ( am == "absolute" )
00149     {
00150         AltitudeSymbol* af = style.getOrCreate<AltitudeSymbol>();
00151         af->clamping() = AltitudeSymbol::CLAMP_ABSOLUTE;
00152     }
00153 
00154     if ( _extrude )
00155     {
00156         ExtrusionSymbol* es = style.getOrCreate<ExtrusionSymbol>();
00157         es->flatten() = false;
00158     }
00159 }
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines