CMake:检测“Q_OBJECT”并将其添加到要由 MOC 处理的文件列表中

发布于 2024-11-30 10:55:21 字数 375 浏览 0 评论 0 原文

目前,我在 CMake 中使用变量 MYPROJECT_CURRENT_HEADERS 来列出所有标头。当我使用 Qt 时,我的 CMakeLists.txt 包含:

QT4_WRAP_CPP(MYPROJECT_CURRENT_MOC ${MYPROJECT_CURRENT_HEADERS})

问题是所有标头都由 moc 处理,即使是那些没有 Q_OBJECT 的标头:因此它会生成许多空文件。

是否有解决方案来“grep”/检测文件是否包含字符串 Q_OBJECT ,如果是这种情况,请将其添加到 MYPROJECT_CURRENT_MOC 吗?

谢谢

Currently, I use a variable MYPROJECT_CURRENT_HEADERS in CMake to list all the headers. As I use Qt, my CMakeLists.txt contains :

QT4_WRAP_CPP(MYPROJECT_CURRENT_MOC ${MYPROJECT_CURRENT_HEADERS})

The problem is that all headers are treated by moc, even those that don't have a Q_OBJECT : so it generates many empty file.

Is there a solution to "grep"/detect if the file contains the string Q_OBJECT and if it's the case, add it to MYPROJECT_CURRENT_MOC ?

Thank you

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

画离情绘悲伤 2024-12-07 10:55:21

即将发布的 CMake 2.8.6 中有一个名为“AUTOMOC”的新目标属性,可以帮助您。

此功能的测试(您可以用作指南或示例)可在此处找到:

http://cmake.org/gitweb?p=cmake.git;a=tree;f=Tests/QtAutomoc;h=7dae3b16a54dc0b2f63bbfa5c218c48b9bbf34a9;hb=nightly-master

非常简单的 CMakeLists。 txt 文件在这里:

http://cmake.org/gitweb?p=cmake.git;a=blob;f=Tests/QtAutomoc/CMakeLists.txt;h=4a5ff1099ba5249a6f22eea745a031b76e6f440f;hb=nightly-master

如果如果您使用此功能,cmake 将扫描 Q_OBJECT 的标头并自动为你运行 moc。

如果您想在 CMake 2.8.6 最终版本发布之前尝试一下,可以在此处下载候选版本之一:

http://cmake.org/files/v2.8/?C=M;O=D

“-rc2”文件确实包含 AUTOMOC 属性。

以下是运行“cmake --help-property AUTOMOC”的帮助文本:

cmake version 2.8.6-rc2
  AUTOMOC
       Should the target be processed with automoc (for Qt projects).

       AUTOMOC is a boolean specifying whether CMake will handle the Qt moc
       preprocessor automatically, i.e.  without having to use the
       QT4_WRAP_CPP() macro.  Currently Qt4 is supported.  When this property
       is set to TRUE, CMake will scan the source files at build time and
       invoke moc accordingly.  If an #include statement like #include
       "moc_foo.cpp" is found, the Q_OBJECT class declaration is expected in
       the header, and moc is run on the header file.  If an #include
       statement like #include "foo.moc" is found, then a Q_OBJECT is
       expected in the current source file and moc is run on the file itself.
       Additionally, all header files are parsed for Q_OBJECT macros, and if
       found, moc is also executed on those files.  The resulting moc files,
       which are not included as shown above in any of the source files are
       included in a generated _automoc.cpp file, which is
       compiled as part of the target.This property is initialized by the
       value of the variable CMAKE_AUTOMOC if it is set when a target is
       created.

There's a new target property in the soon-to-be-released CMake 2.8.6 called "AUTOMOC" that may help you out.

The test for this feature (which you can use as a guide or example) is found here:

http://cmake.org/gitweb?p=cmake.git;a=tree;f=Tests/QtAutomoc;h=7dae3b16a54dc0b2f63bbfa5c218c48b9bbf34a9;hb=nightly-master

The very simple CMakeLists.txt file is here:

http://cmake.org/gitweb?p=cmake.git;a=blob;f=Tests/QtAutomoc/CMakeLists.txt;h=4a5ff1099ba5249a6f22eea745a031b76e6f440f;hb=nightly-master

If you use this feature, cmake will scan the headers for Q_OBJECT and automatically run moc for you.

If you'd like to try it out before the final release of CMake 2.8.6, you can download one of the release candidates here:

http://cmake.org/files/v2.8/?C=M;O=D

The "-rc2" files do include the AUTOMOC property.

Here's the help text from running "cmake --help-property AUTOMOC":

cmake version 2.8.6-rc2
  AUTOMOC
       Should the target be processed with automoc (for Qt projects).

       AUTOMOC is a boolean specifying whether CMake will handle the Qt moc
       preprocessor automatically, i.e.  without having to use the
       QT4_WRAP_CPP() macro.  Currently Qt4 is supported.  When this property
       is set to TRUE, CMake will scan the source files at build time and
       invoke moc accordingly.  If an #include statement like #include
       "moc_foo.cpp" is found, the Q_OBJECT class declaration is expected in
       the header, and moc is run on the header file.  If an #include
       statement like #include "foo.moc" is found, then a Q_OBJECT is
       expected in the current source file and moc is run on the file itself.
       Additionally, all header files are parsed for Q_OBJECT macros, and if
       found, moc is also executed on those files.  The resulting moc files,
       which are not included as shown above in any of the source files are
       included in a generated _automoc.cpp file, which is
       compiled as part of the target.This property is initialized by the
       value of the variable CMAKE_AUTOMOC if it is set when a target is
       created.
酷遇一生 2024-12-07 10:55:21

我不知道从列表中选择具有字符串的标头的简单命令,但您始终可以创建一个循环来查找所有此类标头:

set(HEADERS_HAVING_Q_OBJECT)
foreach(header ${MYPROJECT_CURRENT_HEADERS})
    file(STRINGS "${header}" lines REGEX "Q_OBJECT")
    if(lines)
        list(APPEND HEADERS_HAVING_Q_OBJECT "${header}")
    endif()
endforeach()

但此解决方案有其自身的缺点:如果您添加 Q_OBJECT进入过滤掉的文件之一,您需要手动重新运行 cmake。否则,在构建过程中将不会自动生成新文件的 moc 代码。

I don't know a simple command to pick headers having a string from the list but you can always make a loop to find all such headers:

set(HEADERS_HAVING_Q_OBJECT)
foreach(header ${MYPROJECT_CURRENT_HEADERS})
    file(STRINGS "${header}" lines REGEX "Q_OBJECT")
    if(lines)
        list(APPEND HEADERS_HAVING_Q_OBJECT "${header}")
    endif()
endforeach()

But this solution has its own drawback: if you add a Q_OBJECT into one of the filtered out files you need to rerun cmake manually. Otherwise moc code for new file will not be automatically generated during the build process.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文