From 4e99da7b6212fdba121d93892f48f6bce158e2a6 Mon Sep 17 00:00:00 2001 From: Sefa Eyeoglu Date: Sun, 3 Jul 2022 22:40:05 +0200 Subject: [PATCH] refactor: query Qt variables using ECM Signed-off-by: Sefa Eyeoglu --- CMakeLists.txt | 13 +++-- cmake/ECMQueryQt.cmake | 100 ++++++++++++++++++++++++++++++++++++ cmake/QMakeQuery.cmake | 18 ------- cmake/QtVersionOption.cmake | 38 ++++++++++++++ 4 files changed, 144 insertions(+), 25 deletions(-) create mode 100644 cmake/ECMQueryQt.cmake delete mode 100644 cmake/QMakeQuery.cmake create mode 100644 cmake/QtVersionOption.cmake diff --git a/CMakeLists.txt b/CMakeLists.txt index 5041e580..f56c4070 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -185,15 +185,14 @@ else() message(FATAL_ERROR "Qt version ${Launcher_QT_VERSION_MAJOR} is not supported") endif() -# The Qt5 cmake files don't provide its install paths, so ask qmake. -include(QMakeQuery) -query_qmake(QT_INSTALL_PLUGINS QT_PLUGINS_DIR) -query_qmake(QT_INSTALL_IMPORTS QT_IMPORTS_DIR) -query_qmake(QT_INSTALL_LIBS QT_LIBS_DIR) -query_qmake(QT_INSTALL_LIBEXECS QT_LIBEXECS_DIR) -query_qmake(QT_HOST_DATA QT_DATA_DIR) +include(ECMQueryQt) +ecm_query_qt(QT_PLUGINS_DIR QT_INSTALL_PLUGINS) +ecm_query_qt(QT_LIBS_DIR QT_INSTALL_LIBS) +ecm_query_qt(QT_LIBEXECS_DIR QT_INSTALL_LIBEXECS) +ecm_query_qt(QT_DATA_DIR QT_HOST_DATA) set(QT_MKSPECS_DIR ${QT_DATA_DIR}/mkspecs) +# NOTE: Qt 6 already sets this by default if (Qt5_POSITION_INDEPENDENT_CODE) SET(CMAKE_POSITION_INDEPENDENT_CODE ON) endif() diff --git a/cmake/ECMQueryQt.cmake b/cmake/ECMQueryQt.cmake new file mode 100644 index 00000000..98eb5008 --- /dev/null +++ b/cmake/ECMQueryQt.cmake @@ -0,0 +1,100 @@ +# SPDX-FileCopyrightText: 2014 Rohan Garg +# SPDX-FileCopyrightText: 2014 Alex Merry +# SPDX-FileCopyrightText: 2014-2016 Aleix Pol +# SPDX-FileCopyrightText: 2017 Friedrich W. H. Kossebau +# SPDX-FileCopyrightText: 2022 Ahmad Samir +# +# SPDX-License-Identifier: BSD-3-Clause +#[=======================================================================[.rst: +ECMQueryQt +--------------- +This module can be used to query the installation paths used by Qt. + +For Qt5 this uses ``qmake``, and for Qt6 this used ``qtpaths`` (the latter has built-in +support to query the paths of a target platform when cross-compiling). + +This module defines the following function: +:: + + ecm_query_qt( [TRY]) + +Passing ``TRY`` will result in the method not making the build fail if the executable +used for querying has not been found, but instead simply print a warning message and +return an empty string. + +Example usage: + +.. code-block:: cmake + + include(ECMQueryQt) + ecm_query_qt(bin_dir QT_INSTALL_BINS) + +If the call succeeds ``${bin_dir}`` will be set to ``/path/to/bin/dir`` (e.g. +``/usr/lib64/qt/bin/``). + +Since: 5.93 +#]=======================================================================] + +include(${CMAKE_CURRENT_LIST_DIR}/QtVersionOption.cmake) +include(CheckLanguage) +check_language(CXX) +if (CMAKE_CXX_COMPILER) + # Enable the CXX language to let CMake look for config files in library dirs. + # See: https://gitlab.kitware.com/cmake/cmake/-/issues/23266 + enable_language(CXX) +endif() + +if (QT_MAJOR_VERSION STREQUAL "5") + # QUIET to accommodate the TRY option + find_package(Qt${QT_MAJOR_VERSION}Core QUIET) + if(TARGET Qt5::qmake) + get_target_property(_qmake_executable_default Qt5::qmake LOCATION) + + set(QUERY_EXECUTABLE ${_qmake_executable_default} + CACHE FILEPATH "Location of the Qt5 qmake executable") + set(_exec_name_text "Qt5 qmake") + set(_cli_option "-query") + endif() +elseif(QT_MAJOR_VERSION STREQUAL "6") + # QUIET to accommodate the TRY option + find_package(Qt6 COMPONENTS CoreTools QUIET CONFIG) + if (TARGET Qt6::qtpaths) + get_target_property(_qtpaths_executable Qt6::qtpaths LOCATION) + + set(QUERY_EXECUTABLE ${_qtpaths_executable} + CACHE FILEPATH "Location of the Qt6 qtpaths executable") + set(_exec_name_text "Qt6 qtpaths") + set(_cli_option "--query") + endif() +endif() + +function(ecm_query_qt result_variable qt_variable) + set(options TRY) + set(oneValueArgs) + set(multiValueArgs) + + cmake_parse_arguments(ARGS "${options}" "${oneValueArgs}" "${multiValueArgs}" ${ARGN}) + + if(NOT QUERY_EXECUTABLE) + if(ARGS_TRY) + set(${result_variable} "" PARENT_SCOPE) + message(STATUS "No ${_exec_name_text} executable found. Can't check ${qt_variable}") + return() + else() + message(FATAL_ERROR "No ${_exec_name_text} executable found. Can't check ${qt_variable} as required") + endif() + endif() + execute_process( + COMMAND ${QUERY_EXECUTABLE} ${_cli_option} "${qt_variable}" + RESULT_VARIABLE return_code + OUTPUT_VARIABLE output + ) + if(return_code EQUAL 0) + string(STRIP "${output}" output) + file(TO_CMAKE_PATH "${output}" output_path) + set(${result_variable} "${output_path}" PARENT_SCOPE) + else() + message(WARNING "Failed call: ${_command} \"${qt_variable}\"") + message(FATAL_ERROR "${_exec_name_text} call failed: ${return_code}") + endif() +endfunction() diff --git a/cmake/QMakeQuery.cmake b/cmake/QMakeQuery.cmake deleted file mode 100644 index b1025d65..00000000 --- a/cmake/QMakeQuery.cmake +++ /dev/null @@ -1,18 +0,0 @@ -if(__QMAKEQUERY_CMAKE__) - return() -endif() -set(__QMAKEQUERY_CMAKE__ TRUE) - -if(QT_VERSION_MAJOR EQUAL 5) - get_target_property(QMAKE_EXECUTABLE Qt5::qmake LOCATION) -elseif(QT_VERSION_MAJOR EQUAL 6) - get_target_property(QMAKE_EXECUTABLE Qt6::qmake LOCATION) -endif() - -function(QUERY_QMAKE VAR RESULT) - exec_program(${QMAKE_EXECUTABLE} ARGS "-query ${VAR}" RETURN_VALUE return_code OUTPUT_VARIABLE output ) - if(NOT return_code) - file(TO_CMAKE_PATH "${output}" output) - set(${RESULT} ${output} PARENT_SCOPE) - endif(NOT return_code) -endfunction(QUERY_QMAKE) diff --git a/cmake/QtVersionOption.cmake b/cmake/QtVersionOption.cmake new file mode 100644 index 00000000..1390f9db --- /dev/null +++ b/cmake/QtVersionOption.cmake @@ -0,0 +1,38 @@ +#.rst: +# QtVersionOption +# --------------- +# +# Adds a build option to select the major Qt version if necessary, +# that is, if the major Qt version has not yet been determined otherwise +# (e.g. by a corresponding find_package() call). +# +# This module is typically included by other modules requiring knowledge +# about the major Qt version. +# +# ``QT_MAJOR_VERSION`` is defined to either be "5" or "6". +# +# +# Since 5.82.0. + +#============================================================================= +# SPDX-FileCopyrightText: 2021 Volker Krause +# +# SPDX-License-Identifier: BSD-3-Clause + +if (DEFINED QT_MAJOR_VERSION) + return() +endif() + +if (TARGET Qt5::Core) + set(QT_MAJOR_VERSION 5) +elseif (TARGET Qt6::Core) + set(QT_MAJOR_VERSION 6) +else() + option(BUILD_WITH_QT6 "Build against Qt 6" OFF) + + if (BUILD_WITH_QT6) + set(QT_MAJOR_VERSION 6) + else() + set(QT_MAJOR_VERSION 5) + endif() +endif()