- Qt 6.9
- Qt Qml
- qt_add_qml_module
- Qt 6.9.3 Reference Documentation

# qt_add_qml_module

This command was introduced in Qt 6.2.

The command is defined in the `Qml` component of the `Qt6` package, which can be loaded like so:

     find_package(Qt6 REQUIRED COMPONENTS Qml)

## Synopsis

     qt_add_qml_module(
         target
         URI uri
         [VERSION version]
         [PAST_MAJOR_VERSIONS ...]
         [STATIC | SHARED]
         [PLUGIN_TARGET plugin_target]
         [OUTPUT_DIRECTORY output_dir]
         [RESOURCE_PREFIX resource_prefix]
         [CLASS_NAME class_name]
         [TYPEINFO typeinfo]
         [IMPORTS ...]
         [OPTIONAL_IMPORTS ...]
         [DEFAULT_IMPORTS ...]
         [DEPENDENCIES ...]
         [IMPORT_PATH ...]
         [SOURCES ...]
         [QML_FILES ...]
         [RESOURCES ...]
         [OUTPUT_TARGETS out_targets_var]
         [DESIGNER_SUPPORTED]
         [FOLLOW_FOREIGN_VERSIONING]
         [NAMESPACE namespace]
         [NO_PLUGIN]
         [NO_PLUGIN_OPTIONAL]
         [NO_CREATE_PLUGIN_TARGET]
         [NO_GENERATE_PLUGIN_SOURCE]
         [NO_GENERATE_QMLTYPES]
         [NO_GENERATE_QMLDIR]
         [NO_GENERATE_EXTRA_QMLDIRS]
         [NO_LINT]
         [NO_CACHEGEN]
         [NO_RESOURCE_TARGET_PATH]
         [NO_IMPORT_SCAN]
         [ENABLE_TYPE_COMPILER]
         [TYPE_COMPILER_NAMESPACE namespace]
         [QMLTC_EXPORT_DIRECTIVE export_macro]
         [QMLTC_EXPORT_FILE_NAME header_defining_export_macro]

     )

If versionless commands are disabled, use `qt6_add_qml_module()` instead. It supports the same set of arguments as this command.

See Building a QML application and Building a reusable QML module for examples that define QML modules.

See QT_QML_GENERATE_QMLLS_INI for configuring your project such that information about QML modules is exposed to the QML Language Server.

## Description

This command defines a QML module that can consist of C++ sources, `.qml` files, or both. It ensures that essential module details are provided and that they are consistent. It also sets up and coordinates things like cached compilation of `.qml` sources, resource embedding, linting checks, and auto-generation of some key module files.

### Target Structure

A QML module can be structured in a few different ways. The following scenarios are the typical arrangements:

#### Separate backing and plugin targets

This is the recommended arrangement for most QML modules. All of the module's functionality is implemented in the backing target, which is given as the first command argument. C++ sources, `.qml` files, and resources should all be added to the backing target. The backing target is a library that should be installed in the same location as any other library defined by the project.

The source directory structure under which the backing target is created should match the target path of the QML module (the target path is the module's URI with dots replaced by forward slashes). If the source directory structure doesn't match the target path, `qt_add_qml_module()` will issue a warning.

The following example shows a suitable source directory structure for a QML module with a URI of `MyThings.Panels`. The call to `qt_add_qml_module()` would be in the `CMakeLists.txt` file shown.

     src
      +-- MyThings
           +-- Panels
                +-- CMakeLists.txt

A separate plugin target is associated with the QML module. It is used at runtime to load the module dynamically when the application doesn't already link to the backing target. The plugin target will also be a library and is normally installed to the same directory as the module's qmldir file.

The plugin target should ideally contain nothing more than a trivial implementation of the plugin class. This allows the plugin to be designated as optional in the `qmldir` file. Other targets can then link directly to the backing target and the plugin will not be needed at runtime, which can improve load-time performance. By default, a C++ source file that defines a minimal plugin class will be automatically generated and added to the plugin target. For cases where the QML module needs a custom plugin class implementation, the NO_GENERATE_PLUGIN_SOURCE and usually the NO_PLUGIN_OPTIONAL options will be needed.

The `STATIC` QML modules also generate the static QML plugins if `NO_PLUGIN` is not specified. Targets that import such `STATIC` QML modules also need to explicitly link to corresponding QML plugins.

Note: When using static linking, it might be necessary to use Q_IMPORT_QML_PLUGIN to ensure that the QML plugin is correctly linked.

#### Plugin target with no backing target

A QML module can be defined with the plugin target serving as its own backing target. In this case, the module must be loaded dynamically at runtime and cannot be linked to directly by other targets. To create this arrangement, the `PLUGIN_TARGET` keyword must be used, with the `target` repeated as the plugin target name. For example:

     qt_add_qml_module(someTarget
         PLUGIN_TARGET someTarget
         ...
     )

While this arrangement may seem marginally simpler to deploy, a separate backing target should be preferred where possible due to the potentially better load-time performance.

#### Executable as a QML module

An executable target can act as a backing target for a QML module. In this case, there will be no plugin library, since the QML module will always be loaded directly as part of the application. The `qt_add_qml_module()` command will detect when an executable is used as the backing target and will automatically disable the creation of a separate plugin. Do not use any of the options with `PLUGIN` in their name when using this arrangement.

When an executable is used as the backing target, the source directory structure is not expected to match the QML module's target path. See Caching compiled QML sources for additional target path differences for compiled-in resources.

### Auto-generating `qmldir` and typeinfo files

By default, a qmldir file and a typeinfo file will be auto-generated for the QML module being defined. The contents of those files are determined by the various arguments given to this command, as well as the sources and `.qml` files added to the backing target. The OUTPUT_DIRECTORY argument determines where the `qmldir` and typeinfo files will be written to. If the QML module has a plugin, that plugin will also be created in the same directory as the `qmldir` file.

If QTP0004 policy is set to `NEW`, for each further directory that contains `.qml` files another `qmldir` file is generated. These extra `qmldir` files merely redirect to the module's base directory via a `prefer` directive. This is so that all the QML components in a module can access each other, no matter which directory they are stored in.

If using a statically built Qt, the backing target's `.qml` files will be scanned during the CMake configure run to determine the imports used by the module and to set up linking relationships (the `NO_IMPORT_SCAN` keyword can be given to disable this). When a `.qml` file is added to or removed from the module, CMake will normally re-run automatically and the relevant files will be re-scanned, since a `CMakeLists.txt` file will have been modified. During the course of development, an existing `.qml` file may add or remove an import or a type. On its own, this would not cause CMake to re-run automatically, so you should explicitly re-run CMake to force the `qmldir` file to be regenerated and any linking relationships to be updated.

The backing target's C++ sources are scanned at build time to generate a typeinfo file and a C++ file to register the associated types. The generated C++ file is automatically added to the backing target as a source. This requires `AUTOMOC` to be enabled on the target. The project is responsible for ensuring this, usually by setting the `CMAKE_AUTOMOC` variable to `TRUE` before calling `qt_add_qml_module()`, or by passing in an existing target with the `AUTOMOC` target property already set to `TRUE`. It isn't an error to have `AUTOMOC` disabled on the target, but the project is then responsible for handling the consequences. This may include having to manually generate the typeinfo file instead of allowing it to be auto-generated with missing details, and adding C++ code to register the types.

Projects should prefer to use the auto-generated typeinfo and `qmldir` files where possible. They are easier to maintain and they don't suffer from the same susceptibility to errors that hand-written files do. Nevertheless, for situations where the project needs to provide these files itself, the auto-generation can be disabled. The `NO_GENERATE_QMLDIR` option disables the `qmldir` auto-generation and the `NO_GENERATE_QMLTYPES` option disables the typeinfo and C++ type registration auto-generation. If the auto-generated typeinfo file is acceptable, but the project wants to use a different name for that file, it can override the default name with the `TYPEINFO` option (but this should not typically be needed).

### Caching compiled QML sources

All `.qml`, `.js`, and `.mjs` files added to the module via the `QML_FILES` argument will be compiled to bytecode and cached directly in the backing target. This improves load-time performance of the module. The original uncompiled files are also stored in the backing target's resources, as these may still be needed in certain situations by the QML engine.

The resource path of each file is determined by its path relative to the current source directory (`CMAKE_CURRENT_SOURCE_DIR`). This resource path is appended to a prefix formed by concatenating the RESOURCE_PREFIX and the target path (but see NO_RESOURCE_TARGET_PATH for an exception to this).

If QTP0001 policy is set to `NEW`, the RESOURCE_PREFIX defaults to `/qt/qml/` which is the default import path of the QML engine. This ensures that modules are put into the QML Import Path and can be found without further setup.

Ordinarily, the project should aim to place `.qml` files in the same relative location as they would have in the resources. If the `.qml` file is in a different relative directory to its desired resource path, its location in the resources needs to be explicitly specified. This is done by setting the `QT_RESOURCE_ALIAS` source file property, which must be set before the `.qml` file is added. For example:

     set_source_files_properties(path/to/somewhere/MyFrame.qml PROPERTIES
         QT_RESOURCE_ALIAS MyFrame.qml
     )

     qt_add_qml_module(someTarget
         URI MyCo.Frames
         RESOURCE_PREFIX /my.company.com/imports
         QML_FILES
             path/to/somewhere/MyFrame.qml
             AnotherFrame.qml
     )

In the above example, the target path will be `MyCo/Frames`. After taking into account the source file properties, the two `.qml` files will be found at the following resource paths:

- `/my.company.com/imports/MyCo/Frames/MyFrame.qml`
- `/my.company.com/imports/MyCo/Frames/AnotherFrame.qml`

In the rare case that you want to override the automatic selection of the qmlcachegen program to be used, you may set the `QT_QMLCACHEGEN_EXECUTABLE` target property on the module target. For example:

     set_target_properties(someTarget PROPERTIES
         QT_QMLCACHEGEN_EXECUTABLE qmlcachegen
     )

This explicitly selects qmlcachegen as the program to be used, even if better alternatives are available.

Furthermore, you can pass extra arguments to qmlcachegen, by setting the `QT_QMLCACHEGEN_ARGUMENTS` option. In particular, the `--only-bytecode` option will turn off compilation of QML script code to C++. For example:

     set_target_properties(someTarget PROPERTIES
         QT_QMLCACHEGEN_ARGUMENTS "--only-bytecode"
     )

Another important argument is `--direct-calls`. You can use it to enable the direct mode of The QML script compiler in case the Qt Quick Compiler Extensions are installed. If the extensions are not installed, the argument is ignored. There is a shorthand called `QT_QMLCACHEGEN_DIRECT_CALLS` for it.

     set_target_properties(someTarget PROPERTIES
         QT_QMLCACHEGEN_DIRECT_CALLS ON
     )

Finally, the `--verbose` argument can be used to see diagnostic output from qmlcachegen:

     set_target_properties(someTarget PROPERTIES
         QT_QMLCACHEGEN_ARGUMENTS "--verbose"
     )

With this flag set, qmlcachegen will output warnings for each function it cannot compile to C++. Some of these warnings will point to problems in your QML code and some will tell you that certain features of the QML language are not implemented in the C++ code generator. In both cases, qmlcachegen will still generate byte code for such functions. If you want to see only the problems in your QML code, you should use qmllint and the targets generated for it instead.

### Linting QML sources

A separate linting target will be automatically created if any `.qml` files are added to the module via the `QML_FILES` keyword, or by a later call to qt_target_qml_sources(). The name of the linting target will be the `target` followed by `_qmllint`. An `all_qmllint` target which depends on all the individual `*_qmllint` targets is also provided as a convenience.

### Naming conventions for `.js` files

JavaScript file names that are intended to be addressed as components should start with an uppercase letter.

Alternatively, you may use lowercase file names and set the source file property QT_QML_SOURCE_TYPENAME to the desired type name.

### Singletons

If a QML module has `.qml` files which provide singleton types, these files need to have their `QT_QML_SINGLETON_TYPE` source property set to `TRUE`, to ensure that the `singleton` command is written into the qmldir file. This must be done in addition to the QML file containing the `pragma Singleton` statement. The source property must be set before creating the module the singleton belongs to.

See qt_target_qml_sources() for an example on how to set the `QT_QML_SINGLETON_TYPE` property.

### Compiling QML to C++ with QML type compiler

Note: The QML type compiler `qmltc` does not guarantee that the generated C++ stays API-, source- or binary-compatible between past or future versions, even patch versions. Furthermore, qmltc-compiled apps using Qt's QML modules will require linking against private Qt API, see also Compiling QML code with qmltc.

If a QML module has `.qml` files, you can compile them to C++ using qmltc. Unlike bytecode compilation, you have to explicitly enable qmltc via ENABLE_TYPE_COMPILER argument. In which case, `.qml` files specified under `QML_FILES` would be compiled. Files ending with `.js` and `.mjs` are ignored as qmltc does not compile JavaScript code. Additionally, files marked with QT_QML_SKIP_TYPE_COMPILER source file property are also skipped.

By default, qmltc creates lower-case `.h` and `.cpp` files for a given `.qml` file. For example, `Foo.qml` ends up being compiled into `foo.h` and `foo.cpp`.

The created C++ files are placed into a dedicated `.qmltc/<target>/` sub-directory of the `BINARY_DIR` of the `target`. These files are then automatically added to the target sources and compiled as Qt C++ code along with other source files.

While processing QML_FILES, the following source file properties are respected:

- `QT_QMLTC_FILE_BASENAME`: use this source file property to specify a non-default .h and .cpp file name, which might be useful to e.g. resolve conflicting file names (imagine you have main.qml that is being compiled, but main.h already exists, so #include "main.h" might not do what you expect it to do). QT_QMLTC_FILE_BASENAME is expected to be a file name (without extension), so any preceding directory is ignored. Unlike in the case of default behavior, the QT_QMLTC_FILE_BASENAME is not lower-cased.
- `QT_QML_SKIP_TYPE_COMPILER`: use this source file property to specify that a QML file must be ignored by qmltc.

## Arguments

### Required arguments

The `target` specifies the name of the backing target for the QML module. By default, it is created as a shared library if Qt was built as shared libraries, or as a static library otherwise. This choice can be explicitly overridden with the `STATIC` or `SHARED` options.

Every QML module must define a `URI`. It should be specified in dotted URI notation, such as `QtQuick.Layouts`. Each segment must be a well-formed ECMAScript Identifier Name. This means, for example, the segments must not start with a number and they must not contain - (minus) characters. As the `URI` will be translated into directory names, you should restrict it to alphanumeric characters of the latin alphabet, underscores, and dots. Other QML modules may use this name in import statements to import the module. The `URI` will be used in the `module` line of the generated qmldir file. The `URI` is also used to form the target path by replacing dots with forward slashes.

See Identified Modules for further in-depth discussion of the module URI.

### Versions

A QML module can also define a `VERSION` in the form `Major.Minor`, where both `Major` and `Minor` must be integers. An additional `.Patch` component may be appended, but will be ignored. A list of earlier major versions the module provides types for can also optionally be given after the `PAST_MAJOR_VERSIONS` keyword (see below). See Identified Modules for further in-depth discussion of version numbering, Registering past major versions for registering past major versions, and Keeping module versions in sync for keeping module versions in sync.

If you don't need versions you should omit the `VERSION` argument. It defaults to the highest possible version. Internal versioning of QML modules has some fundamental flaws. You should use an external package management mechanism to manage different versions of your QML modules.

### Adding sources and resources to the module

`SOURCES` specifies a list of non-QML sources to be added to the backing target. It is provided as a convenience and is equivalent to adding the sources to the backing target with the built-in `target_sources()` CMake command.

`QML_FILES` lists the `.qml`, `.js` and `.mjs` files for the module. These will be automatically compiled into bytecode and embedded in the backing target unless the `NO_CACHEGEN` option is given. The uncompiled file is always stored in the embedded resources of the backing target, even if `NO_CACHEGEN` is specified. Unless the `NO_LINT` option is given, the uncompiled files will also be processed by `qmllint` via a separate custom build target. The files will also be used to populate type information in the generated qmldir file by default. `NO_GENERATE_QMLDIR` can be given to disable the automatic generation of the `qmldir` file. This should normally be avoided, but for cases where the project needs to provide its own `qmldir` file, this option can be used. Since Qt 6.8, when QTP0004 is enabled, `qt_add_qml_module` will create additional `qmldir` files for each subdirectory in the QML module, which ensure that each QML file will import its own module via the implicit import. This behavior can be turned off for a QML module by passing the `NO_GENERATE_EXTRA_QMLDIRS` flag to it. The `NO_GENERATE_QMLDIR` implies `NO_GENERATE_EXTRA_QMLDIRS`.

Note: See qt_target_qml_sources() for further details on how to add qmlfiles after `qt_add_qml_module()` was called. For example, you may wish to add files conditionally based on an if statement expression, or from subdirectories that will only be added if certain criteria are met. Furthermore, files added with qt_target_qml_sources() also can specify if they should be skipped for the linting, bytecode compilation or `qmldir` file generation.

`RESOURCES` lists any other files needed by the module, such as images referenced from the QML code. These files will be added as compiled-in resources (see RESOURCE_PREFIX for an explanation of the base point they will be located under). If needed, their relative location can be controlled by setting the `QT_RESOURCE_ALIAS` source property, just as for `.qml` files (see Caching compiled QML sources).

`RESOURCE_PREFIX` is intended to encapsulate a namespace for the project and will often be the same for all QML modules that the project defines.

However, it is better to set the QTP0001 CMake policy instead. It defines a default resource prefix that ensures that your QML module ends up under one of the QML engine's default import paths.

If you set a `RESOURCE_PREFIX`, you should also add it to the import paths for the QML Engine to find the QML module.

If QTP0001 is enabled (e.g. via `qt_standard_project_setup(REQUIRES 6.5)`), the default value is `"/qt/qml/"`, otherwise it is `"/"`.

When various files are added to the compiled-in resources, they are placed under a path formed by concatenating the `RESOURCE_PREFIX` and the target path. For the special case where the backing target is an executable, it may be desirable to place the module's `.qml` files and other resources directly under the `RESOURCE_PREFIX` instead. This can be achieved by specifying the `NO_RESOURCE_TARGET_PATH` option, which may only be used if the backing target is an executable.

### Registering past major versions

`PAST_MAJOR_VERSIONS` contains a list of additional major version that the module provides. For each of those versions and each QML file without a `QT_QML_SOURCE_VERSIONS` setting an additional entry in the qmldir file will be generated to specify the extra version. Furthermore, the generated module registration code will register the past major versions using qmlRegisterModule() on the C++ side. The module registration code is automatically generated for your QML module, unless you specify `NO_GENERATE_QMLTYPES` (but use of this option is strongly discouraged). Usage of `PAST_MAJOR_VERSIONS` adds some overhead when your module is imported. You should increment the major version of your module as rarely as possible. Once you can rely on all QML files importing this module to omit the version in their imports, you can safely omit `PAST_MAJOR_VERSIONS`. All the QML files will then import the latest version of your module. If you have to support versioned imports, consider supporting only a limited number of past major versions.

### Declaring module dependencies

`IMPORTS` provides a list of other QML modules that this module imports. Each module listed here will be added as an `import` entry in the generated qmldir file. If a QML file imports this module, it also imports all the modules listed under `IMPORTS`. Optionally, a version can be specified by appending it after a slash, such as `QtQuick/2.0`. Omitting the version will cause the greatest version available to be imported. You may only specify the major version, as in `QtQuick/2`. In that case the greatest minor version available with the given major version will be imported. Finally, `auto` may be given as version (`QtQuick/auto`). If `auto` is given, the version that the current module is being imported with is propagated to the module to be imported. Given an entry `QtQuick/auto` in a module `YourModule`, if a QML file specifies `import YourModule 3.14`, this results in importing version `3.14` of `QtQuick`. For related modules that follow a common versioning scheme, you should use `auto`.

`OPTIONAL_IMPORTS` provides a list of other QML modules that this module may import at run-time. These are not automatically imported by the QML engine when importing the current module, but rather serve as hints to tools like `qmllint`. Versions can be specified in the same way as for `IMPORTS`. Each module listed here will be added as an `optional import` entry in the generated qmldir file.

`DEFAULT_IMPORTS` specifies which of the optional imports are the default entries that should be loaded by tooling. One entry should be specified for every group of `OPTIONAL_IMPORTS` in the module. As optional imports are only resolved at runtime, tooling like qmllint cannot in general know which of the optional imports should be resolved. To remedy this, you can specify one of the optional imports as the default import; tooling will then pick it. If you have one optional import that gets used at runtime without any further configuration, that is an ideal candidate for the default import.

`DEPENDENCIES` provides a list of other QML modules that this module depends on, but doesn't necessarily import. It would typically be used for dependencies that only exist at the C++ level, such as a module registering a class to QML which is a subclass of one defined in another module.

For example, if one would like to subclass `QQuickItem` as following:

     class MyItem: public QQuickItem { ... };

then one has to make sure that the module containing `QQuickItem`, called `QtQuick`, is declared as a dependency via the `DEPENDENCIES` option. Not doing so might result in errors during type compilation with qmltc or during binding and function compilation to C++ with qmlcachegen.

Note: Adding the module to `DEPENDENCIES` is not necessary if the module is already imported via the `IMPORTS` option. The recommended way is to use the lighter alternative `DEPENDENCIES` over `IMPORTS`.

The module version of the dependencies must be specified along with the module name, in the same form as used for `IMPORTS` and `OPTIONAL_IMPORTS`. Each module listed here will be added as a `depends` entry in the generated qmldir file.

`IMPORT_PATH` can be used to add to the search paths where other QML modules that this one depends on can be found. The other modules must have their `qmldir` file under their own target path below one of the search paths.

If the backing target is a static library and that static library will be installed, `OUTPUT_TARGETS` should be given to provide a variable in which to store a list of additional targets that will also need to be installed. These additional targets are generated internally by `qt_add_qml_module()` and are referenced by the backing target's linking requirements as part of ensuring that resources are set up and loaded correctly.

Note: Since Qt 6.8, it is possible to pass a target name to IMPORTS and DEPENDENCIES. See QTP0005 for more details.

### Targets and plugin targets

`PLUGIN_TARGET` specifies the plugin target associated with the QML module. The `PLUGIN_TARGET` can be the same as the backing `target`, in which case there will be no separate backing target. If `PLUGIN_TARGET` is not given, it defaults to `target` with `plugin` appended. For example, a backing target called `mymodule` would have a default plugin name of `mymoduleplugin`. The plugin target's name will be used to populate a `plugin` line in the generated qmldir file. Therefore, you must not try to change the plugin's output name by setting target properties like `OUTPUT_NAME` or any of its related properties.

The backing `target` and the plugin target (if different) will be created by the command, unless they already exist. Projects should generally let them be created by the command so that they are created as the appropriate target type. If the backing `target` is a static library, the plugin will also be created as a static library. If the backing `target` is a shared library, the plugin will be created as a module library. If an existing `target` is passed in and it is an executable target, there will be no plugin. If you intend to always link directly to the backing target and do not need a plugin, it can be disabled by adding the `NO_PLUGIN` option. Specifying both `NO_PLUGIN` and `PLUGIN_TARGET` is an error.

In certain situations, the project may want to delay creating the plugin target until after the call. The `NO_CREATE_PLUGIN_TARGET` option can be given in that situation. The project is then expected to call qt_add_qml_plugin() on the plugin target once it has been created. When `NO_CREATE_PLUGIN_TARGET` is given, `PLUGIN_TARGET` must also be provided to explicitly name the plugin target.

By default, `qt_add_qml_module()` will auto-generate a `.cpp` file that implements the plugin class named by the `CLASS_NAME` argument. The generated `.cpp` file will be automatically added to the plugin target as a source file to be compiled. If the project wants to provide its own implementation of the plugin class, the `NO_GENERATE_PLUGIN_SOURCE` option should be given. Where no `CLASS_NAME` is provided, it defaults to the `URI` with dots replaced by underscores, then `Plugin` appended. Unless the QML module has no plugin, the class name will be recorded as a `classname` line in the generated qmldir file. You need to add any C++ files with custom plugin code to the plugin target. Since the plugin then likely contains functionality that goes beyond simply loading the backing library, you will probably want to add NO_PLUGIN_OPTIONAL, too. Otherwise the QML engine may skip loading the plugin if it detects that the backing library is already linked.

If the `NO_PLUGIN` keyword is given, then no plugin will be built. This keyword is thus incompatible with all the options that customize the plugin target, in particular NO_GENERATE_PLUGIN_SOURCE, NO_PLUGIN_OPTIONAL, PLUGIN_TARGET, NO_CREATE_PLUGIN_TARGET, and CLASS_NAME. If you do not provide a plugin for your module, it will only be fully usable if its backing library has been linked into the executable. It is generally hard to guarantee that a linker preserves the linkage to a library it considers unused.

If the `NO_PLUGIN_OPTIONAL` keyword is given, then the plugin is recorded in the generated `qmldir` file as non-optional. If all of a QML module's functionality is implemented in its backing target and the plugin target is separate, then the plugin can be optional, which is the default and recommended arrangement. The auto-generated plugin source file satisfies this requirement. Where a project provides its own `.cpp` implementation for the plugin, that would normally mean the `NO_PLUGIN_OPTIONAL` keyword is also needed because the plugin will almost certainly contain functionality that the QML module requires.

### Automatic type registration

Type registration is automatically performed for the backing target's C++ sources that are processed by AUTOMOC. This will generate a typeinfo file in the output directory, the file name being the `target` name with `.qmltypes` appended. This file name can be changed using the `TYPEINFO` option if desired, but this should not normally be necessary. The file name is also recorded as a `typeinfo` entry in the generated qmldir file. Automatic type registration can be disabled using the `NO_GENERATE_QMLTYPES` option, in which case no typeinfo file will be generated, but the project will still be expected to generate a typeinfo file and place it in the same directory as the generated `qmldir` file.

`OUTPUT_DIRECTORY` specifies where the plugin library, `qmldir` and typeinfo files are generated. When this keyword is not given, the default value will be the target path (formed from the `URI`) appended to the value of the QT_QML_OUTPUT_DIRECTORY variable. If that variable is not defined, the default depends on the type of backing target. For executables, the value will be the target path appended to `${CMAKE_CURRENT_BINARY_DIR}`, whereas for other targets it will be just `${CMAKE_CURRENT_BINARY_DIR}`. When the structure of the source tree matches the structure of QML module target paths (which is highly recommended), QT_QML_OUTPUT_DIRECTORY often isn't needed. In order to match the structure of the target paths, you have to call your directories exactly like the segments of your module URI. For example, if your module URI is `MyUpperCaseThing.mylowercasething`, you need to put this in a directory called `MyUpperCaseThing/mylowercasething/`.

The need for specifying the `OUTPUT_DIRECTORY` keyword should be rare, but if it is used, it is likely that the caller will also need to add to the IMPORT_PATH to ensure that linting, cached compilation of qml sources, automatic importing of plugins in static builds, and deploying imported QML modules for non-static builds all work correctly.

### Qt Quick Designer compatibility

`DESIGNER_SUPPORTED` should be given if the QML module supports Qt Quick Designer. When present, the generated `qmldir` file will contain a `designersupported` line. See Module Definition qmldir Files for how this affects the way Qt Quick Designer handles the plugin.

### Keeping module versions in sync

The `FOLLOW_FOREIGN_VERSIONING` keyword relates to base types of your own C++-defined QML types that live in different QML modules. Typically, the versioning scheme of your module does not match that of the module providing the base types. Therefore, by default all revisions of the base types are made available in any import of your module. If `FOLLOW_FOREIGN_VERSIONING` is given, the version information attached to the base types and their properties is respected. So, an `import MyModule 2.8` will then only make available versioned properties up to version `2.8` of any base types outside `MyModule`. This is mostly useful if you want to keep your module version in sync with other modules you're basing types on. In that case you might want your custom types to not expose properties from a module's base type version greater than the one being imported.

### C++ namespaces of generated code

If a namespace is given with the `NAMESPACE` keyword, the plugin and registration code will be generated into a C++ namespace of this name.

### qmlimportscanner and NO_IMPORT_SCAN

For static Qt builds, `qmlimportscanner` is run at configure time to scan the `.qml` files of a QML module and identify the QML imports it uses (see qt_import_qml_plugins()). For non-static Qt builds, if the target is an executable, a similar scan is performed at build time to provide the information needed by deployment scripts (see qt_deploy_qml_imports()). Both scans can be disabled by providing the `NO_IMPORT_SCAN` option. Doing so means the project takes on the responsibility of ensuring all required plugins are instantiated and linked for static builds. For non-static builds the project must manually work out and deploy all QML modules used by an executable target.

### Arguments for qmltc

`ENABLE_TYPE_COMPILER` can be used to compile `.qml` files to C++ source code with qmltc. Files with the source property `QT_QML_SKIP_TYPE_COMPILER` are not compiled to C++.

`TYPE_COMPILER_NAMESPACE` argument allows to override the namespace in which qmltc generates code. By default, the namespace of the generated code follows the module hierarchy as depicted in the URI, e.g., `MyModule` for a module with URI `MyModule` or `com::example::Module` for URI `com.example.MyModule`. By specifying the `TYPE_COMPILER_NAMESPACE` option, the generated code can be put instead in a custom namespace, where different subnamespaces are to be separated by a "::", e.g. "MyNamespace::MySubnamespace" for the namespace MySubnamespace that is inside the MyNamespace. Apart from the "::", C++ namespace naming rules apply.

`QMLTC_QMLTC_EXPORT_DIRECTIVE` should be used with `QMLTC_EXPORT_FILE_NAME` when the classes generated by qmltc should be exported from the qml library. By default, classes generated by qmltc are not exported from their library. The header defining the export macro for the current library can be specified as an optional argument to `QMLTC_EXPORT_FILE_NAME` while the exporting macro name should be specified as an argument to `QMLTC_QMLTC_EXPORT_DIRECTIVE`. If no additional include is required or wanted, e.g. when the header of the export macro is already indirectly included by a base class, then the `QMLTC_EXPORT_FILE_NAME` option can be left out.