Skip to content

Commit e58f837

Browse files
author
wonder
committed
Applied patch from #2640: improved rendering of selected features (symbology-ng).
+ fixed font marker scaling for printing Contributed by Chris Crook. Thanks! git-svn-id: http://svn.osgeo.org/qgis/trunk/qgis@13322 c8812cc2-4d05-0410-92ff-de0c093fc19c
1 parent 9f3dcf4 commit e58f837

14 files changed

+141
-60
lines changed

python/core/symbology-ng-core.sip

Lines changed: 10 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -79,7 +79,7 @@ public:
7979

8080
virtual QgsSymbolV2List symbols()=0;
8181

82-
virtual void renderFeature(QgsFeature& feature, QgsRenderContext& context, int layer = -1, bool drawVertexMarker = false );
82+
virtual void renderFeature(QgsFeature& feature, QgsRenderContext& context, int layer = -1, bool selected = false, bool drawVertexMarker = false );
8383

8484
bool usingSymbolLevels() const;
8585
void setUsingSymbolLevels(bool usingSymbolLevels);
@@ -453,7 +453,7 @@ class QgsSymbolV2RenderContext
453453
%End
454454

455455
public:
456-
QgsSymbolV2RenderContext( QgsRenderContext& c, QgsSymbolV2::OutputUnit u , qreal alpha = 1.0 );
456+
QgsSymbolV2RenderContext( QgsRenderContext& c, QgsSymbolV2::OutputUnit u , qreal alpha = 1.0, bool selected = false );
457457
~QgsSymbolV2RenderContext();
458458

459459
QgsRenderContext& renderContext();
@@ -465,6 +465,11 @@ class QgsSymbolV2RenderContext
465465
qreal alpha() const;
466466
void setAlpha( qreal alpha );
467467

468+
bool selected() const;
469+
void setSelected( bool selected ) const;
470+
471+
static QColor selectionColor();
472+
468473
double outputLineWidth(double width) const;
469474
double outputPixelSize(double size) const;
470475
};
@@ -574,7 +579,7 @@ public:
574579
void setSize(double size);
575580
double size();
576581

577-
void renderPoint(const QPointF& point, QgsRenderContext& context, int layer = -1);
582+
void renderPoint(const QPointF& point, QgsRenderContext& context, int layer = -1, bool selected = false );
578583

579584
virtual QgsSymbolV2* clone() const /Factory/;
580585
};
@@ -593,7 +598,7 @@ public:
593598
void setWidth(double width);
594599
double width();
595600

596-
void renderPolyline(const QPolygonF& points, QgsRenderContext& context, int layer = -1);
601+
void renderPolyline(const QPolygonF& points, QgsRenderContext& context, int layer = -1, bool selected = false );
597602

598603
virtual QgsSymbolV2* clone() const /Factory/;
599604
};
@@ -609,7 +614,7 @@ class QgsFillSymbolV2 : QgsSymbolV2
609614
public:
610615
QgsFillSymbolV2(QgsSymbolLayerV2List layers /Transfer/ = QgsSymbolLayerV2List());
611616

612-
void renderPolygon(const QPolygonF& points, QList<QPolygonF>* rings, QgsRenderContext& context, int layer = -1);
617+
void renderPolygon(const QPolygonF& points, QList<QPolygonF>* rings, QgsRenderContext& context, int layer = -1, bool selected = false );
613618

614619
virtual QgsSymbolV2* clone() const /Factory/;
615620
};

src/core/qgsvectorlayer.cpp

Lines changed: 2 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -705,15 +705,6 @@ void QgsVectorLayer::drawRendererV2( QgsRenderContext& rendererContext, bool lab
705705

706706
mRendererV2->startRender( rendererContext, this );
707707

708-
QgsSingleSymbolRendererV2* selRenderer = NULL;
709-
if ( !mSelectedFeatureIds.isEmpty() )
710-
{
711-
selRenderer = new QgsSingleSymbolRendererV2( QgsSymbolV2::defaultSymbol( geometryType() ) );
712-
selRenderer->symbol()->setColor( QgsRenderer::selectionColor() );
713-
selRenderer->setVertexMarkerAppearance( currentVertexMarkerType(), currentVertexMarkerSize() );
714-
selRenderer->startRender( rendererContext, this );
715-
}
716-
717708
#ifndef Q_WS_MAC
718709
int totalFeatures = pendingFeatureCount();
719710
int featureCount = 0;
@@ -747,10 +738,7 @@ void QgsVectorLayer::drawRendererV2( QgsRenderContext& rendererContext, bool lab
747738
bool drawMarker = ( mEditable && ( !vertexMarkerOnlyForSelection || sel ) );
748739

749740
// render feature
750-
if ( sel )
751-
selRenderer->renderFeature( fet, rendererContext, -1, drawMarker );
752-
else
753-
mRendererV2->renderFeature( fet, rendererContext, -1, drawMarker );
741+
mRendererV2->renderFeature( fet, rendererContext, -1, sel, drawMarker );
754742

755743
// labeling - register feature
756744
if ( labeling && mRendererV2->symbolForFeature( fet ) != NULL )
@@ -771,8 +759,6 @@ void QgsVectorLayer::drawRendererV2( QgsRenderContext& rendererContext, bool lab
771759
++featureCount;
772760
#endif //Q_WS_MAC
773761
}
774-
775-
stopRendererV2( rendererContext, selRenderer );
776762
}
777763

778764
void QgsVectorLayer::drawRendererV2Levels( QgsRenderContext& rendererContext, bool labeling )
@@ -885,10 +871,7 @@ void QgsVectorLayer::drawRendererV2Levels( QgsRenderContext& rendererContext, bo
885871

886872
try
887873
{
888-
if ( sel )
889-
selRenderer->renderFeature( *fit, rendererContext, -1, drawMarker );
890-
else
891-
mRendererV2->renderFeature( *fit, rendererContext, layer, drawMarker );
874+
mRendererV2->renderFeature( *fit, rendererContext, layer, sel, drawMarker );
892875
}
893876
catch ( const QgsCsException &cse )
894877
{

src/core/symbology-ng/qgsfillsymbollayerv2.cpp

Lines changed: 15 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,10 @@ void QgsSimpleFillSymbolLayerV2::startRender( QgsSymbolV2RenderContext& context
4747
{
4848
mColor.setAlphaF( context.alpha() );
4949
mBrush = QBrush( mColor, mBrushStyle );
50+
QColor selColor = context.selectionColor();
51+
// selColor.setAlphaF( context.alpha() );
52+
mSelBrush = QBrush( selColor );
53+
if ( selectFillStyle ) mSelBrush.setStyle( mBrushStyle );
5054
mBorderColor.setAlphaF( context.alpha() );
5155
mPen = QPen( mBorderColor );
5256
mPen.setStyle( mBorderStyle );
@@ -65,7 +69,7 @@ void QgsSimpleFillSymbolLayerV2::renderPolygon( const QPolygonF& points, QList<Q
6569
return;
6670
}
6771

68-
p->setBrush( mBrush );
72+
p->setBrush( context.selected() ? mSelBrush : mBrush );
6973
p->setPen( mPen );
7074

7175
_renderPolygon( p, points, rings );
@@ -209,18 +213,25 @@ void QgsSVGFillSymbolLayer::renderPolygon( const QPolygonF& points, QList<QPolyg
209213
{
210214
return;
211215
}
212-
p->setBrush( mBrush );
213216
p->setPen( QPen( Qt::NoPen ) );
217+
if ( context.selected() )
218+
{
219+
QColor selColor = context.selectionColor();
220+
if ( ! selectionIsOpaque ) selColor.setAlphaF( context.alpha() );
221+
p->setBrush( QBrush( selColor ) );
222+
_renderPolygon( p, points, rings );
223+
}
224+
p->setBrush( mBrush );
214225
_renderPolygon( p, points, rings );
215226
if ( mOutline )
216227
{
217-
mOutline->renderPolyline( points, context.renderContext() );
228+
mOutline->renderPolyline( points, context.renderContext(), -1, selectFillBorder && context.selected() );
218229
if ( rings )
219230
{
220231
QList<QPolygonF>::const_iterator ringIt = rings->constBegin();
221232
for ( ; ringIt != rings->constEnd(); ++ringIt )
222233
{
223-
mOutline->renderPolyline( *ringIt, context.renderContext() );
234+
mOutline->renderPolyline( *ringIt, context.renderContext(), -1, selectFillBorder && context.selected() );
224235
}
225236
}
226237
}

src/core/symbology-ng/qgsfillsymbollayerv2.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -54,6 +54,7 @@ class CORE_EXPORT QgsSimpleFillSymbolLayerV2 : public QgsFillSymbolLayerV2
5454

5555
protected:
5656
QBrush mBrush;
57+
QBrush mSelBrush;
5758
Qt::BrushStyle mBrushStyle;
5859
QColor mBorderColor;
5960
Qt::PenStyle mBorderStyle;

src/core/symbology-ng/qgslinesymbollayerv2.cpp

Lines changed: 12 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -83,6 +83,11 @@ void QgsSimpleLineSymbolLayerV2::startRender( QgsSymbolV2RenderContext& context
8383
}
8484
mPen.setJoinStyle( mPenJoinStyle );
8585
mPen.setCapStyle( mPenCapStyle );
86+
87+
mSelPen = mPen;
88+
QColor selColor = context.selectionColor();
89+
if ( ! selectionIsOpaque ) selColor.setAlphaF( context.alpha() );
90+
mSelPen.setColor( selColor );
8691
}
8792

8893
void QgsSimpleLineSymbolLayerV2::stopRender( QgsSymbolV2RenderContext& context )
@@ -97,7 +102,7 @@ void QgsSimpleLineSymbolLayerV2::renderPolyline( const QPolygonF& points, QgsSym
97102
return;
98103
}
99104

100-
p->setPen( mPen );
105+
p->setPen( context.selected() ? mSelPen : mPen );
101106
if ( mOffset == 0 )
102107
{
103108
p->drawPolyline( points );
@@ -309,7 +314,7 @@ void QgsMarkerLineSymbolLayerV2::renderPolylineNoOffset( const QPolygonF& points
309314
// draw first marker
310315
if ( first )
311316
{
312-
mMarker->renderPoint( lastPt, rc );
317+
mMarker->renderPoint( lastPt, rc, -1, context.selected() );
313318
first = false;
314319
}
315320

@@ -319,7 +324,7 @@ void QgsMarkerLineSymbolLayerV2::renderPolylineNoOffset( const QPolygonF& points
319324
// "c" is 1 for regular point or in interval (0,1] for begin of line segment
320325
lastPt += c * diff;
321326
lengthLeft -= painterUnitInterval;
322-
mMarker->renderPoint( lastPt, rc );
327+
mMarker->renderPoint( lastPt, rc, -1, context.selected() );
323328
c = 1; // reset c (if wasn't 1 already)
324329
}
325330

@@ -401,6 +406,9 @@ void QgsLineDecorationSymbolLayerV2::startRender( QgsSymbolV2RenderContext& cont
401406
QColor penColor = mColor;
402407
penColor.setAlphaF( context.alpha() );
403408
mPen.setColor( penColor );
409+
QColor selColor = context.selectionColor();
410+
if ( ! selectionIsOpaque ) selColor.setAlphaF( context.alpha() );
411+
mSelPen.setColor( selColor );
404412
}
405413

406414
void QgsLineDecorationSymbolLayerV2::stopRender( QgsSymbolV2RenderContext& context )
@@ -442,7 +450,7 @@ void QgsLineDecorationSymbolLayerV2::renderPolyline( const QPolygonF& points, Qg
442450
QPointF p2_1 = p2 - QPointF( size * cos( angle1 ), size * sin( angle1 ) );
443451
QPointF p2_2 = p2 - QPointF( size * cos( angle2 ), size * sin( angle2 ) );
444452

445-
p->setPen( mPen );
453+
p->setPen( context.selected() ? mSelPen : mPen );
446454
p->drawLine( p2, p2_1 );
447455
p->drawLine( p2, p2_2 );
448456
}

src/core/symbology-ng/qgslinesymbollayerv2.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -64,6 +64,7 @@ class CORE_EXPORT QgsSimpleLineSymbolLayerV2 : public QgsLineSymbolLayerV2
6464
Qt::PenJoinStyle mPenJoinStyle;
6565
Qt::PenCapStyle mPenCapStyle;
6666
QPen mPen;
67+
QPen mSelPen;
6768
double mOffset;
6869
//use a custom dash dot pattern instead of the predefined ones
6970
bool mUseCustomDashPattern;
@@ -159,6 +160,7 @@ class CORE_EXPORT QgsLineDecorationSymbolLayerV2 : public QgsLineSymbolLayerV2
159160

160161
protected:
161162
QPen mPen;
163+
QPen mSelPen;
162164

163165
};
164166

src/core/symbology-ng/qgsmarkersymbollayerv2.cpp

Lines changed: 52 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -68,6 +68,10 @@ void QgsSimpleMarkerSymbolLayerV2::startRender( QgsSymbolV2RenderContext& contex
6868
mBrush = QBrush( mColor );
6969
mPen = QPen( mBorderColor );
7070
mPen.setWidthF( context.outputLineWidth( mPen.widthF() ) );
71+
QColor selColor = context.selectionColor();
72+
mSelBrush = QBrush( selColor );
73+
mSelPen = QPen( selColor == mColor ? selColor : mBorderColor );
74+
mSelPen.setWidthF( mPen.widthF() );
7175

7276
mPolygon.clear();
7377

@@ -148,6 +152,9 @@ void QgsSimpleMarkerSymbolLayerV2::startRender( QgsSymbolV2RenderContext& contex
148152
else
149153
{
150154
// some markers can't be drawn as a polygon (circle, cross)
155+
// For these set the selected border color to the selected color
156+
157+
if ( mName != "circle" ) mSelPen.setColor( selColor );
151158
}
152159

153160
// rotate if needed
@@ -176,10 +183,40 @@ void QgsSimpleMarkerSymbolLayerV2::startRender( QgsSymbolV2RenderContext& contex
176183
drawMarker( &p, context );
177184
p.end();
178185

186+
// Construct the selected version of the Cache
187+
188+
mSelCache = QImage( QSize( imageSize, imageSize ), QImage::Format_ARGB32_Premultiplied );
189+
mSelCache.fill( 0 );
190+
191+
p.begin( &mSelCache );
192+
p.setRenderHint( QPainter::Antialiasing );
193+
p.setBrush( mSelBrush );
194+
p.setPen( mSelPen );
195+
p.translate( QPointF( center, center ) );
196+
drawMarker( &p, context );
197+
p.end();
198+
199+
// Check that the selected version is different. If not, then re-render,
200+
// filling the background with the selection colour and using the normal
201+
// colours for the symbol .. could be ugly!
202+
203+
if ( mSelCache == mCache )
204+
{
205+
p.begin( &mSelCache );
206+
p.setRenderHint( QPainter::Antialiasing );
207+
p.fillRect( 0, 0, imageSize, imageSize, selColor );
208+
p.setBrush( mBrush );
209+
p.setPen( mPen );
210+
p.translate( QPointF( center, center ) );
211+
drawMarker( &p, context );
212+
p.end();
213+
}
214+
179215
//opacity
180216
if ( context.alpha() < 1.0 )
181217
{
182218
QgsSymbolLayerV2Utils::multiplyImageOpacity( &mCache, context.alpha() );
219+
if ( ! selectionIsOpaque ) QgsSymbolLayerV2Utils::multiplyImageOpacity( &mSelCache, context.alpha() );
183220
}
184221
}
185222

@@ -203,11 +240,12 @@ void QgsSimpleMarkerSymbolLayerV2::renderPoint( const QPointF& point, QgsSymbolV
203240
//p->translate(point);
204241

205242
//drawMarker(p);
206-
//mCache.save("/home/marco/tmp/marker.png", "PNG");
207-
double s = mCache.width() / context.renderContext().rasterScaleFactor();
243+
//mCache.save("/home/marco/tmp/marker.png","PNG");
244+
QImage &img = context.selected() ? mSelCache : mCache;
245+
double s = img.width() / context.renderContext().rasterScaleFactor();
208246
p->drawImage( QRectF( point.x() - s / 2.0 + context.outputLineWidth( mOffset.x() ),
209247
point.y() - s / 2.0 + context.outputLineWidth( mOffset.y() ),
210-
s, s ), mCache );
248+
s, s ), img );
211249
//p->restore();
212250
}
213251

@@ -328,6 +366,13 @@ void QgsSvgMarkerSymbolLayerV2::startRender( QgsSymbolV2RenderContext& context )
328366
QSvgRenderer renderer( mPath );
329367
QPainter painter( &mPicture );
330368
renderer.render( &painter, rect );
369+
double selPictureSize = pictureSize * 1.2;
370+
QPainter selPainter( &mSelPicture );
371+
selPainter.setRenderHint( QPainter::Antialiasing );
372+
selPainter.setBrush( QBrush( context.selectionColor() ) );
373+
selPainter.setPen( Qt::NoPen );
374+
selPainter.drawEllipse( QPointF( 0, 0 ), pictureSize*0.6, pictureSize*0.6 );
375+
renderer.render( &selPainter, rect );
331376
}
332377

333378
void QgsSvgMarkerSymbolLayerV2::stopRender( QgsSymbolV2RenderContext& context )
@@ -350,7 +395,8 @@ void QgsSvgMarkerSymbolLayerV2::renderPoint( const QPointF& point, QgsSymbolV2Re
350395
if ( mAngle != 0 )
351396
p->rotate( mAngle );
352397

353-
p->drawPicture( 0, 0, mPicture );
398+
QPicture &pct = context.selected() ? mSelPicture : mPicture;
399+
p->drawPicture( 0, 0, pct );
354400

355401
if ( mAngle != 0 )
356402
p->rotate( -mAngle );
@@ -515,7 +561,7 @@ QString QgsFontMarkerSymbolLayerV2::layerType() const
515561

516562
void QgsFontMarkerSymbolLayerV2::startRender( QgsSymbolV2RenderContext& context )
517563
{
518-
mFont = QFont( mFontFamily, MM2POINT( mSize ) );
564+
mFont = QFont( mFontFamily, MM2POINT( mSize ) / context.renderContext().rasterScaleFactor() );
519565
QFontMetrics fm( mFont );
520566
mChrOffset = QPointF( fm.width( mChr ) / 2, -fm.ascent() / 2 );
521567

@@ -529,7 +575,7 @@ void QgsFontMarkerSymbolLayerV2::stopRender( QgsSymbolV2RenderContext& context )
529575
void QgsFontMarkerSymbolLayerV2::renderPoint( const QPointF& point, QgsSymbolV2RenderContext& context )
530576
{
531577
QPainter* p = context.renderContext().painter();
532-
QColor penColor = mColor;
578+
QColor penColor = context.selected() ? context.selectionColor() : mColor;
533579
penColor.setAlphaF( context.alpha() );
534580
p->setPen( penColor );
535581
p->setFont( mFont );

src/core/symbology-ng/qgsmarkersymbollayerv2.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -59,6 +59,9 @@ class CORE_EXPORT QgsSimpleMarkerSymbolLayerV2 : public QgsMarkerSymbolLayerV2
5959
QPolygonF mPolygon;
6060
QString mName;
6161
QImage mCache;
62+
QPen mSelPen;
63+
QBrush mSelBrush;
64+
QImage mSelCache;
6265
};
6366

6467
//////////
@@ -110,6 +113,7 @@ class CORE_EXPORT QgsSvgMarkerSymbolLayerV2 : public QgsMarkerSymbolLayerV2
110113

111114
QString mPath;
112115
QPicture mPicture;
116+
QPicture mSelPicture;
113117
};
114118

115119

0 commit comments

Comments
 (0)