- Add QgsMapToolRegularPolygonCenterCorner and change

QgsMapToolRegularPolygonCenterPoint
- Add QgsMapToolCircle2TangentsPoint
This commit is contained in:
lbartoletti 2017-10-03 14:33:16 +02:00
parent 4c8171d770
commit 0204302aaa
15 changed files with 769 additions and 12 deletions

View File

@ -578,12 +578,14 @@
<file>themes/default/mActionRectangleExtent.svg</file>
<file>themes/default/mActionRectangle3Points.svg</file>
<file>themes/default/mActionRectangleCenter.svg</file>
<file>themes/default/mActionRegularPolygonCenterPoint.svg</file>
<file>themes/default/mActionRegularPolygonCenterCorner.svg</file>
<file>themes/default/mActionRegularPolygon2Points.svg</file>
<file>themes/default/mActionSquareCenter.svg</file>
<file>themes/default/mActionCircle3Tangents.svg</file>
<file>themes/default/mActionAddGeoPackageLayer.svg</file>
<file>icons/qgis_icon.svg</file>
<file>themes/default/mActionCircle2TangentsPoint.svg</file>
<file>themes/default/mActionRegularPolygonCenterPoint.svg</file>
</qresource>
<qresource prefix="/images/tips">
<file alias="symbol_levels.png">qgis_tips/symbol_levels.png</file>

View File

@ -0,0 +1,116 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
height="24"
viewBox="0 0 24 24"
width="24"
version="1.1"
id="svg4016"
sodipodi:docname="mActionCircle2TangentsPoint.svg"
inkscape:version="0.92.1 r15371">
<metadata
id="metadata4022">
<rdf:RDF>
<cc:Work
rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
<dc:title />
</cc:Work>
</rdf:RDF>
</metadata>
<defs
id="defs4020" />
<sodipodi:namedview
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1"
objecttolerance="10"
gridtolerance="10"
guidetolerance="10"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:window-width="1680"
inkscape:window-height="991"
id="namedview4018"
showgrid="false"
inkscape:zoom="31.083333"
inkscape:cx="-0.32745931"
inkscape:cy="16.341225"
inkscape:window-x="0"
inkscape:window-y="0"
inkscape:window-maximized="1"
inkscape:current-layer="svg4016"
inkscape:measure-start="7.94638,12.8686"
inkscape:measure-end="4.08579,12.8365" />
<linearGradient
gradientUnits="userSpaceOnUse"
x1="-10"
x2="-10"
y1="15"
y2="21"
id="linearGradient3996">
<stop
offset="0"
stop-color="#555753"
id="stop3992" />
<stop
offset="1"
stop-color="#555753"
stop-opacity="0"
id="stop3994" />
</linearGradient>
<g
id="g4531">
<circle
r="7.430634"
style="fill:none;stroke:#8cbe8c;stroke-width:3.13873196;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
cy="11"
cx="10"
id="path4032" />
<g
transform="translate(33)"
id="g4004">
<rect
height="11"
rx="2.0114901"
width="11"
x="-20"
y="13"
id="rect3998"
style="fill:#c4a000" />
<path
d="m -15,14 v 2.0625 c -0.537663,0.111041 -1.024662,0.383291 -1.375,0.78125 l -1.78125,-1.03125 -0.5,0.875 1.78125,1.03125 C -16.957063,17.966182 -17,18.225145 -17,18.5 c 0,0.274855 0.04294,0.533818 0.125,0.78125 l -1.78125,1.03125 0.5,0.875 1.78125,-1.03125 c 0.352503,0.40042 0.832682,0.670182 1.375,0.78125 V 23 h 1 v -2.0625 c 0.537663,-0.111041 1.024662,-0.383291 1.375,-0.78125 l 1.78125,1.03125 0.5,-0.875 -1.78125,-1.03125 C -12.042937,19.033818 -12,18.774855 -12,18.5 c 0,-0.274855 -0.04294,-0.533818 -0.125,-0.78125 l 1.78125,-1.03125 -0.5,-0.875 -1.78125,1.03125 C -12.977503,16.44333 -13.457682,16.173568 -14,16.0625 V 14 Z m 0.5,3.5 c 0.552,0 1,0.448 1,1 0,0.552 -0.448,1 -1,1 -0.552,0 -1,-0.448 -1,-1 0,-0.552 0.448,-1 1,-1 z"
id="path4000"
inkscape:connector-curvature="0"
style="fill:#fcffff" />
<path
d="m -19,19 9,-0.0096 c 0,0 0,0 0,-2 C -10,14 -11,14 -14.5,14 c -3.5,0 -4.5,0 -4.5,3 0,2 0,2 0,2 z"
id="path4002"
inkscape:connector-curvature="0"
style="opacity:0.3;fill:#fcffff;fill-rule:evenodd" />
</g>
<path
inkscape:connector-curvature="0"
id="path4501"
d="M 3.491401,18.096279 2.1386259,7.9583643"
style="fill:none;stroke:#8c8c8c;stroke-width:3.13899994;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1" />
<path
inkscape:connector-curvature="0"
id="path4501-6"
d="m 11.427835,2.3970039 7.707332,6.723418"
style="fill:none;stroke:#8c8c8c;stroke-width:3.13899994;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1" />
<path
d="M 4.2345845,3.4624663 V 0.46246623 h -3 V 3.4624663 Z"
id="path4008-7"
inkscape:connector-curvature="0"
style="fill:#bebebe;stroke:#8c8c8c;stroke-width:0.99999994" />
</g>
</svg>

After

Width:  |  Height:  |  Size: 4.2 KiB

View File

@ -0,0 +1,122 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
height="24"
viewBox="0 0 24 24"
width="24"
version="1.1"
id="svg4016"
sodipodi:docname="mActionRegularPolygonCenterPoint.svg"
inkscape:version="0.92.1 r15371">
<metadata
id="metadata4022">
<rdf:RDF>
<cc:Work
rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
<dc:title />
</cc:Work>
</rdf:RDF>
</metadata>
<defs
id="defs4020" />
<sodipodi:namedview
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1"
objecttolerance="10"
gridtolerance="10"
guidetolerance="10"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:window-width="1680"
inkscape:window-height="991"
id="namedview4018"
showgrid="false"
inkscape:zoom="31.083333"
inkscape:cx="7.1707899"
inkscape:cy="13.088849"
inkscape:window-x="0"
inkscape:window-y="0"
inkscape:window-maximized="1"
inkscape:current-layer="svg4016"
inkscape:measure-start="7.94638,12.8686"
inkscape:measure-end="4.08579,12.8365" />
<linearGradient
gradientUnits="userSpaceOnUse"
x1="-10"
x2="-10"
y1="15"
y2="21"
id="linearGradient3996">
<stop
offset="0"
stop-color="#555753"
id="stop3992" />
<stop
offset="1"
stop-color="#555753"
stop-opacity="0"
id="stop3994" />
</linearGradient>
<g
id="g4510">
<path
inkscape:transform-center-y="0.064125878"
inkscape:transform-center-x="0.75844594"
d="M 18.756051,5.9746749 19,16.0625 9.4812931,19.411818 3.3544594,11.393987 9.0865748,3.0893753 Z"
inkscape:randomized="0"
inkscape:rounded="0"
inkscape:flatsided="true"
sodipodi:arg2="-0.024177838"
sodipodi:arg1="-0.65249637"
sodipodi:r2="6.9443798"
sodipodi:r1="8.583725"
sodipodi:cy="11.186471"
sodipodi:cx="11.935676"
sodipodi:sides="5"
id="path4494"
style="fill:none;stroke:#8cbe8c;stroke-width:3.13899994;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
sodipodi:type="star" />
<g
transform="translate(33)"
id="g4004">
<rect
height="11"
rx="2.0114901"
width="11"
x="-20"
y="13"
id="rect3998"
style="fill:#c4a000" />
<path
d="m -15,14 v 2.0625 c -0.537663,0.111041 -1.024662,0.383291 -1.375,0.78125 l -1.78125,-1.03125 -0.5,0.875 1.78125,1.03125 C -16.957063,17.966182 -17,18.225145 -17,18.5 c 0,0.274855 0.04294,0.533818 0.125,0.78125 l -1.78125,1.03125 0.5,0.875 1.78125,-1.03125 c 0.352503,0.40042 0.832682,0.670182 1.375,0.78125 V 23 h 1 v -2.0625 c 0.537663,-0.111041 1.024662,-0.383291 1.375,-0.78125 l 1.78125,1.03125 0.5,-0.875 -1.78125,-1.03125 C -12.042937,19.033818 -12,18.774855 -12,18.5 c 0,-0.274855 -0.04294,-0.533818 -0.125,-0.78125 l 1.78125,-1.03125 -0.5,-0.875 -1.78125,1.03125 C -12.977503,16.44333 -13.457682,16.173568 -14,16.0625 V 14 Z m 0.5,3.5 c 0.552,0 1,0.448 1,1 0,0.552 -0.448,1 -1,1 -0.552,0 -1,-0.448 -1,-1 0,-0.552 0.448,-1 1,-1 z"
id="path4000"
inkscape:connector-curvature="0"
style="fill:#fcffff" />
<path
d="m -19,19 9,-0.0096 c 0,0 0,0 0,-2 C -10,14 -11,14 -14.5,14 c -3.5,0 -4.5,0 -4.5,3 0,2 0,2 0,2 z"
id="path4002"
inkscape:connector-curvature="0"
style="opacity:0.3;fill:#fcffff;fill-rule:evenodd" />
</g>
<path
d="m 1.9959781,9.9343162 h 3 v 2.9999998 h -3 z"
id="path4008"
inkscape:connector-curvature="0"
style="fill:#bebebe;stroke:#8c8c8c;stroke-width:0.99999994" />
<path
d="m 10.510724,9.6126005 h 3 v 3.0000005 h -3 z"
id="path4012"
inkscape:connector-curvature="0"
style="fill:#bebebe;stroke:#8c8c8c;stroke-width:1" />
</g>
</svg>

After

Width:  |  Height:  |  Size: 4.3 KiB

View File

@ -42,7 +42,7 @@
id="namedview4018"
showgrid="false"
inkscape:zoom="31.083333"
inkscape:cx="7.1707899"
inkscape:cx="2.0715941"
inkscape:cy="13.088849"
inkscape:window-x="0"
inkscape:window-y="0"
@ -68,7 +68,7 @@
id="stop3994" />
</linearGradient>
<g
id="g4510">
id="g4506">
<path
inkscape:transform-center-y="0.064125878"
inkscape:transform-center-x="0.75844594"
@ -109,7 +109,7 @@
style="opacity:0.3;fill:#fcffff;fill-rule:evenodd" />
</g>
<path
d="m 1.9959781,9.9343162 h 3 v 2.9999998 h -3 z"
d="m 4.6662194,5.7841821 h 3 v 2.9999998 h -3 z"
id="path4008"
inkscape:connector-curvature="0"
style="fill:#bebebe;stroke:#8c8c8c;stroke-width:0.99999994" />

Before

Width:  |  Height:  |  Size: 4.3 KiB

After

Width:  |  Height:  |  Size: 4.3 KiB

View File

@ -135,6 +135,7 @@ SET(QGIS_APP_SRCS
qgsmaptoolcircle2points.cpp
qgsmaptoolcircle3points.cpp
qgsmaptoolcircle3tangents.cpp
qgsmaptoolcircle2tangentspoint.cpp
qgsmaptoolcirclecenterpoint.cpp
qgsmaptooladdellipse.cpp
qgsmaptoolellipsefoci.cpp
@ -149,6 +150,7 @@ SET(QGIS_APP_SRCS
qgsmaptoolsquarecenter.cpp
qgsmaptoolregularpolygon2points.cpp
qgsmaptoolregularpolygoncenterpoint.cpp
qgsmaptoolregularpolygoncentercorner.cpp
composer/qgsattributeselectiondialog.cpp
composer/qgscomposer.cpp
@ -310,6 +312,7 @@ SET (QGIS_APP_MOC_HDRS
qgsmaptoolcircle2points.h
qgsmaptoolcircle3points.h
qgsmaptoolcircle3tangents.h
qgsmaptoolcircle2tangentspoint.h
qgsmaptoolcirclecenterpoint.h
qgsmaptooladdellipse.h
qgsmaptoolellipsefoci.h
@ -324,6 +327,7 @@ SET (QGIS_APP_MOC_HDRS
qgsmaptoolsquarecenter.h
qgsmaptoolregularpolygon2points.h
qgsmaptoolregularpolygoncenterpoint.h
qgsmaptoolregularpolygoncentercorner.h
nodetool/qgsselectedfeature.h
nodetool/qgsnodeeditor.h

View File

@ -338,6 +338,7 @@ Q_GUI_EXPORT extern int qt_defaultDpiX();
#include "qgsmaptoolcircle2points.h"
#include "qgsmaptoolcircle3points.h"
#include "qgsmaptoolcircle3tangents.h"
#include "qgsmaptoolcircle2tangentspoint.h"
#include "qgsmaptoolcirclecenterpoint.h"
#include "qgsmaptoolellipsecenter2points.h"
#include "qgsmaptoolellipsecenterpoint.h"
@ -349,6 +350,7 @@ Q_GUI_EXPORT extern int qt_defaultDpiX();
#include "qgsmaptoolsquarecenter.h"
#include "qgsmaptoolregularpolygon2points.h"
#include "qgsmaptoolregularpolygoncenterpoint.h"
#include "qgsmaptoolregularpolygoncentercorner.h"
#include "qgsmaptooldeletering.h"
#include "qgsmaptooldeletepart.h"
#include "qgsmaptoolfeatureaction.h"
@ -1303,6 +1305,7 @@ QgisApp::~QgisApp()
delete mMapTools.mCircle2Points;
delete mMapTools.mCircle3Points;
delete mMapTools.mCircle3Tangents;
delete mMapTools.mCircle2TangentsPoint;
delete mMapTools.mCircleCenterPoint;
delete mMapTools.mEllipseCenter2Points;
delete mMapTools.mEllipseCenterPoint;
@ -1314,6 +1317,7 @@ QgisApp::~QgisApp()
delete mMapTools.mSquareCenter;
delete mMapTools.mRegularPolygon2Points;
delete mMapTools.mRegularPolygonCenterPoint;
delete mMapTools.mRegularPolygonCenterCorner;
delete mpMaptip;
delete mpGpsWidget;
@ -1779,6 +1783,7 @@ void QgisApp::createActions()
connect( mActionCircle2Points, &QAction::triggered, this, &QgisApp::circle2Points );
connect( mActionCircle3Points, &QAction::triggered, this, &QgisApp::circle3Points );
connect( mActionCircle3Tangents, &QAction::triggered, this, &QgisApp::circle3Tangents );
connect( mActionCircle2TangentsPoint, &QAction::triggered, this, &QgisApp::circle2TangentsPoint );
connect( mActionCircleCenterPoint, &QAction::triggered, this, &QgisApp::circleCenterPoint );
connect( mActionEllipseCenter2Points, &QAction::triggered, this, &QgisApp::ellipseCenter2Points );
connect( mActionEllipseCenterPoint, &QAction::triggered, this, &QgisApp::ellipseCenterPoint );
@ -1790,6 +1795,7 @@ void QgisApp::createActions()
connect( mActionSquareCenter, &QAction::triggered, this, &QgisApp::squareCenter );
connect( mActionRegularPolygon2Points, &QAction::triggered, this, &QgisApp::regularPolygon2Points );
connect( mActionRegularPolygonCenterPoint, &QAction::triggered, this, &QgisApp::regularPolygonCenterPoint );
connect( mActionRegularPolygonCenterCorner, &QAction::triggered, this, &QgisApp::regularPolygonCenterCorner );
connect( mActionMoveFeature, &QAction::triggered, this, &QgisApp::moveFeature );
connect( mActionMoveFeature, &QAction::triggered, this, &QgisApp::moveFeature );
connect( mActionMoveFeatureCopy, &QAction::triggered, this, &QgisApp::moveFeatureCopy );
@ -2067,6 +2073,7 @@ void QgisApp::createActionGroups()
mMapToolGroup->addAction( mActionCircle2Points );
mMapToolGroup->addAction( mActionCircle3Points );
mMapToolGroup->addAction( mActionCircle3Tangents );
mMapToolGroup->addAction( mActionCircle2TangentsPoint );
mMapToolGroup->addAction( mActionCircleCenterPoint );
mMapToolGroup->addAction( mActionEllipseCenter2Points );
mMapToolGroup->addAction( mActionEllipseCenterPoint );
@ -2078,6 +2085,7 @@ void QgisApp::createActionGroups()
mMapToolGroup->addAction( mActionSquareCenter );
mMapToolGroup->addAction( mActionRegularPolygon2Points );
mMapToolGroup->addAction( mActionRegularPolygonCenterPoint );
mMapToolGroup->addAction( mActionRegularPolygonCenterCorner );
mMapToolGroup->addAction( mActionMoveFeature );
mMapToolGroup->addAction( mActionMoveFeatureCopy );
mMapToolGroup->addAction( mActionRotateFeature );
@ -2592,6 +2600,7 @@ void QgisApp::createToolBars()
tbAddCircle->addAction( mActionCircle2Points );
tbAddCircle->addAction( mActionCircle3Points );
tbAddCircle->addAction( mActionCircle3Tangents );
tbAddCircle->addAction( mActionCircle2TangentsPoint );
tbAddCircle->addAction( mActionCircleCenterPoint );
tbAddCircle->setDefaultAction( mActionCircle2Points );
connect( tbAddCircle, &QToolButton::triggered, this, &QgisApp::toolButtonActionTriggered );
@ -2624,6 +2633,7 @@ void QgisApp::createToolBars()
tbAddRegularPolygon->setPopupMode( QToolButton::MenuButtonPopup );
tbAddRegularPolygon->addAction( mActionRegularPolygon2Points );
tbAddRegularPolygon->addAction( mActionRegularPolygonCenterPoint );
tbAddRegularPolygon->addAction( mActionRegularPolygonCenterCorner );
tbAddRegularPolygon->setDefaultAction( mActionRegularPolygon2Points );
connect( tbAddRegularPolygon, &QToolButton::triggered, this, &QgisApp::toolButtonActionTriggered );
mRegularShapeDigitizeToolBar->insertWidget( mActionNodeTool, tbAddRegularPolygon );
@ -3203,6 +3213,8 @@ void QgisApp::createCanvasTools()
mMapTools.mCircle3Points->setAction( mActionCircle3Points );
mMapTools.mCircle3Tangents = new QgsMapToolCircle3Tangents( dynamic_cast<QgsMapToolAddFeature *>( mMapTools.mAddFeature ), mMapCanvas );
mMapTools.mCircle3Tangents->setAction( mActionCircle3Tangents );
mMapTools.mCircle2TangentsPoint = new QgsMapToolCircle2TangentsPoint( dynamic_cast<QgsMapToolAddFeature *>( mMapTools.mAddFeature ), mMapCanvas );
mMapTools.mCircle2TangentsPoint->setAction( mActionCircle2TangentsPoint );
mMapTools.mCircleCenterPoint = new QgsMapToolCircleCenterPoint( dynamic_cast<QgsMapToolAddFeature *>( mMapTools.mAddFeature ), mMapCanvas );
mMapTools.mCircleCenterPoint->setAction( mActionCircleCenterPoint );
mMapTools.mEllipseCenter2Points = new QgsMapToolEllipseCenter2Points( dynamic_cast<QgsMapToolAddFeature *>( mMapTools.mAddFeature ), mMapCanvas );
@ -3225,6 +3237,8 @@ void QgisApp::createCanvasTools()
mMapTools.mRegularPolygon2Points->setAction( mActionRegularPolygon2Points );
mMapTools.mRegularPolygonCenterPoint = new QgsMapToolRegularPolygonCenterPoint( dynamic_cast<QgsMapToolAddFeature *>( mMapTools.mAddFeature ), mMapCanvas );
mMapTools.mRegularPolygonCenterPoint->setAction( mActionRegularPolygonCenterPoint );
mMapTools.mRegularPolygonCenterCorner = new QgsMapToolRegularPolygonCenterCorner( dynamic_cast<QgsMapToolAddFeature *>( mMapTools.mAddFeature ), mMapCanvas );
mMapTools.mRegularPolygonCenterCorner->setAction( mActionRegularPolygonCenterCorner );
mMapTools.mMoveFeature = new QgsMapToolMoveFeature( mMapCanvas, QgsMapToolMoveFeature::Move );
mMapTools.mMoveFeature->setAction( mActionMoveFeature );
mMapTools.mMoveFeatureCopy = new QgsMapToolMoveFeature( mMapCanvas, QgsMapToolMoveFeature::CopyMove );
@ -7806,6 +7820,11 @@ void QgisApp::circle3Tangents()
mMapCanvas->setMapTool( mMapTools.mCircle3Tangents );
}
void QgisApp::circle2TangentsPoint()
{
mMapCanvas->setMapTool( mMapTools.mCircle2TangentsPoint );
}
void QgisApp::circleCenterPoint()
{
mMapCanvas->setMapTool( mMapTools.mCircleCenterPoint );
@ -7861,6 +7880,11 @@ void QgisApp::regularPolygonCenterPoint()
mMapCanvas->setMapTool( mMapTools.mRegularPolygonCenterPoint );
}
void QgisApp::regularPolygonCenterCorner()
{
mMapCanvas->setMapTool( mMapTools.mRegularPolygonCenterCorner );
}
void QgisApp::selectFeatures()
{
mMapCanvas->setMapTool( mMapTools.mSelectFeatures );
@ -11202,6 +11226,7 @@ void QgisApp::activateDeactivateLayerRelatedActions( QgsMapLayer *layer )
mActionCircle2Points->setEnabled( false );
mActionCircle3Points->setEnabled( false );
mActionCircle3Tangents->setEnabled( false );
mActionCircle2TangentsPoint->setEnabled( false );
mActionCircleCenterPoint->setEnabled( false );
mActionEllipseCenter2Points->setEnabled( false );
mActionEllipseCenterPoint->setEnabled( false );
@ -11212,6 +11237,7 @@ void QgisApp::activateDeactivateLayerRelatedActions( QgsMapLayer *layer )
mActionSquareCenter->setEnabled( false );
mActionRegularPolygon2Points->setEnabled( false );
mActionRegularPolygonCenterPoint->setEnabled( false );
mActionRegularPolygonCenterCorner->setEnabled( false );
mActionMoveFeature->setEnabled( false );
mActionMoveFeatureCopy->setEnabled( false );
mActionRotateFeature->setEnabled( false );
@ -11354,6 +11380,8 @@ void QgisApp::activateDeactivateLayerRelatedActions( QgsMapLayer *layer )
&& ( vlayer->geometryType() == QgsWkbTypes::LineGeometry || vlayer->geometryType() == QgsWkbTypes::PolygonGeometry ) );
mActionCircle3Tangents->setEnabled( isEditable && ( canAddFeatures || canChangeGeometry )
&& ( vlayer->geometryType() == QgsWkbTypes::LineGeometry || vlayer->geometryType() == QgsWkbTypes::PolygonGeometry ) );
mActionCircle2TangentsPoint->setEnabled( isEditable && ( canAddFeatures || canChangeGeometry )
&& ( vlayer->geometryType() == QgsWkbTypes::LineGeometry || vlayer->geometryType() == QgsWkbTypes::PolygonGeometry ) );
mActionCircleCenterPoint->setEnabled( isEditable && ( canAddFeatures || canChangeGeometry )
&& ( vlayer->geometryType() == QgsWkbTypes::LineGeometry || vlayer->geometryType() == QgsWkbTypes::PolygonGeometry ) );
mActionEllipseCenter2Points->setEnabled( isEditable && ( canAddFeatures || canChangeGeometry )
@ -11376,6 +11404,8 @@ void QgisApp::activateDeactivateLayerRelatedActions( QgsMapLayer *layer )
&& ( vlayer->geometryType() == QgsWkbTypes::LineGeometry || vlayer->geometryType() == QgsWkbTypes::PolygonGeometry ) );
mActionRegularPolygonCenterPoint->setEnabled( isEditable && ( canAddFeatures || canChangeGeometry )
&& ( vlayer->geometryType() == QgsWkbTypes::LineGeometry || vlayer->geometryType() == QgsWkbTypes::PolygonGeometry ) );
mActionRegularPolygonCenterCorner->setEnabled( isEditable && ( canAddFeatures || canChangeGeometry )
&& ( vlayer->geometryType() == QgsWkbTypes::LineGeometry || vlayer->geometryType() == QgsWkbTypes::PolygonGeometry ) );
//does provider allow deleting of features?
mActionDeleteSelected->setEnabled( isEditable && canDeleteFeatures && layerHasSelection );
mActionCutFeatures->setEnabled( isEditable && canDeleteFeatures && layerHasSelection );

View File

@ -1229,6 +1229,8 @@ class APP_EXPORT QgisApp : public QMainWindow, private Ui::MainWindow
void circle3Points();
//! activates the add circle from 3 tangents tool
void circle3Tangents();
//! activates the add circle from 2 tangents and a point tool
void circle2TangentsPoint();
//! activates the add circle from center and radius tool
void circleCenterPoint();
//! activates the add ellipse from center and 2 points tool
@ -1251,6 +1253,8 @@ class APP_EXPORT QgisApp : public QMainWindow, private Ui::MainWindow
void regularPolygon2Points();
//! activates the add regular polygon from center and a point tool
void regularPolygonCenterPoint();
//! activates the add regular polygon from center and a corner tool
void regularPolygonCenterCorner();
//! activates the move feature tool
void moveFeature();
//! activates the copy and move feature tool
@ -1823,6 +1827,7 @@ class APP_EXPORT QgisApp : public QMainWindow, private Ui::MainWindow
QgsMapTool *mCircle2Points = nullptr;
QgsMapTool *mCircle3Points = nullptr;
QgsMapTool *mCircle3Tangents = nullptr;
QgsMapTool *mCircle2TangentsPoint = nullptr;
QgsMapTool *mCircleCenterPoint = nullptr;
QgsMapTool *mEllipseCenter2Points = nullptr;
QgsMapTool *mEllipseCenterPoint = nullptr;
@ -1834,6 +1839,7 @@ class APP_EXPORT QgisApp : public QMainWindow, private Ui::MainWindow
QgsMapTool *mSquareCenter = nullptr;
QgsMapTool *mRegularPolygon2Points = nullptr;
QgsMapTool *mRegularPolygonCenterPoint = nullptr;
QgsMapTool *mRegularPolygonCenterCorner = nullptr;
QgsMapTool *mMoveFeature = nullptr;
QgsMapTool *mMoveFeatureCopy = nullptr;
QgsMapTool *mOffsetCurve = nullptr;

View File

@ -20,6 +20,11 @@
class QgsGeometryRubberBand;
struct EdgesOnlyFilter : public QgsPointLocator::MatchFilter
{
bool acceptMatch( const QgsPointLocator::Match &m ) override { return m.hasEdge(); }
};
class QgsMapToolAddCircle: public QgsMapToolCapture
{
Q_OBJECT

View File

@ -0,0 +1,274 @@
/***************************************************************************
qgsmaptoolcircle2tangentspoint.h - map tool for adding circle
from 2 tangents and a point
---------------------
begin : July 2017
copyright : (C) 2017 by Loïc Bartoletti
email : lbartoletti at tuxfamily dot org
***************************************************************************
* *
* 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 "qgsmaptoolcircle2tangentspoint.h"
#include "qgsgeometryrubberband.h"
#include "qgsadvanceddigitizingdockwidget.h"
#include "qgssnappingutils.h"
#include "qgsmapcanvas.h"
#include "qgspoint.h"
#include "qgisapp.h"
#include "qgsstatusbar.h"
#include "qgslinestring.h"
#include "qgsmultipolygon.h"
#include <memory>
#include <QMouseEvent>
QgsMapToolCircle2TangentsPoint::QgsMapToolCircle2TangentsPoint( QgsMapToolCapture *parentTool,
QgsMapCanvas *canvas, CaptureMode mode )
: QgsMapToolAddCircle( parentTool, canvas, mode )
{
mCenters.clear();
}
QgsMapToolCircle2TangentsPoint::~QgsMapToolCircle2TangentsPoint()
{
deleteRadiusSpinBox();
mCenters.clear();
}
void QgsMapToolCircle2TangentsPoint::cadCanvasReleaseEvent( QgsMapMouseEvent *e )
{
QgsPoint mapPoint( e->mapPoint() );
QgsPointXY p1, p2;
if ( e->button() == Qt::LeftButton )
{
if ( mPoints.size() < 2 * 2 )
{
EdgesOnlyFilter filter;
QgsPointLocator::Match match = mCanvas->snappingUtils()->snapToMap( mapPoint, &filter );
if ( match.isValid() )
{
match.edgePoints( p1, p2 );
mPoints.append( QgsPoint( p1 ) );
mPoints.append( QgsPoint( p2 ) );
}
}
if ( mPoints.size() == 4 )
{
QgsPointXY ptInter = intersect( QgsPointXY( mPoints.at( 0 ) ), QgsPointXY( mPoints.at( 1 ) ),
QgsPointXY( mPoints.at( 2 ) ), QgsPointXY( mPoints.at( 3 ) ) );
if ( ptInter == QgsPointXY() )
{
QgisApp::instance()->messageBar()->pushMessage( tr( "Error" ), tr( "Segments are parallels" ),
QgsMessageBar::CRITICAL, QgisApp::instance()->messageTimeout() );
deactivate();
}
createRadiusSpinBox();
}
}
else if ( e->button() == Qt::RightButton )
{
mPoints.clear();
if ( mTempRubberBand )
{
delete mTempRubberBand;
mTempRubberBand = nullptr;
}
for ( int i = 0; i < mRubberBands.size() ; ++i )
{
delete mRubberBands.at( i );
}
mRubberBands.clear();
deactivate();
deleteRadiusSpinBox();
mCenters.clear();
if ( mParentTool )
{
mParentTool->canvasReleaseEvent( e );
}
}
}
void QgsMapToolCircle2TangentsPoint::cadCanvasMoveEvent( QgsMapMouseEvent *e )
{
QgsPoint mapPoint( e->mapPoint() );
if ( mPoints.size() == 4 )
{
if ( !mTempRubberBand )
{
mTempRubberBand = createGeometryRubberBand( ( mode() == CapturePolygon ) ? QgsWkbTypes::PolygonGeometry : QgsWkbTypes::LineGeometry, true );
mTempRubberBand->show();
}
QgsPoint center = QgsPoint( mCenters.at( 0 ) );
double currentDist = mapPoint.distanceSquared( center );
for ( int i = 1; i < mCenters.size(); ++i )
{
double testDist = mapPoint.distanceSquared( mCenters.at( i ).x(), mCenters.at( i ).y() );
if ( testDist < currentDist )
center = QgsPoint( mCenters.at( i ) );
}
mCircle = QgsCircle( center, mRadius );
mTempRubberBand->setGeometry( mCircle.toPolygon() );
}
}
QgsPointXY QgsMapToolCircle2TangentsPoint::intersect( QgsPointXY seg1_pt1, QgsPointXY seg1_pt2, QgsPointXY seg2_pt1, QgsPointXY seg2_pt2 )
{
/*
* Public domain function by Darel Rex Finley, 2006
* http://alienryderflex.com/intersect/
*/
QgsPointXY ptInter;
double Ax = seg1_pt1.x();
double Ay = seg1_pt1.y();
double Bx = seg1_pt2.x();
double By = seg1_pt2.y();
double Cx = seg2_pt1.x();
double Cy = seg2_pt1.y();
double Dx = seg2_pt2.x();
double Dy = seg2_pt2.y();
if ( ( ( Ax == Bx ) && ( Ay == By ) ) || ( ( Cx == Dx ) && ( Cy == Dy ) ) )
return ptInter;
// (1) Translate the system so that point A is on the origin.
Bx -= Ax;
By -= Ay;
Cx -= Ax;
Cy -= Ay;
Dx -= Ax;
Dy -= Ay;
// Discover the length of segment A-B
double distAB = sqrt( Bx * Bx + By * By );
// (2) Rotate the system so that point B is on the positive X axis.
double theCos = Bx / distAB;
double theSin = By / distAB;
double newX = Cx * theCos + Cy * theSin;
Cy = Cy * theCos - Cx * theSin;
Cx = newX;
newX = Dx * theCos + Dy * theSin;
Dy = Dy * theCos - Dx * theSin;
Dx = newX;
// Fail if the lines are parallel.
if ( Cy == Dy )
return ptInter;
// (3) Discover the position of the intersection point along line A-B.
double ABpos = Dx + ( Cx - Dx ) * Dy / ( Dy - Cy );
// (4) Apply the discovered position to line A-B
// in the original coordinate system.
ptInter.setX( Ax + ABpos * theCos );
ptInter.setY( Ay + ABpos * theSin );
// Success
return ptInter;
}
void QgsMapToolCircle2TangentsPoint::getPossibleCenter( )
{
mCenters.clear();
if ( mPoints.size() == 4 )
{
std::unique_ptr<QgsLineString> l1( new QgsLineString() );
l1->addVertex( mPoints.at( 0 ) );
l1->addVertex( mPoints.at( 1 ) );
std::unique_ptr<QgsLineString> l2( new QgsLineString() );
l2->addVertex( mPoints.at( 2 ) );
l2->addVertex( mPoints.at( 3 ) );
/* use magic default values (8, QgsGeometry::JoinStyleBevel, 5), is useless for segments */
QgsGeometry line1 = QgsGeometry( l1.release() );
QgsGeometry line1m = line1.offsetCurve( - mRadius, 8, QgsGeometry::JoinStyleBevel, 5 );
QgsGeometry line1p = line1.offsetCurve( + mRadius, 8, QgsGeometry::JoinStyleBevel, 5 );
QgsGeometry line2 = QgsGeometry( l2.release() );
QgsGeometry line2m = line2.offsetCurve( - mRadius, 8, QgsGeometry::JoinStyleBevel, 5 );
QgsGeometry line2p = line2.offsetCurve( + mRadius, 8, QgsGeometry::JoinStyleBevel, 5 );
QgsPointXY p1 = intersect( line1m.asPolyline().at( 0 ), line1m.asPolyline().at( 1 ),
line2m.asPolyline().at( 0 ), line2m.asPolyline().at( 1 ) );
QgsPointXY p2 = intersect( line1m.asPolyline().at( 0 ), line1m.asPolyline().at( 1 ),
line2p.asPolyline().at( 0 ), line2p.asPolyline().at( 1 ) );
QgsPointXY p3 = intersect( line1p.asPolyline().at( 0 ), line1p.asPolyline().at( 1 ),
line2m.asPolyline().at( 0 ), line2m.asPolyline().at( 1 ) );
QgsPointXY p4 = intersect( line1p.asPolyline().at( 0 ), line1p.asPolyline().at( 1 ),
line2p.asPolyline().at( 0 ), line2p.asPolyline().at( 1 ) );
mCenters.append( p1 );
mCenters.append( p2 );
mCenters.append( p3 );
mCenters.append( p4 );
}
}
void QgsMapToolCircle2TangentsPoint::createRadiusSpinBox()
{
deleteRadiusSpinBox();
mRadiusSpinBox = new QSpinBox();
mRadiusSpinBox->setMaximum( 99999999 );
mRadiusSpinBox->setMinimum( 0 );
mRadiusSpinBox->setPrefix( tr( "Radius of the circle: " ) );
mRadiusSpinBox->setValue( mRadius );
QgisApp::instance()->addUserInputWidget( mRadiusSpinBox );
mRadiusSpinBox->setFocus( Qt::TabFocusReason );
QObject::connect( mRadiusSpinBox, SIGNAL( valueChanged( int ) ), this, SLOT( radiusSpinBoxChanged( int ) ) );
}
void QgsMapToolCircle2TangentsPoint::deleteRadiusSpinBox()
{
if ( mRadiusSpinBox )
{
QgisApp::instance()->statusBarIface()->removeWidget( mRadiusSpinBox );
delete mRadiusSpinBox;
mRadiusSpinBox = nullptr;
}
}
void QgsMapToolCircle2TangentsPoint::radiusSpinBoxChanged( int radius )
{
mRadius = radius;
getPossibleCenter( );
for ( int i = 0; i < mRubberBands.size() ; ++i )
{
delete mRubberBands.at( i );
}
mRubberBands.clear();
if ( mTempRubberBand )
{
std::unique_ptr<QgsMultiPolygonV2> rb( new QgsMultiPolygonV2() );
for ( int i = 0; i < mCenters.size(); ++i )
{
std::unique_ptr<QgsGeometryRubberBand> tempRB( createGeometryRubberBand( ( mode() == CapturePolygon ) ? QgsWkbTypes::PolygonGeometry : QgsWkbTypes::LineGeometry, true ) );
tempRB->setGeometry( QgsCircle( QgsPoint( mCenters.at( i ) ), static_cast<int>( log10( mRadius ) ) + 1 ).toPolygon() );
tempRB->show();
mRubberBands.append( tempRB.release() );
}
}
}

View File

@ -0,0 +1,59 @@
/***************************************************************************
qgsmaptoolcircle2tangentspoint.h - map tool for adding circle
from 2 tangents and a point
---------------------
begin : July 2017
copyright : (C) 2017 by Loïc Bartoletti
email : lbartoletti at tuxfamily dot org
***************************************************************************
* *
* 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 3 of the License, or *
* (at your option) any later version. *
* *
***************************************************************************/
#ifndef QGSMAPTOOLCIRCLE2TANGENTSPOINT_H
#define QGSMAPTOOLCIRCLE2TANGENTSPOINT_H
#include "qgspointlocator.h"
#include "qgsmaptooladdcircle.h"
#include "qspinbox.h"
class QSpinBox;
class QgsMapToolCircle2TangentsPoint: public QgsMapToolAddCircle
{
Q_OBJECT
public:
QgsMapToolCircle2TangentsPoint( QgsMapToolCapture *parentTool, QgsMapCanvas *canvas, CaptureMode mode = CaptureLine );
~QgsMapToolCircle2TangentsPoint();
void cadCanvasReleaseEvent( QgsMapMouseEvent *e ) override;
void cadCanvasMoveEvent( QgsMapMouseEvent *e );
public slots:
void radiusSpinBoxChanged( int radius );
private:
//! Return the point where segments are intersected. Method from QgsGeometryUtils doesn't work for special cases used by this tool.
QgsPointXY intersect( QgsPointXY seg1_pt1, QgsPointXY seg1_pt2, QgsPointXY seg2_pt1, QgsPointXY seg2_pt2 );
//! Compute 4 possible centers
void getPossibleCenter();
//! (re-)create the spin box to enter the radius of the circle
void createRadiusSpinBox();
//! delete the spin box to enter the radius of the circle, if it exists
void deleteRadiusSpinBox();
QSpinBox *mRadiusSpinBox = nullptr;
int mRadius = 0;
QVector<QgsPointXY> mCenters;
QVector<QgsGeometryRubberBand *> mRubberBands;
};
#endif // QGSMAPTOOLCIRCLE2TANGENTSPOINT_H

View File

@ -20,11 +20,6 @@
#include "qgspointlocator.h"
#include "qgsmaptooladdcircle.h"
struct EdgesOnlyFilter : public QgsPointLocator::MatchFilter
{
bool acceptMatch( const QgsPointLocator::Match &m ) override { return m.hasEdge(); }
};
class QgsMapToolCircle3Tangents: public QgsMapToolAddCircle
{
Q_OBJECT

View File

@ -0,0 +1,79 @@
/***************************************************************************
qgsmaptoolregularpolygoncentercorner.cpp - map tool for adding regular
polygon from center and a corner
---------------------
begin : July 2017
copyright : (C) 2017 by Loïc Bartoletti
email : lbartoletti at tuxfamily dot org
***************************************************************************
* *
* 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 "qgsmaptoolregularpolygoncentercorner.h"
#include "qgsgeometryrubberband.h"
#include "qgsmapcanvas.h"
#include "qgspoint.h"
#include <QMouseEvent>
QgsMapToolRegularPolygonCenterCorner::QgsMapToolRegularPolygonCenterCorner( QgsMapToolCapture *parentTool,
QgsMapCanvas *canvas, CaptureMode mode )
: QgsMapToolAddRegularPolygon( parentTool, canvas, mode )
{
}
QgsMapToolRegularPolygonCenterCorner::~QgsMapToolRegularPolygonCenterCorner()
{
if ( mNumberSidesSpinBox )
{
deleteNumberSidesSpinBox();
}
}
void QgsMapToolRegularPolygonCenterCorner::cadCanvasReleaseEvent( QgsMapMouseEvent *e )
{
QgsPoint mapPoint( e->mapPoint() );
if ( e->button() == Qt::LeftButton )
{
mPoints.append( mapPoint );
if ( !mPoints.isEmpty() )
{
if ( !mTempRubberBand )
{
mTempRubberBand = createGeometryRubberBand( ( mode() == CapturePolygon ) ? QgsWkbTypes::PolygonGeometry : QgsWkbTypes::LineGeometry, true );
mTempRubberBand->show();
createNumberSidesSpinBox();
if ( mNumberSidesSpinBox )
{
mNumberSidesSpinBox->setMinimum( 3 );
}
}
}
}
else if ( e->button() == Qt::RightButton )
{
deactivate();
if ( mParentTool )
{
mParentTool->canvasReleaseEvent( e );
}
}
}
void QgsMapToolRegularPolygonCenterCorner::cadCanvasMoveEvent( QgsMapMouseEvent *e )
{
QgsPoint mapPoint( e->mapPoint() );
if ( mTempRubberBand )
{
QgsRegularPolygon::ConstructionOption option = QgsRegularPolygon::InscribedCircle;
mRegularPolygon = QgsRegularPolygon( mPoints.at( 0 ), mapPoint, mNumberSidesSpinBox->value(), option );
mTempRubberBand->setGeometry( mRegularPolygon.toPolygon() );
}
}

View File

@ -0,0 +1,34 @@
#ifndef QGSMAPTOOLREGULARPOLYGONCENTERCORNER_H
#define QGSMAPTOOLREGULARPOLYGONCENTERCORNER_H
/***************************************************************************
qgsmaptoolregularpolygoncentercorner.h - map tool for adding regular
polygon from center and a corner
---------------------
begin : July 2017
copyright : (C) 2017 by Loïc Bartoletti
email : lbartoletti at tuxfamily dot org
***************************************************************************
* *
* 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 "qgsmaptooladdregularpolygon.h"
class QgsMapToolRegularPolygonCenterCorner: public QgsMapToolAddRegularPolygon
{
Q_OBJECT
public:
QgsMapToolRegularPolygonCenterCorner( QgsMapToolCapture *parentTool, QgsMapCanvas *canvas, CaptureMode mode = CaptureLine );
~QgsMapToolRegularPolygonCenterCorner();
void cadCanvasReleaseEvent( QgsMapMouseEvent *e ) override;
void cadCanvasMoveEvent( QgsMapMouseEvent *e ) override;
};
#endif // QGSMAPTOOLREGULARPOLYGONCENTERCORNER_H

View File

@ -72,8 +72,7 @@ void QgsMapToolRegularPolygonCenterPoint::cadCanvasMoveEvent( QgsMapMouseEvent *
QgsPoint mapPoint( e->mapPoint() );
if ( mTempRubberBand )
{
// TODO: get option from Toolbar
QgsRegularPolygon::ConstructionOption option = QgsRegularPolygon::InscribedCircle;
QgsRegularPolygon::ConstructionOption option = QgsRegularPolygon::CircumscribedCircle;
mRegularPolygon = QgsRegularPolygon( mPoints.at( 0 ), mapPoint, mNumberSidesSpinBox->value(), option );
mTempRubberBand->setGeometry( mRegularPolygon.toPolygon() );
}

View File

@ -235,7 +235,7 @@
</widget>
<widget class="QMenu" name="mVectorMenu">
<property name="title">
<string>Vect&amp;or</string>
<string>&amp;Vector</string>
</property>
<widget class="QMenu" name="menuOpenStreetMap">
<property name="title">
@ -279,6 +279,7 @@
<addaction name="mActionCircle2Points"/>
<addaction name="mActionCircle3Points"/>
<addaction name="mActionCircle3Tangents"/>
<addaction name="mActionCircle2TangentsPoint"/>
<addaction name="mActionCircleCenterPoint"/>
</widget>
<widget class="QMenu" name="mMenuEllipse">
@ -304,6 +305,7 @@
<string>Add Regular Polygon</string>
</property>
<addaction name="mActionRegularPolygonCenterPoint"/>
<addaction name="mActionRegularPolygonCenterCorner"/>
<addaction name="mActionRegularPolygon2Points"/>
</widget>
<addaction name="mActionUndo"/>
@ -2929,6 +2931,36 @@ Acts on currently active editable layer</string>
<string>Add rectangle from 3 points</string>
</property>
</action>
<action name="mActionCircle2TangentsPoint">
<property name="checkable">
<bool>true</bool>
</property>
<property name="icon">
<iconset resource="../../images/images.qrc">
<normaloff>:/images/themes/default/mActionCircle2TangentsPoint.svg</normaloff>:/images/themes/default/mActionCircle2TangentsPoint.svg</iconset>
</property>
<property name="text">
<string>Add Circle &amp;from 2 Tangents and a point</string>
</property>
<property name="toolTip">
<string>Add circle from 2 tangents and a point</string>
</property>
</action>
<action name="mActionRegularPolygonCenterCorner">
<property name="checkable">
<bool>true</bool>
</property>
<property name="icon">
<iconset resource="../../images/images.qrc">
<normaloff>:/images/themes/default/mActionRegularPolygonCenterCorner.svg</normaloff>:/images/themes/default/mActionRegularPolygonCenterCorner.svg</iconset>
</property>
<property name="text">
<string>Add Regular &amp;Polygon From Center and a Corner</string>
</property>
<property name="toolTip">
<string>Add regular polygon from center and a corner</string>
</property>
</action>
</widget>
<resources>
<include location="../../images/images.qrc"/>