Qt 5 cmake завершается неудачно с неопределенной ссылкой на vtable в hello world с inc & src в качестве подкаталогов
После небольшого перебора (и некоторого редактирования сгенерированных Make-файлов), похоже, что происходит то, что moc не обрабатывает должным образомMainWindow.h
(включеноmain.cpp
а такжеMainWindow.cpp
если он не находится в той же папке, что и исходные файлы, в которые он был включен.
Мок работает наMainWindow.cpp
, не обрабатывает включение и, следовательно, не видит макрос Q_OBJECT, поэтому переходит к созданию пустого выходного файла. Я не уверен, включает ли moc обычно процессы или просто просматривает каталог, но в любом случае заголовки, которые требуют перемещения, но находятся в других каталогах, не обрабатываются!
Проблема, по-видимому, связана с продукцией, производимой moc. В первом случае (тот, который компилируется),hello-world_automoc.cpp
а такжеmoc_MainWindow.cpp
генерируются.hello-world_automoc.cpp
выглядит как
/* This file is autogenerated, do not edit*/
#include "moc_MainWindow.cpp"
Во втором случаеhello-world_automoc.cpp
производится что выглядит
/* This file is autogenerated, do not edit*/
enum some_compilers { need_more_than_nothing };
и нетmoc_MainWindow.cpp
вообще. Если я вручную вызываю moc из cmake вместо использования automoc в неработающем случае, я получаюmoc_MainWindow.cpp
но это пусто.
Во-первых, нет, я не забылset(CMAKE_AUTOMOC ON)
, Также обратите внимание, чтоMainWindow
«sдеструктор объявлен и реализован.
Когда моя структура каталогов выглядит так:
CMakeLists.txt |__ main.cpp |__ MainWindow.cpp |__ MainWindow.h |__ MainWindow.ui
компиляция работает просто отлично.
Тем не менее, когда это выглядит так:
helloworld/ |__ CMakeLists.txt |__ src/ | |__ CMakeLists.txt | |__ main.cpp | |__ MainWindow.cpp | |__ inc/ | |__ MainWindow.h | |__ gui/ |__ MainWindow.ui
Я получаю ссылки на ошибки:
Linking CXX executable hello-world
CMakeFiles/hello-world.dir/MainWindow.cpp.o: In function `MainWindow::MainWindow()':
MainWindow.cpp:(.text+0x3b): undefined reference to `vtable for MainWindow'
MainWindow.cpp:(.text+0x4d): undefined reference to `vtable for MainWindow'
CMakeFiles/hello-world.dir/MainWindow.cpp.o: In function `MainWindow::~MainWindow()':
MainWindow.cpp:(.text+0xaf): undefined reference to `vtable for MainWindow'
MainWindow.cpp:(.text+0xc1): undefined reference to `vtable for MainWindow'
collect2: error: ld returned 1 exit status
make[2]: *** [src/hello-world] Error 1
make[1]: *** [src/CMakeFiles/hello-world.dir/all] Error 2
Мне бы очень хотелось, чтобы мои источники и заголовки были в соответствующих подкаталогах, но я не совсем уверен, как это исправить.
На самом деле это самый простой опознаваемый случай ошибки из гораздо более крупного проекта, так что я действительно не сильно стремлюсь сгладить каталоги проектов только потому, что добавляю в него графический интерфейс Qt.