14 changes: 14 additions & 0 deletions src/app/qgisapp.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -8810,6 +8810,16 @@ void QgisApp::openURL( QString url, bool useQgisDocDirectory )
#endif
}

void QgisApp::registerMapLayerPropertiesFactory( QgsMapLayerPropertiesFactory* factory )
{
mMapLayerPropertiesFactories << factory;

This comment has been minimized.

Copy link
@nyalldawson

nyalldawson May 30, 2016

Collaborator

@manisandro should ownership of factory be transferred here? If so, this is leaky. If not, it would be nice to clarify this in the docs.

This comment has been minimized.

Copy link
@manisandro

manisandro May 30, 2016

Author Member

@nyalldawson I suppose it could transfer ownership, though for proper cleanup plugins should remove the factory themselves when unloading. First would be safer, second would enforce good practice by plugin authors. I'd go with the docstring.

This comment has been minimized.

Copy link
@nyalldawson

nyalldawson May 30, 2016

Collaborator

@manisandro I think the current approach is better (no ownership transfer). But the docs should mention that plugins must unregister their factories or crashes will occur.

}

void QgisApp::unregisterMapLayerPropertiesFactory( QgsMapLayerPropertiesFactory* factory )
{
mMapLayerPropertiesFactories.removeAll( factory );
}

/** Get a pointer to the currently selected map layer */
QgsMapLayer *QgisApp::activeLayer()
{
Expand Down Expand Up @@ -11021,6 +11031,10 @@ void QgisApp::showLayerProperties( QgsMapLayer *ml )
#else
QgsVectorLayerProperties *vlp = new QgsVectorLayerProperties( vlayer, this );
#endif
foreach ( QgsMapLayerPropertiesFactory* factory, mMapLayerPropertiesFactories )
{
vlp->addPropertiesPageFactory( factory );
}

if ( vlp->exec() )
{
Expand Down
9 changes: 9 additions & 0 deletions src/app/qgisapp.h
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,7 @@ class QgsLayerTreeMapCanvasBridge;
class QgsLayerTreeView;
class QgsMapCanvas;
class QgsMapLayer;
class QgsMapLayerPropertiesFactory;
class QgsMapTip;
class QgsMapTool;
class QgsMapToolAdvancedDigitizing;
Expand Down Expand Up @@ -501,6 +502,12 @@ class APP_EXPORT QgisApp : public QMainWindow, private Ui::MainWindow

void parseVersionInfo( QNetworkReply* reply, int& latestVersion, QStringList& versionInfo );

/** Register a new tab in the layer properties dialog */
void registerMapLayerPropertiesFactory( QgsMapLayerPropertiesFactory* factory );

/** Unregister a previously registered tab in the layer properties dialog */
void unregisterMapLayerPropertiesFactory( QgsMapLayerPropertiesFactory* factory );

public slots:
void layerTreeViewDoubleClicked( const QModelIndex& index );
//! Make sure the insertion point for new layers is up-to-date with the current item in layer tree view
Expand Down Expand Up @@ -1745,6 +1752,8 @@ class APP_EXPORT QgisApp : public QMainWindow, private Ui::MainWindow

QgsSnappingUtils* mSnappingUtils;

QList<QgsMapLayerPropertiesFactory*> mMapLayerPropertiesFactories;

QDateTime mProjectLastModified;

QgsWelcomePage* mWelcomePage;
Expand Down
10 changes: 10 additions & 0 deletions src/app/qgisappinterface.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -475,6 +475,16 @@ bool QgisAppInterface::unregisterMainWindowAction( QAction* action )
return QgsShortcutsManager::instance()->unregisterAction( action );
}

void QgisAppInterface::registerMapLayerPropertiesFactory( QgsMapLayerPropertiesFactory* factory )
{
qgis->registerMapLayerPropertiesFactory( factory );
}

void QgisAppInterface::unregisterMapLayerPropertiesFactory( QgsMapLayerPropertiesFactory* factory )
{
qgis->unregisterMapLayerPropertiesFactory( factory );
}

//! Menus
Q_DECL_DEPRECATED QMenu *QgisAppInterface::fileMenu() { return qgis->projectMenu(); }
QMenu *QgisAppInterface::projectMenu() { return qgis->projectMenu(); }
Expand Down
6 changes: 6 additions & 0 deletions src/app/qgisappinterface.h
Original file line number Diff line number Diff line change
Expand Up @@ -288,6 +288,12 @@ class APP_EXPORT QgisAppInterface : public QgisInterface
/** Unregister a previously registered action. (e.g. when plugin is going to be unloaded. */
virtual bool unregisterMainWindowAction( QAction* action ) override;

/** Register a new tab in the layer properties dialog */
virtual void registerMapLayerPropertiesFactory( QgsMapLayerPropertiesFactory* factory ) override;

/** Unregister a previously registered tab in the layer properties dialog */
virtual void unregisterMapLayerPropertiesFactory( QgsMapLayerPropertiesFactory* factory ) override;

/** Accessors for inserting items into menus and toolbars.
* An item can be inserted before any existing action.
*/
Expand Down
21 changes: 21 additions & 0 deletions src/app/qgsvectorlayerproperties.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,7 @@
#include "qgslabel.h"
#include "qgsgenericprojectionselector.h"
#include "qgslogger.h"
#include "qgsmaplayerpropertiesfactory.h"
#include "qgsmaplayerregistry.h"
#include "qgsmaplayerstyleguiutils.h"
#include "qgspluginmetadata.h"
Expand All @@ -44,6 +45,7 @@
#include "qgsloadstylefromdbdialog.h"
#include "qgsvectorlayer.h"
#include "qgsvectorlayerproperties.h"
#include "qgsvectorlayerpropertiespage.h"
#include "qgsconfig.h"
#include "qgsvectordataprovider.h"
#include "qgsquerybuilder.h"
Expand Down Expand Up @@ -323,6 +325,19 @@ void QgsVectorLayerProperties::setLabelCheckBox()
labelCheckBox->setCheckState( Qt::Checked );
}

void QgsVectorLayerProperties::addPropertiesPageFactory( QgsMapLayerPropertiesFactory* factory )
{
QListWidgetItem* item = factory->createVectorLayerPropertiesItem( mLayer, mOptionsListWidget );
if ( item )
{
mOptionsListWidget->addItem( item );

QgsVectorLayerPropertiesPage* page = factory->createVectorLayerPropertiesPage( mLayer, this );
mLayerPropertiesPages << page;
mOptionsStackedWidget->addWidget( page );
}
}

void QgsVectorLayerProperties::insertField()
{
// Convert the selected field to an expression and
Expand Down Expand Up @@ -606,6 +621,12 @@ void QgsVectorLayerProperties::apply()
//apply diagram settings
diagramPropertiesDialog->apply();

// apply all plugin dialogs
foreach ( QgsVectorLayerPropertiesPage* page, mLayerPropertiesPages )
{
page->apply();
}

//layer title and abstract
mLayer->setShortName( mLayerShortNameLineEdit->text() );
mLayer->setTitle( mLayerTitleLineEdit->text() );
Expand Down
8 changes: 8 additions & 0 deletions src/app/qgsvectorlayerproperties.h
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,8 @@ class QgsLabelingWidget;
class QgsDiagramProperties;
class QgsFieldsProperties;
class QgsRendererV2PropertiesDialog;
class QgsMapLayerPropertiesFactory;
class QgsVectorLayerPropertiesPage;

class APP_EXPORT QgsVectorLayerProperties : public QgsOptionsDialogBase, private Ui::QgsVectorLayerPropertiesBase
{
Expand Down Expand Up @@ -74,6 +76,9 @@ class APP_EXPORT QgsVectorLayerProperties : public QgsOptionsDialogBase, private
@return false in case of a non-existing attribute.*/
bool deleteAttribute( int attr );

/** Adds a properties page factory to the vector layer properties dialog. */
void addPropertiesPageFactory( QgsMapLayerPropertiesFactory *factory );

public slots:

/** Insert a field in the expression text for the map tip **/
Expand Down Expand Up @@ -190,6 +195,9 @@ class APP_EXPORT QgsVectorLayerProperties : public QgsOptionsDialogBase, private
//! List of joins of a layer at the time of creation of the dialog. Used to return joins to previous state if dialog is cancelled
QList< QgsVectorJoinInfo > mOldJoins;

//! A list of additional pages provided by plugins
QList<QgsVectorLayerPropertiesPage*> mLayerPropertiesPages;

/** Previous layer style. Used to reset style to previous state if new style
* was loaded but dialog is cancelled */
QgsMapLayerStyle mOldStyle;
Expand Down
4 changes: 4 additions & 0 deletions src/core/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -81,6 +81,7 @@ SET(QGIS_CORE_SRCS
qgsactionmanager.cpp
qgsaggregatecalculator.cpp
qgsattributetableconfig.cpp
qgsbillboardregistry.cpp
qgsbrowsermodel.cpp
qgscachedfeatureiterator.cpp
qgscacheindex.cpp
Expand Down Expand Up @@ -167,6 +168,7 @@ SET(QGIS_CORE_SRCS
qgspallabeling.cpp
qgspluginlayer.cpp
qgspluginlayerregistry.cpp
qgsplugininterface.cpp
qgspoint.cpp
qgspointlocator.cpp
qgsproject.cpp
Expand Down Expand Up @@ -449,6 +451,7 @@ ENDIF(NOT MSVC)

SET(QGIS_CORE_MOC_HDRS
qgsapplication.h
qgsbillboardregistry.h
qgsbrowsermodel.h
qgscontexthelp.h
qgscoordinatetransform.h
Expand Down Expand Up @@ -479,6 +482,7 @@ SET(QGIS_CORE_MOC_HDRS
qgsofflineediting.h
qgsowsconnection.h
qgspluginlayer.h
qgsplugininterface.h
qgspointlocator.h
qgsproject.h
qgsrelationmanager.h
Expand Down
2 changes: 1 addition & 1 deletion src/core/dxf/qgsdxfexport.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3706,7 +3706,7 @@ QgsRectangle QgsDxfExport::dxfExtent() const
else
{
QgsRectangle layerExtent = layerIt->first->extent();
extent.combineExtentWith( &layerExtent );
extent.combineExtentWith( layerExtent );
}
}
}
Expand Down
2 changes: 1 addition & 1 deletion src/core/geometry/qgscircularstringv2.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -78,7 +78,7 @@ QgsRectangle QgsCircularStringV2::calculateBoundingBox() const
else
{
QgsRectangle segmentBox = segmentBoundingBox( QgsPointV2( mX[i], mY[i] ), QgsPointV2( mX[i + 1], mY[i + 1] ), QgsPointV2( mX[i + 2], mY[i + 2] ) );
bbox.combineExtentWith( &segmentBox );
bbox.combineExtentWith( segmentBox );
}
}

Expand Down
2 changes: 1 addition & 1 deletion src/core/geometry/qgscompoundcurvev2.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -95,7 +95,7 @@ QgsRectangle QgsCompoundCurveV2::calculateBoundingBox() const
for ( int i = 1; i < mCurves.size(); ++i )
{
QgsRectangle curveBox = mCurves.at( i )->boundingBox();
bbox.combineExtentWith( &curveBox );
bbox.combineExtentWith( curveBox );
}
return bbox;
}
Expand Down
2 changes: 1 addition & 1 deletion src/core/geometry/qgsgeometrycollectionv2.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -336,7 +336,7 @@ QgsRectangle QgsGeometryCollectionV2::calculateBoundingBox() const
for ( int i = 1; i < mGeometries.size(); ++i )
{
QgsRectangle geomBox = mGeometries.at( i )->boundingBox();
bbox.combineExtentWith( &geomBox );
bbox.combineExtentWith( geomBox );
}
return bbox;
}
Expand Down
42 changes: 42 additions & 0 deletions src/core/qgsbillboardregistry.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
/***************************************************************************
qgsbillboardregistry.cpp
------------------------
begin : February 2016
copyright : (C) 2016 by Sandro Mani
email : smani@sourcepole.ch
***************************************************************************/

/***************************************************************************
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
***************************************************************************/

#include "qgsbillboardregistry.h"

void QgsBillBoardRegistry::addItem( void* parent, const QImage &image, const QgsPoint &worldPos , const QString &layerId )
{
QMap<void*, QgsBillBoardItem*>::iterator it = mItems.find( parent );

This comment has been minimized.

Copy link
@nyalldawson

nyalldawson May 30, 2016

Collaborator

@manisandro so each parent can only have a single billboard? Do you think there is any use case where a layer may want to register multiple billboards?

This comment has been minimized.

Copy link
@manisandro

manisandro May 30, 2016

Author Member

Let me redesign this... (The background for this approach was that to update a billboard you could simply re-add it with addItem and the same parent, and in my use-case there was always one billboard per parent. So the docstring is actually wrong, I got confused myself about how I had implemented this.)

This comment has been minimized.

Copy link
@m-kuhn

m-kuhn May 30, 2016

Member

@manisandro is there a reason to ship the billboard with this release?
I.e. is it actually usable or does it only exist in the globe? And could it be implemented via annotations. I think the two functionalities are quite similar and could potentially be merged for not maintaining duplicate code?

This comment has been minimized.

Copy link
@manisandro

manisandro May 30, 2016

Author Member

@m-kuhn Billboards do end up as annotations in the globe. The only reason for this class to exist is to allow code outside the globe plugin to interact with it. Unless one moved the globe to core, I don't think there is an easier approach?

This comment has been minimized.

Copy link
@m-kuhn

m-kuhn via email May 30, 2016

Member

This comment has been minimized.

Copy link
@m-kuhn

m-kuhn May 31, 2016

Member

@manisandro revisiting this, can you clarify

  • about the difference between billboard and QGIS map annotations, could they be consolidated and one bridge built to expose all kinds of annotations to globe (or wherever)
  • if the billboard is usable at the moment from the user interface from a standard QGIS installation (without using any forks)

This comment has been minimized.

Copy link
@manisandro

manisandro May 31, 2016

Author Member

@m-kuhn Billboard are generic georeferenced symbols. This image might be an appropriately rendered annotation item, or also point symbols of a layer (so for instance, a plugin layer with points can add register these points with an appropriate image - say, a tree - as billboards).

At the moment they are usable by plugins.

This comment has been minimized.

Copy link
@m-kuhn

m-kuhn via email May 31, 2016

Member

This comment has been minimized.

Copy link
@manisandro

manisandro via email May 31, 2016

Author Member

This comment has been minimized.

Copy link
@m-kuhn

m-kuhn via email Jun 1, 2016

Member

This comment has been minimized.

Copy link
@manisandro

manisandro via email Jun 2, 2016

Author Member

This comment has been minimized.

Copy link
@m-kuhn

m-kuhn via email Jun 2, 2016

Member

This comment has been minimized.

Copy link
@manisandro

manisandro via email Jun 2, 2016

Author Member

This comment has been minimized.

Copy link
@m-kuhn

m-kuhn Jun 3, 2016

Member

Or we allow registering plugins their custom API which would IMO be cleaner but needs to be discussed.

Sure, if you feel uncomfortable with this API I have no problems removing it again for the time being.

I would say so.

In general it's good practice to create multiple pull requests for independent functionality so it can be reviewed and merged individually.
And on a related note, it is also good practice to give credits when you make a pull request or presentation heavily based on someone else work.

This comment has been minimized.

Copy link
@manisandro

manisandro via email Jun 3, 2016

Author Member

This comment has been minimized.

Copy link
@m-kuhn

m-kuhn Jun 3, 2016

Member

Thanks a lot ! 👍

if ( it == mItems.end() )
{
it = mItems.insert( parent, new QgsBillBoardItem );
}
it.value()->image = image;
it.value()->worldPos = worldPos;
it.value()->layerId = layerId;
emit itemAdded( it.value() );
}

void QgsBillBoardRegistry::removeItem( void* parent )
{
emit itemRemoved( mItems[parent] );
delete mItems.take( parent );
}

QList<QgsBillBoardItem*> QgsBillBoardRegistry::items() const
{
return mItems.values();
}
82 changes: 82 additions & 0 deletions src/core/qgsbillboardregistry.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,82 @@
/***************************************************************************
qgsbillboardregistry.h
----------------------
begin : February 2016
copyright : (C) 2016 by Sandro Mani
email : smani@sourcepole.ch
***************************************************************************/

/***************************************************************************
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
***************************************************************************/

#ifndef QGSBILLBOARDREGISTRY_H
#define QGSBILLBOARDREGISTRY_H

#include <QObject>
#include <QImage>
#include "qgspoint.h"

class QgsMapCanvasItem;

/** Billboard items stored in the QgsBillBoardRegistry */
class CORE_EXPORT QgsBillBoardItem
{
public:
QImage image; /* The image of the billboard */
QgsPoint worldPos; /* The WGS84 world position of the billboard */
QString layerId; /* The layer which the image is part of, if any */
};

/**
* @brief The QgsBillBoardRegistry class stores images which should
* be displayed as billboards in the globe plugin.
* Map canvas items and layers may decide to add items which should
* be drawn as billboards in the globe.
*
* Retreive the instance pointer to a QgsBillBoardRegistry for a
* project via QgsProject::instance()->billboardRegistry().
*/
class CORE_EXPORT QgsBillBoardRegistry : public QObject
{
Q_OBJECT
public:
/**
* @brief Adds a billboard to the registry
* @param parent The parent (i.e. a QgsMapLayer or a QgsMapCanvasItem) which is creating the billboard
* @param image The billboard image
* @param worldPos The geo position of the image, in WGS84
* @param layerId The id of the layer to which the item belongs, if any
*/
void addItem( void* parent, const QImage& image, const QgsPoint& worldPos, const QString& layerId = QString() );
/**
* @brief Removes all billboards which were created by the specified parent
* @param parent The parent
*/
void removeItem( void* parent );

/**
* @brief Retreive all registered billboard items
* @return List of registered billboard items
*/
QList<QgsBillBoardItem*> items() const;

signals:
/** Emitted when an item is added to the registry */
void itemAdded( QgsBillBoardItem* item );
/** Emitted when an item is removed from the registry */
void itemRemoved( QgsBillBoardItem* item );

private:
friend class QgsProject; // Only QgsProject is allowed to construct this class
QgsBillBoardRegistry( QObject* parent = 0 ) : QObject( parent ) {}

QMap<void*, QgsBillBoardItem*> mItems;
};

#endif // QGSBILLBOARDREGISTRY_H
6 changes: 6 additions & 0 deletions src/core/qgsmapsettings.h
Original file line number Diff line number Diff line change
Expand Up @@ -114,6 +114,11 @@ class CORE_EXPORT QgsMapSettings
//! @note added in 2.8
void setLayerStyleOverrides( const QMap<QString, QString>& overrides );

//! Get custom rendering flags, separated by ';'. Layers might honour these to alter their rendering.
const QString& customRenderFlags() const { return mCustomRenderFlags; }
//! Set custom rendering flags, separated by ';'. Layers might honour these to alter their rendering.
void setCustomRenderFlags( const QString& customRenderFlags ) { mCustomRenderFlags = customRenderFlags; }

//! sets whether to use projections for this layer set
void setCrsTransformEnabled( bool enabled );
//! returns true if projections are enabled for this layer set
Expand Down Expand Up @@ -290,6 +295,7 @@ class CORE_EXPORT QgsMapSettings

QStringList mLayers;
QMap<QString, QString> mLayerStyleOverrides;
QString mCustomRenderFlags;
QgsExpressionContext mExpressionContext;

bool mProjectionsEnabled;
Expand Down
Empty file added src/core/qgsplugininterface.cpp
Empty file.
33 changes: 33 additions & 0 deletions src/core/qgsplugininterface.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
/***************************************************************************
qgsplugininterface.h
--------------------------------------
Date : 21.8.2013
Copyright : (C) 2013 Matthias Kuhn
Email : matthias dot kuhn at gmx dot ch
***************************************************************************
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
***************************************************************************/

#ifndef QGSPLUGININTERFACE_H
#define QGSPLUGININTERFACE_H

#include <QObject>

/**
* @brief Trivial base class for plugin interfaces
*/
class CORE_EXPORT QgsPluginInterface : public QObject
{
Q_OBJECT

protected:
/** Should only be instantiated from subclasses */
QgsPluginInterface( QObject* parent = 0 ) : QObject( parent ) {}
};

#endif // QGSPLUGININTERFACE_H
2 changes: 2 additions & 0 deletions src/core/qgsproject.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@

#include "qgsproject.h"

#include "qgsbillboardregistry.h"
#include "qgsdatasourceuri.h"
#include "qgsexception.h"
#include "qgslayertree.h"
Expand Down Expand Up @@ -361,6 +362,7 @@ QgsProject::QgsProject()
, mBadLayerHandler( new QgsProjectBadLayerDefaultHandler() )
, mRelationManager( new QgsRelationManager( this ) )
, mRootGroup( new QgsLayerTreeGroup )
, mBillboardRegistry( new QgsBillBoardRegistry( this ) )
{
clear();

Expand Down
8 changes: 8 additions & 0 deletions src/core/qgsproject.h
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,7 @@ class QDomDocument;
class QDomElement;
class QDomNode;

class QgsBillBoardRegistry;
class QgsLayerTreeGroup;
class QgsLayerTreeRegistryBridge;
class QgsMapLayer;
Expand Down Expand Up @@ -323,6 +324,11 @@ class CORE_EXPORT QgsProject : public QObject

QgsRelationManager* relationManager() const;

/** Return the project's billboard manager instance pointer
* @note added in QGIS 2.16
*/
QgsBillBoardRegistry* billboardRegistry() const { return mBillboardRegistry; }

/** Return pointer to the root (invisible) node of the project's layer tree
* @note added in 2.4
*/
Expand Down Expand Up @@ -487,6 +493,8 @@ class CORE_EXPORT QgsProject : public QObject

QgsLayerTreeRegistryBridge* mLayerTreeRegistryBridge;

QgsBillBoardRegistry* mBillboardRegistry;

//! map of transaction group: QPair( providerKey, connString ) -> transactionGroup
QMap< QPair< QString, QString>, QgsTransactionGroup*> mTransactionGroups;

Expand Down
10 changes: 5 additions & 5 deletions src/core/qgsrectangle.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -194,14 +194,14 @@ bool QgsRectangle::contains( const QgsPoint &p ) const
ymin <= p.y() && p.y() <= ymax;
}

void QgsRectangle::combineExtentWith( QgsRectangle * rect )
void QgsRectangle::combineExtentWith( const QgsRectangle &rect )
{

xmin = (( xmin < rect->xMinimum() ) ? xmin : rect->xMinimum() );
xmax = (( xmax > rect->xMaximum() ) ? xmax : rect->xMaximum() );
xmin = (( xmin < rect.xMinimum() ) ? xmin : rect.xMinimum() );
xmax = (( xmax > rect.xMaximum() ) ? xmax : rect.xMaximum() );

ymin = (( ymin < rect->yMinimum() ) ? ymin : rect->yMinimum() );
ymax = (( ymax > rect->yMaximum() ) ? ymax : rect->yMaximum() );
ymin = (( ymin < rect.yMinimum() ) ? ymin : rect.yMinimum() );
ymax = (( ymax > rect.yMaximum() ) ? ymax : rect.yMaximum() );

}

Expand Down
2 changes: 1 addition & 1 deletion src/core/qgsrectangle.h
Original file line number Diff line number Diff line change
Expand Up @@ -97,7 +97,7 @@ class CORE_EXPORT QgsRectangle
//! return true when rectangle contains a point
bool contains( const QgsPoint &p ) const;
//! expand the rectangle so that covers both the original rectangle and the given rectangle
void combineExtentWith( QgsRectangle *rect );
void combineExtentWith( const QgsRectangle& rect );
//! expand the rectangle so that covers both the original rectangle and the given point
void combineExtentWith( double x, double y );
//! test if rectangle is empty.
Expand Down
10 changes: 5 additions & 5 deletions src/core/qgsvectorlayer.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -717,7 +717,7 @@ QgsRectangle QgsVectorLayer::boundingBoxOfSelected()
if ( !fet.constGeometry() || fet.constGeometry()->isEmpty() )
continue;
r = fet.constGeometry()->boundingBox();
retval.combineExtentWith( &r );
retval.combineExtentWith( r );
}
}
else
Expand All @@ -732,7 +732,7 @@ QgsRectangle QgsVectorLayer::boundingBoxOfSelected()
if ( fet.constGeometry() )
{
r = fet.constGeometry()->boundingBox();
retval.combineExtentWith( &r );
retval.combineExtentWith( r );
}
}
}
Expand Down Expand Up @@ -1000,7 +1000,7 @@ QgsRectangle QgsVectorLayer::extent()
if ( mDataProvider->featureCount() != 0 )
{
QgsRectangle r = mDataProvider->extent();
rect.combineExtentWith( &r );
rect.combineExtentWith( r );
}

if ( mEditBuffer )
Expand All @@ -1010,7 +1010,7 @@ QgsRectangle QgsVectorLayer::extent()
if ( it->constGeometry() )
{
QgsRectangle r = it->constGeometry()->boundingBox();
rect.combineExtentWith( &r );
rect.combineExtentWith( r );
}
}
}
Expand All @@ -1026,7 +1026,7 @@ QgsRectangle QgsVectorLayer::extent()
if ( fet.constGeometry() && fet.constGeometry()->type() != QGis::UnknownGeometry )
{
QgsRectangle bb = fet.constGeometry()->boundingBox();
rect.combineExtentWith( &bb );
rect.combineExtentWith( bb );
}
}
}
Expand Down
3 changes: 3 additions & 0 deletions src/gui/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -239,6 +239,7 @@ SET(QGIS_GUI_SRCS
qgsmaplayeractionregistry.cpp
qgsmaplayercombobox.cpp
qgsmaplayermodel.cpp
qgsmaplayerpropertiesfactory.cpp
qgsmaplayerproxymodel.cpp
qgsmapmouseevent.cpp
qgsmapoverviewcanvas.cpp
Expand Down Expand Up @@ -292,6 +293,7 @@ SET(QGIS_GUI_SRCS
qgsunitselectionwidget.cpp
qgsuserinputdockwidget.cpp
qgsvariableeditorwidget.cpp
qgsvectorlayerpropertiespage.cpp
qgsvertexmarker.cpp
)

Expand Down Expand Up @@ -431,6 +433,7 @@ SET(QGIS_GUI_MOC_HDRS
qgsunitselectionwidget.h
qgsuserinputdockwidget.h
qgsvariableeditorwidget.h
qgsvectorlayerpropertiespage.h

raster/qgsmultibandcolorrendererwidget.h
raster/qgspalettedrendererwidget.h
Expand Down
2 changes: 1 addition & 1 deletion src/gui/editorwidgets/qgsrelationreferencewidget.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -617,7 +617,7 @@ void QgsRelationReferenceWidget::highlightFeature( QgsFeature f, CanvasExtent ca
QgsRectangle extent = mCanvas->extent();
if ( !extent.contains( featBBox ) )
{
extent.combineExtentWith( &featBBox );
extent.combineExtentWith( featBBox );
extent.scale( 1.1 );
mCanvas->setExtent( extent );
mCanvas->refresh();
Expand Down
2 changes: 1 addition & 1 deletion src/gui/layertree/qgslayertreeviewdefaultactions.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -242,7 +242,7 @@ void QgsLayerTreeViewDefaultActions::zoomToLayers( QgsMapCanvas* canvas, const Q
if ( canvas->hasCrsTransformEnabled() )
layerExtent = canvas->mapSettings().layerExtentToOutputExtent( layer, layerExtent );

extent.combineExtentWith( &layerExtent );
extent.combineExtentWith( layerExtent );
}

if ( extent.isNull() )
Expand Down
7 changes: 7 additions & 0 deletions src/gui/qgisinterface.h
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,7 @@ class QgsLayerTreeView;
class QgsLegendInterface;
class QgsMapCanvas;
class QgsMapLayer;
class QgsMapLayerPropertiesFactory;
class QgsMessageBar;
class QgsPluginManagerInterface;
class QgsRasterLayer;
Expand Down Expand Up @@ -328,6 +329,12 @@ class GUI_EXPORT QgisInterface : public QObject
/** Unregister a previously registered action. (e.g. when plugin is going to be unloaded) */
virtual bool unregisterMainWindowAction( QAction* action ) = 0;

/** Register a new tab in the vector layer properties dialog */
virtual void registerMapLayerPropertiesFactory( QgsMapLayerPropertiesFactory* factory ) = 0;

/** Unregister a previously registered tab in the layer properties dialog */
virtual void unregisterMapLayerPropertiesFactory( QgsMapLayerPropertiesFactory* factory ) = 0;

// @todo is this deprecated in favour of QgsContextHelp?
/** Open a url in the users browser. By default the QGIS doc directory is used
* as the base for the URL. To open a URL that is not relative to the installed
Expand Down
2 changes: 1 addition & 1 deletion src/gui/qgsmapcanvas.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1177,7 +1177,7 @@ void QgsMapCanvas::zoomToFeatureIds( QgsVectorLayer* layer, const QgsFeatureIds&
return;
}
QgsRectangle r = mapSettings().layerExtentToOutputExtent( layer, geom->boundingBox() );
rect.combineExtentWith( &r );
rect.combineExtentWith( r );
featureCount++;
}

Expand Down
24 changes: 24 additions & 0 deletions src/gui/qgsmaplayerpropertiesfactory.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
/***************************************************************************
qgslayeroptionsfactory.cpp
--------------------------------------
Date : 9.7.2013
Copyright : (C) 2013 Matthias Kuhn
Email : matthias dot kuhn at gmx dot ch
***************************************************************************
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
***************************************************************************/

#include "qgsmaplayerpropertiesfactory.h"

QgsMapLayerPropertiesFactory::QgsMapLayerPropertiesFactory()
{
}

QgsMapLayerPropertiesFactory::~QgsMapLayerPropertiesFactory()
{
}
52 changes: 52 additions & 0 deletions src/gui/qgsmaplayerpropertiesfactory.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
/***************************************************************************
qgslayeroptionsfactory.h
--------------------------------------
Date : 9.7.2013
Copyright : (C) 2013 Matthias Kuhn
Email : matthias dot kuhn at gmx dot ch
***************************************************************************
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
***************************************************************************/

#ifndef QGSLAYERPROPERTIESFACTORY_H
#define QGSLAYERPROPERTIESFACTORY_H

#include <QListWidgetItem>

#include "qgsvectorlayerpropertiespage.h"

/**
* @brief Factory class for creating custom map layer property pages
*/
class GUI_EXPORT QgsMapLayerPropertiesFactory
{
public:
/** Constructor */
QgsMapLayerPropertiesFactory();

/** Destructor */
virtual ~QgsMapLayerPropertiesFactory();

/**
* @brief Create a new properties page
* @param layer The layer for which to create the page
* @param parent The parent widget
* @return The new properties page instance
*/
virtual QgsVectorLayerPropertiesPage* createVectorLayerPropertiesPage( QgsVectorLayer* layer, QWidget* parent ) = 0;

/**
* @brief Creates the QListWidgetItem for the properties page
* @param layer The layer for which to create the item
* @param view The parent QListView
* @return The QListWidgetItem for the properties page
*/
virtual QListWidgetItem* createVectorLayerPropertiesItem( QgsVectorLayer* layer, QListWidget* view ) = 0;
};

#endif // QGSLAYERPROPERTIESFACTORY_H
2 changes: 1 addition & 1 deletion src/gui/qgsrubberband.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -558,7 +558,7 @@ void QgsRubberBand::updateRect()
}
else
{
r.combineExtentWith( &rect );
r.combineExtentWith( rect );
}
}
}
Expand Down
22 changes: 22 additions & 0 deletions src/gui/qgsvectorlayerpropertiespage.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
/***************************************************************************
qgsvectorlayerpropertiespage.cpp
--------------------------------------
Date : 8.7.2013
Copyright : (C) 2013 Matthias Kuhn
Email : matthias dot kuhn at gmx dot ch
***************************************************************************
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
***************************************************************************/

#include "qgsvectorlayerpropertiespage.h"

QgsVectorLayerPropertiesPage::QgsVectorLayerPropertiesPage( QWidget *parent ) :
QWidget( parent )
{
}

38 changes: 38 additions & 0 deletions src/gui/qgsvectorlayerpropertiespage.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
/***************************************************************************
qgsvectorlayerpropertiespage.h
--------------------------------------
Date : 8.7.2013
Copyright : (C) 2013 Matthias Kuhn
Email : matthias dot kuhn at gmx dot ch
***************************************************************************
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
***************************************************************************/

#ifndef QGSVECTORLAYERPROPERTIESPAGE_H
#define QGSVECTORLAYERPROPERTIESPAGE_H

#include <QWidget>

class QgsVectorLayer;

/**
* @brief Base class for custom vector layer property pages
*/
class GUI_EXPORT QgsVectorLayerPropertiesPage : public QWidget
{
Q_OBJECT
public:
/** Constructor */
explicit QgsVectorLayerPropertiesPage( QWidget *parent = 0 );

public slots:
/** Apply changes */
virtual void apply() = 0;
};

#endif // QGSVECTORLAYERPROPERTIESPAGE_H
117 changes: 59 additions & 58 deletions src/plugins/globe/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -1,102 +1,103 @@
# set path to additional CMake modules
SET(CMAKE_MODULE_PATH ${CMAKE_CURRENT_SOURCE_DIR}/CMakeModules ${CMAKE_MODULE_PATH})
IF (KEEP_GLOBE_CXX_FLAGS)
SET(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS_OLD}")
ENDIF()

FIND_PACKAGE(OSG REQUIRED)
FIND_PACKAGE(OSGEARTH REQUIRED)
FIND_PACKAGE(Threads)
IF(QT5_BUILD)
FIND_PACKAGE(Qt5OpenGL REQUIRED)
ENDIF(QT5_BUILD)

IF(HAVE_OSGEARTH_CHILD_SPACING)
ADD_DEFINITIONS(-DHAVE_OSGEARTH_CHILD_SPACING)
ENDIF(HAVE_OSGEARTH_CHILD_SPACING)

IF(OSGEARTH_ELEVATION_QUERY)
ADD_DEFINITIONS(-DHAVE_OSGEARTH_ELEVATION_QUERY)
ENDIF(OSGEARTH_ELEVATION_QUERY)

########################################################
# Files

SET (globe_plugin_SRCS
globe_plugin.cpp
qgsosgearthtilesource.cpp
globe_plugin_dialog.cpp
SET (GLOBE_PLUGIN_SRCS
globe_plugin.cpp
qgsglobetilesource.cpp
qgsglobeplugindialog.cpp
qgsglobeinterface.cpp
qgsglobevectorlayerproperties.cpp
qgsglobefeatureidentify.cpp
qgsglobefrustumhighlight.cpp
qgsglobewidget.cpp
)

SET (GLOBE_PLUGIN_UIS
qgsglobeplugindialog.ui
qgsglobevectorlayerpropertiespage.ui
)

SET (GLOBE_PLUGIN_MOC_HDRS
globe_plugin.h
qgsglobeplugindialog.h
qgsglobeinterface.h
qgsglobevectorlayerproperties.h
qgsglobetilesource.h
qgsglobewidget.h
)
IF (NOT HAVE_OSGEARTHQT)
SET(globe_plugin_SRCS
${globe_plugin_SRCS}
osgEarthQt/ViewerWidget.cpp
osgEarthUtil/Controls.cpp
)
ENDIF (NOT HAVE_OSGEARTHQT)

SET (globe_plugin_UIS
globe_plugin_dialog_guibase.ui
)

SET (globe_plugin_MOC_HDRS
globe_plugin.h
globe_plugin_dialog.h

SET (GLOBE_PLUGIN_HDRS
qgsglobeinterface.h
qgsglobevectorlayerproperties.h
qgsglobefeatureidentify.h
qgsglobefrustumhighlight.h
)

SET (globe_plugin_RCCS globe_plugin.qrc)
SET (GLOBE_PLUGIN_RCCS globe_plugin.qrc)

########################################################
# Build

QT4_WRAP_UI (globe_plugin_UIS_H ${globe_plugin_UIS})
IF(WIN32)
ADD_DEFINITIONS("\"-DGLOBE_EXPORT=${DLLEXPORT}\"")
ELSE(WIN32)
ADD_DEFINITIONS("-DGLOBE_EXPORT=")
ENDIF(WIN32)

QT4_WRAP_CPP (globe_plugin_MOC_SRCS ${globe_plugin_MOC_HDRS})
QT4_WRAP_UI (GLOBE_PLUGIN_UIS_H ${GLOBE_PLUGIN_UIS})

QT4_ADD_RESOURCES(globe_plugin_RCC_SRCS ${globe_plugin_RCCS})
QT4_WRAP_CPP (GLOBE_PLUGIN_MOC_SRCS ${GLOBE_PLUGIN_MOC_HDRS})

ADD_LIBRARY (globeplugin MODULE ${globe_plugin_SRCS} ${globe_plugin_MOC_SRCS} ${globe_plugin_RCC_SRCS} ${globe_plugin_UIS_H})
QT4_ADD_RESOURCES(GLOBE_PLUGIN_RCC_SRCS ${GLOBE_PLUGIN_RCCS})

INCLUDE_DIRECTORIES(SYSTEM
${Qt5OpenGL_INCLUDE_DIRS}
${OSGEARTH_INCLUDE_DIR}
${OSG_INCLUDE_DIR}
${GEOS_INCLUDE_DIR}
)
ADD_LIBRARY (globeplugin SHARED ${GLOBE_PLUGIN_SRCS} ${GLOBE_PLUGIN_MOC_SRCS} ${GLOBE_PLUGIN_RCC_SRCS} ${GLOBE_PLUGIN_UIS_H} ${GLOBE_PLUGIN_HDRS})

INCLUDE_DIRECTORIES(
${CMAKE_CURRENT_BINARY_DIR}
../../core ../../core/geometry ../../core/raster
${OSGEARTH_INCLUDE_DIR}
${OSG_INCLUDE_DIR}
${GEOS_INCLUDE_DIR}
${SIP_INCLUDE_DIR}
../../core
../../core/geometry
../../core/raster
../../core/symbology-ng
../../gui
..
)

SET (OSGEARTH_LIBS
${OSGEARTH_LIBRARY}
${OSGEARTHFEATURES_LIBRARY}
${OSGEARTHUTIL_LIBRARY}
)
IF (HAVE_OSGEARTHQT)
SET(OSGEARTH_LIBS
${OSGEARTH_LIBS}
${OSGEARTHQT_LIBRARY}
)
ENDIF (HAVE_OSGEARTHQT)
TARGET_LINK_LIBRARIES(globeplugin
qgis_core
qgis_gui
${QT_QTOPENGL_LIBRARY}
${Qt5OpenGL_LIBRARIES}
${OSGDB_LIBRARY}
${OSGGA_LIBRARY}
${OSGUTIL_LIBRARY}
${OSG_LIBRARY}
${OSGQT_LIBRARY}
${OSGVIEWER_LIBRARY}
${OSGEARTH_LIBS}
${OSGEARTH_LIBRARY}
${OSGEARTHANNOTATION_LIBRARY}
${OSGEARTHFEATURES_LIBRARY}
${OSGEARTHUTIL_LIBRARY}
${OSGEARTHSYMBOLOGY_LIBRARY}
${OSGEARTHQT_LIBRARY}
${OPENTHREADS_LIBRARY}
)

IF (WITH_BINDINGS)
# Restore default CXX flags (without visibility=hidden, which breaks python bindings)
SET(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS_OLD}")
ADD_SUBDIRECTORY(python)
ENDIF (WITH_BINDINGS)
ADD_SUBDIRECTORY(featuresource)

########################################################
# Install
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
# Required Vars:
# ${LIB_NAME}
# ${LIB_PUBLIC_HEADERS}

SET(INSTALL_INCDIR include)

# FIXME: Do not run for OS X framework
INSTALL(
FILES ${LIB_PUBLIC_HEADERS}
DESTINATION ${INSTALL_INCDIR}/osgEarthDrivers/${LIB_NAME}
)
361 changes: 361 additions & 0 deletions src/plugins/globe/CMakeModules/OsgEarthMacroUtils.cmake

Large diffs are not rendered by default.

50 changes: 50 additions & 0 deletions src/plugins/globe/featuresource/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
###################################################
# osgEarth plugin
###################################################

SET(OSGEARTH_PLUGIN_PREFIX "")
SET(LIB_POSTFIX ${LIB_SUFFIX})
SET(DYNAMIC_OSGEARTH "ON" )
SET(OSGEARTH_USER_DEFINED_DYNAMIC_OR_STATIC "SHARED")

# SET(CMAKE_SHARED_MODULE_PREFIX ${OSGEARTH_PLUGIN_PREFIX})
SET(TARGET_DEFAULT_PREFIX "osgdb_")
SET(TARGET_DEFAULT_LABEL_PREFIX "Plugin")

INCLUDE( OsgEarthMacroUtils )

SET(TARGET_SRC
qgsglobefeaturesource.cpp
)

SET (TARGET_MOC_HDRS
qgsglobefeaturesource.h
)

SET(TARGET_HDRS
qgsglobefeaturecursor.h
qgsglobefeatureoptions.h
qgsglobefeatureutils.h
)

QT4_WRAP_CPP(TARGET_MOC_SRCS ${TARGET_MOC_HDRS})

SET(TARGET_SRC ${TARGET_SRC} ${TARGET_MOC_SRCS})

SET(TARGET_COMMON_LIBRARIES ${TARGET_COMMON_LIBRARIES}
qgis_core
qgis_gui
${OSGDB_LIBRARY}
${OSG_LIBRARY}
${OSGEARTH_LIBRARY}
${OSGEARTHFEATURES_LIBRARY}
${OSGEARTHSYMBOLOGY_LIBRARY}
${OSGEARTHUTIL_LIBRARY}
${OPENTHREADS_LIBRARY}
)
SETUP_PLUGIN(osgearth_feature_qgis)

# to install public driver includes:
SET(LIB_NAME feature_qgis)
SET(LIB_PUBLIC_HEADERS ${TARGET_HDRS} ${TARGET_MOC_HDRS})
INCLUDE(ModuleInstallOsgEarthDriverIncludes OPTIONAL)
66 changes: 66 additions & 0 deletions src/plugins/globe/featuresource/qgsglobefeaturecursor.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,66 @@
/***************************************************************************
qgsglobefeaturecursor.h
--------------------------------------
Date : 11.7.2013
Copyright : (C) 2013 Matthias Kuhn
Email : matthias dot kuhn at gmx dot ch
***************************************************************************
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
***************************************************************************/

#ifndef QGSGLOBEFEATURECURSOR_H
#define QGSGLOBEFEATURECURSOR_H

#include <osgEarthFeatures/FeatureCursor>
#include <qgsfeature.h>
#include <qgsfeatureiterator.h>
#include <qgsvectorlayer.h>

#include "qgsglobefeatureutils.h"


class QgsGlobeFeatureCursor : public osgEarth::Features::FeatureCursor
{
public:
QgsGlobeFeatureCursor( QgsVectorLayer* layer, const QgsFeatureIterator& iterator )
: mIterator( iterator )
, mLayer( layer )
{
mIterator.nextFeature( mFeature );
}

bool hasMore() const override
{
return mFeature.isValid();
}

osgEarth::Features::Feature* nextFeature() override
{
if ( mFeature.isValid() )
{
osgEarth::Features::Feature *feat = QgsGlobeFeatureUtils::featureFromQgsFeature( mLayer, mFeature );
mIterator.nextFeature( mFeature );
return feat;
}
else
{
QgsDebugMsg( "WARNING: Returning NULL feature to osgEarth" );
return NULL;
}
}

private:
QgsFeatureIterator mIterator;
QgsVectorLayer* mLayer;
// Cached feature which will be returned next.
// Always contains the next feature which will be returned
// (Because hasMore() needs to know if we are able to return a next feature)
QgsFeature mFeature;
};

#endif // QGSGLOBEFEATURECURSOR_H
81 changes: 81 additions & 0 deletions src/plugins/globe/featuresource/qgsglobefeatureoptions.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,81 @@
/* -*-c++-*- */
/*
* 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/>
*/
#ifndef QGSGLOBEFEATUREOPTIONS_H
#define QGSGLOBEFEATUREOPTIONS_H

#include <osgEarth/Common>
#include <osgEarthFeatures/FeatureSource>

class QgsVectorLayer;

class QgsGlobeFeatureOptions : public osgEarth::Features::FeatureSourceOptions // NO EXPORT; header only
{
private:
template <class T>
class RefPtr : public osg::Referenced
{
public:
RefPtr( T* ptr ) : mPtr( ptr ) {}
T* ptr() { return mPtr; }

private:
T* mPtr;
};

public:
QgsGlobeFeatureOptions( const ConfigOptions& opt = ConfigOptions() )
: osgEarth::Features::FeatureSourceOptions( opt )
{
// Call the driver declared as "osgearth_feature_qgis"
setDriver( "qgis" );
fromConfig( _conf );
}

osgEarth::Config getConfig() const override
{
osgEarth::Config conf = osgEarth::Features::FeatureSourceOptions::getConfig();
conf.updateIfSet( "layerId", mLayerId );
conf.updateNonSerializable( "layer", new RefPtr< QgsVectorLayer >( mLayer ) );
return conf;
}

osgEarth::optional<std::string>& layerId() { return mLayerId; }
const osgEarth::optional<std::string>& layerId() const { return mLayerId; }

QgsVectorLayer* layer() const { return mLayer; }
void setLayer( QgsVectorLayer* layer ) { mLayer = layer; }

protected:
void mergeConfig( const osgEarth::Config& conf ) override
{
osgEarth::Features::FeatureSourceOptions::mergeConfig( conf );
fromConfig( conf );
}

private:
void fromConfig( const osgEarth::Config& conf )
{
conf.getIfSet( "layerId", mLayerId );
RefPtr< QgsVectorLayer > *layer_ptr = conf.getNonSerializable< RefPtr< QgsVectorLayer > >( "layer" );
mLayer = layer_ptr ? layer_ptr->ptr() : 0;
}

osgEarth::optional<std::string> mLayerId;
QgsVectorLayer* mLayer;
};

#endif // QGSGLOBEFEATUREOPTIONS_H

145 changes: 145 additions & 0 deletions src/plugins/globe/featuresource/qgsglobefeaturesource.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,145 @@
#include <osgDB/ReaderWriter>
#include <osgDB/FileNameUtils>

#include <qgsfeature.h>
#include <qgsfeatureiterator.h>
#include <qgsgeometry.h>
#include <qgslogger.h>
#include <qgsrectangle.h>
#include "qgsvectorlayer.h"

#include "qgsglobefeaturecursor.h"
#include "qgsglobefeatureutils.h"
#include "qgsglobefeaturesource.h"


QgsGlobeFeatureSource::QgsGlobeFeatureSource( const QgsGlobeFeatureOptions& options ) :
mOptions( options ),
mLayer( 0 ),
mProfile( 0 )
{
}

void QgsGlobeFeatureSource::initialize( const osgDB::Options* dbOptions )
{
Q_UNUSED( dbOptions )
mLayer = mOptions.layer();

connect( mLayer, SIGNAL( attributeValueChanged( QgsFeatureId, int, QVariant ) ), this, SLOT( attributeValueChanged( QgsFeatureId, int, QVariant ) ) );
connect( mLayer, SIGNAL( geometryChanged( QgsFeatureId, QgsGeometry& ) ), this, SLOT( geometryChanged( QgsFeatureId, QgsGeometry& ) ) );

// create the profile
osgEarth::SpatialReference* ref = osgEarth::SpatialReference::create( mLayer->crs().toWkt().toStdString() );
if ( 0 == ref )
{
std::cout << "Cannot find the spatial reference" << std::endl;
return;
}
QgsRectangle ext = mLayer->extent();
osgEarth::GeoExtent geoext( ref, ext.xMinimum(), ext.yMinimum(), ext.xMaximum(), ext.yMaximum() );
mProfile = new osgEarth::Features::FeatureProfile( geoext );
mSchema = QgsGlobeFeatureUtils::schemaForFields( mLayer->pendingFields() );
}

osgEarth::Features::FeatureCursor* QgsGlobeFeatureSource::createFeatureCursor( const osgEarth::Symbology::Query& query )
{
QgsFeatureRequest request;

if ( query.expression().isSet() )
{
QgsDebugMsg( QString( "Ignoring query expression '%1'" ). arg( query.expression().value().c_str() ) );
}

if ( query.bounds().isSet() )
{
QgsRectangle bounds( query.bounds()->xMin(), query.bounds()->yMin(), query.bounds()->xMax(), query.bounds()->yMax() );
request.setFilterRect( bounds );
}

QgsFeatureIterator it = mLayer->getFeatures( request );
return new QgsGlobeFeatureCursor( mLayer, it );
}

osgEarth::Features::Feature* QgsGlobeFeatureSource::getFeature( osgEarth::Features::FeatureID fid )
{
QgsFeature feat;
mLayer->getFeatures( QgsFeatureRequest().setFilterFid( fid ) ).nextFeature( feat );
osgEarth::Features::Feature* feature = QgsGlobeFeatureUtils::featureFromQgsFeature( mLayer, feat );
FeatureMap_t::iterator it = mFeatures.find( fid );
if ( it == mFeatures.end() )
{
mFeatures.insert( std::make_pair( fid, osg::observer_ptr<osgEarth::Features::Feature>( feature ) ) );
}
else
{
it->second = osg::observer_ptr<osgEarth::Features::Feature>( feature );
}
return feature;
}

osgEarth::Features::Geometry::Type QgsGlobeFeatureSource::getGeometryType() const
{
switch ( mLayer->geometryType() )
{
case QGis::Point:
return osgEarth::Features::Geometry::TYPE_POINTSET;

case QGis::Line:
return osgEarth::Features::Geometry::TYPE_LINESTRING;

case QGis::Polygon:
return osgEarth::Features::Geometry::TYPE_POLYGON;

default:
return osgEarth::Features::Geometry::TYPE_UNKNOWN;
}

return osgEarth::Features::Geometry::TYPE_UNKNOWN;
}

int QgsGlobeFeatureSource::getFeatureCount() const
{
return mLayer->featureCount();
}

void QgsGlobeFeatureSource::attributeValueChanged( const QgsFeatureId& featureId, int idx, const QVariant& value )
{
FeatureMap_t::iterator it = mFeatures.find( featureId );
if ( it != mFeatures.end() )
{
osgEarth::Features::Feature* feature = it->second.get();
QgsGlobeFeatureUtils::setFeatureField( feature, mLayer->pendingFields().at( idx ), value );
}
}

void QgsGlobeFeatureSource::geometryChanged( const QgsFeatureId& featureId, QgsGeometry& geometry )
{
FeatureMap_t::iterator it = mFeatures.find( featureId );
if ( it != mFeatures.end() )
{
osgEarth::Features::Feature* feature = it->second.get();
feature->setGeometry( QgsGlobeFeatureUtils::geometryFromQgsGeometry( geometry ) );
}
}


class QgsGlobeFeatureSourceFactory : public osgEarth::Features::FeatureSourceDriver
{
public:
QgsGlobeFeatureSourceFactory()
{
supportsExtension( "osgearth_feature_qgis", "QGIS feature driver for osgEarth" );
}

virtual osgDB::ReaderWriter::ReadResult readObject( const std::string& file_name, const osgDB::Options* options ) const override
{
// this function seems to be called for every plugin
// we declare supporting the special extension "osgearth_feature_qgis"
if ( !acceptsExtension( osgDB::getLowerCaseFileExtension( file_name ) ) )
return osgDB::ReaderWriter::ReadResult::FILE_NOT_HANDLED;

return osgDB::ReaderWriter::ReadResult( new QgsGlobeFeatureSource( getFeatureSourceOptions( options ) ) );
}
};

REGISTER_OSGPLUGIN( osgearth_feature_qgis, QgsGlobeFeatureSourceFactory )
48 changes: 48 additions & 0 deletions src/plugins/globe/featuresource/qgsglobefeaturesource.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
#ifndef QGSGLOBEFEATURESOURCE_H
#define QGSGLOBEFEATURESOURCE_H

#include <osgEarthFeatures/FeatureSource>
#include <QObject>

#include "qgsglobefeatureoptions.h"
#include "qgsfeature.h"

class QgsGlobeFeatureSource : public QObject, public osgEarth::Features::FeatureSource
{
Q_OBJECT
public:
QgsGlobeFeatureSource( const QgsGlobeFeatureOptions& options = osgEarth::Features::ConfigOptions() );

osgEarth::Features::FeatureCursor* createFeatureCursor( const osgEarth::Symbology::Query& query = osgEarth::Symbology::Query() ) override;

int getFeatureCount() const override;
osgEarth::Features::Feature* getFeature( osgEarth::Features::FeatureID fid ) override;
osgEarth::Features::Geometry::Type getGeometryType() const override;

QgsVectorLayer* layer() const { return mLayer; }

const char* className() const override { return "QGISFeatureSource"; }
const char* libraryName() const override { return "QGIS"; }

void initialize( const osgDB::Options* dbOptions );

protected:
const osgEarth::Features::FeatureProfile* createFeatureProfile() override { return mProfile; }
const osgEarth::Features::FeatureSchema& getSchema() const override { return mSchema; }

~QgsGlobeFeatureSource() {}

private:
QgsGlobeFeatureOptions mOptions;
QgsVectorLayer* mLayer;
osgEarth::Features::FeatureProfile* mProfile;
osgEarth::Features::FeatureSchema mSchema;
typedef std::map<osgEarth::Features::FeatureID, osg::observer_ptr<osgEarth::Features::Feature> > FeatureMap_t;
FeatureMap_t mFeatures;

private slots:
void attributeValueChanged( const QgsFeatureId&featureId, int idx, const QVariant &value );
void geometryChanged( const QgsFeatureId&featureId, QgsGeometry&geometry );
};

#endif // QGSGLOBEFEATURESOURCE_H
254 changes: 254 additions & 0 deletions src/plugins/globe/featuresource/qgsglobefeatureutils.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,254 @@
/***************************************************************************
qgsglobefeatureutils.h
--------------------------------------
Date : 11.7.2013
Copyright : (C) 2013 Matthias Kuhn
Email : matthias dot kuhn at gmx dot ch
***************************************************************************
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
***************************************************************************/

#ifndef QGSGLOBEFEATUREUTILS_H
#define QGSGLOBEFEATUREUTILS_H

#include <osgEarthFeatures/Feature>
#include <osg/ValueObject>

#include <qgsfield.h>
#include <qgsgeometry.h>
#include <qgsmultipointv2.h>
#include <qgsmultilinestringv2.h>
#include <qgsmultipolygonv2.h>
#include <qgspolygonv2.h>
#include <qgslinestringv2.h>
#include <qgsvectorlayer.h>

class QgsGlobeFeatureUtils
{
public:
static inline QgsPointV2 qgsPointFromPoint( const osg::Vec3d& pt )
{
return QgsPointV2( QgsWKBTypes::PointZ, pt.x(), pt.y(), pt.z() );
}

static inline osg::Vec3d pointFromQgsPoint( const QgsPointV2& pt )
{
return osg::Vec3d( pt.x(), pt.y(), pt.z() );
}

static inline osgEarth::Features::LineString* lineStringFromQgsLineString( const QgsLineStringV2* lineString )
{
QgsLineStringV2* linearString = lineString->curveToLine();
osgEarth::Features::LineString* retLineString = new osgEarth::Features::LineString();
for ( int iVtx = 0, nVtx = linearString->vertexCount(); iVtx < nVtx; ++iVtx )
{
retLineString->push_back( pointFromQgsPoint( linearString->vertexAt( QgsVertexId( 0, 0, iVtx ) ) ) );
}
delete linearString;
return retLineString;
}

static inline osgEarth::Features::Polygon* polygonFromQgsPolygon( const QgsPolygonV2* polygon )
{
QgsPolygonV2* linearPolygon = polygon->toPolygon();
// a ring for osg earth is open (first point != last point)
// an outer ring is oriented CCW, an inner ring is oriented CW
osgEarth::Features::Polygon* retPoly = new osgEarth::Features::Polygon();

// the outer ring
for ( int iVtx = 0, nVtx = linearPolygon->vertexCount( 0, 0 ); iVtx < nVtx; ++iVtx )
{
retPoly->push_back( pointFromQgsPoint( linearPolygon->vertexAt( QgsVertexId( 0, 0, iVtx ) ) ) );
}
retPoly->rewind( osgEarth::Symbology::Ring::ORIENTATION_CCW );

for ( int iRing = 1, nRings = linearPolygon->ringCount( 0 ); iRing < nRings; ++iRing )
{
osgEarth::Features::Ring* innerRing = new osgEarth::Features::Ring();
for ( int iVtx = 0, nVtx = linearPolygon->vertexCount( 0, iRing ); iVtx < nVtx; ++iVtx )
{
innerRing->push_back( pointFromQgsPoint( linearPolygon->vertexAt( QgsVertexId( 0, iRing, iVtx ) ) ) );
}
innerRing->rewind( osgEarth::Symbology::Ring::ORIENTATION_CW );
retPoly->getHoles().push_back( osg::ref_ptr<osgEarth::Features::Ring>( innerRing ) );
}
delete linearPolygon;
return retPoly;
}

static inline osgEarth::Features::Geometry* geometryFromQgsGeometry( const QgsGeometry& geom )
{
#if 0
// test srid
std::cout << "geom = " << &geom << std::endl;
std::cout << "wkb = " << geom.asWkb() << std::endl;
uint32_t srid;
memcpy( &srid, geom.asWkb() + 2 + sizeof( void* ), sizeof( uint32_t ) );
std::cout << "srid = " << srid << std::endl;
#endif

switch ( QgsWKBTypes::flatType( geom.geometry()->wkbType() ) )
{
case QgsWKBTypes::Point:
{
osgEarth::Features::PointSet* pointSet = new osgEarth::Features::PointSet();
pointSet->push_back( pointFromQgsPoint( *static_cast<QgsPointV2*>( geom.geometry() ) ) );
return pointSet;
}

case QGis::WKBMultiPoint:
{
osgEarth::Features::PointSet* pointSet = new osgEarth::Features::PointSet();
QgsMultiPointV2* multiPoint = static_cast<QgsMultiPointV2*>( geom.geometry() );
for ( int i = 0, n = multiPoint->numGeometries(); i < n; ++i )
{
pointSet->push_back( pointFromQgsPoint( *static_cast<QgsPointV2*>( multiPoint->geometryN( i ) ) ) );
}
return pointSet;
}

case QgsWKBTypes::LineString:
case QgsWKBTypes::CircularString:
case QgsWKBTypes::CompoundCurve:
{
return lineStringFromQgsLineString( static_cast<QgsLineStringV2*>( geom.geometry() ) );
}

case QgsWKBTypes::MultiLineString:
{
osgEarth::Features::MultiGeometry* multiGeometry = new osgEarth::Features::MultiGeometry();
QgsMultiLineStringV2* multiLineString = static_cast<QgsMultiLineStringV2*>( geom.geometry() );
for ( int i = 0, n = multiLineString->numGeometries(); i < n; ++i )
{
multiGeometry->getComponents().push_back( lineStringFromQgsLineString( static_cast<QgsLineStringV2*>( multiLineString->geometryN( i ) ) ) );
}
return multiGeometry;
}

case QgsWKBTypes::Polygon:
case QgsWKBTypes::CurvePolygon:
{
return polygonFromQgsPolygon( static_cast<QgsPolygonV2*>( geom.geometry() ) );
}

case QgsWKBTypes::MultiPolygon:
{
osgEarth::Features::MultiGeometry* multiGeometry = new osgEarth::Features::MultiGeometry();
QgsMultiPolygonV2* multiPolygon = static_cast<QgsMultiPolygonV2*>( geom.geometry() );
for ( int i = 0, n = multiPolygon->numGeometries(); i < n; ++i )
{
multiGeometry->getComponents().push_back( polygonFromQgsPolygon( static_cast<QgsPolygonV2*>( multiPolygon->geometryN( i ) ) ) );
}
return multiGeometry;
}

default:
break;
}
return 0;
}

static osgEarth::Features::Feature* featureFromQgsFeature( QgsVectorLayer* layer, QgsFeature& feat )
{
osgEarth::Features::Geometry* nGeom = geometryFromQgsGeometry( *feat.geometry() );
osgEarth::Features::Feature* retFeat = new osgEarth::Features::Feature( nGeom, 0, osgEarth::Style(), feat.id() );

const QgsFields& fields = layer->pendingFields();
const QgsAttributes& attrs = feat.attributes();

for ( int idx = 0, numFlds = fields.size(); idx < numFlds; ++idx )
{
setFeatureField( retFeat, fields.at( idx ), attrs[idx] );
}
retFeat->setUserValue( "qgisLayerId", layer->id().toStdString() );

return retFeat;
}

static void setFeatureField( osgEarth::Features::Feature* feature, const QgsField& field, const QVariant& value )
{
std::string name = field.name().toStdString();
switch ( field.type() )
{
case QVariant::Bool:
if ( !value.isNull() )
feature->set( name, value.toBool() );
else
feature->setNull( name, osgEarth::Features::ATTRTYPE_BOOL );

break;

case QVariant::Int:
case QVariant::UInt:
case QVariant::LongLong:
case QVariant::ULongLong:
if ( !value.isNull() )
feature->set( name, value.toInt() );
else
feature->setNull( name, osgEarth::Features::ATTRTYPE_INT );

break;

case QVariant::Double:
if ( !value.isNull() )
feature->set( name, value.toDouble() );
else
feature->setNull( name, osgEarth::Features::ATTRTYPE_DOUBLE );

break;

case QVariant::Char:
case QVariant::String:
default:
if ( !value.isNull() )
feature->set( name, value.toString().toStdString() );
else
feature->setNull( name, osgEarth::Features::ATTRTYPE_STRING );

break;
}
}

static osgEarth::Features::FeatureSchema schemaForFields( const QgsFields& fields )
{
osgEarth::Features::FeatureSchema schema;

for ( int idx = 0, numFlds = fields.size(); idx < numFlds; ++idx )
{
const QgsField& fld = fields.at( idx );
std::string name = fld.name().toStdString();

switch ( fld.type() )
{
case QVariant::Bool:
schema.insert( std::make_pair( name, osgEarth::Features::ATTRTYPE_BOOL ) );
break;

case QVariant::Int:
case QVariant::UInt:
case QVariant::LongLong:
case QVariant::ULongLong:
schema.insert( std::make_pair( name, osgEarth::Features::ATTRTYPE_INT ) );
break;

case QVariant::Double:
schema.insert( std::make_pair( name, osgEarth::Features::ATTRTYPE_DOUBLE ) );
break;

case QVariant::Char:
case QVariant::String:
default:
schema.insert( std::make_pair( name, osgEarth::Features::ATTRTYPE_STRING ) );
break;
}
}
return schema;
}
};

#endif // QGSGLOBEFEATUREUTILS_H
1,900 changes: 903 additions & 997 deletions src/plugins/globe/globe_plugin.cpp

Large diffs are not rendered by default.

330 changes: 123 additions & 207 deletions src/plugins/globe/globe_plugin.h
Original file line number Diff line number Diff line change
Expand Up @@ -19,171 +19,165 @@
#ifndef QGS_GLOBE_PLUGIN_H
#define QGS_GLOBE_PLUGIN_H

#include "qgsconfig.h"
#include "qgisplugin.h"
#include "qgsosgearthtilesource.h"
#include "globe_plugin_dialog.h"
#include <qgisplugin.h>
#include <QObject>
#include <osgViewer/Viewer>
#include <osgEarth/MapNode>
#include <osgEarth/ImageLayer>
#include <osgEarthUtil/EarthManipulator>
#ifndef HAVE_OSGEARTHQT //use backported controls if osgEarth <= 2.1
#define USE_BACKPORTED_CONTROLS
#endif
#ifdef USE_BACKPORTED_CONTROLS
#include "osgEarthUtil/Controls"
using namespace osgEarth::Util::Controls21;
#else
#include <osgEarthUtil/Controls>
using namespace osgEarth::Util::Controls;
#endif
#ifdef HAVE_OSGEARTH_ELEVATION_QUERY
#include <osgEarth/ElevationQuery>
#include <osgEarthUtil/ObjectLocator>
#else
#include <osgEarthUtil/ElevationManager>
#include <osgEarthUtil/ObjectPlacer>
#endif
#include <osg/ref_ptr>
#include <osgEarth/Version>

#if 0
#include <iostream>
#endif
#include "qgsglobeinterface.h"
#include "qgsglobeplugindialog.h"
#include "qgsrectangle.h"

class QAction;
class QToolBar;
class QgisInterface;
class QDateTime;
class QDockWidget;
class QgsAnnotationItem;
class QgsBillBoardItem;
class QgsGlobeAnnotation;
class QgsGlobeLayerPropertiesFactory;
class QgsGlobeInterface;
class QgsGlobePluginDialog;
class QgsGlobeWidget;
class QgsMapLayer;
class QgsPoint;
class QgsRectangle;
class QgsGlobeFrustumHighlightCallback;
class QgsGlobeFeatureIdentifyCallback;
class QgsGlobeTileSource;
class QgsGlobeVectorLayerConfig;

namespace osg
{
class Group;
class Vec3d;
}
namespace osgViewer { class Viewer; }

namespace osgEarth
{
class GeoPoint;
class GeoExtent;
class ImageLayer;
class MapNode;
namespace Annotation { class PlaceNode; }
namespace QtGui { class ViewerWidget; }
namespace Util
{
class FeatureHighlightCallback;
class FeatureQueryTool;
class SkyNode;
class VerticalScale;
namespace Controls
{
class Control;
class ControlEventHandler;
class LabelControl;
}
}
}

namespace osgEarth { namespace QtGui { class ViewerWidget; } }
namespace osgEarth { namespace Util { class SkyNode; class VerticalScale; } }

class GlobePlugin : public QObject, public QgisPlugin
class GLOBE_EXPORT GlobePlugin : public QObject, public QgisPlugin
{
Q_OBJECT

public:
explicit GlobePlugin( QgisInterface* theQgisInterface );
virtual ~GlobePlugin();
GlobePlugin( QgisInterface* theQgisInterface );
~GlobePlugin();

public slots:
//! offer an interface for python plugins
virtual QgsPluginInterface* pluginInterface();
//! init the gui
virtual void initGui() override;
//! Show the dialog box
void run();
//! Show the settings dialog box
void settings();
//! Reset globe
void reset();
//! unload the plugin
void unload() override;
//! show the help document
void help();

//! Called when a new set of image layers has been received
void imageLayersChanged();
//! Called when a new set of elevation layers has been received
void elevationLayersChanged();
//! Set a different base map (QString::null will disable the base map)
void setBaseMap( QString url );
//! Called when the extents of the map change
void setSkyParameters( bool enabled, const QDateTime& dateTime, bool autoAmbience );
//! Called when the extents of the map change
void extentsChanged();
//! Sync globe extent to mapCanavas
void syncExtent();
#if OSGEARTH_VERSION_GREATER_OR_EQUAL( 2, 5, 0 )
//! Set vertical scale
void setVerticalScale( double scale );
#endif
//! Enable or disable frustum highlight
void enableFrustumHighlight( bool statu );
//! Enable or disable feature identification
void enableFeatureIdentification( bool status );

//! called when a project has been read successfully
void projectReady();
//! called when a new project has been created successfully
void blankProjectReady();
//! called when the globe window is closed
void setGlobeNotRunning();
//! set the globe coordinates of a user right-click on the globe
void setSelectedCoordinates( osg::Vec3d coords );
void setSelectedCoordinates( const osg::Vec3d& coords );
//! get a coordinates vector
osg::Vec3d getSelectedCoordinates();
//! prints the ccordinates in a QMessageBox
void showSelectedCoordinates();
//! emits signal with current mouse coordinates
void showCurrentCoordinates( double lon, double lat );
void showCurrentCoordinates( const osgEarth::GeoPoint &geoPoint );
//! get longitude of user right click
double getSelectedLon();
double getSelectedLon() const { return mSelectedLon; }
//! get latitude of user right click
double getSelectedLat();
double getSelectedLat() const { return mSelectedLat; }
//! get elevation of user right click
double getSelectedElevation();

//! Place an OSG model on the globe
void placeNode( osg::Node* node, double lat, double lon, double alt = 0.0 );
double getSelectedElevation() { return mSelectedElevation; }

//! Get the OSG viewer
osgViewer::Viewer* osgViewer() { return mOsgViewer; }
//! Get OSG map node
osgEarth::MapNode* mapNode() { return mMapNode; }

//! Recursive copy folder
static void copyFolder( QString sourceFolder, QString destFolder );
QgisInterface* qgisIface() const { return mQGisIface; }

private:
//! Set HTTP proxy settings
void setupProxy();
//! Setup map
void setupMap();
//! Setup map controls
void setupControls();
public slots:
void run();
void updateLayers();
void showSettings();
void syncExtent();

private://! Checks if the globe is open
//! Pointer to the QGIS interface object
private:
QgisInterface *mQGisIface;
//!pointer to the qaction for this plugin
QAction * mQActionPointer;
//!pointer to the qaction for this plugin
QAction * mQActionSettingsPointer;
QAction * mQActionUnload;
//! OSG Viewer
osgViewer::Viewer* mOsgViewer;
//! QT viewer widget

QAction* mActionToggleGlobe;
osgEarth::QtGui::ViewerWidget* mViewerWidget;
//! Settings Dialog
QgsGlobePluginDialog *mSettingsDialog;
//! OSG root node
osg::Group* mRootNode;
//! Map node
osgEarth::MapNode* mMapNode;
//! Base layer
osg::ref_ptr<osgEarth::ImageLayer> mBaseLayer;
//! Sky node
QgsGlobeWidget* mDockWidget;
QgsGlobePluginDialog* mSettingsDialog;

QgsGlobeInterface mGlobeInterface;
QString mBaseLayerUrl;
QList<QgsGlobePluginDialog::LayerDataSource> mImagerySources;
QList<QgsGlobePluginDialog::LayerDataSource> mElevationSources;
double mSelectedLat, mSelectedLon, mSelectedElevation;

osg::ref_ptr<osgViewer::Viewer> mOsgViewer;
osg::ref_ptr<osgEarth::MapNode> mMapNode;
osg::ref_ptr<osg::Group> mRootNode;
osg::ref_ptr<osgEarth::Util::SkyNode> mSkyNode;
#if OSGEARTH_VERSION_GREATER_OR_EQUAL( 2, 5, 0 )
osg::ref_ptr<osgEarth::ImageLayer> mBaseLayer;
osg::ref_ptr<osgEarth::ImageLayer> mQgisMapLayer;
osg::ref_ptr<QgsGlobeTileSource> mTileSource;
QMap<QString, QgsRectangle> mLayerExtents;
osg::ref_ptr<osgEarth::Util::VerticalScale> mVerticalScale;
#endif
//! QGIS maplayer
osgEarth::ImageLayer* mQgisMapLayer;
//! Tile source
osgEarth::Drivers::QgsOsgEarthTileSource* mTileSource;
//! Control Canvas
ControlCanvas* mControlCanvas;
#ifdef HAVE_OSGEARTH_ELEVATION_QUERY
//! Elevation manager
osgEarth::ElevationQuery* mElevationManager;
//! Object placer
osgEarth::Util::ObjectLocator* mObjectPlacer;
#else
//! Elevation manager
osgEarth::Util::ElevationManager* mElevationManager;
//! Object placer
osgEarth::Util::ObjectPlacer* mObjectPlacer;
#endif
//! tracks if the globe is open
bool mIsGlobeRunning;
//! coordinates of the right-clicked point on the globe
double mSelectedLat, mSelectedLon, mSelectedElevation;

#if 0
std::streambuf *mCoutRdBuf, *mCerrRdBuf;
//! Creates additional pages in the layer properties for adjusting 3D properties
QgsGlobeLayerPropertiesFactory* mLayerPropertiesFactory;
osg::ref_ptr<QgsGlobeFrustumHighlightCallback> mFrustumHighlightCallback;
osg::ref_ptr<QgsGlobeFeatureIdentifyCallback> mFeatureQueryToolIdentifyCb;
// TODO: How to port highlight to 2.7.0?
#if OSGEARTH_VERSION_LESS_THAN(2, 7, 0)
osg::ref_ptr<osgEarth::Util::FeatureHighlightCallback> mFeatureQueryToolHighlightCb;
#endif
osg::ref_ptr<osgEarth::Util::FeatureQueryTool> mFeatureQueryTool;
osg::ref_ptr<osgEarth::Util::Controls::LabelControl> mStatsLabel;

osg::Group* mAnnotationsGroup;
QMap<QString, QMap<QgsBillBoardItem*, osg::ref_ptr<osgEarth::Annotation::PlaceNode> > > mAnnotations;

void setupProxy();
void addControl( osgEarth::Util::Controls::Control* control, int x, int y, int w, int h, osgEarth::Util::Controls::ControlEventHandler* handler );
void addImageControl( const std::string &imgPath, int x, int y, osgEarth::Util::Controls::ControlEventHandler* handler = 0 );
void addModelLayer( QgsVectorLayer* mapLayer , QgsGlobeVectorLayerConfig *layerConfig );
void setupControls();
void applyProjectSettings();

private slots:
void setGlobeEnabled( bool enabled );
void reset();
void projectRead();
void applySettings();
void layerChanged( QgsMapLayer* mapLayer = 0 );
void addBillboard( QgsBillBoardItem* item );
void removeBillboard( QgsBillBoardItem* item );
void refreshQGISMapLayer( QgsRectangle rect = QgsRectangle() );
void updateTileStats( int queued, int tot );

signals:
//! emits current mouse position
Expand All @@ -192,82 +186,4 @@ class GlobePlugin : public QObject, public QgisPlugin
void newCoordinatesSelected( const QgsPoint & p );
};

class FlyToExtentHandler : public osgGA::GUIEventHandler
{
public:
explicit FlyToExtentHandler( GlobePlugin* globe ) : mGlobe( globe ) { }

bool handle( const osgGA::GUIEventAdapter& ea, osgGA::GUIActionAdapter& aa ) override;

private:
GlobePlugin* mGlobe;
};

// An event handler that will print out the coordinates at the clicked point
#ifdef HAVE_OSGEARTH_ELEVATION_QUERY
#else
class QueryCoordinatesHandler : public osgGA::GUIEventHandler
{
public:
QueryCoordinatesHandler( GlobePlugin* globe, osgEarth::Util::ElevationManager* elevMan,
const osgEarth::SpatialReference* mapSRS )
: mGlobe( globe ), _mapSRS( mapSRS ), _elevMan( elevMan ) { }

bool handle( const osgGA::GUIEventAdapter& ea, osgGA::GUIActionAdapter& aa );

virtual osg::Vec3d getCoords( float x, float y, osgViewer::View* view, bool getElevation = false );

private:
GlobePlugin* mGlobe;
osg::ref_ptr<const SpatialReference> _mapSRS;
osg::ref_ptr<osgEarth::Util::ElevationManager> _elevMan;
};
#endif


class KeyboardControlHandler : public osgGA::GUIEventHandler
{
public:
explicit KeyboardControlHandler( osgEarth::Util::EarthManipulator* manip ) : _manip( manip ) { }

bool handle( const osgGA::GUIEventAdapter& ea, osgGA::GUIActionAdapter& aa ) override;

private:
osg::observer_ptr<osgEarth::Util::EarthManipulator> _manip;
};


namespace osgEarth
{
namespace Util
{
#ifdef USE_BACKPORTED_CONTROLS
namespace Controls21
#else
namespace Controls
#endif
{
class NavigationControlHandler : public ControlEventHandler
{
public:
virtual void onMouseDown( class Control* control, int mouseButtonMask ) { Q_UNUSED( control ); Q_UNUSED( mouseButtonMask ); }
virtual void onClick( class Control* control, int mouseButtonMask, const osgGA::GUIEventAdapter& ea, osgGA::GUIActionAdapter& aa ) { Q_UNUSED( control ); Q_UNUSED( mouseButtonMask ); Q_UNUSED( ea ); Q_UNUSED( aa ); }
virtual void onClick( class Control* control, int mouseButtonMask ) override { Q_UNUSED( control ); Q_UNUSED( mouseButtonMask ); }
};

class NavigationControl : public ImageControl
{
public:
explicit NavigationControl( osg::Image* image = nullptr ) : ImageControl( image ), _mouse_down_event( nullptr ) {}

protected:
virtual bool handle( const osgGA::GUIEventAdapter& ea, osgGA::GUIActionAdapter& aa, ControlContext& cx ) override;

private:
osg::ref_ptr<const osgGA::GUIEventAdapter> _mouse_down_event;
};
}
}
}

#endif // QGS_GLOBE_PLUGIN_H
4 changes: 2 additions & 2 deletions src/plugins/globe/globe_plugin.qrc
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
<RCC>
<qresource prefix="/globe/" >
<qresource prefix="/globe">
<file alias="globe.png">images/globe.png</file>
<file alias="icon.svg">images/icon.svg</file>
</qresource>
</RCC>

700 changes: 0 additions & 700 deletions src/plugins/globe/globe_plugin_dialog.cpp

This file was deleted.

104 changes: 0 additions & 104 deletions src/plugins/globe/globe_plugin_dialog.h

This file was deleted.

782 changes: 0 additions & 782 deletions src/plugins/globe/globe_plugin_dialog_guibase.ui

This file was deleted.

Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file modified src/plugins/globe/images/gui/button-background.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added src/plugins/globe/images/gui/settings.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file modified src/plugins/globe/images/gui/zoom-in.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file modified src/plugins/globe/images/gui/zoom-out.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
143 changes: 143 additions & 0 deletions src/plugins/globe/images/icon.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
92 changes: 0 additions & 92 deletions src/plugins/globe/osgEarthQt/Common

This file was deleted.

91 changes: 0 additions & 91 deletions src/plugins/globe/osgEarthQt/ViewerWidget

This file was deleted.

167 changes: 0 additions & 167 deletions src/plugins/globe/osgEarthQt/ViewerWidget.cpp

This file was deleted.

Loading