diff --git a/python/gui/layout/qgslayoutdesignerinterface.sip b/python/gui/layout/qgslayoutdesignerinterface.sip index 8508aaf1c04..c22d0ecc206 100644 --- a/python/gui/layout/qgslayoutdesignerinterface.sip +++ b/python/gui/layout/qgslayoutdesignerinterface.sip @@ -55,11 +55,6 @@ class QgsLayoutDesignerInterface: QObject Closes the layout designer. %End - virtual void zoomFull() = 0; -%Docstring - Zooms to full extent of layout. -%End - }; /************************************************************************ diff --git a/python/gui/layout/qgslayoutview.sip b/python/gui/layout/qgslayoutview.sip index c3e1f27641f..e34c97f89bc 100644 --- a/python/gui/layout/qgslayoutview.sip +++ b/python/gui/layout/qgslayoutview.sip @@ -86,6 +86,14 @@ class QgsLayoutView: QGraphicsView .. seealso:: zoomIn() .. seealso:: zoomOut() .. seealso:: zoomActual() +%End + + void zoomWidth(); +%Docstring + Zooms the view to the full width of the layout. +.. seealso:: zoomIn() +.. seealso:: zoomOut() +.. seealso:: zoomActual() %End void zoomIn(); diff --git a/src/app/layout/qgslayoutdesignerdialog.cpp b/src/app/layout/qgslayoutdesignerdialog.cpp index e6d66ffeeae..2f1bf4fd6f8 100644 --- a/src/app/layout/qgslayoutdesignerdialog.cpp +++ b/src/app/layout/qgslayoutdesignerdialog.cpp @@ -35,6 +35,8 @@ //add some nice zoom levels for zoom comboboxes QList QgsLayoutDesignerDialog::sStatusZoomLevelsList { 0.125, 0.25, 0.5, 1.0, 2.0, 4.0, 8.0}; +#define FIT_LAYOUT -101 +#define FIT_LAYOUT_WIDTH -102 QgsAppLayoutDesignerInterface::QgsAppLayoutDesignerInterface( QgsLayoutDesignerDialog *dialog ) : QgsLayoutDesignerInterface( dialog ) @@ -56,11 +58,6 @@ void QgsAppLayoutDesignerInterface::close() mDesigner->close(); } -void QgsAppLayoutDesignerInterface::zoomFull() -{ - mDesigner->zoomFull(); -} - QgsLayoutDesignerDialog::QgsLayoutDesignerDialog( QWidget *parent, Qt::WindowFlags flags ) : QMainWindow( parent, flags ) @@ -145,9 +142,11 @@ QgsLayoutDesignerDialog::QgsLayoutDesignerDialog( QWidget *parent, Qt::WindowFla Q_FOREACH ( double level, sStatusZoomLevelsList ) { - mStatusZoomCombo->insertItem( 0, tr( "%1%" ).arg( level * 100.0, 0, 'f', 1 ) ); + mStatusZoomCombo->insertItem( 0, tr( "%1%" ).arg( level * 100.0, 0, 'f', 1 ), level ); } - connect( mStatusZoomCombo, static_cast( &QComboBox::currentIndexChanged ), this, &QgsLayoutDesignerDialog::statusZoomCombo_currentIndexChanged ); + mStatusZoomCombo->insertItem( 0, tr( "Fit Layout" ), FIT_LAYOUT ); + mStatusZoomCombo->insertItem( 0, tr( "Fit Layout Width" ), FIT_LAYOUT_WIDTH ); + connect( mStatusZoomCombo, static_cast( &QComboBox::activated ), this, &QgsLayoutDesignerDialog::statusZoomCombo_currentIndexChanged ); connect( mStatusZoomCombo->lineEdit(), &QLineEdit::returnPressed, this, &QgsLayoutDesignerDialog::statusZoomCombo_zoomEntered ); mStatusBar->addPermanentWidget( mStatusZoomCombo ); @@ -192,7 +191,7 @@ void QgsLayoutDesignerDialog::open() { show(); activate(); - zoomFull(); // zoomFull() does not work properly until we have called show() + mView->zoomFull(); // zoomFull() does not work properly until we have called show() #if 0 // TODO @@ -219,14 +218,6 @@ void QgsLayoutDesignerDialog::activate() #endif } -void QgsLayoutDesignerDialog::zoomFull() -{ - if ( mView ) - { - mView->fitInView( mLayout->sceneRect(), Qt::KeepAspectRatio ); - } -} - void QgsLayoutDesignerDialog::closeEvent( QCloseEvent * ) { emit aboutToClose(); @@ -253,12 +244,24 @@ void QgsLayoutDesignerDialog::itemTypeAdded( int type ) void QgsLayoutDesignerDialog::statusZoomCombo_currentIndexChanged( int index ) { - double selectedZoom = sStatusZoomLevelsList.at( sStatusZoomLevelsList.count() - index - 1 ); - if ( mView ) + QVariant data = mStatusZoomCombo->itemData( index ); + if ( data.toInt() == FIT_LAYOUT ) { - mView->setZoomLevel( selectedZoom ); - //update zoom combobox text for correct format (one decimal place, trailing % sign) - whileBlocking( mStatusZoomCombo )->lineEdit()->setText( tr( "%1%" ).arg( selectedZoom * 100.0, 0, 'f', 1 ) ); + mView->zoomFull(); + } + else if ( data.toInt() == FIT_LAYOUT_WIDTH ) + { + mView->zoomWidth(); + } + else + { + double selectedZoom = data.toDouble(); + if ( mView ) + { + mView->setZoomLevel( selectedZoom ); + //update zoom combobox text for correct format (one decimal place, trailing % sign) + whileBlocking( mStatusZoomCombo )->lineEdit()->setText( tr( "%1%" ).arg( selectedZoom * 100.0, 0, 'f', 1 ) ); + } } } diff --git a/src/app/layout/qgslayoutdesignerdialog.h b/src/app/layout/qgslayoutdesignerdialog.h index 1a601f30799..e890b9dce67 100644 --- a/src/app/layout/qgslayoutdesignerdialog.h +++ b/src/app/layout/qgslayoutdesignerdialog.h @@ -40,7 +40,6 @@ class QgsAppLayoutDesignerInterface : public QgsLayoutDesignerInterface public slots: void close() override; - void zoomFull() override; private: @@ -99,11 +98,6 @@ class QgsLayoutDesignerDialog: public QMainWindow, private Ui::QgsLayoutDesigner */ void activate(); - /** - * Zooms to show full layout. - */ - void zoomFull(); - signals: /** diff --git a/src/gui/layout/qgslayoutdesignerinterface.h b/src/gui/layout/qgslayoutdesignerinterface.h index 947767fa0e0..abc76013de2 100644 --- a/src/gui/layout/qgslayoutdesignerinterface.h +++ b/src/gui/layout/qgslayoutdesignerinterface.h @@ -68,11 +68,6 @@ class GUI_EXPORT QgsLayoutDesignerInterface: public QObject */ virtual void close() = 0; - /** - * Zooms to full extent of layout. - */ - virtual void zoomFull() = 0; - }; #endif // QGSLAYOUTDESIGNERINTERFACE_H diff --git a/src/gui/layout/qgslayoutview.cpp b/src/gui/layout/qgslayoutview.cpp index 9ebf889147a..065d8ea9eec 100644 --- a/src/gui/layout/qgslayoutview.cpp +++ b/src/gui/layout/qgslayoutview.cpp @@ -95,6 +95,7 @@ void QgsLayoutView::scaleSafe( double scale ) scale *= currentScale; scale = qBound( MIN_VIEW_SCALE, scale, MAX_VIEW_SCALE ); setTransform( QTransform::fromScale( scale, scale ) ); + emit zoomLevelChanged(); } void QgsLayoutView::setZoomLevel( double level ) @@ -113,6 +114,28 @@ void QgsLayoutView::setZoomLevel( double level ) void QgsLayoutView::zoomFull() { fitInView( scene()->sceneRect(), Qt::KeepAspectRatio ); + emit zoomLevelChanged(); +} + +void QgsLayoutView::zoomWidth() +{ + //get current visible part of scene + QRect viewportRect( 0, 0, viewport()->width(), viewport()->height() ); + QRectF visibleRect = mapToScene( viewportRect ).boundingRect(); + + double verticalCenter = ( visibleRect.top() + visibleRect.bottom() ) / 2.0; + // expand out visible rect to include left/right edges of scene + // centered on current visible vertical center + // note that we can't have a 0 height rect - fitInView doesn't handle that + // so we just set a very small height instead. + const double tinyHeight = 0.01; + QRectF targetRect( scene()->sceneRect().left(), + verticalCenter - tinyHeight, + scene()->sceneRect().width(), + tinyHeight * 2 ); + + fitInView( targetRect, Qt::KeepAspectRatio ); + emit zoomLevelChanged(); } void QgsLayoutView::zoomIn() diff --git a/src/gui/layout/qgslayoutview.h b/src/gui/layout/qgslayoutview.h index a66d94e575d..928e3cd1178 100644 --- a/src/gui/layout/qgslayoutview.h +++ b/src/gui/layout/qgslayoutview.h @@ -109,6 +109,14 @@ class GUI_EXPORT QgsLayoutView: public QGraphicsView */ void zoomFull(); + /** + * Zooms the view to the full width of the layout. + * \see zoomIn() + * \see zoomOut() + * \see zoomActual() + */ + void zoomWidth(); + /** * Zooms in to the view by a preset amount. * \see zoomFull()