summaryrefslogtreecommitdiffstats
path: root/src/interfaceframework/doc/src/ifcodegen/generator-usage.qdoc
blob: 3d53051ca30c59b7f2f8d71fd4bd66153d5033d5 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
864
865
866
867
868
869
870
871
872
873
874
// Copyright (C) 2021 The Qt Company Ltd.
// Copyright (C) 2019 Luxoft Sweden AB
// Copyright (C) 2018 Pelagicore AG
// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR GFDL-1.3-no-invariants-only
/*!
    \page generator-usage.html
    \title Use the Generator
    \previouspage Jinja Template Syntax
    \nextpage Filter Reference

    This topic describes how to use the QtIF generator.

    \section1 Introduction

    The Generator is a Python script that can be run manually or using the \l {Build System Integration}.
    This script uses QFace as the autogenerator framework which parses the
    Interface Definition Language (IDL) file, generates the domain model
    (similar to an Abstract Syntax Tree (AST)) and then feeds it to the generator.
    Depending on the type of the project to generate, different \c{formats} are specified.

    \section1 Command Line Parameters
    To run the generation, use the following command:

    \code
    $$[QT_HOST_LIBEXECS]/ifcodegen/generate.py -T $$[QT_INSTALL_DATA]/ifcodegen-templates
    --format=backend_simulator interface.qface out_dir
    \endcode

    The options and parameters are:
    \table 100%
        \header
            \li Option/Parameter
            \li Description
        \row
            \li \c{--reload} / \c{--no-reload} [optional]
            \li Specifies whether the generator should keep track of the changes in the IDL file
                and update the output on the fly; the default is \c{--no-reload}
        \row
            \li  \c -T, \c --template-search-path <search-path>
            \target template-search-path-option
            \li Adds the given path to the list of search paths. All directories in this list are
                scanned for generation templates (identified by the \l{Generation YAML}).
                The identified templates can be selected with the
                \l{template}{--template option}.
        \row
            \li  \c -t, \c --template
            \target template
            \li Selects the template which should be used for the generation. Templates are searched
                within the \l{template-search-path-option}{template search path}. Instead of the
                template name, an absolute path to a template can be provided. This template doesn't
                need to be part of the template search path.
                The following templates are usually installed by default:
                \list
                \li \c frontend
                \li \c qmlplugin
                \li \c backend_simulator
                \li \c backend_qtro
                \li \c server_qtro
                \li \c server_qtro_simulator
                \endlist
        \row
            \li -A, --annotations <annotation-file>
            \target annotations-option
            \li Merges the given annotation file with annotations already in the QFace file and the
                implicit annotation file. These files are merged according to the order in which
                they are passed to the generator. Providing a duplicate key in the YAML file
                overrides the previously set value. This option can be used multiple times. For
                more information, see \l{merge-annotations}{Merge Annotations}.
        \row
            \li -I, --import <import-path>
            \target import-option
            \li Adds the given path to the list of import paths. All directories in this list are
                scanned recursively for QFace files. The QFace files found are then used to resolve
                the information required when importing a module; this is similar to how C++ include
                paths work.
        \row
            \li source
            \li Path or paths to the IDL source files. If there are multiple entries, each one is
                handled. If a directory path is provided, it's scanned for IDL files.
        \row
            \li outputdir
            \li The destination folder for the generated files.
        \row
            \li --help
            \li Display options and exit.
    \endtable

    Currently, based on the \l{template}{\c {--template}} value, the generator can generate multiple
    types of projects with a given IDL file:

    \table 100%
        \header
            \li Project Type
            \li Description
        \row
            \li \l frontend
            \target frontend-template
            \li Generates an API using base classes from qtinterfaceframework and the \l{Dynamic Backend System}
        \row
            \li \l {QML Plugin} {qmlplugin}
            \li Generates a C++ QML Plugin which registers all frontend types in QML.
        \row
            \li \l {Backend Simulator} {backend_simulator}
            \target backend-simulator-template
            \li Generates a simulation backend for the API first generated by the \c frontend option.
                This backend serves as a mock implementation.
        \row
            \li \l {QtRemoteObjects Backend} {backend_qtro}
            \target backend-qtro-template
            \li Generates a QtRemoteObjects based backend client for the API first generated by the
                \c frontend option. This backend connects to a backend server.
        \row
            \li \l {QtRemoteObjects Server} {server_qtro}
            \target server-qtro-template
            \li Generates a QtRemoteObjects based backend server stub for the API first generated
                by the \c frontend option.
        \row
            \li \l {QtRemoteObjects Simulation Server} {server_qtro_simulator}
            \target server-qtro-simulator-template
            \li Generates a QtRemoteObjects based simulation server for the API first generated by
                the \c frontend option.
        \row
            \li folder path
            \li Uses templates inside the folder. A YAML file with the same name as the folder
                should provide a list of template files in the folder. This is useful if you want
                to write your own templates. For more details, see \l{Generation YAML}.
    \endtable

    \section1 Configure the Generator

    The generator's Python script parses the input files and creates a domain model. This domain
    model is then passed as a context to the Jinja template engine. Use the Generation YAML file
    to specify which files to generate. Afterwards, you can use an Annotation YAML file to add more
    information to the IDL file, which is generator specific.

    \section2 Generation YAML

    After the domain model tree is created, this tree is traversed and each leaf of the domain
    model object tree (module, interface, structure, and so on) is passed to a specific Jinja
    template defined by the configuration file.

    The Generation YAML file defines which template to use to generate which file. Suppose you want
    to generate a header file for each module in your domain model. But, a module can have multiple
    interfaces, so, you want to use a different header file for each interface and structure. In
    this case, the Generation YAML file defines a set of rules to specify which template file to
    use and how to name them.

    This YAML file must have the following structure:

    \code
    frontend:
        module:
            documents:
                - "{{module.module_name|lower}}plugin.h": "plugin.h.tpl"
        interface:
            documents:
                - '{{interface|lower}}backend.h': 'backend.h.tpl'
    \endcode

    For every entity, there's a list of templates that must be called, when traversing this entity
    in the domain model tree. Here, the YAML file defines a list of documents, which need to be
    generated for all modules and a list for all interfaces. Every list entry consists of two
    parts; the first part is the name of the file that needs to be created, as specified in the \l
    {Jinja template syntax}{Jinja template language} format. The value of the object property used
    in the template's name is processed and substituted into the template, thus forming the final
    name of the file to create. The second part is the name of the template to use. For the Interface Framework
    generator, you must specify rules for three kinds of entities: modules, interfaces and
    structures. See the \l{QFace - Rule Base Generation}{QFace Rule Base Generation Documentation}
    for more information.

    \section3 Extra Jinja Filters

    Sometimes the Jinja filters provided by ifcodegen are not enough, but it is possible to write your
    own filters using Python.
    If you add a python script called \c{filters.py} within your template it will be loaded automatically.
    You can use the following boiler-plate code as a template:

    \quotefile filters.py

    To share filters also between templates, you can also specify other python scripts which should
    be loaded in addition. This needs to be done in the Generation YAML file.

    The following snippet generates a plugin.h and loads additional filters from a folder called
    extra-filter:

    \code
    frontend:
        extra_filters: [ "extra-filter/filters.py" ]
        module:
            documents:
                - "{{module.module_name|lower}}plugin.h": "plugin.h.tpl"
    \endcode

    \section2 Annotations YAML

    Currently, not all aspects of the interface description can be expressed using the IDL itself.
    For instance, there is no language construct to define a default value for a property or a
    range of valid values a property can take. Still, this can be achieved via a mechanism called
    \l{annotations_reference}{Annotations}. Annotations provide freedom and flexibility to express
    any concepts and constructs.

    The code snippet below shows an example of using annotations in the IDL. Here, we define an
    interface that is zoned, and specify its ID.

    \code
    @config: {zoned: true, id: "org.qt-project.interfaceframework.ClimateControl/1.2"}
    \endcode

    It does not make sense to place all of the annotations in the main IDL file. For instance, you
    may need to define some aspects of the auto-test code generation. Such annotations can be put
    in the YAML file that accompanies the main IDL file, with the same name. During the parse phase
    QFace automatically picks this file up and merges the annotation specified in this YAML file
    with those defined in the IDL file.

    Since the accompanying YAML file is always picked up automatically, it won't work for
    annotations that you need for some specific projects, such as when generating a backend plugin.
    For this use case, you can pass multiple additional annotation YAML files to the generator.

    In QtInterfaceFramework, the following annotations are used to define IDLs:

    \table 100%
        \header
            \li Tag
            \li Where
            \li Object type
            \li Purpose
        \row
            \li \code
                @config: {namespace: "module"}
                \endcode
            \target config_namespace
            \li Main IDL file
            \li Module
            \li Defines the C++ namespace the generated code should use. Available options are:
                \list
                    \li \b <novalue> Use no namespace (\b default)
                    \li \b qt Use the qt namespace
                    \li \b module Use the full module name as namespace
                    \li \b <value> Use the provided value as namespace
                \endlist
        \row
            \li \code
                @config: {interfaceBuilder: "FunctionName"}
                \endcode
            \li Main IDL file
            \li Module
            \li Declares a function that is called in the plugin to generate the instances for
                every interface. The function takes a pointer to the plugin instance and returns a
                \c {QVector<QIfFeatureInterface *>}. Interfaces should be generated in the same
                order as defined by \c {Plugin::interfaces()}. Use this tag to instantiate classes
                derived from the generated plugin interfaces' classes.
        \row
            \li \code
                @config: {zoned: true}
                \endcode
            \li Main IDL file
            \li Interface
            \li Tells the generator whether the interface is zoned or not. Use this tag to define
                whether the backend feature interface is derived from QIfZonedFeatureInterface or
                QIfFeatureInterface.
        \row
            \li \code
                @config: {id: "org.qt.project.interfaceframework.ClimateControl/1.0"}
                \endcode
            \li Main IDL file
            \li Interface
            \li Defines the interface ID, which is a string used by the QtInterfaceFramework service manager to
                glue a frontend interface with its backend implementation. For more information,
                see \l {Dynamic Backend System}.
        \row
            \li \code
                @config: {getter_name: "isHeaterEnabled"}
                \endcode
            \li Main IDL file
            \li Property
            \li Overrides the default getter method's name. Useful for boolean properties, such as
                the getter for a property: 'enabled', should be 'isEnabled' instead of the default.
        \row
            \li \code
                @config: {setter_name: "setHeaterEnabled"}
                \endcode
            \li Main IDL file
            \li Property
            \li Overrides the default setter method's name.
        \row
            \li \code
                @config: {qml_name: "ClimateControl"}
                \endcode or
                \code
                @config: {qml_type: "ClimateControl"}
                \endcode
            \li Main IDL file
            \li Module, Interface
            \li Defines the name this interface or module should use in QML. For interfaces, it is
                the name which is used to export the interface to QML. For modules, it defines the
                URI of the complete module. The last part of the URI is also used for the singleton
                that exports all enums to QML.
        \row
            \li \code
                @designer: {categoryName: "Smart Home Components"}
                \endcode
            \li Main IDL file
            \li Module, Interface
            \li Defines the category name this interface should be listed under in the Qt Design Studio
                Library. When defined for a module it sets the category name for all interfaces inside
                that module, but it can be overridden per interface by defining it there as well.
        \row
            \li \code
                @designer: {name: "Climate Control"}
                \endcode
            \li Main IDL file
            \li Interface
            \li Defines the name this interface should be listed under in the Qt Design Studio
                Library.
        \row
            \li \code
                @designer: {typeIcon: "images/climate.png"}
                \endcode
            \li Main IDL file
            \li Interface
            \li The typeIcon is a 16x16 icon used in the Navigator Pane within Qt Design Studio.
                \note The icon needs to be copied to the correct folder by a custom build rule.
        \row
            \li \code
                @designer: {libraryIcon: "images/climate.png"}
                \endcode
            \li Main IDL file
            \li Interface
            \li The libraryIcon is shown in the Library within Qt Design Studio.
                \note The icon needs to be copied to the correct folder by a custom build rule.
        \row
            \li \code
                @config: { configurationId: "smarthome"}
                \endcode
            \li Main IDL file
            \li Module, Interface
            \li Defines the configurationId of this interface. The configurationId can be used to
                specify a configuration for the interface from a central location using
                \l QIfConfiguration. When defined for a module, it sets the configurationId for all
                interfaces inside that module, but it can be overridden per interface by defining it
                there as well.
                Defaults to \c module.name
    \endtable

    Annotations that are not logically part of the interface description, but rather the ones used
    to specify additional information, are put in the accompanying YAML file.

    Here is a list of annotations used to define the various aspects of the generated backends and
    servers:

    \section3 backend_simulator

    \table 100%
        \header
            \li Tag
            \li Where
            \li Object type
            \li Purpose
        \row
            \li
            \code
            config_simulator:
                serviceObjectId: "smarthome_simulation"
            \endcode
            \li Accompanying YAML file
            \li Module
            \li Defines the id of the generated plugin. See \l QIfServiceObject::id for more information.
                Defaults to \c module.name + "_simulation"
        \row
            \li
            \code
            config_simulator:
                configurationId: "smarthome"
            \endcode
            \li Accompanying YAML file
            \li Module
            \li Defines the configurationId of the generated plugin, which can be used with
                \l QIfConfiguration to provide settings to the backend.
                Defaults to \c module.name
        \row
            \li
            \target config_simulator_simulationFile
            \code
            config_simulator:
                simulationFile: ":/qrc/simulation.qml"
            \endcode
            \li Accompanying YAML file
            \li Module
            \li Defines which simulation QML file the simulation backend should load. The snippet
                provided loads the QML file from the resource system, which the developer needs to
                embed.
        \row
            \li
            \target config_simulator_defaultServerMode
            \code
            config_simulator:
                defaultApplicationMode: "gui"
            \endcode
            \li Accompanying YAML file
            \li Module
            \li Defines the default mode used by the server generated from the
                \l{QtRemoteObjects Simulation Server}{server_qtro_simulator}
                template. Valid options are "gui" or "headless" (default).
        \row
            \li
            \code
            config_simulator:
                zones: [ Left,
                         Right
                       ]
            \endcode
            \li Accompanying YAML file
            \li Interface
            \li Defines a list of zones that the simulation code should support, for the backend
                simulator.
        \row
            \li
            \target config_simulator_default
            \code
            config_simulator:
            default:
                MyFlag.Value1 |
                MyFlag.Value2
            \endcode
            \li Accompanying YAML file
            \li Property
            \li Defines the initial values for the property returned by the simulator backend.

            For zoned properties, you can map a zone to a default value. The default key of the map
            is "=".
            \code
            config_simulator:
            default: {
                Left: 21.0,
                Right: 22.5,
                =: 0.0
            }
            \endcode
        \row
            \li \code
            config_simulator:
            minimum: 10
            \endcode
            \li Accompanying YAML file
            \li Property
            \li Defines the minimum value for integer and real properties; the generated code in
                the simulator backend validates the value.
        \row
            \li \code
            config_simulator:
            maximum: 10
            \endcode
            \li Accompanying YAML file
            \li Property
            \li Defines the maximum value for integer and real properties; the generated code in
                the simulator backend validates the value.
        \row
            \li \code
            config_simulator:
            range: [10, 20]
            \endcode
            \li Accompanying YAML file
            \li Property
            \li Defines the range value for integer and real properties; the generated code in the
                simulator backend validates the value.
        \row
            \li \code
            config_simulator:
            domain: {10, 20, 30}
            \endcode
            \li Accompanying YAML file
            \li Property
            \li Defines the possible values for the property; the generated code in the simulator
                backend validates the value.
        \row
            \li
            \target config_simulator_unsupported
            \code
            config_simulator:
            unsupported: yes
            \endcode
            \li Accompanying YAML file
            \li Property
            \li Defines whether the property is \c supported; the generated code in the simulator
                backend validates the value and reports a warning when you try to change an
                \c unsupported property.
    \endtable

    \section3 backend_qtro

    \table 100%
        \header
            \li Tag
            \li Where
            \li Object type
            \li Purpose
        \row
            \li
            \code
            config_qtro:
                serviceObjectId: "smarthome_qtro"
            \endcode
            \li Accompanying YAML file
            \li Module
            \li Defines the id of the generated plugin. See \l QIfServiceObject::id for more information.
                Defaults to \c module.name + "_qtro"
        \row
            \li
            \code
            config_qtro:
                configurationId: "smarthome"
            \endcode
            \li Accompanying YAML file
            \li Module
            \li Defines the configurationId of the generated plugin, which can be used with
                \l QIfConfiguration to provide settings to the backend.
                Defaults to \c module.name
    \endtable

    \section3 config_server_qtro

    \table 100%
        \header
            \li Tag
            \li Where
            \li Object type
            \li Purpose
        \row
            \li
            \target config_server_qtro_useGeneratedMain
            \code
            config_server_qtro:
                useGeneratedMain: true
            \endcode
            \li Accompanying YAML file
            \li Module
            \li Generates a main.cpp with common command-line options and a \l QIfRemoteObjectsConfig
                instance which is passed to a user-provided serverMain function.
    \endtable


    \section1 Structure for Generated Projects

    In the generator output directory, first, a new subfolder is created and named after the module ID.
    All the generated files are placed in this folder. The tables below describe the files that are
    generated for the frontend and backend.

    \section2 Frontend

    Generates a QML-friendly C++ API based on the \l {Dynamic Backend System}.

    \table 100%
        \header
            \li Filename
            \li Purpose
        \row
            \li {{module.module_name|lower}}global.h
            \li Standard file with global EXPORT defines.
        \row
            \li {{module.module_name|lower}}module.h/cpp
            \li Files defining a module class used for module global variables and types.
        \row
            \li {{module.module_name|lower}}module_enum.qdocinc
            \li Documentation for all values of all enums which can be included by qdoc.
        \row
            \li {{module.module_name|lower}}modulefactory.h/cpp
            \li Files defining a module factory class used for factory methods for all structs.
        \row
            \li {{module|lower|replace('.', '-')}}.pri
            \li A standard Qt \c{.pri} file that contains all the generated files. Use this
                \c{.pri} file to include the generated files into a qmake project.
        \row
            \li CMakeLists.txt
            \li File to integrate with the CMake build system. This file defines the rules
                how to build the generated files with CMake. In addition extra variables
                can be exposed by using \l {qt6_set_ifcodegen_variable}.
        \row
            \li qml/{{module|qml_type|replace('.', '/')}}/plugins.qmltypes
            \li QML code-completion file for use in QtCreator.
        \row
            \li {{interface|lower}}backendinterface.h/cpp
            \li Files defining the interface need to be implemented by the backend implementation
                of the feature.
        \row
            \li {{interface|lower}}.h/cpp
            \li Frontend implementation of the feature, ready to be used from QML.
        \row
            \li {{interface|lower}}_p.h
            \li Private part of the frontend implementation.
        \row
            \li {{struct|lower}}.h/cpp
            \li Frontend implementation for the struct, implemented as Q_GADGET.
    \endtable

    \section2 QML Plugin

    Generates a C++ QML Plugin which registers all types from the frontend in QML.

    \note For CMake this template has been superseded by the new QML type registration system.
    Please see \l {QML Type Registration} for more information.

    \table 100%
        \header
            \li Filename
            \li Purpose
        \row
            \li plugin.cpp
            \li The C++ QML Plugin class.
        \row
            \li {{module|lower|replace('.', '-')}}.pri
            \li A standard Qt \c{.pri} file that contains all the generated files. Use this
                \c{.pri} file to include the generated files into a qmake project.
        \row
            \li CMakeLists.txt
            \li File to integrate with the CMake build system. This file defines the rules
                how to build the generated files with CMake. In addition extra variables
                can be exposed by using \l {qt6_set_ifcodegen_variable}.
        \row
            \li plugins.qmltypes
            \li QML code-completion file for use in QtCreator.
        \row
            \li qmldir
            \li QML config file to register the plugin with the QML plugin system.
    \endtable

    \section2 Backend Simulator

    Provides a simulator backend using the QIfSimulationEngine to implement the simulation
    behavior in QML files.

    \table 100%
        \header
            \li Filename
            \li Purpose
        \row
            \li {{module.module_name|lower}}plugin.h/cpp
            \li Files defining implementation of QtInterfaceFramework backend plugin implementing
                QIfServiceInterface.
        \row
            \li {{module.module_name|lower}}.json
            \li File containing identifiers of the exposed feature interfaces needed by the Qt
                plugin system.
        \row
            \li {{module|lower|replace('.', '-')}}.pri
            \li A standard Qt \c{.pri} file that contains all the generated files. Use this \c{.pri}
                file to include the generated files into a qmake project.
        \row
            \li CMakeLists.txt
            \li File to integrate with the CMake build system. This file defines the rules
                how to build the generated files with CMake. In addition extra variables
                can be exposed by using \l {qt6_set_ifcodegen_variable}.
        \row
            \li {{module.module_name|lower}}_simulation.qml
            \li QML simulation file that loads the interface specific QML simulation files.
        \row
            \li {{module.module_name|lower}}_simulation_data.json
            \li Simulation data exported from the config_simulator annotations.
        \row
            \li {{module.module_name|lower}}.qrc
            \li Qt Resource file that contains the QML and JSON files.
        \row
            \li qml/{{module|qml_type|replace('.', '/')}}/plugins.qmltypes
            \li QML code-completion file for use in QtCreator.
        \row
            \li qml/{{module|qml_type|replace('.', '/')}}/simulation/plugins.qmltypes"
            \li QML code-completion file for use in QtCreator for the simulation API.
        \row
            \li {{interface|lower}}backend.h/cpp
            \li Files containing the implementation of the simulation backend.
        \row
            \li {{interface|upperfirst}}Simulation.qml
            \li Interface-specific QML simulation files.
    \endtable

    \section2 QtRemoteObjects Backend

    The backend_qtro template is only available if the QtRemoteObjects module was detected when building
    the qtinterfaceframework repository. This backend is a client for connecting to the remote backend
    server; not the location to implement the actual backend logic.

    \table 100%
        \header
            \li Filename
            \li Purpose
        \row
            \li {{module.module_name|lower}}plugin.h/cpp
            \li Files that define the implementation of the QtInterfaceFramework backend plugin, which implements
            QIfServiceInterface.
        \row
            \li {{module.module_name|lower}}.json
            \li File containing identifiers of the exposed feature interfaces needed by the Qt plugin
            system.
        \row
            \li {{module|lower|replace('.', '-')}}.pri
            \li A standard Qt \c{.pri} file that contains all the generated files. Use this \c{.pri}
            file to include the generated files into a qmake project. Also includes the \c{.rep} file
            to the project and calls the remote object compiler.
        \row
            \li CMakeLists.txt
            \li File to integrate with the CMake build system. This file defines the rules
                how to build the generated files with CMake. In addition extra variables
                can be exposed by using \l {qt6_set_ifcodegen_variable}.
        \row
            \li {{interface|lower}}backend.h/cpp
            \li Files containing the implementation of the remote object backend.
            Establishes the connection and initializes the remote object replica.
        \row
            \li {{interface|lower}}.rep
            \li The input file for Qt’s
            \l [QtRemoteObjects] {Qt Remote Objects Compiler} {replica compiler} to produce the
            replica class code.
        \row
            \li pagingmodel.rep
            \li The input file for Qt’s
            \l [QtRemoteObjects] {Qt Remote Objects Compiler} {replica compiler} to produce the
            replica class code for all models.
    \endtable

    \section2 QtRemoteObjects Server

    The server_qtro template is only available if the QtRemoteObjects module was detected when building
    the qtinterfaceframework repository. The code produced only contains the source classes to inherit
    and the code for establishing the connection. The developer must implement the actual backend logic.

    \table 100%
        \header
            \li Filename
            \li Purpose
        \row
            \li core.h/cpp
            \li Code for establishing the connection and starting the remoting for the source
                objects.
        \row
            \li {{srcBase|lower}}.pri
            \li A standard Qt \c{.pri} file that contains all the generated files. Use this \c{.pri}
                file to include the generated files into a qmake project. Also includes the \c{.rep}
                file to the project and calls the remote object compiler.
        \row
            \li CMakeLists.txt
            \li File to integrate with the CMake build system. This file defines the rules
                how to build the generated files with CMake. In addition extra variables
                can be exposed by using \l {qt6_set_ifcodegen_variable}.
        \row
            \li {{interface|lower}}.rep
            \li The input file for the Qt’s
            \l [QtRemoteObjects] {Qt Remote Objects Compiler} {replica compiler} to produce the
            source class code.
        \row
            \li pagingmodel.rep
            \li The input file for Qt’s
                \l [QtRemoteObjects] {Qt Remote Objects Compiler} {replica compiler} to produce the
                replica class code for all models.
    \endtable

    \section2 QtRemoteObjects Simulation Server

    The server_qtro template is only available if the QtRemoteObjects module was detected when building
    the qtinterfaceframework repository. The code produced contains a fully-implemented server that
    may use the same implementation as the backend_simulator template, which uses the QIfSimulationEngine
    to implement the simulation behavior in QML.

    By default a QCoreApplication is used in the generated server and enables the server to be
    run headless. To also allow instantiating UI controls inside the simulation QML code, the
    server can be started in GUI mode (--gui option). The default mode can be changed using the
    \l{config_simulator_defaultServerMode} annotation.

    \table 100%
        \header
            \li Filename
            \li Purpose
        \row
            \li {{module.module_name|lower}}_simulation.qml
            \li QML simulation file which loads the interface specific QML simulation files.
        \row
            \li {{module.module_name|lower}}_simulation_data.json
            \li Simulation data exported from the config_simulator annotations.
        \row
            \li {{module.module_name|lower}}.qrc
            \li Qt Resource file which contains the QML and JSON files.
        \row
            \li qml/{{module|qml_type|replace('.', '/')}}/plugins.qmltypes
            \li QML code-completion file for use in QtCreator.
        \row
            \li qml/{{module|qml_type|replace('.', '/')}}/simulation/plugins.qmltypes
            \li QML code-completion file for use in QtCreator for the simulation API.
        \row
            \li core.h/cpp
            \li Code for establishing the connection and starting the remoting for the source objects.
        \row
            \li main.cpp
            \li The main file.
        \row
            \li {{srcBase|lower}}.pri
            \li A standard Qt \c{.pri} file that contains all the generated files. Use this \c{.pri}
                file to include the generated files into a qmake project. Also includes the \c{.rep}
                file to the project and calls the remote object compiler.
        \row
            \li CMakeLists.txt
            \li File to integrate with the CMake build system. This file defines the rules
                how to build the generated files with CMake. In addition extra variables
                can be exposed by using \l {qt6_set_ifcodegen_variable}.
        \row
            \li {{interface|lower}}.rep
            \li The input file for the Qt’s
                \l [QtRemoteObjects] {Qt Remote Objects Compiler} {replica compiler} to produce the
                source class code.
        \row
            \li {{interface|lower}}adapter.h/cpp
            \li QtRemoteObjects Adapter classes for the backend implementations.
        \row
            \li pagingmodel.rep
            \li The input file for Qt’s
                \l [QtRemoteObjects] {Qt Remote Objects Compiler} {replica compiler} to produce the
            replica class code for all models.
        \row
            \li {{interface|lower}}backend.h/cpp
            \li Files that contain the simulation backend implementation.
        \row
            \li {{interface|upperfirst}}Simulation.qml
            \li Interface-specific QML simulation files.
    \endtable

    \section1 Backend specific configuration option

    Some of the generated backends can be provided with service settings using the
    \l QIfConfiguration class. The following table describes the available settings per template

    \section2 Backend Simulator

    The generated code doesn't have any service setting itself, but it forwards the serviceSettings
    to the QML simulation. A handwritten QML simulation can use the serviceSettings property
    of the BackendInterface object to change the behavior when such a setting is set.

    \section2 QtRemoteObjects Backend
    \target backend_qtro_configuration

    \table
    \header
        \li Name
        \li Description
    \row
        \li connectionUrl
        \li The url the interface tries to connect to using Qt Remote Objects. Defaults to
            \c {local + {{module.module_name|lower}}}.
            Changing this value at runtime will reconnect the backend to the new URL.
    \row
        \li connectionTimeout
        \li Defines when a timeout warning should be printed (in milliseconds).
            To disable the warning set the timeout to -1.
    \endtable

    In addition to those global settings, the values can also be provided per backend interface and
    this allows the backend to connect to multiple remote object instances. Interface specific
    settings need to be prefixed with the interface name. The following example creates a
    Configuration, which is applied to all Items that are part of the \c cluster group.
    The service settings applied to the currently connected backend use a global \c
    connectionTimeout and a specific \c connectionUrl for the InstrumentCluster interface in the
    cluster module, while all other interfaces use the default \c connectionUrl:

    \badcode
    InterfaceFrameworkConfiguration {
        name: "cluster"
        serviceSettings: {
            "connectionTimeout": 1000,
            "cluster.InstrumentCluster": {
                "connectionUrl": "tcp://127.0.0.1:1234"
            }
        }
    }

    Instead of providing settings per interface, it is also possible to provide the settings on a
    per module basis using the module name as a key.
    \endcode
*/