如何使用QMake的子目录模板?

67

我开始学习Qt。我正在从Visual Studio世界转移,我正在寻找一种使用QMake组织项目结构的方法。我找到了“subdirs”模板,但我很难理解它。

我的项目结构如下:

project_dir/
    main.cpp
    project.pro
    logic/
      logic.pro
      some logic files
    gui/
      gui.pro
      gui files

我的 project.pro 看起来像这样

TEMPLATE = subdirs
SUBDIRS = logic \
          gui
SOURCES += main.cpp
在子目录的 .pro 文件中,我已经设置了适当的 SOURCESHEADERSRESOURCES 变量。
请告诉我在这些 .pro 文件中应设置哪些 TARGETTEMPLATE 和其他必要的值。
此外,除了官方文档以外,是否有一些好的 QMake 教程?
2个回答

87
除了Troubadour的评论之外,我要指出SUBDIRS目标仅适用于指定子目录。因此,您额外的一行是多余的。

SOURCES += main.cpp

在您的project.pro文件中存在错误,最坏的情况是无法构建main.cpp文件。最好的情况是qmake将拒绝解析该文件,因为它具有冲突的规范。我已经使用了几次SUBDIRS模板,如果您可以将部分构建成更或多或少独立的库,那么这种方法就很好,显然像您现在将逻辑和gui分开一样。以下是一种实现方式:
project_dir/
-project.pro
-common.pri
-logic/
----logic.pro
----some logic files
-gui/
----gui.pro
----gui files
-build/
----build.pro
----main.cpp

project.pro:

TEMPLATE = subdirs
SUBDIRS = logic \
          gui

# build must be last:
CONFIG += ordered
SUBDIRS += build

common.pri:

#Includes common configuration for all subdirectory .pro files.
INCLUDEPATH += . ..
WARNINGS += -Wall

TEMPLATE = lib

# The following keeps the generated files at least somewhat separate 
# from the source files.
UI_DIR = uics
MOC_DIR = mocs
OBJECTS_DIR = objs

logic/logic.pro:

# Check if the config file exists
! include( ../common.pri ) {
    error( "Couldn't find the common.pri file!" )
}

HEADERS += logic.h
SOURCES += logic.cpp

# By default, TARGET is the same as the directory, so it will make 
# liblogic.a (in linux).  Uncomment to override.
# TARGET = target

gui/gui.pro:

! include( ../common.pri ) {
    error( "Couldn't find the common.pri file!" )
}

FORMS += gui.ui
HEADERS += gui.h
SOURCES += gui.cpp

# By default, TARGET is the same as the directory, so it will make 
# libgui.a (in linux).  Uncomment to override.
# TARGET = target

build/build.pro:

TEMPLATE = app

SOURCES += main.cpp

LIBS += -L../logic -L../gui -llogic -lgui

# Will build the final executable in the main project directory.
TARGET = ../project

我的印象是,“ordered”是全局的。它似乎不会使前两个库并发。 - Walter Nissen
@Walter Nissen:据我所知,您是正确的。有序意味着它们都按顺序依次运行。如果需要的话,您实际上可以手动指定子目录目标之间的依赖关系,这可能允许并发构建,但更难正确设置。 - Caleb Huitt - cjhuitt
抱歉,我很蠢,请问您能否澄清一下:“我想指出SUBDIRS目标仅适用于指定子目录。”您的意思是说,您不能在同一个.pro文件中同时使用TEMPLATE = subdirs和指定TARGETSOURCES等来实际构建某些东西吗? - spinkus
2
继续我之前的问题:如建议所述,您也可以从子目录项目文件进行“app”构建,但实际上您不需要将主可执行文件的qmake放在子目录“build/”中。您可以将“build.pro”添加到SUBDIRS列表的末尾 - 即在顶层有两个.pro文件。 - spinkus
@SamPinkus 没错。我不记得我写这个答案时是否支持这种方式,但在某些情况下,这可能比创建整个子目录更简单,以获得最终链接。 - Caleb Huitt - cjhuitt

18

如果 logicgui 文件夹实际上代表某种目标(例如库),可以独立于其他任何内容构建,则使用 subdirs。 如果是这种情况,只需使用:


TEMPLATE = subdirs

SUBDIRS = logic \
          gui
TEMPLATE = lib
TARGET = logic
CONFIG += dll

在logic.pro中。

如果它们不是独立的目标,而只是存在于组织源文件的文件夹中,那么您可以在每个文件夹中使用.pri文件,并将它们包含在.pro文件中使用。

include(logic/logic.pri)
include(gui/gui.pri)

请记住,.pri文件中的文件路径是相对于.pro文件而不是.pri文件。另外,使用.pri文件是可选的,因为您仍然可以直接在.pro文件中列出这些文件夹中的文件。 .pri文件只是让它看起来更整洁,帮助保持.pro文件更短。


3
据我所了解,使用 .pri 文件的方法会让 Qt Creator 显示每个 .pri 文件及其内容的子文件夹。 - zarzych
3
@zarzych: 这是真的,但它也令人烦恼地不尊重.pri文件在文件系统中的位置,只会在.pro级别上将它们显示为一个平面列表。如果你有几个同名的文件,这会特别让人烦恼。 - Troubadour

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接