X-Git-Url: https://git.sur5r.net/?a=blobdiff_plain;f=src%2Fsearchview.cpp;h=6536d0b4edaebb0bf69401ccec918f6b33772185;hb=434d88418722fd7717038e44bd74271ca1d92771;hp=bf48028953b1a01f0b66e2f1fb97adb7df614159;hpb=533489a63a9716c645a11a99ca446978b20eedd0;p=minitube diff --git a/src/searchview.cpp b/src/searchview.cpp index bf48028..6536d0b 100644 --- a/src/searchview.cpp +++ b/src/searchview.cpp @@ -19,16 +19,19 @@ along with Minitube. If not, see . $END_LICENSE */ #include "searchview.h" +#include "channelsuggest.h" #include "constants.h" #include "fontutils.h" #include "searchparams.h" #include "ytsuggester.h" -#include "channelsuggest.h" #ifdef APP_MAC_SEARCHFIELD #include "searchlineedit_mac.h" #else #include "searchlineedit.h" #endif +#ifdef APP_MAC +#include "macutils.h" +#endif #ifdef APP_EXTRA #include "extra.h" #endif @@ -36,22 +39,22 @@ $END_LICENSE */ #include "activation.h" #include "activationview.h" #endif +#include "clickablelabel.h" +#include "iconutils.h" #include "mainwindow.h" #include "painterutils.h" -#include "iconutils.h" -#include "clickablelabel.h" namespace { -static const QString recentKeywordsKey = "recentKeywords"; -static const QString recentChannelsKey = "recentChannels"; -} +const QString recentKeywordsKey = "recentKeywords"; +const QString recentChannelsKey = "recentChannels"; +} // namespace SearchView::SearchView(QWidget *parent) : View(parent) { - const int padding = 30; + setBackgroundRole(QPalette::Base); + setForegroundRole(QPalette::Text); + setAutoFillBackground(true); - // speedup painting since we'll paint the whole background - // by ourselves anyway in paintEvent() - setAttribute(Qt::WA_OpaquePaintEvent); + const int padding = 30; QBoxLayout *vLayout = new QVBoxLayout(this); vLayout->setMargin(padding); @@ -71,8 +74,12 @@ SearchView::SearchView(QWidget *parent) : View(parent) { hLayout->addStretch(); - logo = new ClickableLabel(this); - logo->setPixmap(IconUtils::pixmap(":/images/app.png")); + logo = new ClickableLabel(); + auto setLogoPixmap = [this] { + logo->setPixmap(IconUtils::pixmap(":/images/app.png", logo->devicePixelRatioF())); + }; + setLogoPixmap(); + connect(window()->windowHandle(), &QWindow::screenChanged, this, setLogoPixmap); connect(logo, &ClickableLabel::clicked, MainWindow::instance(), &MainWindow::visitSite); hLayout->addWidget(logo, 0, Qt::AlignTop); hLayout->addSpacing(padding); @@ -81,65 +88,41 @@ SearchView::SearchView(QWidget *parent) : View(parent) { layout->setAlignment(Qt::AlignCenter); hLayout->addLayout(layout); - QColor titleColor = palette().color(QPalette::WindowText); - titleColor.setAlphaF(.75); - int r,g,b,a; - titleColor.getRgb(&r,&g,&b,&a); - QString cssColor = QString::asprintf("rgba(%d,%d,%d,%d)", r, g, b, a); - - QLabel *welcomeLabel = - new QLabel(QString("

").arg(cssColor) + - tr("Welcome to %2,") - .replace(""); + QLabel *welcomeLabel = new QLabel(); + auto setupWelcomeLabel = [this, welcomeLabel] { + QColor titleColor = palette().color(QPalette::WindowText); + titleColor.setAlphaF(.75); + int r, g, b, a; + titleColor.getRgb(&r, &g, &b, &a); + QString cssColor = QString::asprintf("rgba(%d,%d,%d,%d)", r, g, b, a); + QString text = + QString("

").arg(cssColor) + + tr("Welcome to %2,") + .replace(""; + welcomeLabel->setText(text); + }; + setupWelcomeLabel(); + connect(qApp, &QGuiApplication::paletteChanged, this, setupWelcomeLabel); welcomeLabel->setOpenExternalLinks(true); - welcomeLabel->setProperty("heading", true); - welcomeLabel->setFont(FontUtils::light(welcomeLabel->font().pointSize() * 1.25)); + welcomeLabel->setFont(FontUtils::light(welcomeLabel->font().pointSize())); layout->addWidget(welcomeLabel); layout->addSpacing(padding / 2); -#ifndef APP_MAC - const QFont &biggerFont = FontUtils::big(); -#endif - //: "Enter", as in "type". The whole phrase says: "Enter a keyword to start watching videos" // QLabel *tipLabel = new QLabel(tr("Enter"), this); - QString tip; if (qApp->layoutDirection() == Qt::RightToLeft) { tip = tr("to start watching videos.") + " " + tr("a keyword") + " " + tr("Enter"); } else { tip = tr("Enter") + " " + tr("a keyword") + " " + tr("to start watching videos."); } - QLabel *tipLabel = new QLabel(tip); - -#ifndef APP_MAC - tipLabel->setFont(biggerFont); -#endif - layout->addWidget(tipLabel); - - /* - typeCombo = new QComboBox(this); - typeCombo->addItem(tr("a keyword")); - typeCombo->addItem(tr("a channel")); -#ifndef APP_MAC - typeCombo->setFont(biggerFont); -#endif - connect(typeCombo, SIGNAL(currentIndexChanged(int)), SLOT(searchTypeChanged(int))); - tipLayout->addWidget(typeCombo); - - tipLabel = new QLabel(tr("to start watching videos."), this); -#ifndef APP_MAC - tipLabel->setFont(biggerFont); -#endif - tipLayout->addWidget(tipLabel); - */ layout->addSpacing(padding / 2); - QHBoxLayout *searchLayout = new QHBoxLayout(); + QBoxLayout *searchLayout = new QHBoxLayout(); searchLayout->setAlignment(Qt::AlignVCenter); #ifdef APP_MAC_SEARCHFIELD @@ -148,34 +131,31 @@ SearchView::SearchView(QWidget *parent) : View(parent) { setFocusProxy(slem); #else SearchLineEdit *sle = new SearchLineEdit(this); - sle->setFont(biggerFont); + sle->setFont(FontUtils::medium()); + int tipWidth = sle->fontMetrics().size(Qt::TextSingleLine, tip).width(); + sle->setMinimumWidth(tipWidth + sle->fontMetrics().width('m') * 6); + sle->setSizePolicy(QSizePolicy::Fixed, QSizePolicy::Preferred); queryEdit = sle; #endif - connect(queryEdit->toWidget(), SIGNAL(search(const QString&)), SLOT(watch(const QString&))); - connect(queryEdit->toWidget(), SIGNAL(textChanged(const QString &)), SLOT(textChanged(const QString &))); - connect(queryEdit->toWidget(), SIGNAL(textEdited(const QString &)), SLOT(textChanged(const QString &))); - connect(queryEdit->toWidget(), SIGNAL(suggestionAccepted(Suggestion*)), SLOT(suggestionAccepted(Suggestion*))); + connect(queryEdit->toWidget(), SIGNAL(search(const QString &)), SLOT(watch(const QString &))); + connect(queryEdit->toWidget(), SIGNAL(textChanged(const QString &)), + SLOT(textChanged(const QString &))); + connect(queryEdit->toWidget(), SIGNAL(textEdited(const QString &)), + SLOT(textChanged(const QString &))); + connect(queryEdit->toWidget(), SIGNAL(suggestionAccepted(Suggestion *)), + SLOT(suggestionAccepted(Suggestion *))); + queryEdit->setPlaceholderText(tip); youtubeSuggest = new YTSuggester(this); channelSuggest = new ChannelSuggest(this); - connect(channelSuggest, SIGNAL(ready(QVector)), SLOT(onChannelSuggestions(QVector))); + connect(channelSuggest, SIGNAL(ready(QVector)), + SLOT(onChannelSuggestions(QVector))); searchTypeChanged(0); searchLayout->addWidget(queryEdit->toWidget(), 0, Qt::AlignBaseline); - searchLayout->addSpacing(padding); - watchButton = new QPushButton(tr("Watch")); -#ifndef APP_MAC - watchButton->setFont(biggerFont); -#endif - watchButton->setDefault(true); - watchButton->setEnabled(false); - watchButton->setSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed); - connect(watchButton, SIGNAL(clicked()), this, SLOT(watch())); - searchLayout->addWidget(watchButton, 0, Qt::AlignBaseline); - - layout->addItem(searchLayout); + layout->addLayout(searchLayout); layout->addSpacing(padding); @@ -188,9 +168,9 @@ SearchView::SearchView(QWidget *parent) : View(parent) { recentKeywordsLayout->setSpacing(0); recentKeywordsLayout->setAlignment(Qt::AlignTop | Qt::AlignLeft); recentKeywordsLabel = new QLabel(tr("Recent keywords")); - recentKeywordsLabel->setEnabled(false); recentKeywordsLabel->setProperty("recentHeader", true); recentKeywordsLabel->hide(); + recentKeywordsLabel->setEnabled(false); recentKeywordsLayout->addWidget(recentKeywordsLabel); recentLayout->addLayout(recentKeywordsLayout); @@ -199,9 +179,9 @@ SearchView::SearchView(QWidget *parent) : View(parent) { recentChannelsLayout->setSpacing(0); recentChannelsLayout->setAlignment(Qt::AlignTop | Qt::AlignLeft); recentChannelsLabel = new QLabel(tr("Recent channels")); - recentChannelsLabel->setEnabled(false); recentChannelsLabel->setProperty("recentHeader", true); recentChannelsLabel->hide(); + recentChannelsLabel->setEnabled(false); recentChannelsLayout->addWidget(recentChannelsLabel); recentLayout->addLayout(recentChannelsLayout); @@ -213,39 +193,30 @@ SearchView::SearchView(QWidget *parent) : View(parent) { #ifdef APP_ACTIVATION if (!Activation::instance().isActivated()) - vLayout->addWidget(ActivationView::buyButton(tr("Get the full version")), 0, Qt::AlignRight); + vLayout->addWidget(ActivationView::buyButton(tr("Get the full version")), 0, + Qt::AlignRight); #endif } void SearchView::appear() { MainWindow *w = MainWindow::instance(); - w->showActionInStatusBar(w->getAction("manualplay"), true); - w->showActionInStatusBar(w->getAction("safeSearch"), true); - w->showActionInStatusBar(w->getAction("definition"), true); + w->showActionsInStatusBar( + {w->getAction("manualplay"), w->getAction("safeSearch"), w->getAction("definition")}, + true); updateRecentKeywords(); updateRecentChannels(); queryEdit->selectAll(); queryEdit->enableSuggest(); - if (!queryEdit->toWidget()->hasFocus()) queryEdit->toWidget()->setFocus(); - - connect(window()->windowHandle(), SIGNAL(screenChanged(QScreen*)), SLOT(screenChanged()), Qt::UniqueConnection); - - qApp->processEvents(); - update(); - -#ifdef APP_MAC - // Workaround cursor bug on macOS - window()->unsetCursor(); -#endif + QTimer::singleShot(0, queryEdit->toWidget(), SLOT(setFocus())); } void SearchView::disappear() { MainWindow *w = MainWindow::instance(); - w->showActionInStatusBar(w->getAction("safeSearch"), false); - w->showActionInStatusBar(w->getAction("definition"), false); - w->showActionInStatusBar(w->getAction("manualplay"), false); + w->showActionsInStatusBar( + {w->getAction("manualplay"), w->getAction("safeSearch"), w->getAction("definition")}, + false); } void SearchView::updateRecentKeywords() { @@ -257,7 +228,8 @@ void SearchView::updateRecentKeywords() { // cleanup QLayoutItem *item; - while ((item = recentKeywordsLayout->takeAt(1)) != 0) { + while (recentKeywordsLayout->count() - 1 > recentKeywords.size() && + (item = recentKeywordsLayout->takeAt(1)) != nullptr) { item->widget()->close(); delete item; } @@ -267,37 +239,66 @@ void SearchView::updateRecentKeywords() { const int maxDisplayLength = 25; +#ifdef APP_MAC + QPalette p = palette(); + p.setColor(QPalette::Highlight, mac::accentColor()); +#endif + + int counter = 1; for (const QString &keyword : keywords) { QString link = keyword; QString display = keyword; - if (keyword.startsWith(QLatin1String("http://")) || keyword.startsWith(QLatin1String("https://"))) { + if (keyword.startsWith(QLatin1String("http://")) || + keyword.startsWith(QLatin1String("https://"))) { int separator = keyword.indexOf('|'); if (separator > 0 && separator + 1 < keyword.length()) { link = keyword.left(separator); - display = keyword.mid(separator+1); + display = keyword.mid(separator + 1); } } - bool needStatusTip = false; - if (display.length() > maxDisplayLength) { + bool needStatusTip = display.length() > maxDisplayLength; + if (needStatusTip) { display.truncate(maxDisplayLength); display.append(QStringLiteral("\u2026")); - needStatusTip = true; } - QPushButton *itemButton = new QPushButton(display); - itemButton->setAttribute(Qt::WA_DeleteOnClose); - itemButton->setProperty("recentItem", true); - itemButton->setCursor(Qt::PointingHandCursor); - itemButton->setFocusPolicy(Qt::TabFocus); - itemButton->setSizePolicy(QSizePolicy::MinimumExpanding, QSizePolicy::Preferred); + + ClickableLabel *item; + if (recentKeywordsLayout->count() - 1 >= counter) { + item = qobject_cast(recentKeywordsLayout->itemAt(counter)->widget()); + + } else { + item = new ClickableLabel(); +#ifdef APP_MAC + item->setPalette(p); +#endif + item->setAttribute(Qt::WA_DeleteOnClose); + item->setProperty("recentItem", true); + item->setFocusPolicy(Qt::TabFocus); + connect(item, &ClickableLabel::hovered, this, [item, this](bool value) { + item->setForegroundRole(value ? QPalette::Highlight : QPalette::WindowText); + if (value) { + for (int i = 1; i < recentKeywordsLayout->count(); ++i) { + QWidget *w = recentKeywordsLayout->itemAt(i)->widget(); + if (w != item) { + w->setForegroundRole(QPalette::WindowText); + } + } + } + }); + recentKeywordsLayout->addWidget(item); + } + + item->setText(display); if (needStatusTip) - itemButton->setStatusTip(link); - connect(itemButton, &QPushButton::clicked, [this,link]() { - watchKeywords(link); - }); + item->setStatusTip(link); + else + item->setStatusTip(QString()); - recentKeywordsLayout->addWidget(itemButton); - } + disconnect(item, &ClickableLabel::clicked, nullptr, nullptr); + connect(item, &ClickableLabel::clicked, this, [this, link]() { watchKeywords(link); }); + counter++; + } } void SearchView::updateRecentChannels() { @@ -309,13 +310,17 @@ void SearchView::updateRecentChannels() { // cleanup QLayoutItem *item; - while ((item = recentChannelsLayout->takeAt(1)) != 0) { + while ((item = recentChannelsLayout->takeAt(1)) != nullptr) { item->widget()->close(); delete item; } recentChannelsLabel->setVisible(!keywords.isEmpty()); - // TODO MainWindow::instance()->getAction("clearRecentKeywords")->setEnabled(!keywords.isEmpty()); + +#ifdef APP_MAC + QPalette p = palette(); + p.setColor(QPalette::Highlight, mac::accentColor()); +#endif for (const QString &keyword : keywords) { QString link = keyword; @@ -323,18 +328,21 @@ void SearchView::updateRecentChannels() { int separator = keyword.indexOf('|'); if (separator > 0 && separator + 1 < keyword.length()) { link = keyword.left(separator); - display = keyword.mid(separator+1); + display = keyword.mid(separator + 1); } - QPushButton *itemButton = new QPushButton(display); - itemButton->setAttribute(Qt::WA_DeleteOnClose); - itemButton->setProperty("recentItem", true); - itemButton->setCursor(Qt::PointingHandCursor); - itemButton->setFocusPolicy(Qt::TabFocus); - itemButton->setSizePolicy(QSizePolicy::MinimumExpanding, QSizePolicy::Preferred); - connect(itemButton, &QPushButton::clicked, [this,link]() { - watchChannel(link); + + ClickableLabel *item = new ClickableLabel(display); +#ifdef APP_MAC + item->setPalette(p); +#endif + item->setAttribute(Qt::WA_DeleteOnClose); + item->setProperty("recentItem", true); + item->setFocusPolicy(Qt::TabFocus); + connect(item, &ClickableLabel::clicked, [this, link]() { watchChannel(link); }); + connect(item, &ClickableLabel::hovered, item, [item](bool value) { + item->setForegroundRole(value ? QPalette::Highlight : QPalette::WindowText); }); - recentChannelsLayout->addWidget(itemButton); + recentChannelsLayout->addWidget(item); } } @@ -344,7 +352,6 @@ void SearchView::watch() { } void SearchView::textChanged(const QString &text) { - watchButton->setEnabled(!text.simplified().isEmpty()); lastChannelSuggestions.clear(); } @@ -357,14 +364,6 @@ void SearchView::watch(const QString &query) { return; } - /* - if (typeCombo->currentIndex() == 1) { - // Channel search - MainWindow::instance()->channelSearch(q); - return; - } - */ - SearchParams *searchParams = new SearchParams(); searchParams->setKeywords(q); @@ -401,10 +400,7 @@ void SearchView::watchKeywords(const QString &query) { return; } - // if (typeCombo->currentIndex() == 0) { - queryEdit->setText(q); - watchButton->setEnabled(true); - // } + queryEdit->setText(q); SearchParams *searchParams = new SearchParams(); searchParams->setKeywords(q); @@ -413,18 +409,6 @@ void SearchView::watchKeywords(const QString &query) { emit search(searchParams); } -void SearchView::paintEvent(QPaintEvent *event) { - QWidget::paintEvent(event); - QBrush brush; - if (window()->isActiveWindow()) { - brush = palette().base(); - } else { - brush = palette().window(); - } - QPainter painter(this); - painter.fillRect(0, 0, width(), height(), brush); -} - void SearchView::searchTypeChanged(int index) { if (index == 0) { queryEdit->setSuggester(youtubeSuggest); @@ -438,11 +422,8 @@ void SearchView::searchTypeChanged(int index) { void SearchView::suggestionAccepted(Suggestion *suggestion) { if (suggestion->type == QLatin1String("channel")) { watchChannel(suggestion->userData); - } else watch(suggestion->value); -} - -void SearchView::screenChanged() { - logo->setPixmap(IconUtils::pixmap(":/images/app.png")); + } else + watch(suggestion->value); } void SearchView::onChannelSuggestions(const QVector &suggestions) {