QGIS API Documentation  2.5.0-Master
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Modules Pages
qgsrendererv2widget.cpp
Go to the documentation of this file.
1 /***************************************************************************
2  qgsrendererv2widget.cpp
3  ---------------------
4  begin : November 2009
5  copyright : (C) 2009 by Martin Dobias
6  email : wonder dot sk at gmail dot com
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 #include "qgsrendererv2widget.h"
16 #include "qgssymbolv2.h"
17 #include "qgsvectorlayer.h"
18 #include <QColorDialog>
19 #include <QMessageBox>
20 #include <QInputDialog>
21 #include <QMenu>
22 
25 
26 
28  : QWidget(), mLayer( layer ), mStyle( style )
29 {
30  contextMenu = new QMenu( "Renderer Options " );
31 
32  mCopyAction = contextMenu->addAction( tr( "Copy" ), this, SLOT( copy() ) );
33  mCopyAction->setShortcut( QKeySequence( QKeySequence::Copy ) );
34  mPasteAction = contextMenu->addAction( tr( "Paste" ), this, SLOT( paste() ) );
35  mPasteAction->setShortcut( QKeySequence( QKeySequence::Paste ) );
36 
37  contextMenu->addSeparator();
38  contextMenu->addAction( tr( "Change color" ), this, SLOT( changeSymbolColor( ) ) );
39  contextMenu->addAction( tr( "Change transparency" ), this, SLOT( changeSymbolTransparency() ) );
40  contextMenu->addAction( tr( "Change output unit" ), this, SLOT( changeSymbolUnit() ) );
41 
42  if ( mLayer && mLayer->geometryType() == QGis::Line )
43  {
44  contextMenu->addAction( tr( "Change width" ), this, SLOT( changeSymbolWidth() ) );
45  }
46  else if ( mLayer && mLayer->geometryType() == QGis::Point )
47  {
48  contextMenu->addAction( tr( "Change size" ), this, SLOT( changeSymbolSize() ) );
49  }
50 }
51 
53 {
54  contextMenu->exec( QCursor::pos() );
55 }
56 
58 {
59  QList<QgsSymbolV2*> symbolList = selectedSymbols();
60  if ( symbolList.size() < 1 )
61  {
62  return;
63  }
64 
65  QColor color = QColorDialog::getColor( symbolList.at( 0 )->color(), this, "Change Symbol Color", QColorDialog::ShowAlphaChannel );
66  if ( color.isValid() )
67  {
68  QList<QgsSymbolV2*>::iterator symbolIt = symbolList.begin();
69  for ( ; symbolIt != symbolList.end(); ++symbolIt )
70  {
71  ( *symbolIt )->setColor( color );
72  }
74  }
75 }
76 
78 {
79  QList<QgsSymbolV2*> symbolList = selectedSymbols();
80  if ( symbolList.size() < 1 )
81  {
82  return;
83  }
84 
85  bool ok;
86  double oldTransparency = ( 1 - symbolList.at( 0 )->alpha() ) * 100; // convert to percents
87  double transparency = QInputDialog::getDouble( this, tr( "Transparency" ), tr( "Change symbol transparency [%]" ), oldTransparency, 0.0, 100.0, 0, &ok );
88  if ( ok )
89  {
90  QList<QgsSymbolV2*>::iterator symbolIt = symbolList.begin();
91  for ( ; symbolIt != symbolList.end(); ++symbolIt )
92  {
93  ( *symbolIt )->setAlpha( 1 - transparency / 100 );
94  }
96  }
97 }
98 
100 {
101  QList<QgsSymbolV2*> symbolList = selectedSymbols();
102  if ( symbolList.size() < 1 )
103  {
104  return;
105  }
106 
107  bool ok;
108  int currentUnit = ( symbolList.at( 0 )->outputUnit() == QgsSymbolV2::MM ) ? 0 : 1;
109  QString item = QInputDialog::getItem( this, tr( "Symbol unit" ), tr( "Select symbol unit" ), QStringList() << tr( "Millimeter" ) << tr( "Map unit" ), currentUnit, false, &ok );
110  if ( ok )
111  {
112  QgsSymbolV2::OutputUnit unit = ( item.compare( tr( "Millimeter" ) ) == 0 ) ? QgsSymbolV2::MM : QgsSymbolV2::MapUnit;
113 
114  QList<QgsSymbolV2*>::iterator symbolIt = symbolList.begin();
115  for ( ; symbolIt != symbolList.end(); ++symbolIt )
116  {
117  ( *symbolIt )->setOutputUnit( unit );
118  }
120  }
121 }
122 
124 {
125  QList<QgsSymbolV2*> symbolList = selectedSymbols();
126  if ( symbolList.size() < 1 )
127  {
128  return;
129  }
130 
131  bool ok;
132  double width = QInputDialog::getDouble( this, tr( "Width" ), tr( "Change symbol width" ), dynamic_cast<QgsLineSymbolV2*>( symbolList.at( 0 ) )->width(), 0.0, 999999, 1, &ok );
133  if ( ok )
134  {
135  QList<QgsSymbolV2*>::iterator symbolIt = symbolList.begin();
136  for ( ; symbolIt != symbolList.end(); ++symbolIt )
137  {
138  dynamic_cast<QgsLineSymbolV2*>( *symbolIt )->setWidth( width );
139  }
141  }
142 }
143 
145 {
146  QList<QgsSymbolV2*> symbolList = selectedSymbols();
147  if ( symbolList.size() < 1 )
148  {
149  return;
150  }
151 
152  bool ok;
153  double size = QInputDialog::getDouble( this, tr( "Size" ), tr( "Change symbol size" ), dynamic_cast<QgsMarkerSymbolV2*>( symbolList.at( 0 ) )->size(), 0.0, 999999, 1, &ok );
154  if ( ok )
155  {
156  QList<QgsSymbolV2*>::iterator symbolIt = symbolList.begin();
157  for ( ; symbolIt != symbolList.end(); ++symbolIt )
158  {
159  dynamic_cast<QgsMarkerSymbolV2*>( *symbolIt )->setSize( size );
160  }
162  }
163 }
164 
166 {
167  QgsLegendSymbolList symbols = r->legendSymbolItems();
168 
169  QgsSymbolLevelsV2Dialog dlg( symbols, r->usingSymbolLevels(), this );
170 
171  if ( dlg.exec() )
172  {
173  r->setUsingSymbolLevels( dlg.usingLevels() );
174  }
175 }
176 
177 
179 
180 //#include <QAction>
181 #include "qgsfield.h"
182 #include <QMenu>
183 
184 QgsRendererV2DataDefinedMenus::QgsRendererV2DataDefinedMenus( QMenu* menu, QgsVectorLayer* layer, QString rotationField, QString sizeScaleField, QgsSymbolV2::ScaleMethod scaleMethod )
185  : QObject( menu ), mLayer( layer )
186 {
187  mRotationMenu = new QMenu( tr( "Rotation field" ) );
188  mSizeScaleMenu = new QMenu( tr( "Size scale field" ) );
189 
190  mRotationAttributeActionGroup = new QActionGroup( mRotationMenu );
191  mSizeAttributeActionGroup = new QActionGroup( mSizeScaleMenu );
192  mSizeMethodActionGroup = new QActionGroup( mSizeScaleMenu );
193 
196 
197  mSizeScaleMenu->addSeparator();
198 
199  QAction* aScaleByArea = new QAction( tr( "Scale area" ), mSizeMethodActionGroup ) ;
200  QAction* aScaleByDiameter = new QAction( tr( "Scale diameter" ), mSizeMethodActionGroup );
201 
202  aScaleByArea->setCheckable( true );
203  aScaleByDiameter->setCheckable( true );
204 
205  if ( scaleMethod == QgsSymbolV2::ScaleDiameter )
206  {
207  aScaleByDiameter->setChecked( true );
208  }
209  else
210  {
211  aScaleByArea->setChecked( true );
212  }
213 
214  mSizeScaleMenu->addActions( mSizeMethodActionGroup->actions() );
215 
216  menu->addMenu( mRotationMenu );
217  menu->addMenu( mSizeScaleMenu );
218 
219  connect( mSizeMethodActionGroup, SIGNAL( triggered( QAction* ) ), this, SLOT( scaleMethodSelected( QAction* ) ) );
220  connect( mRotationAttributeActionGroup, SIGNAL( triggered( QAction* ) ), this, SLOT( rotationFieldSelected( QAction* ) ) );
221  connect( mSizeAttributeActionGroup, SIGNAL( triggered( QAction* ) ), this, SLOT( sizeScaleFieldSelected( QAction* ) ) );
222 }
223 
225 {
226  delete mSizeMethodActionGroup;
229  delete mRotationMenu;
230  delete mSizeScaleMenu;
231 }
232 
233 void QgsRendererV2DataDefinedMenus::populateMenu( QMenu* menu, QString fieldName, QActionGroup *actionGroup )
234 {
235  QAction* aExpr = new QAction( tr( "- expression -" ), actionGroup );
236  aExpr->setCheckable( true );
237  menu->addAction( aExpr );
238  menu->addSeparator();
239  QAction* aNo = new QAction( tr( "- no field -" ), actionGroup );
240  aNo->setCheckable( true );
241  menu->addAction( aNo );
242  menu->addSeparator();
243 
244  bool hasField = false;
245  const QgsFields & flds = mLayer->pendingFields();
246  for ( int idx = 0; idx < flds.count(); ++idx )
247  {
248  const QgsField& fld = flds[idx];
249  if ( fld.type() == QVariant::Int || fld.type() == QVariant::Double )
250  {
251  QAction* a = new QAction( fld.name(), actionGroup );
252  a->setCheckable( true );
253  if ( fieldName == fld.name() )
254  {
255  a->setChecked( true );
256  hasField = true;
257  }
258  menu->addAction( a );
259  }
260  }
261 
262  if ( !hasField )
263  {
264  if ( fieldName.isEmpty() )
265  {
266  aNo->setChecked( true );
267  }
268  else
269  {
270  aExpr->setChecked( true );
271  aExpr->setText( tr( "- expression -" ) + fieldName );
272  }
273  }
274 
275 }
276 
278 {
279  if ( a == NULL )
280  return;
281 
282  QString fldName = a->text();
283 #if 0
284  updateMenu( mRotationAttributeActionGroup, fldName );
285 #endif
286  if ( fldName == tr( "- no field -" ) )
287  {
288  fldName = QString();
289  }
290  else if ( fldName.startsWith( tr( "- expression -" ) ) )
291  {
292  QString expr( fldName );
293  expr.replace( 0, tr( "- expression -" ).length(), "" );
294  QgsExpressionBuilderDialog dialog( mLayer, expr );
295  if ( !dialog.exec() ) return;
296  fldName = dialog.expressionText();
297  Q_ASSERT( !QgsExpression( fldName ).hasParserError() );
298  a->setText( tr( "- expression -" ) + fldName );
299  }
300 
301  emit rotationFieldChanged( fldName );
302 }
303 
305 {
306  if ( a == NULL )
307  return;
308 
309  QString fldName = a->text();
310 #if 0
311  updateMenu( mSizeAttributeActionGroup, fldName );
312 #endif
313  if ( fldName == tr( "- no field -" ) )
314  {
315  fldName = QString();
316  }
317  else if ( fldName.startsWith( tr( "- expression -" ) ) )
318  {
319  QString expr( fldName );
320  expr.replace( 0, tr( "- expression -" ).length(), "" );
321  QgsExpressionBuilderDialog dialog( mLayer, expr );
322  if ( !dialog.exec() ) return;
323  fldName = dialog.expressionText();
324  Q_ASSERT( !QgsExpression( fldName ).hasParserError() );
325  a->setText( tr( "- expression -" ) + fldName );
326  }
327 
328  emit sizeScaleFieldChanged( fldName );
329 }
330 
332 {
333  if ( a == NULL )
334  return;
335 
336  if ( a->text() == tr( "Scale area" ) )
337  {
339  }
340  else if ( a->text() == tr( "Scale diameter" ) )
341  {
343  }
344 }
345 #if 0 // MK: is there any reason for this?
346 void QgsRendererV2DataDefinedMenus::updateMenu( QActionGroup* actionGroup, QString fieldName )
347 {
348  foreach ( QAction* a, actionGroup->actions() )
349  {
350  a->setChecked( a->text() == fieldName );
351  }
352 }
353 #endif
Class for parsing and evaluation of expressions (formerly called "search strings").
Definition: qgsexpression.h:89
void showSymbolLevelsDialog(QgsFeatureRendererV2 *r)
show a dialog with renderer's symbol level settings
const QString & name() const
Gets the name of the field.
Definition: qgsfield.cpp:58
virtual QList< QgsSymbolV2 * > selectedSymbols()
Subclasses may provide the capability of changing multiple symbols at once by implementing the follow...
void changeSymbolTransparency()
Change opacity of selected symbols.
void changeSymbolSize()
Change marker sizes of selected symbols.
void contextMenuViewCategories(const QPoint &p)
virtual QgsLegendSymbolList legendSymbolItems(double scaleDenominator=-1, QString rule="")
return a list of item text / symbol
Container of fields for a vector layer.
Definition: qgsfield.h:163
void populateMenu(QMenu *menu, QString fieldName, QActionGroup *actionGroup)
void changeSymbolWidth()
Change line widths of selected symbols.
void setWidth(double width)
QgsVectorLayer * mLayer
void changeSymbolUnit()
Change units mm/map units of selected symbols.
void rotationFieldChanged(QString fldName)
void setSize(double size)
void changeSymbolColor()
Change color of selected symbols.
int count() const
Return number of items.
Definition: qgsfield.h:200
QGis::GeometryType geometryType() const
Returns point, line or polygon.
Encapsulate a field in an attribute table or data source.
Definition: qgsfield.h:33
void scaleMethodChanged(QgsSymbolV2::ScaleMethod scaleMethod)
QgsRendererV2Widget(QgsVectorLayer *layer, QgsStyleV2 *style)
void setUsingSymbolLevels(bool usingSymbolLevels)
void sizeScaleFieldChanged(QString fldName)
bool usingSymbolLevels() const
const QgsFields & pendingFields() const
returns field list in the to-be-committed state
virtual void refreshSymbolView()
QgsRendererV2DataDefinedMenus(QMenu *menu, QgsVectorLayer *layer, QString rotationField, QString sizeScaleField, QgsSymbolV2::ScaleMethod scaleMethod)
Represents a vector layer which manages a vector based data sets.
double size
Definition: qgssvgcache.cpp:77
QList< QPair< QString, QgsSymbolV2 * > > QgsLegendSymbolList
Definition: qgsrendererv2.h:41
A generic dialog for building expression strings.
QVariant::Type type() const
Gets variant type of the field as it will be retrieved from data source.
Definition: qgsfield.cpp:63
#define tr(sourceText)