02-07-2023
Метаобъектный компилятор (сокр. МОК) (от англ.Meta Object Compiler или MOC) предназначен для генерации метаобъектного сопутствующего кода на основе библиотеки Qt. МОК считывает одно (или более) определение C++ класса из заголовочного файла языка C++ или исходного файла программы и генерирует один исходный файл на языке С++, содержащий метаобъектную информацию для классов. Получившийся исходный файл, сгенерированный МОК, должен быть скомпилирован и слинкован с реализацией класса (или может быть включен при помощи инструкции #include в исходный файл с описанием класса). В случае применения программы qmake для создания make-файлов, правила сборки, вызывающие МОК при необходимости, будут автоматически включены, поэтому напрямую вызывать МОК не требуется. Коротко говоря, метаобъектная система - структура, используемая библиотекой Qt для компонентного программирования и необходимая для типовой информации при запуске. она добавляет свойства и наследует информацию в (некоторые) классы, а также реализует новый тип взаимодействия между такими сущностями подобных классов, взаимосвязь, основанную на принципе сигнал-слот.
Параметр | Описание |
---|---|
-o <имя_файла> | Записывает выводимую информацию в файл в более подробном виде, чем в stdout. |
-f | Принудительная генерация инструкции #include в вывод. Является установленным режимом по умолчанию для файлов, чье имя подходит под регулярное выражение .[hH][^.]* (т.е. расширение срабатывает для H или h). Этот параметр полезен только если используются заголовочные файлы, не соответствующие соглашениям о стандартном именовании. |
-i | Не генерировать инструкции #include в вывод. Этот режим может быть полезен для запуска МОК для работы с C++ файлом, содержащим одно или более объявлений класса. В этом случае следует подключить метаобъектный код при помощи инструкции #include в файле .cpp (смотри примеры использования ниже). В случае указания обоих параметров (-f и -i) приоритет получает последний. |
-nw | Не выводить никаких предупреждений (не рекомендуется использовать). |
-ldbg | Запись потока отладочной информации в stdout. |
-p <путь> | Заставляет МОК добавлять спереди "<путь>/" к именам файлов в генерируемой инструкции #include (если она генерируется). |
-q <путь> | Заставляет МОК добавлять спереди "<путь>/" к именам файлов в qt-файлах инструкции #include генерируемого кода. |
-v | Показывает версию МОК и Qt. |
Можно принудительно указать МОК не проверять части заголовочного файла. Он распознает любые комментарии в стиле C++ (//), содержащие подстроки MOC_SKIP_BEGIN (начать пропуск) или MOC_SKIP_END (завершить пропуск). Они работают соответственно названию, и можно задавать их в несколько уровней. В конечном итоге с точки зрения МОК получится такой же результат, как если бы были удалены все строки между MOC_SKIP_BEGIN и MOC_SKIP_END.
МОК почти всегда вызывается при помощи программы make, а не вручную. Обычно МОКу передается файл, содержащий объявления класса, как например:
class YourClass : public QObject {
Q_OBJECT
Q_PROPERTY( ... )
Q_CLASSINFO( ... )
public:
YourClass( QObject * parent=0, const char * name=0 );
~YourClass();
signals:
public slots:
};
Вот полезное правило сборки в make-файле (если используется GNU make):
m%.cpp: %.h
moc $< -o $@
Если требуется написать индивидуальные правила следующего вида:
mNAME.cpp: NAME.h
moc $< -o $@
Необходимо также не забывать добавлять mNAME.cpp в переменные в исходных файлах (заменяя соответствующими именами) и mNAME.o в переменные в объектных файлах. (Несмотря на то, что МОК не различает расширения файлов, что позволяет использовать .C, .cc, .CC, .cxx или даже .c++, все же "хорошим тоном" считается использование .cpp для наименования исходных файлов, написанных на языке C++). Если используется объявление класса в файлах C++, некоторые программисты используют правило make-файлов, наподобие этого:
NAME.o: mNAME.cpp
mNAME.cpp: NAME.cpp
moc -i $< -o $@
Это гарантирует, что make вызовет МОК до компиляции NAME.cpp. Затем можно указать
#include "nNAME.cpp"
в конце NAME.cpp, когда все классы, объявленные в этом файле, будут полностью определены.
Иногда могут выдаваться ошибки линковки, сообщающие о том, что ВашКласс::имяКласса()
неопределено или о том, что ВашКласс
требует таблицу виртуальных методов. Эти ошибки наиболее часто встречаются когда забывают скомпилировать C++ код, сгенерированный МОК, или включить объектный файл в команду линковки. МОК также сообщает о некоторых опасных или неправильных конструкциях.
Метаобъектный компилятор.