Qt on CMake Workshop Summary – May ’19 Porting Qt to the CMake build system

This is a follow-up post to Qt on CMake Workshop Summary – Feb ’19

Intro

From May 2nd to May 3rd another Qt on CMake workshop was hosted at the KDAB premises in Berlin, where interested stakeholders from both The Qt Company and KDAB gathered together to drive the CMake build system in Qt further. Many of KDAB’s customers are using CMake in their Qt projects, so we are keen to see the CMake support for Qt improve and happy to help out to make it happen. The workshop was public, for anyone interested, but we had no external visitors this time. We’d be happy to have some more CMake enthusiasts or interested people in these workshops, so be sure to sign up for the next CMake workshop (watch the qt-development mailing list for this)!

This workshop in May was mostly intended to reassess what has happened in the wip/cmake branch of qtbase since the last workshop and to discuss any further work. We spent almost half of the first day just deciding how to approach certain things such as how the CMake build system port will affect the upcoming Qt6 work, which is currently gaining momentum as well. We had between 8 and 10 people present across the 2 day workshop, from KDAB and (mostly) The Qt Company.

Workshop summary

First of all: Thanks to Alexandru Croitor for driving the porting efforts and for organizing sprints and meetings where interested people can keep track of the progress!

The workshop summary notes are also courtesy of Alexandru, let me try to quickly recap the most interesting bits:

CMake config files in Qt6 and beyond

One of the key considerations of the CMake config files installed as part of the upcoming Qt6 was that there should a) be the possibility to just be able to use CMake targets like Qt::Core (compared to Qt5::Core) and functions/macro names like qt_do_x() (instead of qt5_do_x()) to allow most applications to just pull in a Qt version of their choice and then use “versionless” CMake identifiers. This allows to upgrade Qt versions more easily, without a lot of search-replace in CMake code. Note that you can continue to use the version-specific identifiers as before. This is an additional feature.

But on the other hand we’d also like to keep the possibility to mix Qt version X and Qt version Y in the same CMake project. Think about a project where two executables are being built, one depending on Qt6, the other one a potential Qt7 version. This is not as cumbersome as you’d think; we experience a lot of customer projects where people have this setup. It might as well be the case during a porting project, where old code might still continue to use an older Qt version.

Consider this example (which is not fully implemented yet, but you get the idea):

### Usecase: application wants to mix both Qt5 and Qt6, to allow gradual porting set(QT_CREATE_VERSIONLESS_TARGETS OFF) find_package(Qt5 COMPONENTS Core Gui Widgets) # Creates only Qt5::Core find_package(Qt6 COMPONENTS Core Gui Widgets) # Creates only Qt6::Core target_link_libraries(myapp1 Qt5::Core) target_link_libraries(myapp2 Qt6::Core) ### Usecase: application doesn't mix Qt5 and Qt6, but allows to fully switch to link against either Qt5 or Qt6 set(MY_APP_QT_MAJOR_VERSION 6) # <- potentially set at command line by application developer # set(QT_CREATE_VERSIONLESS_TARGETS ON) <- Default, doesn't need to be set find_package(Qt${MY_APP_QT_MAJOR_VERSION} COMPONENTS Core Gui Widgets) # Creates Qt5::Core and Qt::Core OR Qt6::Core and Qt::Core, based on the variable target_link_libraries(myapp Qt::Core) # Just links to whatever Qt major version was requested

More details (and development notes from the past meetings):

After a lot of back and forth we actually found a straight-forward way to at least create the two namespaces in the CMake config files easily, see e.g.: https://codereview.qt-project.org/#/c/253169/

QMake will still be around in Qt6

As it stands, existing users of Qt and specifically users of QMake do not have to fear the CMake port too much, for now. The current bias is towards keeping the qmake executable (and the associated mkspec functionality) around for the Qt6 lifetime, as we’d obviously create a lot of additional porting effort for our users. During the Qt6 lifetime it would probably be wise to consider moving your pet project to a CMake build system, but only time will tell.

QMake is currently built via the CMake build system in the wip/cmake branch and already available for use. Upside-down world, right. Additionally, we’re looking into generating the QMake module .pri files using CMake as well. All this is definitely no witch craft but just needs dedicated people to implement all of it.

Further notes

You can find a lot more details on the Wiki, in case you are curious, I would not like to duplicate even more of the really comprehensive work log produced here: https://wiki.qt.io/CMake_Port/Development_Notes

If you would like to learn more about CMake, we are offering a one-day Introduction to CMake training at the KDAB training day as part of Qt World Summit in Berlin this year.

If you have comments or if you want to help out, please ideally post feedback on the Qt Project infrastructure. Send a mail to the qt-development mailing list or comment on the wiki page dedicated for the CMake port. Or just join us in the IRC channel #qt-cmake on Freenode!