Skip to content

Commit 91c51cd

Browse files

File tree

5 files changed

+161
-150
lines changed

5 files changed

+161
-150
lines changed
 

‎src/gui/Makefile.am

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -125,6 +125,7 @@ libqgis_guiHEADERS = \
125125
qgsprojectproperties.h \
126126
qgsrangerenderitem.h \
127127
qgsrasterlayerproperties.h \
128+
qgsrubberband.h \
128129
qgsrunprocess.h \
129130
qgsserversourceselect.h \
130131
qgssisydialog.h \
@@ -235,6 +236,7 @@ libqgis_gui_la_SOURCES = \
235236
qgsproject.cpp \
236237
qgsprojectproperties.cpp \
237238
qgsrasterlayerproperties.cpp \
239+
qgsrubberband.cpp \
238240
qgsrunprocess.cpp \
239241
qgsserversourceselect.cpp \
240242
qgssinglesymrenderer.cpp \

‎src/gui/qgsmeasure.cpp

Lines changed: 29 additions & 132 deletions
Original file line numberDiff line numberDiff line change
@@ -13,11 +13,15 @@
1313
* (at your option) any later version. *
1414
* *
1515
***************************************************************************/
16+
/* $Id$ */
17+
1618
#include "qgsmeasure.h"
1719

1820
#include "qgscontexthelp.h"
1921
#include "qgsdistancearea.h"
2022
#include "qgsmapcanvas.h"
23+
#include "qgsmaptopixel.h"
24+
#include "qgsrubberband.h"
2125

2226
#include <QSettings>
2327
#include <iostream>
@@ -27,14 +31,11 @@ QgsMeasure::QgsMeasure(bool measureArea, QgsMapCanvas *mc, QWidget *parent, cons
2731
: QWidget(parent, name, f)
2832
{
2933
setupUi(this);
30-
connect(btnHelp, SIGNAL(clicked()), this, SLOT(showHelp()));
3134
connect(mRestartButton, SIGNAL(clicked()), this, SLOT(restart()));
3235
connect(mCloseButton, SIGNAL(clicked()), this, SLOT(close()));
3336

3437
mMeasureArea = measureArea;
3538
mMapCanvas = mc;
36-
mDynamic = false;
37-
mPixmap = mMapCanvas->canvasPixmap();
3839
mTotal = 0.;
3940

4041
mTable->setLeftMargin(0); // hide row labels
@@ -58,45 +59,40 @@ QgsMeasure::QgsMeasure(bool measureArea, QgsMapCanvas *mc, QWidget *parent, cons
5859

5960
updateUi();
6061

61-
connect ( mMapCanvas, SIGNAL(renderComplete(QPainter*)), this, SLOT(draw(QPainter*)) );
62+
connect( mMapCanvas, SIGNAL(renderComplete(QPainter*)), this, SLOT(mapCanvasChanged()) );
6263
restorePosition();
6364

6465
mCalc = new QgsDistanceArea;
65-
66+
67+
mRubberBand = new QgsRubberBand(mMapCanvas, mMeasureArea);
68+
mRubberBand->show();
6669
}
6770

6871

6972
void QgsMeasure::setMeasureArea(bool measureArea)
7073
{
7174
saveWindowLocation();
72-
restart();
7375
mMeasureArea = measureArea;
74-
updateUi();
76+
restart();
7577
restorePosition();
7678
}
7779

7880

7981
QgsMeasure::~QgsMeasure()
8082
{
8183
delete mCalc;
84+
delete mRubberBand;
8285
}
8386

8487
void QgsMeasure::restart(void )
8588
{
86-
// Delete old line
87-
drawLine();
88-
8989
mPoints.resize(0);
9090
mTable->setNumRows(0);
9191
mTotal = 0.;
9292

9393
updateUi();
94-
95-
if ( mDynamic ) {
96-
drawDynamicLine();
97-
mDynamic = false;
98-
}
99-
94+
95+
mRubberBand->reset(mMeasureArea);
10096
}
10197

10298
void QgsMeasure::addPoint(QgsPoint &point)
@@ -105,15 +101,6 @@ void QgsMeasure::addPoint(QgsPoint &point)
105101
std::cout << "QgsMeasure::addPoint" << point.x() << ", " << point.y() << std::endl;
106102
#endif
107103

108-
// Delete dynamic
109-
if ( mDynamic ) {
110-
drawDynamicLine();
111-
mDynamic = false;
112-
}
113-
114-
// Delete old line
115-
drawLine(true);
116-
117104
// don't add points with the same coordinates
118105
if (mPoints.size() > 0 && point == mPoints[0])
119106
return;
@@ -153,8 +140,9 @@ void QgsMeasure::addPoint(QgsPoint &point)
153140
mTable->ensureCellVisible(row,0);
154141
}
155142

156-
// Draw new line
157-
drawLine();
143+
QgsMapToPixel *trans = mMapCanvas->getCoordinateTransform();
144+
QgsPoint ppnt = trans->transform(point);
145+
mRubberBand->addPoint(QPoint(int(ppnt.x()), int(ppnt.y())));
158146
}
159147

160148
void QgsMeasure::mousePress(QgsPoint &point)
@@ -166,29 +154,6 @@ void QgsMeasure::mousePress(QgsPoint &point)
166154
}
167155

168156
mouseMove(point);
169-
170-
if (mMeasureArea && mPoints.size() > 2)
171-
{
172-
// delete old line which connect 1. and last point
173-
174-
// TODO: Qt4 uses "QRubberBand"s - need to refactor.
175-
#if QT_VERSION < 0x040000
176-
QPainter p;
177-
p.begin(mPixmap);
178-
QPen pen(Qt::gray, 2);
179-
p.setPen(pen);
180-
p.setRasterOp(Qt::XorROP);
181-
182-
QgsMapToPixel *trans = mMapCanvas->getCoordinateTransform();
183-
QgsPoint ppnt = trans->transform(mPoints[mPoints.size()-1]);
184-
p.moveTo(static_cast<int>(ppnt.x()), static_cast<int>(ppnt.y()));
185-
ppnt = trans->transform(mPoints[0]);
186-
p.lineTo(static_cast<int>(ppnt.x()), static_cast<int>(ppnt.y()));
187-
p.end();
188-
#endif
189-
mMapCanvas->repaint(false);
190-
}
191-
192157
}
193158

194159
void QgsMeasure::mouseMove(QgsPoint &point)
@@ -197,92 +162,24 @@ void QgsMeasure::mouseMove(QgsPoint &point)
197162
//std::cout << "QgsMeasure::mouseMove" << point.x() << ", " << point.y() << std::endl;
198163
#endif
199164

200-
if ( mDynamic ) {
201-
drawDynamicLine(); // delete old
202-
}
203-
204-
if ( mPoints.size() > 0 ) {
205-
mDynamicPoints[0] = mPoints[mPoints.size()-1];
206-
mDynamicPoints[1] = point;
207-
drawDynamicLine();
208-
mDynamic = true;
209-
}
165+
QgsMapToPixel *trans = mMapCanvas->getCoordinateTransform();
166+
QgsPoint ppnt = trans->transform(point);
167+
mRubberBand->movePoint(QPoint(int(ppnt.x()), int(ppnt.y())));
210168
}
211169

212-
void QgsMeasure::draw(QPainter *p)
170+
void QgsMeasure::mapCanvasChanged()
213171
{
214172
#ifdef QGISDEBUG
215-
std::cout << "QgsMeasure::draw" << std::endl;
173+
std::cout << "QgsMeasure::mapCanvasChanged" << std::endl;
216174
#endif
217-
218-
drawLine();
219-
mDynamic = false;
220-
}
221-
222-
void QgsMeasure::drawLine(bool erase)
223-
{
224-
#ifdef QGISDEBUG
225-
std::cout << "QgsMeasure::drawLine" << std::endl;
226-
#endif
227-
228-
// TODO: Qt4 uses "QRubberBand"s - need to refactor.
229-
#if QT_VERSION < 0x040000
230-
QPainter p;
231-
p.begin(mPixmap);
232-
QPen pen(Qt::gray, 2);
233-
p.setPen(pen);
234-
p.setRasterOp(Qt::XorROP);
235-
236-
QgsMapToPixel *trans = mMapCanvas->getCoordinateTransform();
237-
for ( int i = 0; i < mPoints.size(); i++ ) {
238-
QgsPoint ppnt = trans->transform(mPoints[i]);
239-
if ( i == 0 ) {
240-
p.moveTo(static_cast<int>(ppnt.x()), static_cast<int>(ppnt.y()));
241-
} else {
242-
p.lineTo(static_cast<int>(ppnt.x()), static_cast<int>(ppnt.y()));
243-
}
244-
}
245-
246-
if (!erase && mMeasureArea && mPoints.size() > 2) // draw the last point of the polygon
247-
{
248-
QgsPoint ppnt = trans->transform(mPoints[0]);
249-
p.lineTo(static_cast<int>(ppnt.x()), static_cast<int>(ppnt.y()));
250-
}
251-
252-
p.end();
253-
#endif
254-
mMapCanvas->repaint(false);
255-
}
256-
257-
void QgsMeasure::drawDynamicLine( void )
258-
{
259-
#ifdef QGISDEBUG
260-
//std::cout << "QgsMeasure::drawDynamicLine" << std::endl;
261-
#endif
262-
263-
// TODO: Qt4 uses "QRubberBand"s and "QPainterPath"s - need to refactor.
264-
#if QT_VERSION < 0x040000
265-
QPainter p;
266-
p.begin(mPixmap);
267-
QPen pen(Qt::gray, 2);
268-
p.setPen(pen);
269-
p.setRasterOp(Qt::XorROP);
270-
271-
QgsMapToPixel *trans = mMapCanvas->getCoordinateTransform();
272-
QgsPoint ppnt = trans->transform(mDynamicPoints[0]);
273-
p.moveTo(static_cast<int>(ppnt.x()), static_cast<int>(ppnt.y()));
274-
QgsPoint ppnt2 = trans->transform(mDynamicPoints[1]);
275-
p.lineTo(static_cast<int>(ppnt2.x()), static_cast<int>(ppnt2.y()));
276-
277-
if (mMeasureArea && mPoints.size() >= 2)
278-
{
279-
ppnt = trans->transform(mPoints[0]);
280-
p.lineTo(static_cast<int>(ppnt.x()), static_cast<int>(ppnt.y()));
281-
}
282-
283-
p.end();
284-
#endif
285-
mMapCanvas->repaint(false);
175+
mRubberBand->setGeometry(mMapCanvas->rect());
176+
mRubberBand->reset(mMeasureArea);
177+
QgsMapToPixel *trans = mMapCanvas->getCoordinateTransform();
178+
for (std::vector<QgsPoint>::iterator it = mPoints.begin(); it != mPoints.end(); ++it)
179+
{
180+
QgsPoint ppnt = trans->transform(*it);
181+
mRubberBand->addPoint(QPoint(int(ppnt.x()), int(ppnt.y())));
182+
}
286183
}
287184

288185
void QgsMeasure::close(void)
@@ -331,7 +228,7 @@ void QgsMeasure::saveWindowLocation()
331228
settings.writeEntry("/Windows/Measure/h", s.height());
332229
}
333230

334-
void QgsMeasure::showHelp()
231+
void QgsMeasure::on_btnHelp_clicked()
335232
{
336233
QgsContextHelp::run(context_id);
337234
}

‎src/gui/qgsmeasure.h

Lines changed: 6 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -23,10 +23,9 @@
2323

2424
class QgsDistanceArea;
2525
class QgsMapCanvas;
26+
class QgsRubberBand;
2627

2728
class QCloseEvent;
28-
class QPainter;
29-
class QPixmap;
3029

3130

3231
class QgsMeasure:public QWidget, private Ui::QgsMeasureBase
@@ -69,11 +68,11 @@ public slots:
6968
//! Close event
7069
void closeEvent(QCloseEvent *e);
7170

72-
//! Connected to canvas renderComplete
73-
void draw(QPainter *);
71+
//! Redraw lines to match current state of canvas
72+
void mapCanvasChanged();
7473

7574
//! Show the help for the dialog
76-
void showHelp();
75+
void on_btnHelp_clicked();
7776

7877
private:
7978

@@ -87,8 +86,6 @@ public slots:
8786
void updateUi();
8887

8988
QgsMapCanvas *mMapCanvas;
90-
91-
QPixmap *mPixmap;
9289

9390
//! distance/area calculator
9491
QgsDistanceArea* mCalc;
@@ -97,17 +94,8 @@ public slots:
9794

9895
double mTotal;
9996

100-
//! Dynamic line from last point to current position was drawn
101-
bool mDynamic;
102-
103-
//! Dynamic line
104-
QgsPoint mDynamicPoints[2];
105-
106-
//! Draw current points with XOR
107-
void drawLine(bool erase = false);
108-
109-
//! Draw current dynamic line
110-
void drawDynamicLine(void);
97+
//! Rubberband widget tracking the lines being drawn
98+
QgsRubberBand *mRubberBand;
11199

112100
//! Help context id
113101
static const int context_id = 940759457;

‎src/gui/qgsrubberband.cpp

Lines changed: 83 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,83 @@
1+
/***************************************************************************
2+
qgsrubberband.cpp - Rubberband widget for drawing multilines and polygons
3+
--------------------------------------
4+
Date : 07-Jan-2006
5+
Copyright : (C) 2006 by Tom Elwertowski
6+
Email : telwertowski at users dot sourceforge dot net
7+
***************************************************************************
8+
* *
9+
* This program is free software; you can redistribute it and/or modify *
10+
* it under the terms of the GNU General Public License as published by *
11+
* the Free Software Foundation; either version 2 of the License, or *
12+
* (at your option) any later version. *
13+
* *
14+
***************************************************************************/
15+
/* $Id$ */
16+
17+
#include "qgsrubberband.h"
18+
#include <QPainter>
19+
20+
/*!
21+
\class QgsRubberBand
22+
\brief The QgsRubberBand class provides a transparent overlay widget
23+
for tracking the mouse while drawing polylines or polygons.
24+
*/
25+
QgsRubberBand::QgsRubberBand(QWidget * parent, bool isPolygon)
26+
: QWidget(parent), mIsPolygon(isPolygon)
27+
{
28+
setGeometry(parent->rect()); // this widget is same size as parent
29+
mPoints.append(QPoint()); // addPoint assumes an initial allocated point
30+
}
31+
32+
QgsRubberBand::~QgsRubberBand()
33+
{}
34+
35+
/*!
36+
Remove all points from the shape being created.
37+
*/
38+
void QgsRubberBand::reset(bool isPolygon)
39+
{
40+
mPoints.resize(1); // addPoint assumes an initial allocated point
41+
mIsPolygon = isPolygon;
42+
update();
43+
}
44+
45+
/*!
46+
Add a point to the shape being created.
47+
*/
48+
void QgsRubberBand::addPoint(const QPoint & p)
49+
{
50+
mPoints.last() = p; // Current mouse position becomes added point
51+
mPoints.append(p); // Allocate new point to continue tracking current mouse position
52+
update();
53+
}
54+
55+
/*!
56+
Update the line between the last added point and the mouse position.
57+
*/
58+
void QgsRubberBand::movePoint(const QPoint & p)
59+
{
60+
mPoints.last() = p; // Update current mouse position
61+
update();
62+
}
63+
64+
/*!
65+
Draw the shape in response to an update event.
66+
*/
67+
void QgsRubberBand::paintEvent(QPaintEvent * event)
68+
{
69+
if (mPoints.count() > 1)
70+
{
71+
QPainter p(this);
72+
p.setPen(Qt::lightGray);
73+
p.setBrush(QBrush(Qt::lightGray, Qt::Dense6Pattern));
74+
if (mIsPolygon)
75+
{
76+
p.drawPolygon(mPoints);
77+
}
78+
else
79+
{
80+
p.drawPolyline(mPoints);
81+
}
82+
}
83+
}

‎src/gui/qgsrubberband.h

Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,41 @@
1+
/***************************************************************************
2+
qgsrubberband.h - Rubberband widget for drawing multilines and polygons
3+
--------------------------------------
4+
Date : 07-Jan-2006
5+
Copyright : (C) 2006 by Tom Elwertowski
6+
Email : telwertowski at users dot sourceforge dot net
7+
***************************************************************************
8+
* *
9+
* This program is free software; you can redistribute it and/or modify *
10+
* it under the terms of the GNU General Public License as published by *
11+
* the Free Software Foundation; either version 2 of the License, or *
12+
* (at your option) any later version. *
13+
* *
14+
***************************************************************************/
15+
/* $Id$ */
16+
#ifndef QGSRUBBERBAND_H
17+
#define QGSRUBBERBAND_H
18+
19+
#include <QWidget>
20+
#include <QPolygon>
21+
class QPaintEvent;
22+
23+
class QgsRubberBand: public QWidget
24+
{
25+
public:
26+
QgsRubberBand(QWidget * parent, bool isPolygon = false);
27+
~QgsRubberBand();
28+
29+
void reset(bool isPolygon = false);
30+
void addPoint(const QPoint & p);
31+
void movePoint(const QPoint & p);
32+
33+
protected:
34+
virtual void paintEvent(QPaintEvent * event);
35+
36+
private:
37+
QPolygon mPoints;
38+
bool mIsPolygon;
39+
};
40+
41+
#endif

0 commit comments

Comments
 (0)
Please sign in to comment.