Initial commit
This commit is contained in:
commit
b7d90b9afe
16245 files changed
+3396666
No files matched your search
@@ -0,0 +1,314 @@
|
||||
|
||||
/**
|
||||
**
|
||||
** @RDE_HEADER@
|
||||
** Implementation of base class for rubberband frame handles
|
||||
** $Id$
|
||||
** $HeadURL$
|
||||
** $Author$
|
||||
**
|
||||
** -----------------------------------------------------------------------------------------------
|
||||
**
|
||||
** Hardware-Environment: Intel-PC
|
||||
** Software-Environment: Windows 7, Qt 5.4. ArcGIS 10.2.5
|
||||
**
|
||||
** Language ........: C++ 11
|
||||
**
|
||||
** -----------------------------------------------------------------------------------------------
|
||||
**
|
||||
** Author ...........: Jörg Turla, SPD G, Tel. 3132
|
||||
**
|
||||
** -----------------------------------------------------------------------------------------------
|
||||
**
|
||||
** Notes .........:
|
||||
**
|
||||
** 27.03.2015, JT : First edition for use with Qt5
|
||||
**
|
||||
** -----------------------------------------------------------------------------------------------
|
||||
*/
|
||||
|
||||
#include "rubberband_frame_handle.h"
|
||||
|
||||
#include <MathUtils/math_const.h>
|
||||
|
||||
#include <arcgis/Map.h>
|
||||
#include <arcgis/MapGraphicsView.h>
|
||||
|
||||
#include <QtWidgets/QGraphicsScene>
|
||||
|
||||
|
||||
namespace SituationMap { namespace RB
|
||||
{
|
||||
|
||||
|
||||
|
||||
|
||||
static QGraphicsPolygonItem * createFrameGraphic( QGraphicsScene * mapScene, qreal zBufferValue )
|
||||
{
|
||||
if (mapScene != nullptr)
|
||||
{
|
||||
QGraphicsPolygonItem * frameSymbol = new QGraphicsPolygonItem();
|
||||
|
||||
frameSymbol -> setZValue( zBufferValue );
|
||||
frameSymbol -> setFlags( QGraphicsItem::ItemIgnoresTransformations );
|
||||
|
||||
mapScene -> addItem( frameSymbol );
|
||||
|
||||
return frameSymbol;
|
||||
}
|
||||
return nullptr;
|
||||
} /* createFrameGraphic */
|
||||
|
||||
|
||||
class FramePoint : public QPointF
|
||||
{
|
||||
public:
|
||||
Q_DECL_CONSTEXPR FramePoint(const QPointF &p) : QPointF(p) {}
|
||||
Q_DECL_CONSTEXPR FramePoint(qreal x, qreal y) : QPointF(x, y) {}
|
||||
|
||||
FramePoint rotate(const QPointF ¢er, qreal sinA, qreal cosA) const
|
||||
{
|
||||
qreal cx = x() - center.x();
|
||||
qreal cy = y() - center.y();
|
||||
qreal px = cx*cosA - cy*sinA + center.x();
|
||||
qreal py = cy*cosA + cx*sinA + center.y();
|
||||
return FramePoint(px, py);
|
||||
} // rotate( const QPointF & center, qreal sin qreal cosA )
|
||||
|
||||
FramePoint rotate(const RubberbandHandle::RubberbandCoordinate & center, qreal sinA, qreal cosA) const
|
||||
{
|
||||
return rotate(QPointF(center._mapCoordinate.x(), center._mapCoordinate.y()), sinA, cosA);
|
||||
} /* rotate */
|
||||
|
||||
FramePoint rotate(qreal sinA, qreal cosA) const
|
||||
{
|
||||
return rotate(QPointF(), sinA, cosA);
|
||||
} // rotate( const QPointF & center, qreal sin qreal cosA )
|
||||
|
||||
|
||||
}; /* FramePoint */
|
||||
|
||||
|
||||
RubberbandFrameHandle::RubberbandFrameHandle( Esri::ArcGISRuntime::MapGraphicsView * mapView
|
||||
, QGraphicsScene * scene
|
||||
, qreal sceneMargin )
|
||||
: RubberbandHandle(mapView,scene)
|
||||
, _frameSymbol(nullptr)
|
||||
, _frameSceneMargin(sceneMargin)
|
||||
, _frameRotationSin(0)
|
||||
, _frameRotationCos(1)
|
||||
, _frameWidth(0)
|
||||
, _frameHeight(0)
|
||||
, _frameCenterCoordinate()
|
||||
, _mapRotateSin(0)
|
||||
, _mapRotateCos(1)
|
||||
, _drawDisabled(false)
|
||||
, _frameLineHandleList()
|
||||
{
|
||||
qreal mapRotatePhi = _mapView->mapRotation() * MathConst::pi / 180.0;
|
||||
|
||||
_mapRotateSin = sin(mapRotatePhi);
|
||||
_mapRotateCos = cos(mapRotatePhi);
|
||||
|
||||
zBufferPlane( ZBufferPlane::FrameHandle );
|
||||
|
||||
_frameSymbol = createFrameGraphic( _scene, _zBufferValue );
|
||||
if (_drawDisabled) _frameSymbol->hide();
|
||||
updateGraphic();
|
||||
} /* RubberbandFrameHandle::RubberbandFrameHandle */
|
||||
|
||||
|
||||
|
||||
RubberbandFrameHandle::~RubberbandFrameHandle()
|
||||
{
|
||||
if (_scene)
|
||||
{
|
||||
if (_frameSymbol)
|
||||
{
|
||||
_scene->removeItem(_frameSymbol);
|
||||
delete _frameSymbol;
|
||||
}
|
||||
}
|
||||
_frameSymbol = nullptr;
|
||||
} /* RubberbandFrameHandle::~RubberbandFrameHandle */
|
||||
|
||||
|
||||
void RubberbandFrameHandle::buildFrameVertexCoordinates()
|
||||
{
|
||||
auto length = [](qreal x, qreal y) -> qreal { return sqrt(x*x+y*y); };
|
||||
|
||||
QPointF center( _frameCenterCoordinate._mapCoordinate.x(), _frameCenterCoordinate._mapCoordinate.y());
|
||||
RubberbandCoordinate marginP( _mapView, _frameCenterCoordinate._sceneCoordinate+QPointF(_frameSceneMargin,0) );
|
||||
qreal margin = length( marginP._mapCoordinate.x()-center.x(), marginP._mapCoordinate.y()-center.y() );
|
||||
|
||||
QPointF vertex[4];
|
||||
|
||||
qreal frameWidth2 = _frameWidth * 0.5;
|
||||
qreal frameHeight2 = _frameHeight * 0.5;
|
||||
|
||||
vertex[0] = QPointF( center.x() - frameWidth2 - margin, center.y() - frameHeight2 - margin );
|
||||
vertex[1] = QPointF( center.x() + frameWidth2 + margin, center.y() - frameHeight2 - margin );
|
||||
vertex[2] = QPointF( center.x() + frameWidth2 + margin, center.y() + frameHeight2 + margin );
|
||||
vertex[3] = QPointF( center.x() - frameWidth2 - margin, center.y() + frameHeight2 + margin );
|
||||
|
||||
for (int i = 0; i < 4; ++i)
|
||||
{
|
||||
const FramePoint & v = FramePoint(vertex[i]).rotate(_frameCenterCoordinate, -_frameRotationSin, _frameRotationCos );
|
||||
_frameVertexCoordinate[i] = RubberbandCoordinate(_mapView, convert(v, _mapView->map()->spatialReference()));
|
||||
}
|
||||
// Now we have the vertex coordinates in map coordinate system
|
||||
|
||||
} /* RubberbandFrameHandle::buildFrameVertexCoordinates */
|
||||
|
||||
|
||||
void RubberbandFrameHandle::adjustCoordinates()
|
||||
{
|
||||
qreal mapRotatePhi = _mapView->mapRotation() * MathConst::pi / 180.0;
|
||||
|
||||
_mapRotateSin = sin(mapRotatePhi);
|
||||
_mapRotateCos = cos(mapRotatePhi);
|
||||
|
||||
_frameCenterCoordinate.mapToScene(_mapView);
|
||||
|
||||
buildFrameVertexCoordinates();
|
||||
updateFramePolygonItem();
|
||||
|
||||
emit adjusted();
|
||||
|
||||
} /* RubberbandFrameHandle::adjustCoordinates */
|
||||
|
||||
|
||||
void RubberbandFrameHandle::adjustWindow( const QRectF& )
|
||||
{
|
||||
onDo_adjustCoordinates();
|
||||
} /* RubberbandFrameHandle::adjustWindow */
|
||||
|
||||
|
||||
void RubberbandFrameHandle::updateFrameShape( const QVector<RubberbandCoordinate> & vertexList, qreal sinA, qreal cosA )
|
||||
{
|
||||
DEBUG_LOG(_logger) << LOGFUNCTION << "( const QVector<RubberbandCoordinate> & vertexList, qreal sinA, qreal cosA )";
|
||||
|
||||
qreal sinPhi = sinA * _mapRotateCos - cosA * _mapRotateSin; // Addition-Theorem get rotation of the frame without map rotation
|
||||
qreal cosPhi = cosA * _mapRotateCos + sinA * _mapRotateSin;
|
||||
|
||||
qreal minX = std::numeric_limits<qreal>::infinity();
|
||||
qreal maxX = -std::numeric_limits<qreal>::infinity();
|
||||
qreal minY = std::numeric_limits<qreal>::infinity();
|
||||
qreal maxY = -std::numeric_limits<qreal>::infinity();
|
||||
|
||||
for (const RubberbandCoordinate & vertex : vertexList)
|
||||
{
|
||||
// eliminate rotation from vertex scene coordinate
|
||||
FramePoint xy = FramePoint(vertex._sceneCoordinate.x(),vertex._sceneCoordinate.y()).rotate( -sinPhi, cosPhi );
|
||||
qreal x = xy.x();
|
||||
qreal y = xy.y();
|
||||
|
||||
if (minX > x) minX = x;
|
||||
if (minY > y) minY = y;
|
||||
if (maxX < x) maxX = x;
|
||||
if (maxY < y) maxY = y;
|
||||
}
|
||||
|
||||
_frameRotationSin = sinA;
|
||||
_frameRotationCos = cosA;
|
||||
|
||||
// calculate rotated coordinates (map rotation) of (minX,minY), (maxX,maxY) and frame scene center
|
||||
FramePoint frameSceneV0 = FramePoint( minX , minY ).rotate( sinPhi, cosPhi );
|
||||
FramePoint frameSceneVW = FramePoint( maxX , minY ).rotate( sinPhi, cosPhi );
|
||||
FramePoint frameSceneVH = FramePoint( minX , maxY ).rotate( sinPhi, cosPhi );
|
||||
FramePoint frameSceneCenter = FramePoint( (minX+maxX)*0.5, (minY+maxY)*0.5 ).rotate( sinPhi, cosPhi );
|
||||
|
||||
_frameCenterCoordinate.updateSceneCoordinate( _mapView, frameSceneCenter );
|
||||
|
||||
// Calculate map coordinates of bounding rectangle
|
||||
RubberbandCoordinate frameV0( _mapView, QPointF(frameSceneV0.x(),frameSceneV0.y()) );
|
||||
RubberbandCoordinate frameVW( _mapView, QPointF(frameSceneVW.x(),frameSceneVW.y()) );
|
||||
RubberbandCoordinate frameVH( _mapView, QPointF(frameSceneVH.x(),frameSceneVH.y()) );
|
||||
|
||||
|
||||
auto length = []( qreal x1, qreal y1, qreal x2, qreal y2 ) -> qreal
|
||||
{
|
||||
qreal dx = x2-x1;
|
||||
qreal dy = y2-y1;
|
||||
return sqrt(dx*dx+dy*dy);
|
||||
};
|
||||
|
||||
// get frame width and height in map coordinates
|
||||
|
||||
_frameWidth = length( frameV0._mapCoordinate.x(), frameV0._mapCoordinate.y(), frameVW._mapCoordinate.x(), frameVW._mapCoordinate.y() );
|
||||
_frameHeight = length( frameV0._mapCoordinate.x(), frameV0._mapCoordinate.y(), frameVH._mapCoordinate.x(), frameVH._mapCoordinate.y() );
|
||||
|
||||
buildFrameVertexCoordinates();
|
||||
updateFramePolygonItem();
|
||||
|
||||
} /* RubberbandFrameHandle::updateFrameShape */
|
||||
|
||||
|
||||
void RubberbandFrameHandle::updateFrameShape()
|
||||
{
|
||||
DEBUG_LOG(_logger) << LOGFUNCTION;
|
||||
|
||||
buildFrameVertexCoordinates();
|
||||
updateFramePolygonItem();
|
||||
|
||||
} /* RubberbandFrameHandle::updateFrameShape */
|
||||
|
||||
|
||||
void RubberbandFrameHandle::updateFramePolygonItem()
|
||||
{
|
||||
QPolygonF framePolygon;
|
||||
|
||||
framePolygon.reserve( 4 );
|
||||
for (auto vertex : _frameVertexCoordinate)
|
||||
{
|
||||
framePolygon.append(vertex.mapToScene(_mapView));
|
||||
}
|
||||
framePolygon.append(_frameVertexCoordinate[0]._sceneCoordinate);
|
||||
|
||||
_frameSymbol->setPolygon(framePolygon);
|
||||
|
||||
} /* RubberbandFrameHandle::updateFramePolygonItem */
|
||||
|
||||
|
||||
void RubberbandFrameHandle::updateGraphic()
|
||||
{
|
||||
if (_frameSymbol)
|
||||
{
|
||||
_frameSymbol -> setPen( QPen(QColor("black"),1,Qt::PenStyle::DashDotLine) );
|
||||
_frameSymbol -> setVisible( _isVisible );
|
||||
|
||||
if (isSelected())
|
||||
_frameSymbol -> setBrush( QBrush(_selectionColor) );
|
||||
else
|
||||
_frameSymbol -> setBrush( QBrush(_fillColor) );
|
||||
}
|
||||
} /* RubberbandFrameHandle::updateGraphic */
|
||||
|
||||
|
||||
void RubberbandFrameHandle::updateCoordinate(const QPointF & scenePosition)
|
||||
{
|
||||
_frameCenterCoordinate.updateSceneCoordinate( _mapView, scenePosition );
|
||||
updateFrameShape();
|
||||
} /* RubberbandFrameHandle::updateCoordinate */
|
||||
|
||||
|
||||
void RubberbandFrameHandle::moveCoordinate(const QPointF & sceneDelta)
|
||||
{
|
||||
_frameCenterCoordinate.updateSceneCoordinate( _mapView, _frameCenterCoordinate._sceneCoordinate+sceneDelta );
|
||||
updateFrameShape();
|
||||
} /* RubberbandFrameHandle::moveCoordinate */
|
||||
|
||||
|
||||
RubberbandHandle::RubberbandCoordinate RubberbandFrameHandle::getCoordinate() const { return _frameCenterCoordinate; }
|
||||
|
||||
|
||||
bool RubberbandFrameHandle::isPositionInside( const QPointF & scenePosition ) const
|
||||
{
|
||||
if (_frameSymbol)
|
||||
{
|
||||
return _frameSymbol->contains( scenePosition );
|
||||
}
|
||||
return false;
|
||||
} /* RubberbandFrameHandle::isPositionInside */
|
||||
|
||||
} } /* namespace SituationMap::RB */
|
||||
Reference in new issue
Block a user