galinette
galinette

Reputation: 9292

Include directive depending on Qt version

I need to include the following header in my code:

#include <5.4.1/QtGui/private/qzipwriter_p.h>

The problem is, we are compiling this on other Qt versions, such as 5.4.2 or 5.5.x

I know I should not use these "private" headers since they are unsupported, but we need them at least until we have a durable replacement.

How can I concatenate the QT_VERSION_STR variable in the path so that this works with all versions?

Upvotes: 4

Views: 2166

Answers (4)

With two letter minor_version e.g. 5.11 not works but it does

#if QT_VERSION >= QT_VERSION_CHECK(5, 11, 0)
    auto isok = f.open(QIODevice::NewOnly| QIODevice::Text);
#else
    auto isok = !QFileInfo::exists(newfile) && f.open(QIODevice::Text);
#endif

Upvotes: 0

Philip Van Hoof
Philip Van Hoof

Reputation: 11

With cmake it would be like this:

CMakeLists.txt:

find_package(Qt5 COMPONENTS Core Qml)
add_definitions(-DQT_VERSION_MAJOR=${Qt5_VERSION_MAJOR})
add_definitions(-DQT_VERSION_MINOR=${Qt5_VERSION_MINOR})
add_definitions(-DQT_VERSION_PATCH=${Qt5_VERSION_PATCH})

yourcode.cpp:

#define p_qqmljslexer(major,minor,patch)  <major.minor.patch/QtQml/private/qqmljslexer_p.h>

#include p_qqmljslexer(QT_VERSION_MAJOR, QT_VERSION_MINOR, QT_VERSION_PATCH)  

Upvotes: 0

Orest Hera
Orest Hera

Reputation: 6776

You can compare numeric QT_VERSION macro using human readable helper QT_VERSION_CHECK that combines major, minor and patch numbers into QT_VERSION format:

#if QT_VERSION == QT_VERSION_CHECK(5, 4, 1)
//...
#endif

The idea for concatenation taken from GCC headers C Macro - Dynamic #include

The problem is that we do not have macro tokens with Qt major, minor and patch versions. There is only numeric QT_VERSION. So, it is tricky to get required numbers. It is possible to transfer them as macro definitions from .pro file using qmake variables QT_*_VERSION:

DEFINES += QT_MAJOR_VERSION=$$QT_MAJOR_VERSION
DEFINES += QT_MINOR_VERSION=$$QT_MINOR_VERSION
DEFINES += QT_PATCH_VERSION=$$QT_PATCH_VERSION

Now those macro versions can be used in source files:

// To return as a string: "5.4.1/QtGui/private/qzipwriter_p.h"
#define qt_header__(x) #x
#define qt_header_(major,minor,patch) qt_header__(major.minor.patch/QtGui/private/qzipwriter_p.h)
#define qt_header(major,minor,patch) qt_header_(major,minor,patch)

// Simpler without stringification, however Qt Creator cannot follow
// that header
#define qt_header(major,minor,patch) <major.minor.patch/QtGui/private/qzipwriter_p.h>

#include qt_header(QT_MAJOR_VERSION, QT_MINOR_VERSION, QT_PATCH_VERSION)

It is better to use stringified variant ("5.4.1/QtGui/private/qzipwriter_p.h"). In that case the latest versions of Qt Creator can follow such qt_header() macro and highlight text accordingly.

Upvotes: 3

SingerOfTheFall
SingerOfTheFall

Reputation: 29966

Use QT_VERSION instead:

QT_VERSION This macro expands a numeric value of the form 0xMMNNPP (MM = major, NN = minor, PP = patch) that specifies Qt's version number.

#if QT_VERSION == 0x050401
  #include <5.4.1/QtGui/private/qzipwriter_p.h>
#endif

Edit:

No idea for concatenating the version string in the path?

The standard doesn't allow that (16.3.4/3):

The resulting completely macro-replaced preprocessing token sequence is not processed as a preprocessing directive even if it resembles one

So you can't make a macro that will be expanded into an #include directive. You also can't use a macro inside the brackets of include (#include <like this>) because everything inside the brackets is just a string.

Upvotes: 5

Related Questions