Skip to content

Commit

Permalink
fix: [searchresultitemdelegate] Fix UI issues
Browse files Browse the repository at this point in the history
- Replaced eventFilter with editorEvent for better event handling.
- Adjusted mouse event handling to update the view correctly.
- Added a new method to draw option backgrounds for better UI feedback.
- Updated drawing methods to ensure consistent icon sizes and margins.

Log: Fix UI issues
Bug: https://pms.uniontech.com/bug-view-272579.html
  • Loading branch information
Kakueeen committed Nov 18, 2024
1 parent 06641cb commit ac8634d
Show file tree
Hide file tree
Showing 6 changed files with 88 additions and 67 deletions.
4 changes: 2 additions & 2 deletions src/plugins/core/gui/dockheader.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -40,8 +40,8 @@ DockHeader::DockHeader(QWidget *parent)
d->select->hide();

d->mainLayout = new QHBoxLayout(this);
d->mainLayout->setContentsMargins(0, 0, 0, 5);
d->mainLayout->setSpacing(0);
d->mainLayout->setContentsMargins(10, 7, 8, 7);
d->mainLayout->setSpacing(2);
d->mainLayout->setAlignment(Qt::AlignRight);

auto nameLayout = new QHBoxLayout;
Expand Down
1 change: 0 additions & 1 deletion src/plugins/core/uicontroller/mainwindow.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -95,7 +95,6 @@ DDockWidget *MainWindow::createDockWidget(DWidget *widget)
delete dock->titleBarWidget();

auto header = new DockHeader(this);
header->setContentsMargins(10, 8, 8, 8);
dock->setTitleBarWidget(header);

dock->setWidget(widget);
Expand Down
1 change: 1 addition & 0 deletions src/plugins/find/gui/advancedsearchwidget.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -204,6 +204,7 @@ QWidget *AdvancedSearchWidgetPrivate::createSearchParamWidget()
QGridLayout *gridLayout = new QGridLayout;
gridLayout->setColumnStretch(0, 1);
gridLayout->setContentsMargins(0, 0, 0, 0);
gridLayout->setSpacing(10);
gridLayout->addWidget(searchEdit, 0, 0);
gridLayout->addWidget(caseBtn, 0, 1);
gridLayout->addWidget(wholeWordBtn, 0, 2);
Expand Down
143 changes: 81 additions & 62 deletions src/plugins/find/gui/searchresultitemdelegate.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -42,9 +42,9 @@ void SearchResultItemDelegate::paint(QPainter *painter, const QStyleOptionViewIt

QStyleOptionViewItem opt = option;
DStyledItemDelegate::initStyleOption(&opt, index);

opt.rect.adjust(0, 0, -10, 0);
painter->setRenderHint(QPainter::Antialiasing);

drawBackground(painter, opt);
if (!index.parent().isValid()) {
const auto &iconRect = drawFileIcon(painter, opt, index);
Expand Down Expand Up @@ -86,47 +86,57 @@ bool SearchResultItemDelegate::helpEvent(QHelpEvent *event, QAbstractItemView *v
return DStyledItemDelegate::helpEvent(event, view, option, index);
}

bool SearchResultItemDelegate::eventFilter(QObject *object, QEvent *event)
bool SearchResultItemDelegate::editorEvent(QEvent *event, QAbstractItemModel *model, const QStyleOptionViewItem &option, const QModelIndex &index)
{
if (event->type() == QEvent::MouseButtonPress && object == view()->viewport()) {
auto mouseEvent = dynamic_cast<QMouseEvent *>(event);
auto index = view()->indexAt(mouseEvent->pos());
if (!index.isValid())
return DStyledItemDelegate::eventFilter(object, event);

auto itemRect = view()->visualRect(index);
itemRect.adjust(0, 0, -10, 0);

auto arrowRect = this->arrowRect(iconRect(itemRect));
if (!index.isValid())
return DStyledItemDelegate::editorEvent(event, model, option, index);

auto mouseEvent = dynamic_cast<QMouseEvent *>(event);
auto itemRect = option.rect;
itemRect.adjust(0, 0, -10, 0);
auto arrowRect = this->arrowRect(iconRect(itemRect));
auto replaceRect = replaceButtonRect(itemRect);
auto closeRect = closeButtonRect(itemRect);

switch (event->type()) {
case QEvent::MouseMove:
case QEvent::MouseButtonPress:
view()->update(index);
break;
case QEvent::MouseButtonRelease: {
if (arrowRect.contains(mouseEvent->pos())) {
if (view()->isExpanded(index)) {
view()->collapse(index);
} else {
view()->expand(index);
}
event->accept();
return true;
}

auto replaceRect = replaceButtonRect(itemRect);
if (replaceRect.contains(mouseEvent->pos())) {
auto model = qobject_cast<SearchResultModel *>(view()->model());
if (model) {
Q_EMIT model->requestReplace(index);
auto viewModel = qobject_cast<SearchResultModel *>(model);
if (viewModel) {
Q_EMIT viewModel->requestReplace(index);
event->accept();
return true;
}
}

auto closeRect = closeButtonRect(itemRect);
if (closeRect.contains(mouseEvent->pos())) {
auto model = qobject_cast<SearchResultModel *>(view()->model());
if (model) {
model->remove(index);
auto viewModel = qobject_cast<SearchResultModel *>(model);
if (viewModel) {
viewModel->remove(index);
event->accept();
return true;
}
}
} break;
default:
break;
}

return DStyledItemDelegate::eventFilter(object, event);
return DStyledItemDelegate::editorEvent(event, model, option, index);
}

QTreeView *SearchResultItemDelegate::view() const
Expand Down Expand Up @@ -234,8 +244,8 @@ QRect SearchResultItemDelegate::drawOptionButton(QPainter *painter, const QStyle

// draw close button
QRect iconRect = closeButtonRect(opt.rect);
QIcon closeIcon = DStyle::standardIcon(opt.widget->style(), DStyle::SP_CloseButton);
drawIcon(painter, opt, closeIcon, iconRect);
drawOptionBackground(painter, option, iconRect);
drawIcon(painter, opt, QIcon::fromTheme("common_close"), iconRect);

// draw replace button
QIcon replaceIcon;
Expand All @@ -245,11 +255,39 @@ QRect SearchResultItemDelegate::drawOptionButton(QPainter *painter, const QStyle
replaceIcon = QIcon::fromTheme("replace");

iconRect = replaceButtonRect(opt.rect);
drawOptionBackground(painter, option, iconRect);
drawIcon(painter, opt, replaceIcon, iconRect);

return iconRect;
}

void SearchResultItemDelegate::drawOptionBackground(QPainter *painter, const QStyleOptionViewItem &option, const QRect &rect) const
{
QPoint mousePos = view()->mapFromGlobal(QCursor::pos());
if (!rect.contains(mousePos))
return;

if (QApplication::mouseButtons() & Qt::LeftButton) {
QColor bgColor(255, 255, 255, qRound(255 * 0.15));
painter->save();
painter->setPen(Qt::NoPen);
painter->setBrush(bgColor);
painter->drawRoundedRect(rect, 6, 6);
painter->restore();
} else if (option.state.testFlag(QStyle::State_MouseOver)) {
QColor bgColor(0, 0, 0, qRound(255 * 0.08));
if (option.state.testFlag(QStyle::State_Selected)) {
bgColor.setRgba(qRgba(255, 255, 255, qRound(255 * 0.2)));
} else if (DGuiApplicationHelper::instance()->themeType() == DGuiApplicationHelper::DarkType) {
bgColor.setRgba(qRgba(255, 255, 255, qRound(255 * 0.08)));
}
painter->save();
painter->setPen(Qt::NoPen);
painter->setBrush(bgColor);
painter->drawRoundedRect(rect, 6, 6);
painter->restore();
}
}

void SearchResultItemDelegate::drawNameItem(QPainter *painter, const QStyleOptionViewItem &option,
const QModelIndex &index, const QRect &iconRect) const
{
Expand Down Expand Up @@ -341,7 +379,9 @@ void SearchResultItemDelegate::drawContextItem(QPainter *painter, const QStyleOp
replaceBackground.setNamedColor("#57965C");
replaceBackground.setAlpha(180);
}
formats << createFormatRange(opt, column, matchedLength, {}, matchedBackground);
auto matchedRange = createFormatRange(opt, column, matchedLength, {}, matchedBackground);
matchedRange.format.setFontStrikeOut(true);
formats << matchedRange;
formats << createFormatRange(opt, replaceTextOffset, replaceText.length(), {}, replaceBackground);
} else {
QColor background;
Expand All @@ -358,15 +398,16 @@ void SearchResultItemDelegate::drawContextItem(QPainter *painter, const QStyleOp
}

void SearchResultItemDelegate::drawDisplay(QPainter *painter, const QStyleOptionViewItem &option, const QRect &rect,
const QString &text, const QList<QTextLayout::FormatRange> &format) const
const QString &text, const QList<QTextLayout::FormatRange> &formatList) const
{
if (option.state & QStyle::State_Selected) {
painter->setPen(option.palette.color(QPalette::Normal, QPalette::HighlightedText));
} else {
painter->setPen(option.palette.color(QPalette::Normal, QPalette::Text));
}

if (text.isEmpty())
QString displayText = text.trimmed();
if (displayText.isEmpty())
return;

const QStyleOptionViewItem opt = option;
Expand All @@ -375,46 +416,24 @@ void SearchResultItemDelegate::drawDisplay(QPainter *painter, const QStyleOption
QStyle *style = widget ? widget->style() : QApplication::style();
const int textMargin = style->pixelMetric(QStyle::PM_FocusFrameHMargin, nullptr, widget) + 1;
QRect textRect = rect.adjusted(textMargin, 0, -textMargin, 0); // remove width padding
const bool wrapText = opt.features & QStyleOptionViewItem::WrapText;
QTextOption textOption;
textOption.setWrapMode(wrapText ? QTextOption::WordWrap : QTextOption::ManualWrap);
textOption.setWrapMode(QTextOption::NoWrap);
textOption.setTextDirection(option.direction);
textOption.setAlignment(QStyle::visualAlignment(option.direction, option.displayAlignment));
QTextLayout textLayout;
textLayout.setTextOption(textOption);
textLayout.setFont(option.font);
textLayout.setText(text);
textLayout.setText(displayText);
textLayout.setFormats(formatList.toVector());

QSizeF textLayoutSize = doTextLayout(&textLayout, textRect.width());

if (textRect.width() < textLayoutSize.width()
|| textRect.height() < textLayoutSize.height()) {
QString elided;
int start = 0;
int end = text.indexOf(QChar::LineSeparator, start);
if (end == -1) {
elided += option.fontMetrics.elidedText(text, option.textElideMode, textRect.width());
} else {
while (end != -1) {
elided += option.fontMetrics.elidedText(text.mid(start, end - start),
option.textElideMode, textRect.width());
elided += QChar::LineSeparator;
start = end + 1;
end = text.indexOf(QChar::LineSeparator, start);
}
// let's add the last line (after the last QChar::LineSeparator)
elided += option.fontMetrics.elidedText(text.mid(start),
option.textElideMode, textRect.width());
}
textLayout.setText(elided);
textLayoutSize = doTextLayout(&textLayout, textRect.width());
if (textRect.width() < textLayoutSize.width()) {
displayText = option.fontMetrics.elidedText(displayText, Qt::ElideRight, textRect.width());
textLayout.setText(displayText);
doTextLayout(&textLayout, textRect.width());
}

const QSize layoutSize(textRect.width(), int(textLayoutSize.height()));
const QRect layoutRect = QStyle::alignedRect(option.direction, option.displayAlignment,
layoutSize, textRect);

textLayout.draw(painter, layoutRect.topLeft(), format.toVector(), layoutRect);
textLayout.draw(painter, textRect.topLeft());
}

QSizeF SearchResultItemDelegate::doTextLayout(QTextLayout *textLayout, int width) const
Expand Down Expand Up @@ -462,8 +481,8 @@ QRect SearchResultItemDelegate::replaceButtonRect(const QRect &itemRect) const
{
QRect replaceButtonRect = itemRect;

replaceButtonRect.setSize(view()->iconSize());
replaceButtonRect.moveLeft(itemRect.right() - 2 * view()->iconSize().width() - 2 * ItemMargin);
replaceButtonRect.setSize({ 20, 20 });
replaceButtonRect.moveLeft(itemRect.right() - 2 * 20 - 5);
replaceButtonRect.moveTop(replaceButtonRect.top() + ((itemRect.bottom() - replaceButtonRect.bottom()) / 2));

return replaceButtonRect;
Expand All @@ -473,8 +492,8 @@ QRect SearchResultItemDelegate::closeButtonRect(const QRect &itemRect) const
{
QRect closeButtonRect = itemRect;

closeButtonRect.setSize(view()->iconSize());
closeButtonRect.moveLeft(itemRect.right() - view()->iconSize().width() - ItemMargin);
closeButtonRect.setSize({ 20, 20 });
closeButtonRect.moveLeft(itemRect.right() - 20 - 3);
closeButtonRect.moveTop(closeButtonRect.top() + ((itemRect.bottom() - closeButtonRect.bottom()) / 2));

return closeButtonRect;
Expand All @@ -501,7 +520,7 @@ void SearchResultItemDelegate::drawIcon(QPainter *painter, const QStyleOptionVie
if (option.state.testFlag(QStyle::State_Selected))
iconMode = QIcon::Selected;

auto px = icon.pixmap({ 18, 18 }, iconMode);
auto px = icon.pixmap(view()->iconSize(), iconMode);
px.setDevicePixelRatio(qApp->devicePixelRatio());

qreal x = rect.x();
Expand Down
5 changes: 3 additions & 2 deletions src/plugins/find/gui/searchresultitemdelegate.h
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ class SearchResultItemDelegate : public DTK_WIDGET_NAMESPACE::DStyledItemDelegat

protected:
bool helpEvent(QHelpEvent *event, QAbstractItemView *view, const QStyleOptionViewItem &option, const QModelIndex &index) override;
bool eventFilter(QObject *object, QEvent *event) override;
bool editorEvent(QEvent *event, QAbstractItemModel *model, const QStyleOptionViewItem &option, const QModelIndex &index) override;

private:
QTreeView *view() const;
Expand All @@ -30,12 +30,13 @@ class SearchResultItemDelegate : public DTK_WIDGET_NAMESPACE::DStyledItemDelegat
const QStyleOptionViewItem &option, const QModelIndex &index) const;
QRect drawResultCount(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const;
QRect drawOptionButton(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const;
void drawOptionBackground(QPainter *painter, const QStyleOptionViewItem &option, const QRect &rect) const;
void drawNameItem(QPainter *painter, const QStyleOptionViewItem &option,
const QModelIndex &index, const QRect &iconRect) const;
void drawContextItem(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const;

void drawDisplay(QPainter *painter, const QStyleOptionViewItem &option, const QRect &rect,
const QString &text, const QList<QTextLayout::FormatRange> &format) const;
const QString &text, const QList<QTextLayout::FormatRange> &formatList) const;
QSizeF doTextLayout(QTextLayout *textLayout, int width) const;
QRect iconRect(const QRect &itemRect) const;
QRect arrowRect(const QRect &iconRect) const;
Expand Down
1 change: 1 addition & 0 deletions src/plugins/find/gui/searchresultwidget.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,7 @@ void SearchResultWidgetPrivate::initUI()
resultView->setFrameShape(QFrame::NoFrame);
resultView->setIconSize({ 16, 16 });
resultView->setIndentation(0);
resultView->setMouseTracking(true);

mainLayout->addWidget(msgLabel);
mainLayout->addWidget(resultView);
Expand Down

0 comments on commit ac8634d

Please sign in to comment.