win10 + cmake3.17 + vs2017编译osgearth2.7.0

2023-12-15 05:04:07

1. 下载文件并配置安装目录

1.1 下载文件

  • 1)osgearth-2.7.0
  • 2)? curl-7.48.0
  • 3)? osg-3.4.1
  • 4)? osg第三方依赖库:3rdParty_VS2017_v141_x64_V11_full.7z
  • 5)osg示例数据:OpenSceneGraph-Data-3.4.0.zip
  • 6)cmake-3.17
  • 7)FindZLIB.cmake
  • 8)FeatureSourceIndexNode.cpp

我已经打包好,大家可自行下载。

百度云下载地址

csdn下载地址

????????https://download.csdn.net/download/Strive_For_Future/88631235

1.2 配置安装目录

创建三个文件夹:

  • build--------用于存放编译osgEarth的过程文件。
  • osgEarth-2.7.0-------用于存放osgEarth的源码
  • osgEarth-2.7.0-x64-vs2017--------用于存放osgEarth的install结果。

如下:?

2. 准备osgEarth的第三方依赖库

2.1 编译curl-7.48.0

比较简单,相关教程见:win10 + vs2017 + cmake3.17 编译 curl-7.48-CSDN博客

2.2 编译osg-3.4.1

有点复杂,具体细节教程见:win10 + vs2017 + cmake3.17编译OSG-3.4.1-CSDN博客

编译完成之后记得把bin目录、osg第三方依赖库添加到环境变量?

3. 修改osgearth2.7.0中存在的两个问题

这两个问题参考:win10 + cmake3.17 + vs2017编译osgearth2.7.0遇到的坑-CSDN博客

3.1)修改src/osgEarthFeatures/FeatureSourceIndexNode.cpp,解决:无法从“std::pair<const _Kty,_Ty>”转换为 to _Objty

debug模式下生成osgEarthAnnotation时,会出现以下错误,

需要对src/osgEarthFeatures/FeatureSourceIndexNode.cpp进行以下修改:

修改后的代码如下,大家可以直接复制替换:

src/osgEarthFeatures/FeatureSourceIndexNode.cpp

/* -*-c++-*- */
/* osgEarth - Dynamic map generation toolkit for OpenSceneGraph
 * Copyright 2015 Pelican Mapping
 * http://osgearth.org
 *
 * osgEarth is free software; you can redistribute it and/or modify
 * it under the terms of the GNU Lesser General Public License as published by
 * the Free Software Foundation; either version 2 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public License
 * along with this program.  If not, see <http://www.gnu.org/licenses/>
 */
#include <osgEarthFeatures/FeatureSourceIndexNode>
#include <osgEarth/Registry>
#include <algorithm>

using namespace osgEarth;
using namespace osgEarth::Features;

// for testing:
//#undef  OE_DEBUG
//#define OE_DEBUG OE_INFO

namespace
{
    // nifty template to iterate over a map's keys
    template<typename T>
    //struct KeyIter : public T::iterator
    struct KeyIter : public std::iterator<std::input_iterator_tag,typename T::value_type>
    {
        typename T::const_iterator it;
        KeyIter(typename T::const_iterator i) : it(i) {}    
        KeyIter &operator++() {++it; return *this;}
        KeyIter operator++(int) {KeyIter t = *this; ++*this; return t;}

        typename T::key_type const *operator->() const {return &(it->first);}
        typename T::key_type const &operator*() const {return it->first;}
        friend bool operator==(KeyIter const &a, KeyIter const &b) {return a.it == b.it;}
        friend bool operator!=(KeyIter const &a, KeyIter const &b) {return a.it != b.it;}
    };
}

//-----------------------------------------------------------------------------


FeatureSourceIndexOptions::FeatureSourceIndexOptions(const Config& conf) :
_enabled      ( true ),
_embedFeatures( false )
{
    conf.getIfSet( "enabled",        _enabled );
    conf.getIfSet( "embed_features", _embedFeatures );
}

Config
FeatureSourceIndexOptions::getConfig() const
{
    Config conf("feature_indexing");
    conf.addIfSet( "enabled",        _enabled );
    conf.addIfSet( "embed_features", _embedFeatures );
    return conf;
}

//-----------------------------------------------------------------------------

#undef  LC
#define LC "[FeatureSourceIndexNode] "

FeatureSourceIndexNode::FeatureSourceIndexNode(FeatureSourceIndex* index) :
_index( index )
{
    if ( !index )
    {
        OE_WARN << LC << "INTERNAL ERROR: created a feature source index node with a NULL index.\n";
    }
}

FeatureSourceIndexNode::~FeatureSourceIndexNode()
{
    if ( _index.valid() )
    {
        // must copy and clear the original list first to dereference the RefIDPair instances.
        std::set<FeatureID> fidsToRemove;
        //fidsToRemove.insert( KeyIter<FIDMap>(_fids.begin()), KeyIter<FIDMap>(_fids.end()) );
        fidsToRemove.insert(KeyIter<FIDMap>(_fids.begin()), KeyIter<FIDMap>(_fids.end()));
        _fids.clear();

        OE_DEBUG << LC << "Removing " << fidsToRemove.size() << " fids\n";
        _index->removeFIDs( fidsToRemove.begin(), fidsToRemove.end() );
    }
}

ObjectID
FeatureSourceIndexNode::tagDrawable(osg::Drawable* drawable, Feature* feature)
{
    if ( !feature || !_index.valid() ) return OSGEARTH_OBJECTID_EMPTY;
    RefIDPair* r = _index->tagDrawable( drawable, feature );
    if ( r ) _fids[ feature->getFID() ] = r;
    return r ? r->_oid : OSGEARTH_OBJECTID_EMPTY;
}

ObjectID
FeatureSourceIndexNode::tagAllDrawables(osg::Node* node, Feature* feature)
{
    if ( !feature || !_index.valid() ) return OSGEARTH_OBJECTID_EMPTY;
    RefIDPair* r = _index->tagAllDrawables( node, feature );
    if ( r ) _fids[ feature->getFID() ] = r;
    return r ? r->_oid : OSGEARTH_OBJECTID_EMPTY;
}

ObjectID
FeatureSourceIndexNode::tagNode(osg::Node* node, Feature* feature)
{
    if ( !feature || !_index.valid() ) return OSGEARTH_OBJECTID_EMPTY;
    RefIDPair* r = _index->tagNode( node, feature );
    if ( r ) _fids[ feature->getFID() ] = r;
    return r ? r->_oid : OSGEARTH_OBJECTID_EMPTY;
}

bool
FeatureSourceIndexNode::getAllFIDs(std::vector<FeatureID>& output) const
{
    KeyIter<FIDMap> start( _fids.begin() );
    KeyIter<FIDMap> end  ( _fids.end() );
    for(KeyIter<FIDMap> i = start; i != end; ++i )
    {
        output.push_back( *i );
    }

    return true;
}

//-----------------------------------------------------------------------------

#undef  LC
#define LC "[FeatureSourceIndex] "

FeatureSourceIndex::FeatureSourceIndex(FeatureSource* featureSource, 
                                       ObjectIndex*   index,
                                       const FeatureSourceIndexOptions& options) :
_featureSource  ( featureSource ), 
_masterIndex    ( index ),
_options        ( options )
{
    _embed = 
        _options.embedFeatures() == true ||
        featureSource == 0L ||
        featureSource->supportsGetFeature() == false;
}

FeatureSourceIndex::~FeatureSourceIndex()
{
    if ( _masterIndex.valid() && !_oids.empty() )
    {
        // remove all OIDs from the master index.
        _masterIndex->remove( KeyIter<OIDMap>(_oids.begin()), KeyIter<OIDMap>(_oids.end()) );
    }

    _oids.clear();
    _fids.clear();
    _embeddedFeatures.clear();
}

RefIDPair*
FeatureSourceIndex::tagDrawable(osg::Drawable* drawable, Feature* feature)
{
    if ( !feature ) return 0L;

    Threading::ScopedMutexLock lock(_mutex);
    
    RefIDPair* p = 0L;
    FeatureID fid = feature->getFID();

    FIDMap::const_iterator f = _fids.find( fid );
    if ( f != _fids.end() )
    {
        ObjectID oid = f->second->_oid;
        _masterIndex->tagDrawable( drawable, oid );
        p = f->second.get();
    }
    else
    {
        ObjectID oid = _masterIndex->tagDrawable( drawable, this );
        p = new RefIDPair( fid, oid );
        _fids[fid] = p;
        _oids[oid] = fid;
    
        if ( _embed )
        {
            _embeddedFeatures[fid] = feature;
        }
    }

    return p;
}

RefIDPair*
FeatureSourceIndex::tagAllDrawables(osg::Node* node, Feature* feature)
{
    if ( !feature ) return 0L;

    Threading::ScopedMutexLock lock(_mutex);
    
    RefIDPair* p = 0L;
    FeatureID fid = feature->getFID();

    FIDMap::const_iterator f = _fids.find( fid );
    if ( f != _fids.end() )
    {
        ObjectID oid = f->second->_oid;
        _masterIndex->tagAllDrawables( node, oid );
        p = f->second.get();
    }
    else
    {
        ObjectID oid = _masterIndex->tagAllDrawables( node, this );
        p = new RefIDPair( fid, oid );
        _fids[fid] = p;
        _oids[oid] = fid;
    
        if ( _embed )
        {
            _embeddedFeatures[fid] = feature;
        }
    }

    return p;
}

RefIDPair*
FeatureSourceIndex::tagNode(osg::Node* node, Feature* feature)
{
    if ( !feature ) return 0L;

    Threading::ScopedMutexLock lock(_mutex);
    
    RefIDPair* p = 0L;
    FeatureID fid = feature->getFID();
    ObjectID oid;

    FIDMap::const_iterator f = _fids.find( fid );
    if ( f != _fids.end() )
    {
        oid = f->second->_oid;
        _masterIndex->tagNode( node, oid );
        p = f->second.get();
    }
    else
    {
        oid = _masterIndex->tagNode( node, this );
        p = new RefIDPair( fid, oid );
        _fids[fid] = p;
        _oids[oid] = fid;
    
        if ( _embed )
        {
            _embeddedFeatures[fid] = feature;
        }
    }

    OE_DEBUG << LC << "Tagging feature ID = " << fid << " => " << oid << " (" << feature->getString("name") << ")\n";

    return p;
}

Feature*
FeatureSourceIndex::getFeature(ObjectID oid) const
{
    Feature* feature = 0L;
    Threading::ScopedMutexLock lock(_mutex);
    OIDMap::const_iterator i = _oids.find( oid );
    if ( i != _oids.end() )
    {
        FeatureID fid = i->second;

        if ( _embed )
        {
            FeatureMap::const_iterator j = _embeddedFeatures.find( fid );
            feature = j != _embeddedFeatures.end() ? j->second.get() : 0L;
        }
        else if ( _featureSource.valid() && _featureSource->supportsGetFeature() )
        {
            feature = _featureSource->getFeature( fid );
        }
    }
    return feature;
}

3.2 拷贝并修改FindZLIB.cmake,解决无法打开输入文件“optimized.lib”

在编译osgearth-2.7.0时,会遇到以下问题

LINK : fatal error LNK1181: 无法打开输入文件“optimized.lib”

问题原因:CMake (3+) comes with a built-in FindZLIB.cmake library for locating the ZLib dependency. But it is introducing this problem. So I copied the old FindZLIB.cmake from the OSG distribution into osgEarth/CMakeModules, and the problem disappeared. (CMake3+使用其自己内置的"FindZLIB.cmake"库去寻找ZLib依赖。但是,这引起了当下这个问题。所以,我从OSG库中拷贝了"FindZLIB.cmake"放在了“/osgEarth/CMakeModules”目录下,这个问题就解决了。)

解决方案:从"OSG-3.4.1\CMakeModules"目录下拷贝一份FindZLIB.cmake放到"osgEarth2.7.0\CMakeModules"目录下,然后用notepad++打开该FindZLIB.cmake文件,定位到第13行或附近,找到下图代码,注释掉。

或者,直接拷贝创建FindZLIB.cmake并放到"osgEarth2.7.0\CMakeModules"目录下

文件:FindZLIB.cmake

# Locate zlib
# This module defines
# ZLIB_LIBRARY
# ZLIB_FOUND, if false, do not try to link to zlib 
# ZLIB_INCLUDE_DIR, where to find the headers
#
# $ZLIB_DIR is an environment variable that would
# correspond to the ./configure --prefix=$ZLIB_DIR
# used in building zlib.
#
# Created by Ulrich Hertlein. 

# prefer FindZLIB from cmake distribution
#if(EXISTS ${CMAKE_ROOT}/Modules/FindZLIB.cmake)
#  include(${CMAKE_ROOT}/Modules/FindZLIB.cmake)
#
#  if(ZLIB_FOUND)
#    return()
#  endif()
#endif()


FIND_PATH(ZLIB_INCLUDE_DIR zlib.h
    $ENV{ZLIB_DIR}/include
    $ENV{ZLIB_DIR}
    ~/Library/Frameworks
    /Library/Frameworks
    /usr/local/include
    /usr/include
    /sw/include # Fink
    /opt/local/include # DarwinPorts
    /opt/csw/include # Blastwave
    /opt/include
    /usr/freeware/include
)

FIND_LIBRARY(ZLIB_LIBRARY 
    NAMES z libz zlib
    PATHS
    $ENV{ZLIB_DIR}/lib
    $ENV{ZLIB_DIR}
    ~/Library/Frameworks
    /Library/Frameworks
    /usr/local/lib
    /usr/lib
    /sw/lib
    /opt/local/lib
    /opt/csw/lib
    /opt/lib
    /usr/freeware/lib64
)

SET(ZLIB_FOUND "NO")
IF(ZLIB_LIBRARY AND ZLIB_INCLUDE_DIR)
    SET(ZLIB_FOUND "YES")
ENDIF(ZLIB_LIBRARY AND ZLIB_INCLUDE_DIR)


4. 配置cmake

打开cmake-gui,将osgEarth-3.4.1中的CMakeLists.txt文件直接拖放到CMake界面

4.1 修改build路径

将“Where to build the binaries”设置为上面设置的build文件夹路径

4.2 修改 THIRD_PARTY_DIR

把THIRD_PARTY_DIR设置为osg第三方依赖库。该依赖库在编译osg-3.4.1的过程中,已经被添加到系统的环境变量中了。cmake在找依赖库时,会优先从这个路径里面找。所以,这里把THIRD_PARTY_DIR设置为编译osg时的第三方依赖库。

4.3 配置CURL依赖

curl在2.2节中被编译好了,这里直接使用。

4.4 cmake应该会自动从THIRD_PARTY_DIR寻找其他依赖并配置

5. cmake编译

依次执行Configure(直至所有cmake配置项变成白色)-->Generate-->Open Project,用VS2017打开项目。

6. VS2017编译

先生成ALL_BUILD,然后生成INSTALL

7. 安装成功测试

7.1 测试数据准备

将“osgearth-2.10\data”以及“osgearth-2.10\tests”中的文件复制到osg示例数据的目录中,我的是:F:\3rd_party\osg\Data

7.2 将OsgEarth\bin”添加到系统环境变量Path中

7.3?在命令行窗口输入“osgearth_viewer gdal_multiple_files.earth”

如显示出地球,则说明osgEarth正常运行。

文章来源:https://blog.csdn.net/Strive_For_Future/article/details/135005984
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。