web-dev-qa-db-ja.com

CMakeを使用して特定のQtインストールを含める方法は?

すべての開発用PCにたくさんのQtコピーがあります-各プロジェクトには、サードパーティのディレクトリに独自のQtコピーがあります。これは、各プロジェクトが独自のQtで開発およびテストされているためです。多くの場合、プロジェクトによってはQtのカスタムビルドが必要です。したがって、上記の理由により、さまざまなQtビルドを保持するための個別のSVNリポジトリと、各Qtプロジェクトの外部(これらのビルドの1つを参照)があります。

問題は、CMakeを使用する場合、Qtのバージョンのみを選択でき、Qt4ファインダーがどのQtを単独で使用するかを決定することです。そして、それは正しいものではありません。プロジェクトのサードパーティディレクトリにある特定のQtコピーのすべてのものを構成するには、Finderをリダイレクトする必要があります。

_FIND_PACKAGE_のPATHSオプションをFIND_PACKAGE( Qt4 REQUIRED PATHS "thirdparty/Qt" )のように指定しようとしましたが、役に立ちませんでした。 _QT_QMAKE_EXECUTABLE_変数を設定しようとしましたが、うまくいきませんでした。インストールに必要なQMakeのパス(FindQt4.cmakeがすべてのディレクトリを特定するために使用)をPATH変数に追加しようとしましたが、それも役に立ちませんでした。

FIND_PACKAGEが提供するすべてのものを、特定のQtコピーに対して使用する方法はありますか?すべてのQtラッパーを実装したり、すべての定義、インクルード、ディレクトリなどを手動で設定したりしたくありません。

これが私のCMakeプロジェクトです。多分それは役立つでしょう:

_CMAKE_MINIMUM_REQUIRED( VERSION 2.8 )

#############################################################################

MACRO( ADD_FILES_TO_FILTER rootFilterName rootFilterPath files )
    FOREACH( curFile ${files} )
        FILE( RELATIVE_PATH curFilter "${CMAKE_CURRENT_SOURCE_DIR}/${rootFilterPath}" "${CMAKE_CURRENT_SOURCE_DIR}/${curFile}" )
        FILE( RELATIVE_PATH test "${CMAKE_CURRENT_SOURCE_DIR}" "${CMAKE_CURRENT_SOURCE_DIR}/${curFile}" )
        GET_FILENAME_COMPONENT( curFilter ${curFilter} PATH )
        SET( curFilter "${rootFilterName}/${curFilter}" )
        STRING( REPLACE "/" "\\\\" curFilter ${curFilter} )
        SOURCE_GROUP( ${curFilter} FILES ${curFile} )
    ENDFOREACH( curFile )
ENDMACRO( ADD_FILES_TO_FILTER rootFilterName rootFilterPath files )

MACRO( TO_RELATIVE_PATHS filePaths )
    SET( resPaths "" )
    FOREACH( curPath ${${filePaths}} )
        FILE( RELATIVE_PATH relPath ${CMAKE_CURRENT_SOURCE_DIR} ${curPath} )
        SET( resPaths ${resPaths} ${relPath} )
    ENDFOREACH( curPath )
    SET( ${filePaths} ${resPaths} )
ENDMACRO( TO_RELATIVE_PATHS filePaths )

######################################################################

# Define project settings
PROJECT( RealTimeCapture )
FIND_PACKAGE( Qt4 REQUIRED PATHS "thirdparty/Qt" )
SET( BOOST_ROOT "thirdparty/boost" )
FIND_PACKAGE( Boost REQUIRED )

# Collect all required files for build
FILE( GLOB_RECURSE headers RELATIVE ${CMAKE_CURRENT_SOURCE_DIR} "src/RTCF/include/*.h" )
FILE( GLOB_RECURSE sources RELATIVE ${CMAKE_CURRENT_SOURCE_DIR} "src/RTCF/src/*.cpp" )
FILE( GLOB_RECURSE resources RELATIVE ${CMAKE_CURRENT_SOURCE_DIR} "src/*.qrc" )
FILE( GLOB_RECURSE forms RELATIVE ${CMAKE_CURRENT_SOURCE_DIR} "src/*.ui" )

# Preprocess all Qt files
QT4_WRAP_CPP( header_mocs ${headers} )
QT4_WRAP_UI( form_headers ${forms} )
QT4_ADD_RESOURCES( resources_rcc ${resources} )

# Convert all generated files paths to relative ones
TO_RELATIVE_PATHS( header_mocs )
TO_RELATIVE_PATHS( form_headers )
TO_RELATIVE_PATHS( resources_rcc )

# Create executable
ADD_EXECUTABLE( RealTimeCapture ${headers} ${sources} ${header_mocs} ${form_headers} ${resources_rcc} )
SET_TARGET_PROPERTIES( RealTimeCapture PROPERTIES COMPILE_FLAGS "/Zc:wchar_t-" )

# Set filters for project according to its namespaces
FILE( RELATIVE_PATH buildDir ${CMAKE_CURRENT_SOURCE_DIR} ${CMAKE_CURRENT_BINARY_DIR} )
ADD_FILES_TO_FILTER( "Headers" "src/RTCF/include" "${headers}" )
ADD_FILES_TO_FILTER( "Sources" "src/RTCF/src" "${sources}" )
ADD_FILES_TO_FILTER( "Generated" "${buildDir}/src/RTCF/include" "${header_mocs}" )
ADD_FILES_TO_FILTER( "Forms" "${buildDir}/src/RTCF/include" "${form_headers}" )
ADD_FILES_TO_FILTER( "Resources" "${buildDir}" "${resources_rcc}" )

# Set additional include directories
INCLUDE_DIRECTORIES( ${CMAKE_CURRENT_BINARY_DIR} )
INCLUDE_DIRECTORIES( "src" )
INCLUDE_DIRECTORIES( "src/RTCF/include" )
INCLUDE_DIRECTORIES( "thirdparty" )

# Configure Qt
SET( QT_USE_QTNETWORK TRUE )
SET( QT_USE_QTSQL TRUE )
SET( QT_USE_QTSCRIPT TRUE )
SET( QT_USE_QTXML TRUE )
SET( QT_USE_QTWEBKIT TRUE )
INCLUDE( ${QT_USE_FILE} )
ADD_DEFINITIONS( ${QT_DEFINITIONS} )
TARGET_LINK_LIBRARIES( RealTimeCapture ${QT_LIBRARIES} )

# Add boost support
INCLUDE_DIRECTORIES( ${Boost_INCLUDE_DIR} )
TARGET_LINK_LIBRARIES( RealTimeCapture ${Boost_LIBRARIES} )

# Add other libs include dirs
INCLUDE_DIRECTORIES( "thirdparty/SimpleCrypt" )
INCLUDE_DIRECTORIES( "thirdparty/id3lib/include" )
INCLUDE_DIRECTORIES( "thirdparty/libtwitcurl" )
INCLUDE_DIRECTORIES( "thirdparty/curl-7.24.0/curl/include" )
INCLUDE_DIRECTORIES( "thirdparty/log4qt/include" )
INCLUDE_DIRECTORIES( "thirdparty/fervor-auto" )

# Add defines
ADD_DEFINITIONS( RealTimeCapture -DQUAZIP_STATIC )
ADD_DEFINITIONS( RealTimeCapture -DBUILDING_LIBCURL )
ADD_DEFINITIONS( RealTimeCapture -DID3LIB_LINKOPTION=1 )
ADD_DEFINITIONS( -DUNICODE -D_UNICODE ) #enable unicode support
_

[〜#〜]更新[〜#〜]

受け入れられた回答へのコメントで言及されているように、_QT_QMAKE_EXECUTABLE_ CMake変数を設定することで、OS PATH変数に追加されたものとは異なるカスタムqmake.exeを設定できました。しかし問題は、qmake実行可能ファイルにすべてのQtのモジュールへのハードコードされたパスがあることでした。したがって、私はカスタムの_qt.conf_ファイルを提供することで解決しました(回答で言及されているとおり)。私はインターネットでそれの例を見つけていませんので、ここにあります、おそらくそれは誰かを助けるでしょう:

_[Paths]
Prefix=..
Documentation=doc
Headers=include
Libraries=lib
Binaries=bin
Plugins=plugins
Imports=imports
Data=
Translations=
Settings=
Examples=
Demos=
_

まさにこれを使いました。ただし、プレフィックスでQtインストールへの絶対パスを指定することを検討できます。任意の場所に複製できるレポで絶対パスを使用したくなかっただけです。 _qt.conf_の使用の詳細については、 this リンクを参照してください。

20
Roman Kruglov

QT_QMAKE_EXECUTABLEで順調に進んでいます。その変数はキャッシュ変数なので、単純に設定しても機能しません... GUIを介して、またはcmakeを初めて実行する前に、またはCMakeCache.txtで、またはキャッシュを使用して変更しない限り、キャッシュされた値はそのまま残ります。 SETへのFORCEオプション。

設定時にわかっている変数に基づいてQTディレクトリを選択するロジックを修正したので、これが私が使用するイディオムです。ここでは、FIND_PACKAGEを実行する前に変数を設定しているため、キャッシュの問題はありません。

IF(WIN32 AND ${CMAKE_SIZEOF_VOID_P} MATCHES 8)
  # Hardcode a location for a QT toolkit compiled for Win64.  By overriding QT_QMAKE, all the rest is found
  # Choose any version of QT found in the 64-bit tools area
  FILE(GLOB QTROOTS c:/Tools_x64/Qt/*/bin)     # */
  FIND_PROGRAM(QT_QMAKE_EXECUTABLE NAMES qmake qmake4 qmake-qt4 qmake-mac PATHS ${QTROOTS})
ENDIF()

これをFIND_PACKAGE(Qt4)の前に置きます

コメントの新しい情報に基づく編集:

ああ、私は今あなたと一緒です。壊れたQtインストールに相当する量があります。 FindQtモジュールは、常にqmake実行可能ファイルを使用してQtツリーの設定を検出します。 Qmakeは、この情報を「永続的なプロパティ」のセットに格納します。このプロパティは、qmake -queryでクエリしたり、qmake -setで設定したりできます。したがって、Qtインストールを「修正」するには、qmakeを実行し、QT_INSTALL_PREFIXプロパティを設定します。これについては、ここに記載されています environment-reference.html

qmake -set "QT_INSTALL_PREFIX" /path/to/qt/

または、古いSO質問 qmakeおよびQT_INSTALL_PREFIXで。Qtライブラリの新しい場所を選択するにはどうすればよいですか? 、受け入れられない回答はqt.confを使用してQTプレフィックスを上書きします。

これらのソリューションはどちらも、Qtインストールの変更を伴います。これを回避する方法があるかどうかはわかりませんが、これがリポジトリとビルドシステムにどのように適合するかは、ここでは範囲外です。

10
Peter

よろしければ、ここに記載されている情報をいくつか入力/確認し、完全な例を示します。

オカルタと同様に、私は自分のプロジェクトに使用する必要があるカスタムビルドのQt環境を持っています。これらは、プロジェクトをコンパイルするために再現した手順です。

  1. 私のプロジェクトのCMakeLists.txtは、すでにすべてのCMakeのものを所有しており、 'qt.cmake'ファイルを含めるだけです。

    include(qt)
    
  2. Qt.cmakeファイルには、Peterのソリューションが含まれており、追加の要素で装飾されています。この構成では、moc、uic、およびrccを使用して、UIファイル、リソースファイルなどを管理できます。コメント付きのファイルを次に示します。それらが厳密に正しくない場合は、遠慮なく修正してください(CMakeの動作はまだ曇っています)。

    # The path where Qt is.
    SET(QT_ROOT_DIR "path/to/qt")
    
    set(QT_QMAKE_EXECUTABLE ${QT_ROOT_DIR}/osx/bin/qmake)
    
    # Loads CMake macros bound to Qt.
    find_package(Qt4 REQUIRED)
    # Includes used Qt headers.
    include(${QT_USE_FILE})
    
  3. また、qmake実行可能ファイルと同じレベルにOccultaのqt.confファイルを追加しました。

これらの3つのステップが完了すると、すべてがうまくいきました。この完全な例が誰かを助けることを願っています。

皆さんありがとう、あなたは明らかに私を助けてくれました!

3
Mankalas

これは私のために働いたものです:

set( QT_ROOT /opt/myqt/ )
set( ENV(CMAKE_PREFIX_PATH) ${QT_ROOT} )
FIND_PACKAGE( Qt4 COMPONENTS QtCore QtGui QtDBUS REQUIRED )

これによりPATH環境変数が変更されますが、別の方法は見つかりませんでした。他の答えは私にとってはうまくいきませんでした。

1
BЈовић