546 changes: 546 additions & 0 deletions images/themes/default/mActionShowHideLabels.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
605 changes: 605 additions & 0 deletions images/themes/gis/mActionShowHideLabels.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
2 changes: 2 additions & 0 deletions src/app/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,7 @@ SET(QGIS_APP_SRCS
qgsmaptoolfeatureaction.cpp
qgsmaptoolformannotation.cpp
qgsmaptoolpinlabels.cpp
qgsmaptoolshowhidelabels.cpp
qgsmaptoolidentify.cpp
qgsmaptoollabel.cpp
qgsmaptoolmeasureangle.cpp
Expand Down Expand Up @@ -206,6 +207,7 @@ SET (QGIS_APP_MOC_HDRS
qgsmaptooldeletevertex.h
qgsmaptoolfeatureaction.h
qgsmaptoolpinlabels.h
qgsmaptoolshowhidelabels.h
qgsmaptoolidentify.h
qgsmaptoolmeasureangle.h
qgsmaptoolmovefeature.h
Expand Down
25 changes: 22 additions & 3 deletions src/app/qgisapp.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -235,6 +235,7 @@
#include "qgsmaptoolsimplify.h"
#include "qgsmeasuretool.h"
#include "qgsmaptoolpinlabels.h"
#include "qgsmaptoolshowhidelabels.h"
#include "qgsmaptoolmovelabel.h"
#include "qgsmaptoolrotatelabel.h"
#include "qgsmaptoolchangelabelproperties.h"
Expand Down Expand Up @@ -715,6 +716,7 @@ QgisApp::~QgisApp()
delete mMapTools.mNodeTool;
delete mMapTools.mRotatePointSymbolsTool;
delete mMapTools.mPinLabels;
delete mMapTools.mShowHideLabels;
delete mMapTools.mMoveLabel;
delete mMapTools.mRotateLabel;
delete mMapTools.mChangeLabelProperties;
Expand Down Expand Up @@ -984,6 +986,7 @@ void QgisApp::createActions()

connect( mActionShowPinnedLabels, SIGNAL( toggled( bool ) ), this, SLOT( showPinnedLabels( bool ) ) );
connect( mActionPinLabels, SIGNAL( triggered() ), this, SLOT( pinLabels() ) );
connect( mActionShowHideLabels, SIGNAL( triggered() ), this, SLOT( showHideLabels() ) );
connect( mActionMoveLabel, SIGNAL( triggered() ), this, SLOT( moveLabel() ) );
connect( mActionRotateLabel, SIGNAL( triggered() ), this, SLOT( rotateLabel() ) );
connect( mActionChangeLabelProperties, SIGNAL( triggered() ), this, SLOT( changeLabelProperties() ) );
Expand Down Expand Up @@ -1094,6 +1097,7 @@ void QgisApp::createActionGroups()
mMapToolGroup->addAction( mActionNodeTool );
mMapToolGroup->addAction( mActionRotatePointSymbols );
mMapToolGroup->addAction( mActionPinLabels );
mMapToolGroup->addAction( mActionShowHideLabels );
mMapToolGroup->addAction( mActionMoveLabel );
mMapToolGroup->addAction( mActionRotateLabel );
mMapToolGroup->addAction( mActionChangeLabelProperties );
Expand Down Expand Up @@ -1628,6 +1632,7 @@ void QgisApp::setTheme( QString theThemeName )
mActionLabeling->setIcon( QgsApplication::getThemeIcon( "/mActionLabeling.png" ) );
mActionShowPinnedLabels->setIcon( QgsApplication::getThemeIcon( "/mActionShowPinnedLabels.svg" ) );
mActionPinLabels->setIcon( QgsApplication::getThemeIcon( "/mActionPinLabels.svg" ) );
mActionShowHideLabels->setIcon( QgsApplication::getThemeIcon( "/mActionShowHideLabels.svg" ) );
mActionMoveLabel->setIcon( QgsApplication::getThemeIcon( "/mActionMoveLabel.png" ) );
mActionRotateLabel->setIcon( QgsApplication::getThemeIcon( "/mActionRotateLabel.svg" ) );
mActionChangeLabelProperties->setIcon( QgsApplication::getThemeIcon( "/mActionChangeLabelProperties.png" ) );
Expand Down Expand Up @@ -1796,6 +1801,8 @@ void QgisApp::createCanvasTools()
mMapTools.mRotatePointSymbolsTool->setAction( mActionRotatePointSymbols );
mMapTools.mPinLabels = new QgsMapToolPinLabels( mMapCanvas );
mMapTools.mPinLabels->setAction( mActionPinLabels );
mMapTools.mShowHideLabels = new QgsMapToolShowHideLabels( mMapCanvas );
mMapTools.mShowHideLabels->setAction( mActionShowHideLabels );
mMapTools.mMoveLabel = new QgsMapToolMoveLabel( mMapCanvas );
mMapTools.mMoveLabel->setAction( mActionMoveLabel );
mMapTools.mRotateLabel = new QgsMapToolRotateLabel( mMapCanvas );
Expand Down Expand Up @@ -4319,6 +4326,11 @@ void QgisApp::pinLabels()
mMapCanvas->setMapTool( mMapTools.mPinLabels );
}

void QgisApp::showHideLabels()
{
mMapCanvas->setMapTool( mMapTools.mShowHideLabels );
}

void QgisApp::moveLabel()
{
mMapCanvas->setMapTool( mMapTools.mMoveLabel );
Expand Down Expand Up @@ -6668,7 +6680,7 @@ void QgisApp::legendLayerSelectionChanged( void )

void QgisApp::activateDeactivateLayerRelatedActions( QgsMapLayer* layer )
{
bool enableMove = false, enableRotate = false, enablePin = false, enableChange = false;
bool enableMove = false, enableRotate = false, enablePin = false, enableShowHide = false, enableChange = false;

QMap<QString, QgsMapLayer*> layers = QgsMapLayerRegistry::instance()->mapLayers();
for ( QMap<QString, QgsMapLayer*>::iterator it = layers.begin(); it != layers.end(); it++ )
Expand All @@ -6678,12 +6690,17 @@ void QgisApp::activateDeactivateLayerRelatedActions( QgsMapLayer* layer )
( !vlayer->diagramRenderer() && vlayer->customProperty( "labeling" ).toString() != QString( "pal" ) ) )
continue;

int colX, colY, colAng;
int colX, colY, colShow, colAng;
enablePin =
enablePin ||
( qobject_cast<QgsMapToolPinLabels*>( mMapTools.mPinLabels ) &&
qobject_cast<QgsMapToolPinLabels*>( mMapTools.mPinLabels )->layerCanPin( vlayer, colX, colY ) );

enableShowHide =
enableShowHide ||
( qobject_cast<QgsMapToolShowHideLabels*>( mMapTools.mShowHideLabels ) &&
qobject_cast<QgsMapToolShowHideLabels*>( mMapTools.mShowHideLabels )->layerCanShowHide( vlayer, colShow ) );

enableMove =
enableMove ||
( qobject_cast<QgsMapToolMoveLabel*>( mMapTools.mMoveLabel ) &&
Expand All @@ -6698,11 +6715,12 @@ void QgisApp::activateDeactivateLayerRelatedActions( QgsMapLayer* layer )

enableChange = true;

if ( enablePin && enableMove && enableRotate && enableChange )
if ( enablePin && enableShowHide && enableMove && enableRotate && enableChange )
break;
}

mActionPinLabels->setEnabled( enablePin );
mActionShowHideLabels->setEnabled( enableShowHide );
mActionMoveLabel->setEnabled( enableMove );
mActionRotateLabel->setEnabled( enableRotate );
mActionChangeLabelProperties->setEnabled( enableChange );
Expand Down Expand Up @@ -6750,6 +6768,7 @@ void QgisApp::activateDeactivateLayerRelatedActions( QgsMapLayer* layer )
mActionRotatePointSymbols->setEnabled( false );

mActionPinLabels->setEnabled( false );
mActionShowHideLabels->setEnabled( false );
mActionMoveLabel->setEnabled( false );
mActionRotateLabel->setEnabled( false );
mActionChangeLabelProperties->setEnabled( false );
Expand Down
3 changes: 3 additions & 0 deletions src/app/qgisapp.h
Original file line number Diff line number Diff line change
Expand Up @@ -876,6 +876,8 @@ class QgisApp : public QMainWindow, private Ui::MainWindow
void showPinnedLabels( bool show );
//! Activates pin labels tool
void pinLabels();
//! Activates show/hide labels tool
void showHideLabels();
//! Activates the move label tool
void moveLabel();
//! Activates rotate label tool
Expand Down Expand Up @@ -1078,6 +1080,7 @@ class QgisApp : public QMainWindow, private Ui::MainWindow
QgsMapTool* mFormAnnotation;
QgsMapTool* mTextAnnotation;
QgsMapTool* mPinLabels;
QgsMapTool* mShowHideLabels;
QgsMapTool* mMoveLabel;
QgsMapTool* mRotateLabel;
QgsMapTool* mChangeLabelProperties;
Expand Down
49 changes: 49 additions & 0 deletions src/app/qgsmaptoollabel.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -480,6 +480,31 @@ bool QgsMapToolLabel::dataDefinedRotation( QgsVectorLayer* vlayer, int featureId
return true;
}

bool QgsMapToolLabel::dataDefinedShowHide( QgsVectorLayer* vlayer, int featureId, int& show, bool& showSuccess, int& showCol )
{
showSuccess = false;
if ( !vlayer )
{
return false;
}

if ( !layerCanShowHide( vlayer, showCol ) )
{
return false;
}

QgsFeature f;
if ( !vlayer->featureAtId( featureId, f, false, true ) )
{
return false;
}

QgsAttributeMap attributes = f.attributeMap();

show = attributes[showCol].toInt( &showSuccess );
return true;
}

bool QgsMapToolLabel::diagramMoveable( const QgsMapLayer* ml, int& xCol, int& yCol ) const
{
const QgsVectorLayer* vlayer = dynamic_cast<const QgsVectorLayer*>( ml );
Expand Down Expand Up @@ -565,3 +590,27 @@ bool QgsMapToolLabel::layerCanPin( const QgsMapLayer* ml, int& xCol, int& yCol )

return true;
}

bool QgsMapToolLabel::layerCanShowHide( const QgsMapLayer* ml, int& showCol ) const
{
const QgsVectorLayer* vlayer = dynamic_cast<const QgsVectorLayer*>( ml );
if ( !vlayer || !vlayer->isEditable() )
{
return false;
}

bool showColOk;

QVariant showColumn = ml->customProperty( "labeling/dataDefinedProperty15" );
if ( !showColumn.isValid() )
{
return false;
}
showCol = showColumn.toInt( &showColOk );
if ( !showColOk )
{
return false;
}

return true;
}
13 changes: 13 additions & 0 deletions src/app/qgsmaptoollabel.h
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,9 @@ class QgsMapToolLabel: public QgsMapTool
@param yCol out: index of the attribute for data defined y coordinate
@return true if layer fields set up and exist*/
bool layerCanPin( const QgsMapLayer* ml, int& xCol, int& yCol ) const;
/**Returns true if layer has attribute field set up
@param showCol out: attribute column for data defined label showing*/
bool layerCanShowHide( const QgsMapLayer* layer, int& showCol ) const;
/**Checks if labels in a layer can be rotated
@param rotationCol out: attribute column for data defined label rotation*/
bool layerIsRotatable( const QgsMapLayer* layer, int& rotationCol ) const;
Expand Down Expand Up @@ -118,6 +121,16 @@ class QgsMapToolLabel: public QgsMapTool
*/
bool dataDefinedRotation( QgsVectorLayer* vlayer, int featureId, double& rotation, bool& rotationSuccess, bool ignoreXY = false );

/**Returns data defined show/hide of a feature.
@param vlayer vector layer
@param featureId feature identification integer
@param show out: show/hide value
@param showSuccess out: false if show/hide value is NULL
@param showCol out: index of the show label column
@return true if data defined show/hide is enabled on the layer
*/
bool dataDefinedShowHide( QgsVectorLayer* vlayer, int featureId, int& show, bool& showSuccess, int& showCol );

private:
QgsPalLayerSettings mInvalidLabelSettings;
};
Expand Down
4 changes: 2 additions & 2 deletions src/app/qgsmaptoolpinlabels.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -203,7 +203,7 @@ void QgsMapToolPinLabels::highlightPinnedLabels()

QList<QgsLabelPosition> labelPosList = labelEngine->labelsWithinRect( ext );

QApplication::setOverrideCursor( Qt::BusyCursor );
QApplication::setOverrideCursor( Qt::WaitCursor );
QList<QgsLabelPosition>::const_iterator it;
for ( it = labelPosList.constBegin() ; it != labelPosList.constEnd(); ++it )
{
Expand Down Expand Up @@ -479,7 +479,7 @@ bool QgsMapToolPinLabels::pinUnpinLabel( QgsVectorLayer* vlayer,
}

bool QgsMapToolPinLabels::hideLabel( QgsVectorLayer* vlayer,
const QgsLabelPosition& labelpos )
const QgsLabelPosition& labelpos )
{
// skip diagrams
if ( labelpos.isDiagram )
Expand Down
293 changes: 293 additions & 0 deletions src/app/qgsmaptoolshowhidelabels.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,293 @@
/***************************************************************************
qgsmaptoolshowhidelabels.cpp
-----------------------
begin : 2012-08-12
copyright : (C) 2012 by Larry Shaffer
email : larrys at dakotacarto dot com
***************************************************************************/

/***************************************************************************
* *
* 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 "qgsmaptoolshowhidelabels.h"

#include "qgsapplication.h"
#include "qgsmapcanvas.h"
#include "qgsvectorlayer.h"

#include "qgsmaptoolselectutils.h"
#include "qgsrubberband.h"
#include <qgslogger.h>

#include <QMouseEvent>
#include <QMessageBox>

QgsMapToolShowHideLabels::QgsMapToolShowHideLabels( QgsMapCanvas* canvas ): QgsMapToolLabel( canvas )
{
mRender = 0;
mRubberBand = 0;
}

QgsMapToolShowHideLabels::~QgsMapToolShowHideLabels()
{
delete mRubberBand;
}

void QgsMapToolShowHideLabels::canvasPressEvent( QMouseEvent * e )
{
Q_UNUSED( e );
mSelectRect.setRect( 0, 0, 0, 0 );
mSelectRect.setTopLeft( e->pos() );
mSelectRect.setBottomRight( e->pos() );
mRubberBand = new QgsRubberBand( mCanvas, true );
}

void QgsMapToolShowHideLabels::canvasMoveEvent( QMouseEvent * e )
{
if ( e->buttons() != Qt::LeftButton )
return;

if ( !mDragging )
{
mDragging = true;
mSelectRect.setTopLeft( e->pos() );
}
mSelectRect.setBottomRight( e->pos() );
QgsMapToolSelectUtils::setRubberBand( mCanvas, mSelectRect, mRubberBand );
}

void QgsMapToolShowHideLabels::canvasReleaseEvent( QMouseEvent * e )
{
//if the user simply clicked without dragging a rect
//we will fabricate a small 1x1 pix rect and then continue
//as if they had dragged a rect
if ( !mDragging )
{
mSelectRect.setLeft( e->pos().x() - 1 );
mSelectRect.setRight( e->pos().x() + 1 );
mSelectRect.setTop( e->pos().y() - 1 );
mSelectRect.setBottom( e->pos().y() + 1 );
}
else
{
// Set valid values for rectangle's width and height
if ( mSelectRect.width() == 1 )
{
mSelectRect.setLeft( mSelectRect.left() + 1 );
}
if ( mSelectRect.height() == 1 )
{
mSelectRect.setBottom( mSelectRect.bottom() + 1 );
}
}

if ( mRubberBand )
{
QgsMapToolSelectUtils::setRubberBand( mCanvas, mSelectRect, mRubberBand );

showHideLabels( e );

mRubberBand->reset( true );
delete mRubberBand;
mRubberBand = 0;
}

mDragging = false;
}

void QgsMapToolShowHideLabels::showHideLabels( QMouseEvent * e )
{

if ( !mCanvas || mCanvas->isDrawing() )
{
QgsDebugMsg( "Canvas not ready" );
return;
}

mRender = mCanvas->mapRenderer();
if ( !mRender )
{
QgsDebugMsg( "Failed to acquire map renderer" );
return;
}

QgsMapLayer* layer = mCanvas->currentLayer();

QgsVectorLayer* vlayer = dynamic_cast<QgsVectorLayer*>( layer );
if ( !vlayer )
{
QgsDebugMsg( "Failed to cast label layer to vector layer" );
return;
}
if ( !vlayer->isEditable() )
{
QgsDebugMsg( "Vector layer not editable, skipping label" );
return;
}

bool doHide = e->modifiers() & Qt::ShiftModifier ? true : false;

QgsFeatureIds selectedFeatIds;

if ( !doHide )
{
QgsDebugMsg( "Showing labels operation" );

if ( !selectedFeatures( vlayer, selectedFeatIds ) )
{
return;
}
}
else
{
QgsDebugMsg( "Hiding labels operation" );

if ( !selectedLabelFeatures( vlayer, selectedFeatIds ) )
{
return;
}
}

QgsDebugMsg( "Number of selected labels or features: " + QString::number( selectedFeatIds.size() ) );


bool labelChanged = false;

foreach ( const QgsFeatureId &fid, selectedFeatIds )
{
if ( showHideLabel( vlayer, fid, doHide ) )
{
// TODO: highlight features (maybe with QTimer?)
labelChanged = true;
}
}

if ( labelChanged )
{
mCanvas->refresh();
}
}

bool QgsMapToolShowHideLabels::selectedFeatures( QgsVectorLayer* vlayer,
QgsFeatureIds& selectedFeatIds )
{
// culled from QgsMapToolSelectUtils::setSelectFeatures()

QgsGeometry* selectGeometry = mRubberBand->asGeometry();

// toLayerCoordinates will throw an exception for any 'invalid' points in
// the rubber band.
// For example, if you project a world map onto a globe using EPSG 2163
// and then click somewhere off the globe, an exception will be thrown.
QgsGeometry selectGeomTrans( *selectGeometry );

if ( mRender->hasCrsTransformEnabled() )
{
try
{
QgsCoordinateTransform ct( mRender->destinationCrs(), vlayer->crs() );
selectGeomTrans.transform( ct );
}
catch ( QgsCsException &cse )
{
Q_UNUSED( cse );
// catch exception for 'invalid' point and leave existing selection unchanged
QgsLogger::warning( "Caught CRS exception " + QString( __FILE__ ) + ": " + QString::number( __LINE__ ) );
QMessageBox::warning( mCanvas, QObject::tr( "CRS Exception" ),
QObject::tr( "Selection extends beyond layer's coordinate system." ) );
return false;
}
}

QApplication::setOverrideCursor( Qt::WaitCursor );

QgsDebugMsg( "Selection layer: " + vlayer->name() );
QgsDebugMsg( "Selection polygon: " + selectGeomTrans.exportToWkt() );

vlayer->select( QgsAttributeList(), selectGeomTrans.boundingBox(), false, true );

QgsFeature f;
while ( vlayer->nextFeature( f ) )
{
QgsGeometry* g = f.geometry();

if ( !selectGeomTrans.intersects( g ) )
continue;

selectedFeatIds.insert( f.id() );
}

QApplication::restoreOverrideCursor();

return true;
}

bool QgsMapToolShowHideLabels::selectedLabelFeatures( QgsVectorLayer* vlayer,
QgsFeatureIds& selectedFeatIds )
{
// get list of all drawn labels from current layer that intersect rubberband

QgsPalLabeling* labelEngine = dynamic_cast<QgsPalLabeling*>( mRender->labelingEngine() );
if ( !labelEngine )
{
QgsDebugMsg( "No labeling engine" );
return false;
}

QApplication::setOverrideCursor( Qt::WaitCursor );

QgsRectangle ext = mRubberBand->asGeometry()->boundingBox();

QList<QgsLabelPosition> labelPosList = labelEngine->labelsWithinRect( ext );

QList<QgsLabelPosition>::const_iterator it;
for ( it = labelPosList.constBegin() ; it != labelPosList.constEnd(); ++it )
{
mCurrentLabelPos = *it;

if ( mCurrentLabelPos.layerID != vlayer->id() )
{
// only work with labels from the current active and editable layer
continue;
}

selectedFeatIds.insert( mCurrentLabelPos.featureId );
}

QApplication::restoreOverrideCursor();

return true;
}

bool QgsMapToolShowHideLabels::showHideLabel( QgsVectorLayer* vlayer,
int fid,
bool hide )
{

// verify attribute table has proper field setup
bool showSuccess;
int showCol;
int show;

if ( !dataDefinedShowHide( vlayer, fid, show, showSuccess, showCol ) )
{
return false;
}

// edit attribute table
QString editTxt = hide ? tr( "Label hidden" ) : tr( "Label shown" );
vlayer->beginEditCommand( editTxt );
if ( !vlayer->changeAttributeValue( fid, showCol, ( hide ? 0 : 1 ), false ) )
{
QgsDebugMsg( "Failed write to attribute table" );
return false;
}
vlayer->endEditCommand();
return true;
}
76 changes: 76 additions & 0 deletions src/app/qgsmaptoolshowhidelabels.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,76 @@
/***************************************************************************
qgsmaptoolshowhidelabels.h
--------------------
begin : 2012-08-12
copyright : (C) 2012 by Larry Shaffer
email : larrys at dakotacarto dot com
***************************************************************************/

/***************************************************************************
* *
* 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. *
* *
***************************************************************************/

#ifndef QGSMAPTOOLSHOWHIDELABELS_H
#define QGSMAPTOOLSHOWHIDELABELS_H

#include "qgsmaptoollabel.h"
#include "qgsfeature.h"


/**A map tool for showing or hidding a feature's label*/
class QgsMapToolShowHideLabels: public QgsMapToolLabel
{
Q_OBJECT

public:
QgsMapToolShowHideLabels( QgsMapCanvas *canvas );
~QgsMapToolShowHideLabels();

//! Overridden mouse move event
virtual void canvasMoveEvent( QMouseEvent * e );

//! Overridden mouse press event
virtual void canvasPressEvent( QMouseEvent * e );

//! Overridden mouse release event
virtual void canvasReleaseEvent( QMouseEvent * e );

protected:

//! Flag to indicate a map canvas drag operation is taking place
bool mDragging;

//! Stores actual select rect
QRect mSelectRect;

//! Stores selection marquee
QgsRubberBand* mRubberBand;

private:

//! Pointer to map renderer
QgsMapRenderer* mRender;

//! Select valid labels to pin or unpin
void showHideLabels( QMouseEvent * e );

//! Return features intersecting rubberband
bool selectedFeatures( QgsVectorLayer* vlayer,
QgsFeatureIds& selectedFeatIds );

//! Return label features intersecting rubberband
bool selectedLabelFeatures( QgsVectorLayer* vlayer,
QgsFeatureIds& selectedFeatIds );

//! Show or hide chosen label by setting data defined Show Label to 0
bool showHideLabel( QgsVectorLayer* vlayer,
int fid,
bool hide );
};

#endif // QGSMAPTOOLSHOWHIDELABELS_H
27 changes: 23 additions & 4 deletions src/ui/qgisapp.ui
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@
<x>0</x>
<y>0</y>
<width>1052</width>
<height>21</height>
<height>22</height>
</rect>
</property>
<widget class="QMenu" name="mEditMenu">
Expand Down Expand Up @@ -403,6 +403,7 @@
<addaction name="mActionLabeling"/>
<addaction name="mActionShowPinnedLabels"/>
<addaction name="mActionPinLabels"/>
<addaction name="mActionShowHideLabels"/>
<addaction name="mActionMoveLabel"/>
<addaction name="mActionRotateLabel"/>
<addaction name="mActionChangeLabelProperties"/>
Expand Down Expand Up @@ -1719,9 +1720,10 @@
<string>Pin/Unpin Labels</string>
</property>
<property name="toolTip">
<string>Pin/Unpin and Hide/Show Labels
Shift unpins, Ctl (Cmd) toggles pin/unpin
Shift+Ctl (Cmd) on label hides, Shift+Ctl (Cmd) on feature shows label</string>
<string>Pin/Unpin Labels
Click or marquee on label to pin
Hold Shift to unpin
Hold Ctl (Cmd) to toggle pin/unpin state</string>
</property>
</action>
<action name="mActionShowPinnedLabels">
Expand Down Expand Up @@ -1775,6 +1777,23 @@ Shift+Ctl (Cmd) on label hides, Shift+Ctl (Cmd) on feature shows label</string>
<string>Cumulative cut stretch using full dataset extent, default limits and estimated values.</string>
</property>
</action>
<action name="mActionShowHideLabels">
<property name="checkable">
<bool>true</bool>
</property>
<property name="icon">
<iconset resource="../../images/images.qrc">
<normaloff>:/images/themes/default/mActionShowHideLabels.svg</normaloff>:/images/themes/default/mActionShowHideLabels.svg</iconset>
</property>
<property name="text">
<string>Show/Hide Labels</string>
</property>
<property name="toolTip">
<string>Show/Hide Labels
Click or marquee on feature to show label
Hold Shift+click or marquee on label to hide it</string>
</property>
</action>
</widget>
<resources>
<include location="../../images/images.qrc"/>
Expand Down