35 #include <QDesktopWidget>
39 : QToolButton( parent )
40 , mDialogTitle( dialogTitle.isEmpty() ? tr(
"Text Format" ) : dialogTitle )
43 setText( tr(
"Font" ) );
45 setAcceptDrops(
true );
46 connect(
this, &QAbstractButton::clicked,
this, &QgsFontButton::showSettingsDialog );
49 mMenu =
new QMenu(
this );
50 connect( mMenu, &QMenu::aboutToShow,
this, &QgsFontButton::prepareMenu );
52 setPopupMode( QToolButton::MenuButtonPopup );
55 QSize size = QToolButton::minimumSizeHint();
57 #if QT_VERSION < QT_VERSION_CHECK(5, 11, 0)
62 mSizeHint = QSize( std::max( minWidth, size.width() ), std::max( size.height(), fontHeight ) );
75 void QgsFontButton::showSettingsDialog()
82 if ( mExpressionContextGenerator )
106 QgsTextFormatDialog dialog( mFormat, mMapCanvas,
this, QgsGuiUtils::ModalDialogFlags, mLayer.data() );
107 dialog.setWindowTitle( mDialogTitle );
108 dialog.setContext( symbolContext );
164 QColor opaque = color;
165 opaque.setAlphaF( 1.0 );
167 if ( mFormat.
color() != opaque )
180 QApplication::clipboard()->setMimeData( mFormat.
toMimeData() );
193 if ( mMode ==
ModeTextRenderer && formatFromMimeData( QApplication::clipboard()->mimeData(), tempFormat ) )
198 else if ( mMode ==
ModeQFont && fontFromMimeData( QApplication::clipboard()->mimeData(), font ) )
207 if ( e->type() == QEvent::ToolTip )
209 QHelpEvent *helpEvent =
static_cast< QHelpEvent *
>( e );
211 double fontSize = 0.0;
215 fontSize = mFormat.
size();
219 fontSize = mFont.pointSizeF();
222 toolTip = QStringLiteral(
"<b>%1</b><br>%2<br>Size: %3" ).arg( text(), mMode ==
ModeTextRenderer ? mFormat.
font().family() : mFont.family() ).arg( fontSize );
223 QToolTip::showText( helpEvent->globalPos(), toolTip );
225 return QToolButton::event( e );
230 if ( e->button() == Qt::RightButton )
232 QToolButton::showMenu();
235 else if ( e->button() == Qt::LeftButton )
237 mDragStartPosition = e->pos();
239 QToolButton::mousePressEvent( e );
246 if ( !( e->buttons() & Qt::LeftButton ) )
249 QToolButton::mouseMoveEvent( e );
253 if ( ( e->pos() - mDragStartPosition ).manhattanLength() < QApplication::startDragDistance() )
256 QToolButton::mouseMoveEvent( e );
261 QDrag *drag =
new QDrag(
this );
274 drag->exec( Qt::CopyAction );
278 bool QgsFontButton::colorFromMimeData(
const QMimeData *mimeData, QColor &resultColor,
bool &hasAlpha )
283 if ( mimeColor.isValid() )
285 resultColor = mimeColor;
299 bool hasAlpha =
false;
301 if ( mMode ==
ModeTextRenderer && formatFromMimeData( e->mimeData(), format ) )
303 e->acceptProposedAction();
304 updatePreview( QColor(), &format );
306 else if ( mMode ==
ModeQFont && fontFromMimeData( e->mimeData(), font ) )
308 e->acceptProposedAction();
309 updatePreview( QColor(),
nullptr, &font );
311 else if ( mMode ==
ModeTextRenderer && colorFromMimeData( e->mimeData(), mimeColor, hasAlpha ) )
316 e->acceptProposedAction();
317 updatePreview( mimeColor );
334 bool hasAlpha =
false;
335 if ( mMode ==
ModeTextRenderer && formatFromMimeData( e->mimeData(), format ) )
341 else if ( mMode ==
ModeQFont && fontFromMimeData( e->mimeData(), font ) )
347 else if ( mMode ==
ModeTextRenderer && colorFromMimeData( e->mimeData(), mimeColor, hasAlpha ) )
350 e->acceptProposedAction();
356 mimeColor.setAlphaF( 1.0 );
371 size = mFormat.
size();
375 size = mFont.pointSizeF();
379 double increment = (
event->modifiers() & Qt::ControlModifier ) ? 0.1 : 1;
380 if (
event->delta() > 0 )
388 size = std::max( size, 1.0 );
402 QFont newFont = mFont;
403 newFont.setPointSizeF( size );
412 QPixmap QgsFontButton::createColorIcon(
const QColor &color )
const
417 pixmap.fill( Qt::transparent );
423 p.setBrush( QBrush( color ) );
426 p.setPen( QColor( 197, 197, 197 ) );
432 QPixmap QgsFontButton::createDragIcon( QSize size,
const QgsTextFormat *tempFormat,
const QFont *tempFont )
const
435 tempFormat = &mFormat;
440 QPixmap pixmap( size.width(), size.height() );
441 pixmap.fill( Qt::transparent );
444 p.setRenderHint( QPainter::Antialiasing );
445 QRect rect( 0, 0, size.width(), size.height() );
447 if ( mMode ==
ModeQFont || tempFormat->
color().lightnessF() < 0.7 )
449 p.setBrush( QBrush( QColor( 255, 255, 255 ) ) );
450 p.setPen( QPen( QColor( 150, 150, 150 ), 0 ) );
454 p.setBrush( QBrush( QColor( 0, 0, 0 ) ) );
455 p.setPen( QPen( QColor( 100, 100, 100 ), 0 ) );
458 p.setBrush( Qt::NoBrush );
459 p.setPen( Qt::NoPen );
470 context.
setScaleFactor( QgsApplication::desktop()->logicalDpiX() / 25.4 );
487 QRectF textRect = rect;
488 textRect.setLeft( xtrans );
489 textRect.setWidth( textRect.width() - xtrans );
490 textRect.setTop( ytrans );
491 if ( textRect.height() > 300 )
492 textRect.setHeight( 300 );
493 if ( textRect.width() > 2000 )
494 textRect.setWidth( 2000 );
497 context, *tempFormat );
502 p.setBrush( Qt::NoBrush );
503 p.setPen( QColor( 0, 0, 0 ) );
504 p.setFont( *tempFont );
505 QRectF textRect = rect;
506 textRect.setLeft( 2 );
507 p.drawText( textRect, Qt::AlignVCenter, tr(
"Aa" ) );
516 void QgsFontButton::prepareMenu()
525 QWidgetAction *sizeAction =
new QWidgetAction( mMenu );
526 QWidget *sizeWidget =
new QWidget();
527 QVBoxLayout *sizeLayout =
new QVBoxLayout();
528 sizeLayout->setMargin( 0 );
529 sizeLayout->setContentsMargins( 0, 0, 0, 3 );
530 sizeLayout->setSpacing( 2 );
532 QString fontHeaderLabel;
540 fontHeaderLabel = tr(
"Font size (pt)" );
545 sizeLayout->addWidget( sizeLabel );
548 sizeSpin->setDecimals( 4 );
549 sizeSpin->setMaximum( 1e+9 );
552 connect( sizeSpin,
static_cast < void (
QgsDoubleSpinBox::* )(
double )
> ( &QgsDoubleSpinBox::valueChanged ),
553 this, [ = ](
double value )
561 mFont.setPointSizeF( value );
567 QHBoxLayout *spinLayout =
new QHBoxLayout();
568 spinLayout->setMargin( 0 );
569 spinLayout->setContentsMargins( 4, 0, 4, 0 );
570 spinLayout->addWidget( sizeSpin );
571 sizeLayout->addLayout( spinLayout );
572 sizeWidget->setLayout( sizeLayout );
573 sizeAction->setDefaultWidget( sizeWidget );
574 sizeWidget->setFocusProxy( sizeSpin );
575 sizeWidget->setFocusPolicy( Qt::StrongFocus );
576 mMenu->addAction( sizeAction );
578 QMenu *recentFontMenu =
new QMenu( tr(
"Recent Fonts" ), mMenu );
580 for (
const QString &family : recentFontFamilies )
582 QAction *fontAction =
new QAction( family, recentFontMenu );
583 QFont f = fontAction->font();
584 f.setFamily( family );
585 fontAction->setFont( f );
586 fontAction->setToolTip( family );
587 recentFontMenu->addAction( fontAction );
589 || ( mMode ==
ModeQFont && family == mFont.family() ) )
591 fontAction->setCheckable(
true );
592 fontAction->setChecked(
true );
594 auto setFont = [
this, family]
601 QFont f = newFormat.
font();
602 f.setFamily( family );
611 font.setFamily( family );
618 connect( fontAction, &QAction::triggered,
this, setFont );
620 mMenu->addMenu( recentFontMenu );
622 QAction *configureAction =
new QAction( tr(
"Configure Format…" ),
this );
623 mMenu->addAction( configureAction );
624 connect( configureAction, &QAction::triggered,
this, &QgsFontButton::showSettingsDialog );
626 QAction *copyFormatAction =
new QAction( tr(
"Copy Format" ),
this );
627 mMenu->addAction( copyFormatAction );
629 QAction *pasteFormatAction =
new QAction( tr(
"Paste Format" ),
this );
635 if ( mMode ==
ModeTextRenderer && formatFromMimeData( QApplication::clipboard()->mimeData(), tempFormat ) )
639 pasteFormatAction->setIcon( createDragIcon( QSize(
iconSize,
iconSize ), &tempFormat ) );
641 else if ( mMode ==
ModeQFont && fontFromMimeData( QApplication::clipboard()->mimeData(), tempFont ) )
643 tempFont.setPointSize( 8 );
644 pasteFormatAction->setIcon( createDragIcon( QSize(
iconSize,
iconSize ),
nullptr, &tempFont ) );
648 pasteFormatAction->setEnabled(
false );
650 mMenu->addAction( pasteFormatAction );
655 mMenu->addSeparator();
662 mMenu->addAction( colorAction );
665 QColor alphaColor = mFormat.
color();
666 alphaColor.setAlphaF( mFormat.
opacity() );
672 double opacity = color.alphaF();
679 mMenu->addAction( alphaAction );
683 QList< QgsColorScheme * >::iterator it = schemeList.begin();
684 for ( ; it != schemeList.end(); ++it )
688 mMenu->addAction( colorAction );
693 mMenu->addSeparator();
695 QAction *copyColorAction =
new QAction( tr(
"Copy Color" ),
this );
696 mMenu->addAction( copyColorAction );
699 QAction *pasteColorAction =
new QAction( tr(
"Paste Color" ),
this );
703 bool hasAlpha =
false;
704 if ( colorFromMimeData( QApplication::clipboard()->mimeData(), clipColor, hasAlpha ) )
706 pasteColorAction->setIcon( createColorIcon( clipColor ) );
710 pasteColorAction->setEnabled(
false );
712 mMenu->addAction( pasteColorAction );
717 void QgsFontButton::addRecentColor(
const QColor &color )
739 mExpressionContextGenerator = generator;
760 bool QgsFontButton::formatFromMimeData(
const QMimeData *mimeData,
QgsTextFormat &resultFormat )
const
767 bool QgsFontButton::fontFromMimeData(
const QMimeData *mimeData, QFont &resultFont )
const
776 if ( e->type() == QEvent::EnabledChange )
780 QToolButton::changeEvent( e );
786 QToolButton::showEvent( e );
791 QToolButton::resizeEvent(
event );
797 void QgsFontButton::updatePreview(
const QColor &color,
QgsTextFormat *format, QFont *font )
803 tempFormat = *format;
805 tempFormat = mFormat;
811 if ( color.isValid() )
814 QSize currentIconSize;
818 if ( !mIconSize.isValid() )
821 QStyleOptionToolButton opt;
822 initStyleOption( &opt );
823 QRect buttonSize = QApplication::style()->subControlRect( QStyle::CC_ToolButton, &opt, QStyle::SC_ToolButton,
827 mIconSize = QSize( buttonSize.width() - 10, height() - 6 );
828 #elif defined(Q_OS_MAC)
829 mIconSize = QSize( buttonSize.width() - 10, height() - 2 );
831 mIconSize = QSize( buttonSize.width() - 10, height() - 12 );
834 currentIconSize = mIconSize;
840 currentIconSize = QSize( width() - 10, height() - 6 );
842 currentIconSize = QSize( width() - 10, height() - 12 );
846 if ( !currentIconSize.isValid() || currentIconSize.width() <= 0 || currentIconSize.height() <= 0 )
852 QPixmap pixmap( currentIconSize );
853 pixmap.fill( Qt::transparent );
856 p.setRenderHint( QPainter::Antialiasing );
857 QRect rect( 0, 0, currentIconSize.width(), currentIconSize.height() );
868 context.
setScaleFactor( QgsApplication::desktop()->logicalDpiX() / 25.4 );
885 QRectF textRect = rect;
886 textRect.setLeft( xtrans );
887 textRect.setWidth( textRect.width() - xtrans );
888 textRect.setTop( ytrans );
889 if ( textRect.height() > 300 )
890 textRect.setHeight( 300 );
891 if ( textRect.width() > 2000 )
892 textRect.setWidth( 2000 );
895 context, tempFormat );
900 p.setBrush( Qt::NoBrush );
901 p.setPen( QColor( 0, 0, 0 ) );
902 p.setFont( tempFont );
903 QRectF textRect = rect;
904 textRect.setLeft( 2 );
905 p.drawText( textRect, Qt::AlignVCenter, text() );
911 setIconSize( currentIconSize );
924 bool hasAlpha =
false;
925 if ( colorFromMimeData( QApplication::clipboard()->mimeData(), clipColor, hasAlpha ) )
935 mDialogTitle = title;