530QSize QLabelPrivate::sizeForWidth(
int w)
const
533 if (q->minimumWidth() > 0)
534 w = qMax(w, q->minimumWidth());
535 QSize contentsMargin(leftmargin + rightmargin, topmargin + bottommargin);
539 int hextra = 2 * margin;
541 QFontMetrics fm = q->fontMetrics();
543 if (icon && !icon->isNull()) {
544 br = QRect(QPoint(0, 0), pixmapSize);
546 }
else if (picture && !picture->isNull()) {
547 br = picture->boundingRect();
550 }
else if (movie && !movie->currentPixmap().isNull()) {
551 br = movie->currentPixmap().rect();
552 br.setSize(movie->currentPixmap().deviceIndependentSize().toSize());
554 }
else if (isTextLabel) {
555 int align = QStyle::visualAlignment(textDirection(), QFlag(
this->align));
559 if (m < 0 && q->frameWidth())
560 m = fm.horizontalAdvance(u'x') - margin*2;
562 if ((align & Qt::AlignLeft) || (align & Qt::AlignRight))
564 if ((align & Qt::AlignTop) || (align & Qt::AlignBottom))
569 ensureTextLayouted();
570 const qreal oldTextWidth = control->textWidth();
572 if (align & Qt::TextWordWrap) {
574 w = qMax(w-hextra-contentsMargin.width(), 0);
575 control->setTextWidth(w);
577 control->adjustSize();
580 control->setTextWidth(-1);
583 QSizeF controlSize = control->size();
584 br = QRect(QPoint(0, 0), QSize(qCeil(controlSize.width()), qCeil(controlSize.height())));
587 control->setTextWidth(oldTextWidth);
591 int flags = align & ~(Qt::AlignVCenter | Qt::AlignHCenter);
593 flags |= Qt::TextShowMnemonic;
596 if (!q->style()->styleHint(QStyle::SH_UnderlineShortcut, &opt, q))
597 flags |= Qt::TextHideMnemonic;
600 bool tryWidth = (w < 0) && (align & Qt::TextWordWrap);
602 w = qMin(fm.averageCharWidth() * 80, q->maximumSize().width());
605 w -= (hextra + contentsMargin.width());
606 br = fm.boundingRect(0, 0, w ,2000, flags, text);
607 if (tryWidth && br.height() < 4*fm.lineSpacing() && br.width() > w/2)
608 br = fm.boundingRect(0, 0, w/2, 2000, flags, text);
609 if (tryWidth && br.height() < 2*fm.lineSpacing() && br.width() > w/4)
610 br = fm.boundingRect(0, 0, w/4, 2000, flags, text);
613 br = QRect(QPoint(0, 0), QSize(fm.averageCharWidth(), fm.lineSpacing()));
616 const QSize contentsSize(br.width() + hextra, br.height() + vextra);
617 return (contentsSize + contentsMargin).expandedTo(q->minimumSize());
985void QLabel::paintEvent(QPaintEvent *)
988 QStyle *style = QWidget::style();
989 QPainter painter(
this);
991 QRect cr = contentsRect();
992 cr.adjust(d->margin, d->margin, -d->margin, -d->margin);
993 int align = QStyle::visualAlignment(d->isTextLabel ? d->textDirection()
994 : layoutDirection(), QFlag(d->align));
997 if (d->movie && !d->movie->currentPixmap().isNull()) {
998 if (d->scaledcontents)
999 style->drawItemPixmap(&painter, cr, align, d->movie->currentPixmap().scaled(cr.size()));
1001 style->drawItemPixmap(&painter, cr, align, d->movie->currentPixmap());
1005 if (d->isTextLabel) {
1006 QRectF lr = d->layoutRect().toAlignedRect();
1009#if QT_CONFIG(style_stylesheet)
1010 if (QStyleSheetStyle* cssStyle = qt_styleSheet(style))
1011 cssStyle->styleSheetPalette(
this, &opt, &opt.palette);
1014#ifndef QT_NO_SHORTCUT
1015 const bool underline =
static_cast<
bool>(style->styleHint(QStyle::SH_UnderlineShortcut,
1016 nullptr,
this,
nullptr));
1017 if (d->shortcutId != 0
1018 && underline != d->shortcutCursor.charFormat().fontUnderline()) {
1019 QTextCharFormat fmt;
1020 fmt.setFontUnderline(underline);
1021 d->shortcutCursor.mergeCharFormat(fmt);
1024 d->ensureTextLayouted();
1026 QAbstractTextDocumentLayout::PaintContext context;
1028 context.palette = opt.palette;
1030 if (foregroundRole() != QPalette::Text && isEnabled())
1031 context.palette.setColor(QPalette::Text, context.palette.color(foregroundRole()));
1034 painter.translate(lr.topLeft());
1035 painter.setClipRect(lr.translated(-lr.x(), -lr.y()));
1036 d->control->setPalette(context.palette);
1037 d->control->drawContents(&painter, QRectF(),
this);
1040 int flags = align | (d->textDirection() == Qt::LeftToRight ? Qt::TextForceLeftToRight
1041 : Qt::TextForceRightToLeft);
1042 if (d->hasShortcut) {
1043 flags |= Qt::TextShowMnemonic;
1044 if (!style->styleHint(QStyle::SH_UnderlineShortcut, &opt,
this))
1045 flags |= Qt::TextHideMnemonic;
1047 style->drawItemText(&painter, lr.toRect(), flags, opt.palette, isEnabled(), d->text, foregroundRole());
1050#ifndef QT_NO_PICTURE
1052 QRect br = d->picture->boundingRect();
1053 int rw = br.width();
1054 int rh = br.height();
1055 if (d->scaledcontents) {
1057 painter.translate(cr.x(), cr.y());
1058 painter.scale((
double)cr.width()/rw, (
double)cr.height()/rh);
1059 painter.drawPicture(-br.x(), -br.y(), *d->picture);
1064 if (align & Qt::AlignVCenter)
1065 yo = (cr.height()-rh)/2;
1066 else if (align & Qt::AlignBottom)
1067 yo = cr.height()-rh;
1068 if (align & Qt::AlignRight)
1070 else if (align & Qt::AlignHCenter)
1071 xo = (cr.width()-rw)/2;
1072 painter.drawPicture(cr.x()+xo-br.x(), cr.y()+yo-br.y(), *d->picture);
1076 if (d->icon && !d->icon->isNull()) {
1077 const qreal dpr = devicePixelRatio();
1078 const QSize size = d->scaledcontents ? cr.size() : d->pixmapSize;
1079 const auto mode = isEnabled() ? QIcon::Normal : QIcon::Disabled;
1080 QPixmap pix = d->icon->pixmap(size, dpr, mode);
1086 if (pix.size() != size * dpr) {
1087 const QString key =
"qt_label_"_L1 % HexString<quint64>(pix.cacheKey())
1088 % HexString<quint8>(mode)
1089 % HexString<uint>(size.width())
1090 % HexString<uint>(size.height())
1091 % HexString<quint16>(qRound(dpr * 1000));
1092 if (!QPixmapCache::find(key, &pix)) {
1093 pix = pix.scaled(size * dpr, Qt::IgnoreAspectRatio, Qt::SmoothTransformation);
1094 pix.setDevicePixelRatio(dpr);
1100 QPixmapCache::insert(key, pix);
1105 style->drawItemPixmap(&painter, cr, align, pix);
1465QRect QLabelPrivate::documentRect()
const
1468 Q_ASSERT_X(isTextLabel,
"documentRect",
"document rect called for label that is not a text label!");
1469 QRect cr = q->contentsRect();
1470 cr.adjust(margin, margin, -margin, -margin);
1471 const int align = QStyle::visualAlignment(isTextLabel ? textDirection()
1472 : q->layoutDirection(), QFlag(
this->align));
1474 if (m < 0 && q->frameWidth())
1475 m = q->fontMetrics().horizontalAdvance(u'x') / 2 - margin;
1477 if (align & Qt::AlignLeft)
1478 cr.setLeft(cr.left() + m);
1479 if (align & Qt::AlignRight)
1480 cr.setRight(cr.right() - m);
1481 if (align & Qt::AlignTop)
1482 cr.setTop(cr.top() + m);
1483 if (align & Qt::AlignBottom)
1484 cr.setBottom(cr.bottom() - m);
1559void QLabelPrivate::ensureTextControl()
const
1565 control =
new QWidgetTextControl(
const_cast<QLabel *>(q));
1566 control->document()->setUndoRedoEnabled(
false);
1567 control->document()->setDefaultFont(q->font());
1568 if (resourceProvider !=
nullptr)
1569 control->document()->setResourceProvider(resourceProvider);
1570 control->setTextInteractionFlags(textInteractionFlags);
1571 control->setOpenExternalLinks(openExternalLinks);
1572 control->setPalette(q->palette());
1573 control->setFocus(q->hasFocus());
1574 QObject::connect(control, &QWidgetTextControl::updateRequest,
1575 q, qOverload<>(&QLabel::update));
1576 QObject::connect(control, &QWidgetTextControl::linkActivated,
1577 q, &QLabel::linkActivated);
1578 QObjectPrivate::connect(control, &QWidgetTextControl::linkHovered,
1579 this, &QLabelPrivate::linkHovered);
1580 textLayoutDirty =
true;