Having trouble with QFrame and palette...
-
I have implemented a simple help file viewer using a
QTreeView
for content navigation and aQListView
for bookmarks, both laid out in separateQFrame
widgets which themselves are laid out vertically in aQSplitter
. These occupy the left-hand part of the main window. The right-hand side has aQTextBrowser
laid out in anotherQFrame
, and this is laid out together with the other splitter horizontally in a second splitter. Everything seems to work, except that I would like to give the user visual feedback as to which pane has the current focus.I can navigate the panes by using the F6 key. To show the user which pane is current, I tried setting the background color of the frame containing the focussed widget to green and when it loses focus back to light gray, hoping that just the margin around the widget would change color. I have set up an event filter to trap the FocusIn and FocusOut events, which seems to work.
But, although I have sized the grid layouts which hold the different views so that there is a 6-pixel wide margin between the frame and its widget, I do not see any color change (using the palette of the frame and setting the color role = Background. The only time I see a change is when I tried to set the Base color of the palette, but then everything turns black (including the background of the widgets inside of the frame!)
I know there must be a way...
-
Now I can see the frame margin after setting the frame's
autoFillBackground
property to true. However, it is always black.Here is the code I have in my event filter:
bool SbblHelpWindow::eventFilter(QObject *watched, QEvent *event) { QColor col_in = QColor(Qt::green); QColor col_out = QColor(Qt::lightGray); QColor col_to_set; if (event->type() == QEvent::FocusIn) { col_to_set = col_in; } else if (event->type() == QEvent::FocusOut) { col_to_set = col_out; } if (watched == ui->treeContents) { QPalette pal = ui->frameContents->palette(); pal.setColor(QPalette::Window, col_to_set); ui->frameContents->setPalette(pal); } else if (watched == ui->lsvBookmarks) { QPalette pal = ui->frameBookmarks->palette(); pal.setColor(QPalette::Window, col_to_set); ui->frameBookmarks->setPalette(pal); } else if (watched == ui->txtPageView) { QPalette pal = ui->framePageView->palette(); pal.setColor(QPalette::Window, col_to_set); ui->framePageView->setPalette(pal); } return false; }
-
Hi
On what platform ?
seems to use it on Windows.
You could test if it even uses the palette on your platform
srand (time(NULL)); QPalette pal = ui->frame_5->palette(); for (int var = QPalette::WindowText; var < QPalette::PlaceholderText; ++var) { QColor col(rand()%255,rand()%255,rand()%255); pal.setColor((QPalette::ColorRole)var, col); } ui->frame_5->setPalette(pal);
-
Hi
On what platform ?
seems to use it on Windows.
You could test if it even uses the palette on your platform
srand (time(NULL)); QPalette pal = ui->frame_5->palette(); for (int var = QPalette::WindowText; var < QPalette::PlaceholderText; ++var) { QColor col(rand()%255,rand()%255,rand()%255); pal.setColor((QPalette::ColorRole)var, col); } ui->frame_5->setPalette(pal);
@mrjj ... thanks for looking into this. I am doing this on Linux Ubuntu 18.04.2 LTS with the default Gnome window manager.
-
@mrjj ... thanks for looking into this. I am doing this on Linux Ubuntu 18.04.2 LTS with the default Gnome window manager.
@robert-hairgrove
Hi
Not all platforms QStyle will draw the same way / use the palette.Can you try the last loop code that changes all entries to a random color and see
if it does change the QFrame look on ubuntu. -
@robert-hairgrove
Hi
Not all platforms QStyle will draw the same way / use the palette.Can you try the last loop code that changes all entries to a random color and see
if it does change the QFrame look on ubuntu.@mrjj Yes, I tweaked the code a bit and added a wait of 1 second ... something like this:
void MainWindow::on_btnGo_clicked() { ui->btnGo->hide(); srand(time(NULL)); QPalette pal = ui->frame2->palette(); for (int var = QPalette::WindowText; var <= QPalette::ToolTipText; ++var) { QColor col(rand()%255,rand()%255,rand()%255); pal.setColor((QPalette::ColorRole)var, col); ui->label->setText(QString::number(var)); ui->frame2->setPalette(pal); ui->frame2->update(); std::this_thread::sleep_for(std::chrono::milliseconds(1000)); QApplication::processEvents(); } ui->btnGo->show(); }
It always changes color when
var==10
, which is theQPalette::Window
enum value. I suppose there is something else going on?? -
Hi
ok super so it does use the QPalette::Window role.Do you use stylesheet or anything like that ?
-
Hi
ok super so it does use the QPalette::Window role.Do you use stylesheet or anything like that ?
@mrjj No, I didn't try the stylesheet way, although I have heard of it.
It's very strange; I can set the palette of all three frames to green, and it looks fine in Qt Designer. But when I use practically the same code as above, I get all black borders. I have these arranged in splitters, too, maybe that has something to do with it?
Thanks for your help, BTW!
-
@robert-hairgrove said in Having trouble with QFrame and palette...:
I get all black borders.
The borders ( the frame in QFrame) is black or
something you see ?I not sure if the QSplitter could do anything as it just manages the widgets.
However , if you use layouts margin feature, you might be seeing through something
as that is not part of the widgets but "outside" it.can you show image of those black borders ?
-
OK, I finally got it to work with style sheets. :) Here is my event filter now:
bool SbblHelpWindow::eventFilter(QObject *watched, QEvent *event) { QString col_in = "green;"; QString col_out = "rgb(238, 238, 236);"; // light gray, this is what Designer gives me QString col_to_set = "background-color:"; bool ok = false; if (event->type() == QEvent::FocusIn) { col_to_set.append(col_in); ok = true; } else if (event->type() == QEvent::FocusOut) { col_to_set.append(col_out); ok = true; } if (ok) { if (watched == ui->treeContents) { ui->frameContents->setStyleSheet(col_to_set); } else if (watched == ui->lsvBookmarks) { ui->frameBookmarks->setStyleSheet(col_to_set); } else if (watched == ui->txtPageView) { ui->framePageView->setStyleSheet(col_to_set); } } return false; }
Thank you very much for the tip, @mrjj !