Skip to content

Commit

Permalink
[FEATURE] symbology enhancements:
Browse files Browse the repository at this point in the history
- add QgsMarkerCatalogue::refreshList() to refresh the symbol list w/o restart
- allow refresh of symbols via popup menu on the renderer's symbol selection
- add support for data define symbol(name)s
- add support for font symbol markers (only data define - no gui yet)
- pass QgsRenderContext to rendering methods
- add symbol size in map units (ie. symbols that keep the size in mapunits
  independant of the mapscale)



git-svn-id: http://svn.osgeo.org/qgis/trunk@11152 c8812cc2-4d05-0410-92ff-de0c093fc19c
  • Loading branch information
jef committed Jul 23, 2009
1 parent c3f6fb8 commit 0c59c74
Show file tree
Hide file tree
Showing 28 changed files with 738 additions and 410 deletions.
5 changes: 3 additions & 2 deletions python/core/qgscontinuouscolorrenderer.sip
Expand Up @@ -10,8 +10,9 @@ class QgsContinuousColorRenderer : QgsRenderer
QgsContinuousColorRenderer(QGis::GeometryType type);
QgsContinuousColorRenderer(const QgsContinuousColorRenderer& other);
virtual ~QgsContinuousColorRenderer();
/**Renders the feature using the minimum and maximum value of the classification field*/
void renderFeature(QPainter* p, QgsFeature& f, QImage* img, bool selected, double widthScale = 1.0, double rasterScaleFactor = 1.0);
/**Renders the feature using the minimum and maximum value of the classification field
* added in 1.2 */
void renderFeature(QgsRenderContext &renderContext, QgsFeature& f, QImage* img, bool selected);
/**Returns the number of the classification field*/
int classificationField() const;
/**Sets the id of the classification field*/
Expand Down
4 changes: 2 additions & 2 deletions python/core/qgsgraduatedsymbolrenderer.sip
Expand Up @@ -48,11 +48,11 @@ class QgsGraduatedSymbolRenderer : QgsRenderer
@param f a pointer to the feature to determine if rendering will happen*/
bool willRenderFeature(QgsFeature *f);

/**Renders an OGRFeature
/**Renders a feature
\param p a painter (usually the one from the current map canvas)
\param f a pointer to a feature to render
\param t the transform object containing the information how to transform the map coordinates to screen coordinates*/
void renderFeature(QPainter* p, QgsFeature& f, QImage* img, bool selected, double widthScale = 1.0, double rasterScaleFactor = 1.0);
void renderFeature(QgsRenderContext &renderContext, QgsFeature& f, QImage* img, bool selected);

/**Sets the number of the classicifation field
\param field the number of the field to classify*/
Expand Down
16 changes: 13 additions & 3 deletions python/core/qgslabel.sip
Expand Up @@ -45,14 +45,24 @@ public:
QgsPoint p;
double angle;
};



/** \brief render label
* \param sizeScale global scale factor for size in pixels, labels in map units are not scaled
*/
\note deprecated
*/
void renderLabel ( QPainter* painter, QgsRectangle& viewExtent,
QgsCoordinateTransform* coordinateTransform,
QgsMapToPixel *transform,
QgsFeature &feature, bool selected, QgsLabelAttributes *classAttributes=0, double sizeScale = 1, double rasterScaleFactor = 1);

/** \brief render label
* \param renderContext renderer context
* \param feature feature to render
* \param selected is to be shown selected
* \param classAttributes attributes to use for labeling
* \note added in 1.2
*/
void renderLabel ( QgsRenderContext &renderContext, QgsFeature &feature, bool selected, QgsLabelAttributes *classAttributes=0);

/** Reads the renderer configuration from an XML file
@param rnode the Dom node to read
Expand Down
12 changes: 11 additions & 1 deletion python/core/qgsmarkercatalogue.sip
@@ -1,6 +1,6 @@

/** Catalogue of point symbols */
class QgsMarkerCatalogue /NoDefaultCtors/
class QgsMarkerCatalogue : QObject /NoDefaultCtors/
{
%TypeHeaderCode
#include <qgsmarkercatalogue.h>
Expand Down Expand Up @@ -29,5 +29,15 @@ public:
/** Returns a pixmap given a file name of a svg marker
* NOTE: this method needs to be public static for QgsMarkerDialog::visualizeMarkers */
static void svgMarker (QPainter * thepPainter, QString name, int size );

public slots:
// reload the symbols
// added in 1.2
void refreshList();

signals:
// symbols were reloaded
// added in 1.2
void markersRefreshed();
};

18 changes: 16 additions & 2 deletions python/core/qgsrenderer.sip
Expand Up @@ -15,8 +15,22 @@ class QgsRenderer
@param p the painter storing brush and pen
@param f a pointer to the feature to be rendered
@param pic pointer to a marker from SVG (is only used by marker renderers)
@param scalefactor pointer to the scale factor for the marker image*/
virtual void renderFeature(QPainter* p, QgsFeature& f,QImage* pic, bool selected, double widthScale = 1.0, double rasterScaleFactor = 1.0)=0;
@param selected feature is to be shown selected
@param widthScale scale factor
@param rasterScaleFactor scale factor for rasters

deprecated */
void renderFeature(QPainter* p, QgsFeature& f,QImage* pic, bool selected, double widthScale = 1.0, double rasterScaleFactor = 1.0);

/**A vector layer passes features to a renderer object to change the brush ans pen of the qpainter
@param renderContext context of the rendering operation
@param f the feature to render
@param pic pointer to marker to render (is only used by marker renderers)
@param selected the feature is to be shown selected

added in 1.2 */
virtual void renderFeature(QgsRenderContext &renderContext, QgsFeature& f,QImage* pic, bool selected)=0;

/**Reads the renderer configuration from an XML file
@param rnode the Dom node to read
@param vl the vector layer which will be associated with the renderer*/
Expand Down
7 changes: 5 additions & 2 deletions python/core/qgssinglesymbolrenderer.sip
Expand Up @@ -9,12 +9,15 @@ class QgsSingleSymbolRenderer : QgsRenderer
QgsSingleSymbolRenderer(QGis::GeometryType type);
QgsSingleSymbolRenderer(const QgsSingleSymbolRenderer& other);
virtual ~QgsSingleSymbolRenderer();

/**Replaces the current mSymbol by sy*/
void addSymbol(QgsSymbol* sy /Transfer/);
/*Returns a pointer to mSymbol*/
const QgsSymbol* symbol() const;
/**Renders an OGRFeature*/
void renderFeature(QPainter* p, QgsFeature& f, QImage* img, bool selected, double widthScale = 1.0, double rasterScaleFactor = 1.0);

/**Renders a feature added in 1.2 */
void renderFeature(QgsRenderContext &renderContext, QgsFeature& f, QImage* img, bool selected);

/**Reads the renderer configuration from an XML file
@param rnode the Dom node to read
@param vl the vector layer which will be associated with the renderer*/
Expand Down
6 changes: 5 additions & 1 deletion python/core/qgsuniquevaluerenderer.sip
Expand Up @@ -11,7 +11,11 @@ class QgsUniqueValueRenderer : QgsRenderer
/** Determines if a feature will be rendered or not
@param f a pointer to the feature to determine if rendering will happen*/
bool willRenderFeature(QgsFeature *f);
void renderFeature(QPainter* p, QgsFeature& f, QImage* img, bool selected, double widthScale = 1.0, double rasterScaleFactor = 1.0);

/* render feature
* added in 1.2 */
void renderFeature(QgsRenderContext &renderContext, QgsFeature& f, QImage* img, bool selected);

/**Reads the renderer configuration from an XML file
@param rnode the Dom node to read
@param vl the vector layer which will be associated with the renderer*/
Expand Down
97 changes: 71 additions & 26 deletions src/app/qgssinglesymboldialog.cpp
Expand Up @@ -40,7 +40,7 @@ QgsSingleSymbolDialog::QgsSingleSymbolDialog(): QDialog(), mVectorLayer( 0 )
QgsDebugMsg( "entered." );
}

QgsSingleSymbolDialog::QgsSingleSymbolDialog( QgsVectorLayer * layer, bool disabled ): QDialog(), mVectorLayer( layer )
QgsSingleSymbolDialog::QgsSingleSymbolDialog( QgsVectorLayer * layer, bool disabled ): QDialog(), mVectorLayer( layer ), mDisabled( disabled )
{
setupUi( this );
QgsDebugMsg( "entered." );
Expand All @@ -59,6 +59,43 @@ QgsSingleSymbolDialog::QgsSingleSymbolDialog( QgsVectorLayer * layer, bool disab
// loops can be removed now with changes I have made to use combo
// boxes for line style and fill style...test and remove if poss.

QAction *refreshAction = new QAction( tr( "Refresh markers" ), lstSymbols );
lstSymbols->addAction( refreshAction );
connect( refreshAction, SIGNAL( triggered() ), QgsMarkerCatalogue::instance(), SLOT( refreshList() ) );
connect( QgsMarkerCatalogue::instance(), SIGNAL( markersRefreshed() ), this, SLOT( refreshMarkers() ) );
lstSymbols->setContextMenuPolicy( Qt::ActionsContextMenu );

//do the signal/slot connections
connect( btnOutlineColor, SIGNAL( clicked() ), this, SLOT( selectOutlineColor() ) );
connect( btnFillColor, SIGNAL( clicked() ), this, SLOT( selectFillColor() ) );
connect( outlinewidthspinbox, SIGNAL( valueChanged( double ) ), this, SLOT( resendSettingsChanged() ) );
connect( mLabelEdit, SIGNAL( textChanged( const QString& ) ), this, SLOT( resendSettingsChanged() ) );
connect( lstSymbols, SIGNAL( currentItemChanged( QListWidgetItem *, QListWidgetItem * ) ),
this, SLOT( symbolChanged( QListWidgetItem *, QListWidgetItem * ) ) );
connect( mPointSizeSpinBox, SIGNAL( valueChanged( double ) ), this, SLOT( resendSettingsChanged() ) );
connect( mPointSizeUnitsCheckBox, SIGNAL( toggled() ), this, SLOT( resendSettingsChanged() ) );
connect( mRotationClassificationComboBox, SIGNAL( currentIndexChanged( const QString & ) ),
this, SLOT( resendSettingsChanged() ) );
connect( mScaleClassificationComboBox, SIGNAL( currentIndexChanged( const QString & ) ),
this, SLOT( resendSettingsChanged() ) );
connect( mSymbolComboBox, SIGNAL( currentIndexChanged( const QString & ) ),
this, SLOT( resendSettingsChanged() ) );
connect( cboOutlineStyle, SIGNAL(
currentIndexChanged( const QString & ) ), this, SLOT( resendSettingsChanged() ) );
connect( cboFillStyle, SIGNAL(
currentIndexChanged( const QString & ) ), this, SLOT( resendSettingsChanged() ) );
//need this to deal with when texture fill is selected or deselected
connect( cboFillStyle, SIGNAL(
currentIndexChanged( int ) ), this, SLOT( fillStyleChanged( int ) ) );
connect( toolSelectTexture, SIGNAL( clicked() ), this, SLOT( selectTextureImage() ) );

refreshMarkers();
}

void QgsSingleSymbolDialog::refreshMarkers()
{
lstSymbols->blockSignals( true );
lstSymbols->clear();

QPen pen( QColor( 0, 0, 255 ) );
QBrush brush( QColor( 220, 220, 220 ), Qt::SolidPattern );
Expand All @@ -73,17 +110,18 @@ QgsSingleSymbolDialog::QgsSingleSymbolDialog( QgsVectorLayer * layer, bool disab
myIcon.addPixmap( myPixmap );
mypItem->setIcon( myIcon );
mypItem->setText( "" );
mypItem->setToolTip( *it );
//store the symbol offset in the UserData role for later retrieval
mypItem->setData( Qt::UserRole, *it );
mypItem->setFlags( Qt::ItemIsSelectable | Qt::ItemIsEnabled );
if ( layer->geometryType() != QGis::Point )
if ( mVectorLayer && mVectorLayer->geometryType() != QGis::Point )
{
break;
}
++myCounter;
}

// Find out the numerical fields of mVectorLayer, and populate the ComboBox
// Find out the numerical fields of mVectorLayer, and populate the ComboBoxes
QgsVectorDataProvider *provider = mVectorLayer->dataProvider();
if ( provider )
{
Expand All @@ -92,6 +130,7 @@ QgsSingleSymbolDialog::QgsSingleSymbolDialog( QgsVectorLayer * layer, bool disab

mRotationClassificationComboBox->addItem( DO_NOT_USE_STR, -1 );
mScaleClassificationComboBox->addItem( DO_NOT_USE_STR, -1 );
mSymbolComboBox->addItem( DO_NOT_USE_STR, -1 );
for ( QgsFieldMap::const_iterator it = fields.begin();
it != fields.end();
++it )
Expand All @@ -102,6 +141,10 @@ QgsSingleSymbolDialog::QgsSingleSymbolDialog( QgsVectorLayer * layer, bool disab
mRotationClassificationComboBox->addItem( it->name(), it.key() );
mScaleClassificationComboBox->addItem( it->name(), it.key() );
}
else if ( type == QVariant::String )
{
mSymbolComboBox->addItem( it->name(), it.key() );
}
}
}
else
Expand Down Expand Up @@ -139,13 +182,13 @@ QgsSingleSymbolDialog::QgsSingleSymbolDialog( QgsVectorLayer * layer, bool disab
cboFillStyle->addItem( QIcon( QgsSymbologyUtils::char2PatternPixmap( "NoBrush" ) ), tr( "No Brush" ), "NoBrush" );
cboFillStyle->addItem( QIcon( QgsSymbologyUtils::char2PatternPixmap( "TexturePattern" ) ), tr( "Texture" ), "TexturePattern" );

if ( mVectorLayer && layer->geometryType() != QGis::Point )
if ( mVectorLayer && mVectorLayer->geometryType() != QGis::Point )
{
mGroupPoint->setVisible( false );
mGroupPoint->setEnabled( false );
}

if ( disabled )
if ( mDisabled )
{
unset();
}
Expand Down Expand Up @@ -173,27 +216,7 @@ QgsSingleSymbolDialog::QgsSingleSymbolDialog( QgsVectorLayer * layer, bool disab
}
}

//do the signal/slot connections
connect( btnOutlineColor, SIGNAL( clicked() ), this, SLOT( selectOutlineColor() ) );
connect( btnFillColor, SIGNAL( clicked() ), this, SLOT( selectFillColor() ) );
connect( outlinewidthspinbox, SIGNAL( valueChanged( double ) ), this, SLOT( resendSettingsChanged() ) );
connect( mLabelEdit, SIGNAL( textChanged( const QString& ) ), this, SLOT( resendSettingsChanged() ) );
connect( lstSymbols, SIGNAL( currentItemChanged( QListWidgetItem *, QListWidgetItem * ) ),
this, SLOT( symbolChanged( QListWidgetItem *, QListWidgetItem * ) ) );
connect( mPointSizeSpinBox, SIGNAL( valueChanged( double ) ), this, SLOT( resendSettingsChanged() ) );
connect( mRotationClassificationComboBox, SIGNAL( currentIndexChanged( const QString & ) ),
this, SLOT( resendSettingsChanged() ) );
connect( mScaleClassificationComboBox, SIGNAL( currentIndexChanged( const QString & ) ),
this, SLOT( resendSettingsChanged() ) );
connect( cboOutlineStyle, SIGNAL(
currentIndexChanged( const QString & ) ), this, SLOT( resendSettingsChanged() ) );
connect( cboFillStyle, SIGNAL(
currentIndexChanged( const QString & ) ), this, SLOT( resendSettingsChanged() ) );
//need this to deal with when texture fill is selected or deselected
connect( cboFillStyle, SIGNAL(
currentIndexChanged( int ) ), this, SLOT( fillStyleChanged( int ) ) );
connect( toolSelectTexture, SIGNAL( clicked() ), this, SLOT( selectTextureImage() ) );

lstSymbols->blockSignals( false );
}

QgsSingleSymbolDialog::~QgsSingleSymbolDialog()
Expand Down Expand Up @@ -264,6 +287,8 @@ void QgsSingleSymbolDialog::apply( QgsSymbol *sy )
if ( mPointSizeSpinBox->isEnabled() )
sy->setPointSize( mPointSizeSpinBox->value() );

if ( mPointSizeUnitsCheckBox->isEnabled() )
sy->setPointSizeUnits( mPointSizeUnitsCheckBox->isChecked() );

std::map<QString, int>::iterator iter;
if ( mRotationClassificationComboBox->isEnabled() )
Expand All @@ -276,6 +301,11 @@ void QgsSingleSymbolDialog::apply( QgsSymbol *sy )
sy->setScaleClassificationField( mScaleClassificationComboBox->itemData( mScaleClassificationComboBox->currentIndex() ).toInt() );
}

if ( mSymbolComboBox->isEnabled() )
{
sy->setSymbolField( mSymbolComboBox->itemData( mSymbolComboBox->currentIndex() ).toInt() );
}

//
// Apply the line style
//
Expand Down Expand Up @@ -323,8 +353,10 @@ void QgsSingleSymbolDialog::unset()
mLabelEdit->setEnabled( false );
lstSymbols->setEnabled( false );
mPointSizeSpinBox->setEnabled( false );
mPointSizeUnitsCheckBox->setEnabled( false );
mRotationClassificationComboBox->setEnabled( false );
mScaleClassificationComboBox->setEnabled( false );
mSymbolComboBox->setEnabled( false );
outlinewidthspinbox->setEnabled( false );
btnOutlineColor->setEnabled( false );
cboOutlineStyle->setEnabled( false );
Expand All @@ -350,6 +382,7 @@ void QgsSingleSymbolDialog::set( const QgsSymbol *sy )
}
}
mPointSizeSpinBox->setValue( sy->pointSize() );
mPointSizeUnitsCheckBox->setChecked( sy->pointSizeUnits() );

int index;

Expand All @@ -359,6 +392,9 @@ void QgsSingleSymbolDialog::set( const QgsSymbol *sy )
index = mScaleClassificationComboBox->findData( sy->scaleClassificationField() );
mScaleClassificationComboBox->setCurrentIndex( index < 0 ? 0 : index );

index = mSymbolComboBox->findData( sy->symbolField() );
mSymbolComboBox->setCurrentIndex( index < 0 ? 0 : index );

outlinewidthspinbox->setValue( sy->pen().widthF() );

//set line width 1 as minimum to avoid confusion between line width 0 and no pen line style
Expand Down Expand Up @@ -418,8 +454,10 @@ void QgsSingleSymbolDialog::set( const QgsSymbol *sy )
mLabelEdit->setEnabled( true );
lstSymbols->setEnabled( true );
mPointSizeSpinBox->setEnabled( true );
mPointSizeUnitsCheckBox->setEnabled( true );
mRotationClassificationComboBox->setEnabled( true );
mScaleClassificationComboBox->setEnabled( true );
mSymbolComboBox->setEnabled( true );
outlinewidthspinbox->setEnabled( true );
btnOutlineColor->setEnabled( true );
cboOutlineStyle->setEnabled( true );
Expand All @@ -442,6 +480,9 @@ void QgsSingleSymbolDialog::updateSet( const QgsSymbol *sy )
if ( mPointSizeSpinBox->isEnabled() && mPointSizeSpinBox->value() != sy->pointSize() )
mPointSizeSpinBox->setEnabled( false );

if ( mPointSizeUnitsCheckBox->isEnabled() && mPointSizeUnitsCheckBox->isChecked() != sy->pointSizeUnits() )
mPointSizeUnitsCheckBox->setEnabled( false );

if ( mRotationClassificationComboBox->isEnabled() &&
mRotationClassificationComboBox->itemData( mRotationClassificationComboBox->currentIndex() ).toInt() != sy->rotationClassificationField() )
mRotationClassificationComboBox->setEnabled( false );
Expand All @@ -450,6 +491,10 @@ void QgsSingleSymbolDialog::updateSet( const QgsSymbol *sy )
mScaleClassificationComboBox->itemData( mScaleClassificationComboBox->currentIndex() ).toInt() != sy->scaleClassificationField() )
mScaleClassificationComboBox->setEnabled( false );

if ( mSymbolComboBox->isEnabled() &&
mSymbolComboBox->itemData( mSymbolComboBox->currentIndex() ).toInt() != sy->symbolField() )
mSymbolComboBox->setEnabled( false );

if ( outlinewidthspinbox->isEnabled() && outlinewidthspinbox->value() != sy->pen().widthF() )
outlinewidthspinbox->setEnabled( false );

Expand Down
3 changes: 3 additions & 0 deletions src/app/qgssinglesymboldialog.h
Expand Up @@ -48,6 +48,7 @@ class QgsSingleSymbolDialog: public QDialog, private Ui::QgsSingleSymbolDialogBa

protected:
QgsVectorLayer* mVectorLayer;
bool mDisabled;

public slots:
/* arrange the widgets on this dialog to reflect the current state of QgsSymbol */
Expand All @@ -65,6 +66,8 @@ class QgsSingleSymbolDialog: public QDialog, private Ui::QgsSingleSymbolDialogBa
*/
void fillStyleChanged( int theIndex );

void refreshMarkers();

protected slots:
void selectOutlineColor();
void selectFillColor();
Expand Down
1 change: 1 addition & 0 deletions src/core/CMakeLists.txt
Expand Up @@ -182,6 +182,7 @@ composer/qgscomposerpicture.h
composer/qgscomposerscalebar.h
composer/qgscomposeritemgroup.h
composer/qgslegendmodel.h
symbology/qgsmarkercatalogue.h
raster/qgsrasterlayer.h
)

Expand Down

0 comments on commit 0c59c74

Please sign in to comment.