QT QApplication:setFont() Questions - c++

In my main.cpp I set the font of the application like so:
//Font
QString fontPath = ":/data/COUR.TTF";
int id = QFontDatabase::addApplicationFont(fontPath);
QString family = QFontDatabase::applicationFontFamilies(id).at(0);
QFont default_font(family);
default_font.setPointSize(10);
QApplication::setFont(default_font);
This works, mostly. For whatever reason all of the application that I can see correctly applies this font except for the very parent widget, QTabWidget.
I also have this snippet of code that is activated on a button press, inside a MainWindow function:
QApplication::setFont(QFontDialog::getFont(0, QApplication::font()));
When activated during runtime, this error is produced:
2017-06-13 21:10:14.622 MYAPP[36930:4140590] Layout still needs update after calling -[QNSPanelContentsWrapper layout].
QNSPanelContentsWrapper or one of its superclasses may have overridden -layout without calling super.
Or, something may have dirtied layout in the middle of updating it. Both are programming errors in Cocoa Autolayout.
The former is pretty likely to arise if some pre-Cocoa Autolayout class had a method called layout, but it should be fixed.
(Edited a little for visual clarity)
I've looked at this bug report, which shows the exact same error and a similar-ish code, it may be relevant: https://bugreports.qt.io/browse/QTBUG-58699
Their code:
QColorDialog::getColor(QColor(1., 1., 1.), myWindow, "My Title", QColorDialog::DontUseNativeDialog);
That error is not produced by the MainWindow function if I remove the main.cpp settings, which makes me doubt its actually this bug. In addition, the MainWindow function correctly applies the font chosen to all but a few (seemingly) random buttons.
They (From the bug report) are on OSX 10.11.6, I am as well. They reported it for QT 5.8, I'm experiencing it with QT 5.9 and 5.8. If this is the case, this doesn't surprise me, as the bug report does not indicate it has been fixed. I can reproduce it on the QT Creator built debug version, and a statically built release version.
So my question boils down to these points:
1) Why does the main.cpp font code not work across all widgets?
2) Why does that MainWindow function not override the main.cpp settings?
3) Why does that MainWindow function (With the main.cpp part removed) not apply the settings to the entire application?
4) Are there better/easier ways to accomplish what I'm trying to do? (Set a font on application start, and provide a way for the user to customize it later)

Related

GTK3: version 3.20 to 3.22 update issues (with window decoration)

I recently updated the GTK3 lib I am using, both on windows and linux,
from version 3.20 to 3.22, and I noticed some bugs in my application (GTK3 + OpenGL using the GtkGLArea widget) appearing after the update.
The bug, namely the disappearance of window decoration appears after a precise, yet simple, succession of events:
1) screen shot before the bug:
2) Exporting an image from this window (using a framebuffer for off-screen rendering)
3) After saving, going back to the main window by closing the dialog box, note that the upper menu bar now appears like if de-activated (grey) but sill works:
4) ... and when re-sizing / hiding / showing again 'ie. configuring' the window the decoration disappear:
5) The menu bar still seems to be there and works fine:
Obviously I looked carefully to the code after the saving action, but what happens remain elusive to me and I do not know what to look for.
The program does not stop and keeps working fine.
There was absolutely no problem with GTK3 3.20, and the bug appears both on windows and Linux.
What can I do to correct this situation ?
In the Gtk-3 series there have been many changes to the CSS system. If you are not using the default Adwaita theme, then probably you have to search for an updated version of the theme you do have installed. It might even be possible that the Adwaita theme wasn't update correctly during your upgrade.
Anyway, nearly all appearance problems are due to changes in the CSS system - Gtk doesn't really occupy itself with the aesthetics anymore.

Qt: QVideoWidget doesn't show up and disables all buttons within application OR extremely slows down the application

To make it clear the question is: Why, when I add a QVideoWidget to my application, all buttons become not clickable, the scrollbars don't work, and the comboboxes as well become not clickable? Is QVideoWidget disabling those functionalities? Or is that maybe (like I read in this SO question) QVideoWidget is extremely slowing down my application, just by being added to the application?
Now the details:
I really hope someone can help me with this. I'm trying to place a QvideoWidget into my desktop application with the following code (nothing special, just like in the tutorials):
// ...
// more code above for other things...
// main video-player widget
video_widget = new QVideoWidget;
video_widget->setMaximumHeight(100); // I could set any size here...this is not the point
video_widget->setMinimumHeight(100);
video_widget->setStyleSheet(STYLE_WIDGET_BG); // same background as the other widgets...
video_widget->setMaximumWidth(100);
video_widget->setMinimumWidth(100);
media_player = new QMediaPlayer(0, QMediaPlayer::VideoSurface);
TV_V_LAYOUT_MAIN_2->addWidget(video_widget); // #define TV_V_LAYOUT_MAIN_2 ui.lvl_4_tv2_h_1 --> this a layout inside another layout...
media_player->setVideoOutput(video_widget);
return; // this function is called inside the MainWindow constructor
So there are the situations:
1) Without adding the videowidget, everything works fine...
2) As soon as I add the QVideoWidget with the code above:
app overview
What happens?
The video player doesn't show up in any way. There should be at least the gray background like the other widgets, but nothing. Yet the buttons position lowers, so I guess the player was inserted...The problem is: all buttons (and I mean ALL buttons within my application) are disabled. So are the comboboxes and the scrollbar. By disabled I mean, when you click them, it doesn't normally "animate" like when a button is cliked, and the scrollbar doesn't scroll...
By the way the QVideoWidget is not places into the same layout as the buttons below. You can see the layout hierarchy here: Layouts with Qt Designer
I guess I'm missing something very simple. Anyone got the solution for me?
INFO: I'm programming with Visual Studio 2013 with Qt Add-In; I use only standard libraries; gstreamer is included in the project as well (nothing implemented yet).
OLD EDIT: it may be that the inserting of the video-widget extremely slows down the application, therefore giving the illusion that the scrollbar and the buttons don't work, just because it takes a lot of time for them to process the user interaction. Is this possible? Any solution for that?
Got the solution:
If your QVideoWidgets or QMediaPlayers extremely slow down your application, all you have to do, if you haven't yet, is to move all (or just the nedeed) Qt dll's into your project folder.
That's very basic, I know, yet that was my problem. Now it works like heaven.

How to add the OS X flavor to a Qt app

I have used Qt previously only in the form of PyQt, and today I tried the original version of Qt in C++.
I got it working, however, when if start up my app, I have several problems with it:
it's stationary, which means, I cannot drag it across the screen
I cannot change the size of the window
it does not have a OS X type status bar (which contains the three colored buttons and the name of the window)
How can I add these features to my C++ Qt app?
I have tried to look for a solution, but only found QtApplication::setStyle();, which did not solve my problem.
You can see the code here.
The code inside your subclass of QMainWindow contains this line:
setWindowFlags(Qt::FramelessWindowHint);
That is probably causing most of the problems you describe. Try removing that line.

Qt5 QWidget::create() with Win32 HWND embedding not longer working after port from Qt4

the following code tries to embed a native Win32 HWND of a custom created OpenGL windows into a QWidget using the create method:
viewer_widget::viewer_widget(
QWidget* parent,
const viewer::viewer_attributes& view_attrib,
const wm::context::attribute_desc& ctx_attrib,
const wm::surface::format_desc& win_fmt)
: QWidget(parent)
{
setMouseTracking(true);
setFocusPolicy(Qt::StrongFocus);
setAttribute(Qt::WA_NativeWindow, true);
setAttribute(Qt::WA_PaintOnScreen, true); // disables qt double buffering (seems X11 only since qt4.5, ...)
setAttribute(Qt::WA_NoSystemBackground, true);
setAutoFillBackground(false);
_viewer = make_shared<viewer>(math::vec2ui(100, 100), parent->winId(), view_attrib, ctx_attrib, win_fmt);
// ok set the native window as this widgets window...and hold thumbs
QWidget::create(_viewer->window()->window_handle(), true, true);
}
The viewer creates a native Win32 (or X11) window wit the parent of the QWidget as a parent. It also creates and initializes an OpenGL context. This was/is done for more control over the context creation and live time (I know that Qt5 is much improved in that regard). The QWidget::create() method now takes the HWND of the native window and embeds it into the current QWidget, so that event handling is completely done through Qt.
This works perfectly on Qt4 (latest used is Qt 4.8.6 x64 on Windows 7/8.1 x64 on Visual Studio 2013).
Now when porting to Qt5 the same code should still work according to the Qt5 documentation. It required minor changes to account for the change in the WId type. The QWidget::winId() methods still return the native HWND handles of the widgets, which I verified using spyxx.exe (Visual Studio Tools).
However, the code does not work anymore (using Qt 5.4.0 x64 on Windows 7/8.1 x64 on Visual Studio 2013). The native window is just not embedded. In Qt4 when inspecting the created QWidget its native handle (winId) after the create call was identical to the native HWND, which meant the embedding worked. Now using Qt5 the QWidget contains its own HWND which I could again confirm using spyxx.exe. Now there is the parent widget/window and two child widgets/windows where there should only be one child (the native one). I looked at the source code of the create() method for both Qt versions and I do not understand why it is not working anymore.
Ok, after the first night trying to figure this out I tried several other methods I could find on forums or the documentation:
QWindow::fromWinId(HWND) and QWidget::createWindowContainer(QWindow): This one seems to be the way Qt-Devs want me to do it:
_viewer = make_shared<viewer>(math::vec2ui(100, 100), par_hndl, view_attrib, ctx_attrib, win_fmt);
QWindow* native_wnd = QWindow::fromWinId((WId)_viewer->window()->window_handle());
QWidget* native_wdgt = QWidget::createWindowContainer(native_wnd);
QHBoxLayout* lo = new QHBoxLayout(this);
lo->setContentsMargins(0, 0, 0, 0);
lo->addWidget(native_wdgt);
This at least at least behaves almost the way I expect. I see my window and in the newly created widget the native window is embedded. BUT: I have found no way to get any mouse events/input from that newly created widget. I added an eventFilter without luck. I tried a QStackedLayout with a transparent top-level widget to catch the input, but this does not work as the widget created through createWindowContainer() is always on top of the windows stack. I tries creating a QWindow-derived class to intercept the nativeEvent() invocation, without luck...
I am at the end of my ideas to get this working as with Qt4. Is there anything I can to differently to get the old behavior back? The keyboard input I can track through the parent widget using a Qt::StrongFocus policy but the mouse input in complete swallows by the native window. I cannot move the the Qt5 OpenGL window code and need to use our custom OpenGL context tools as we are doing things with the contexts that Qt5 still does not fully support.
I could not yet try Qt5 on Linux, but the Qt4 code as seen above did work there.
I have largely solved communication from Qt to the window by subclassing QWidget, using create() as you originally did, and reimplementing the QWidget event functions to make changes to the native window directly. The ones I've found so far (the big ones) are the focus events, resizeEvent, moveEvent, and the contents rect and enable changeEvents. Font, palette, tooltip, etc. changeEvents are probably a lower priority.
The above won't solve the reverse issue, that messages from the native window never arrive in Qt's event dispatcher. You will need to post messages from your WndProc to the widget's HWND (i.e., the return from calling winId()). This also nearly steps around trying to translate virtual key codes to Qt::Keys and back.
Some notes about why this doesn't work gracefully, as it did in Qt4:
QWindow only works on X11 with native child widgets right now. Try testing on Linux as you mentioned.
QWidget::create() and QWindow have been problems since 5.1 at the least. The problems you're having in both implementations seem to fit.
Here is a consolidated bug report about QWindow intended usage and issues
Other notes:
QWidget::effectiveWinId() is preferred even though you are creating an immediate child window. This, unfortunately, breaks in 5.4.1.
Update to 5.4.1. There are binary compatibility issues with 5.4.0 and all other versions of Qt5.

Qt 5 Mac toolbar woes

I am trying to make a very simple toolbar in a QMainWindow on a Mac, with Qt 5.2.1, with not a single satisfaction. I was using still Qt 4.8 but I thought I'd give Qt5 a try.
As QtMacExtras are concerned, I don't find the native toolbar class anymore, except in private headers. So I tried a simple QToolbar.
I have a very basic and stupid toolbar:
setUnifiedTitleAndToolBarOnMac(true);
toolbar_ = new QToolBar(this);
toolbar_->setMovable(false);
toolbar_->setFloatable(false);
toolbar_->addAction("h");
toolbar_->addAction("w");
toolbar_->addSeparator();
toolbar_->addAction("f");
As you can see, well, it isn't acceptable.
Is there any chance, by some arcane and weird means, that I could have a nice unified, or better "native look and feel", toolbar on a mac?
QMainWindow::addToolBar(QToolBar *toolbar) should do it.
The NSToolbar does not form part of the Qt widget hierarchy, so your admirably idiomatic conference of parenthood from the main window to the toolbar is working perfectly to specification, yet is obviously dissatisfying.
However, as the Trolls say in the QMainWindow documentation:
"You add a toolbar to a main window with addToolBar()."
Here is the effect as shown in rsync client for Mac.
I don't have my mac with me otherwise I would give this a quick test. I was surprised when browsing how many bugs are still being reported for Mac. I did find this article, which does appear to have better looking toolbar.