2010-09-06 39 views
5

Tôi đang phát triển một dự án lớn sử dụng Qt 4.6, CMake 2.8 và Visual Studio 2008 cho nền tảng Windows.Qt, CMake, Visual Studio và Q_OBJECT trong các tệp cpp

Hệ thống xây dựng đi xa, tất cả đều là tiêu chuẩn: Tôi đang sử dụng macro QT4_WRAP_CPP của CMake để tạo tệp moc từ tệp tiêu đề, sau đó được liên kết vào tệp thực thi cuối cùng trong lệnh add_executable. Mọi thứ đều hoạt động như mong đợi.

Hạn chế duy nhất với thiết lập này là tôi không thể xác định tiện ích con hoặc người trợ giúp bằng cách sử dụng Q_OBJECT trong các tệp .cpp. Điều này sẽ rất thuận tiện cho các lớp trợ giúp nhỏ, theo ngữ cảnh cụ thể sẽ xuất hiện ngay bên cạnh nơi chúng được sử dụng.

tôi đã cố gắng để vượt qua toàn bộ danh sách các tập tin nguồn (cả .hcpp) để QT4_WRAP_CPP, thay vì chỉ các tập tin tiêu đề, nhưng điều đó không làm việc (liên kết không thành công vì một số moc liên quan biểu tượng không xác định).

Tôi nghĩ vấn đề là, đối với một cặp cho các tập tin foo.hFoo.cpp, các QT4_WRAP_CPP vĩ mô sẽ tạo ra các tập tin moc cùng (moc_foo.cxx) trong cùng thư mục, và rõ ràng điều đó có nghĩa là tệp đầu tiên sẽ bị ghi đè bởi tệp thứ hai và do đó các ký hiệu kết quả sẽ bị thiếu tại thời gian liên kết.

Có cách nào để khắc phục hoặc khắc phục sự cố đó không? Ví dụ, tôi đã cố gắng để thêm một quy tắc cụ thể cho Foo.cpp dạng

QT4_GENERATE_MOC(directory/foo.cpp directory/foo.moc) 

và sau đó thêm

#include "foo.moc" 

vào cuối Foo.cpp. Tôi nghĩ rằng điều này nên làm việc, nhưng alas Visual Studio chỉ cho phép một quy tắc xây dựng cho mỗi tệp và các tệp .cpp đã có quy tắc xây dựng (biên dịch thành tệp đối tượng), vì vậy phương pháp này không hoạt động, ít nhất với Visual Studio .

Một ý tưởng rằng tôi đã có được để tạo ra một macro mới, nói QT4_WRAP_CPP_WITH_PREFIX, dựa trên QT4_WRAP_CPP (được định nghĩa trong share/cmake-2,8/Modules/Qt4Macros.cmake), mà sẽ mất một cuộc tranh cãi tiền tố bổ sung và sẽ thêm tiền tố này vào các tệp moc được tạo. Bằng cách đó, tôi sẽ gọi số QT4_WRAP_CPP_WITH_PREFIX hai lần, một lần cho các tệp .h và một lần cho các tệp .cpp, với các tiền tố khác nhau. Những gì tôi chỉ không thích về phương pháp này là tôi muốn được rối tung với các internals của hỗ trợ Qt của CMake, thay vì sử dụng API công cộng.

Bạn có ý tưởng nào tốt hơn không?

Cheerz, Franz

+0

Tôi không chắc rằng tôi hiểu được chút này: "Hạn chế duy nhất với thiết lập này là tôi không thể xác định tiện ích hoặc trình trợ giúp bằng Q_OBJECT trong tệp .cpp". Bạn không bao giờ cần phải chạy MOC trên bất cứ điều gì ngoại trừ các tập tin tiêu đề? –

+1

Tôi thấy thuận tiện khi xác định dịp một lớp trợ giúp nhỏ trong tệp .cpp và không hiển thị nó bên ngoài tệp .cpp này. Đối với điều này tôi cần để có thể chạy MOC trên tập tin .cpp. Phương pháp macro 'QT4_WRAP_CPP_WITH_PREFIX' được nêu trong bài đăng của tôi hoạt động như một nét duyên dáng. –

+0

@ FrançoisBeaune - bạn đã bao giờ nghĩ ra một giải pháp cho việc này chưa? Ngay cả đối với một cái gì đó đơn giản này: #include #include #include lớp MyClass: QObject công { Q_OBJECT }; int main (int, char * []) ​​ { MyClass myClass; trả lại 0; } Tôi không thể tìm ra cách MOC nó vì nó nằm trong tệp cpp (và tôi gặp lỗi vtable khi cố xây dựng nó bình thường). –

Trả lời

1

Đề cập đến các tài liệu "Sử dụng MOC" (http://doc.qt.nokia.com/4.1/moc.html), bạn chỉ muốn cần phải nhập khẩu "foo. moc "ở cuối tệp triển khai của bạn. Vì bạn không thể tinh chỉnh quy tắc xây dựng tương ứng, hãy thử xuất tệp .pro và áp dụng quy tắc xây dựng như được đề xuất bởi tài liệu nokia.

2

các phiên bản gần đây của CMake có "automoc" mà làm việc như một nét duyên dáng cho tôi: http://blogs.kde.org/2011/11/01/cool-new-stuff-cmake-286-automoc

Chỉ cần thêm trong CMakeLists.txt:

set(CMAKE_AUTOMOC TRUE) 

và sau đó trong cpp (ví dụ như ví dụ. cpp) tệp:

#include "example.moc" 

(* .moc phải khớp với tên tệp của cpp).

Các vấn đề liên quan