|  | Home · Overviews · Examples

# The Qt Jambi Type System

The type system is used when mapping a C++ based library onto a corresponding Java library using the Qt Jambi generator.

The developer can define the scope of the Java API by writing a type system specification. The specification is a handwritten XML document listing the types that will be available in the generated Java API; types that are not declared in the specification will be ignored along with everything that depends on them. In addition, it is possible to manipulate and modify the types and functions. It is even possible to use the type system specification to inject arbitrary code into the source files, such as an extra member function.

The type system specification is passed as an argument to the generator.

Below is a complete reference guide to the various nodes of the type system. For examples of use, take a look at the type system files used to generate the Qt Jambi API. These files can be found in the `generator` directory of the Qt Jambi package.

- Alphabetical List
- Specifying Types

- Value Type Requirements
- Manipulating Object and Value Types
- Manipulating Namespace and Interface Types
- Manipulating Enum Types

- Modifying Functions

- Modifying Arguments

- Using Code Templates

See also: Qt Jambi Generator Example

## Alphabetical List

access, argument-map, conversion-rule, custom-constructor, custom-destructor, define-ownership, enum-type, extra-includes, include, inject-code, insert-template, interface-type, load-typesystem (multiple type system), modify-argument, modify-field, modify-function, namespace-type, object-type, primitive-type, reject-enum-value, rejection, remove, remove-argument, remove-default-expression, rename, replace, replace-default-expression, replace-type, suppress-warning, template, typesystem, value-type

## Specifying Types

Node | Description
--- | ---
typesystem | The `typesystem` node is the root node containing all the type system information.
    <typesystem package="..."
        default-superclass="..." (optional)>
    </typesystem>
The `package` attribute is a string describing the package to be used, e.g.,`"com.trolltech.qt.core"`. The optional `default-superclass` attribute is the complete class name of the default baseclass of all objects in Java, e.g., `"com.trolltech.qt.QtJambiObject"`.
load-typesystem | The `load-typesystem` node specifies which type systems to load when mapping multiple libraries to Java or basing one library on another, and is a child of the typesystem node.
    <typesystem ...>
        <load-typesystem name="..."
            generate="yes | no">
    </typesystem>
The `name` attribute is the filename of the type system to load, the `generate` attribute specifies whether code should be generated or not. The latter must be specified when basing one library on another, making the generator able to understand inheritance hierarchies, primitive mapping, parameter types in functions etc. Most libraries will be based on both the QtCore and QtGui modules, in which case code generation for these libraries will be disabled.
rejection | The `rejection` node rejects the given class, or the specified function or field, and is a child of the typesystem node.
    <typesystem ...>
        <rejection class="..."
            function-name="..." (optional)
            field-name="..." (optional) />
    </typesystem>
The `class` attribute is the C++ class name of the class to reject. Use the optional `function-name` or `field-name` attributes to reject a particular function or field. Note that the `field-name` and `function-name` cannot be specified at the same time. To remove all occurrences of a given field or function, set the `class` attribute to `*`.
primitive-type | The `primitive-type` node describes how a primitive type is mapped from C++ to Java and the Java Native Interface (JNI), and is a child of the typesystem node. Note that most primitives are already specified in the QtCore type system.
    <typesystem ...>
        <primitive-type name="..."
            java-name="..." (optional)
            jni-name="..." (optional)
            preferred-conversion="yes | no" (optional)>
    </typesystem>
The `name` attribute is the name of the primitive in C++, the `java-name` attribute is the name of the primitive in Java, and the `jni-name` attribute is the name of the primitive in JNI. If the latter two attributes are not specified, their default value will be the same as the `name` attribute. If the optional `preferred-conversion` attribute is set to "no", it indicates that this version of the primitive is not the preferred C++ equivalent of the Java type. For example, both "qint64" and "long long" become "long" in Java but we should prefer the "qint64" version. For this reason we mark "long long" with `preferred-conversion="no"`.
namespace-type | The `namespace-type` node maps the given C++ namespace to Java ( note that the namespace becomes an interface in Java), and is a child of the typesystem node. Note that within namespaces, the generator only supports enums (i.e., no functions or classes).
    <typesystem ...>
        <namespace-type name="..."
            package="..." (optional)
            expense-cost="..." (opt)
            expense-limit="..." (opt)/>
    </typesystem>
The `name` attribute is the name of the namespace, e.g., "Qt". The `package` attribute can be used to override the package of the type system. The `expense-cost` attribute specifies the memory cost of using an instance of the given type, allowing the garbage collector to optimize the memory management. The cost is specified using Java code. The `expense-limit` attribute specifies how much an instance's memory consumption must be before the garbage collector is activated (the memory consumption is calculated using the value of the `expense-cost` attribute).
enum-type | The `enum-type` node maps the given enum from C++ to Java, and is a child of the typesystem node. Use the reject-enum-value to reject values.
    <typesystem ...>
        <enum-type name="..."
            flags="yes | no" (optional)
            lower-bound="..." (optional)
            upper-bound="..." (optional)
            force-integer="yes | no" (optional)
            extensible="yes | no" (optional)/>
    </typesystem>
The `name` attribute is the fully qualified C++ name of the enum (e.g.,"Qt::FillRule"). If the optional `flags` attribute is set to `yes` (the default is `no`), the generator will expect an existing QFlags<T> for the given enum type. The `lower-bound` and `upper-bound` attributes are used to specify runtime boundschecking for the enum value. The value must be a compilable java statement, such as "QGradient.Spread.PadSpread". If the `force-integer` attribute is set to `yes` (the default is `no`), the generated Java code will use integers instead of Java enums. And finally, the `extensible` attribute specifies whether the given enum can be extended with user values (the default is `no`).
value-type | The `value-type` node indicates that the given C++ type is mapped onto Java as a value type, and is a child of the typesystem node.
    <typesystem ...>
        <value-type  name="..."
            package ="..." (optional)
            default-superclass ="..." (optional)
            polymorphic-base="yes | no" (opt)
            polymorphic-id-expression="..." (opt)
            expense-cost="..." (opt)
            expense-limit="..." (opt)/>
    </typesystem>
The `name` attribute is the fully qualified C++ class name, such as "QMatrix" or "QPainterPath::Element". The `package` attribute can be used to override the package of the type system. If there is no C++ base class, the `default-superclass` attribute can be used to specify a superclass for the given type, in the generated Java API. The `polymorphic-base` and `polymorphic-id-expression` attributes have the same meaning as the object-type node, and the `expense-cost` and `expense-limit` attributes have the same meaning as for the namespace-type node.
object-type | The `object-type` node indicates that the given C++ type is mapped onto Java as an object type, and is a child of the typesystem node.
    <typesystem ...>
        <object-type name="..."
            package ="..." (optional)
            default-superclass ="..." (optional)
            polymorphic-base="yes | no" (opt)
            polymorphic-id-expression="..." (opt)
            expense-cost="..." (opt)
            expense-limit="..." (opt)/>
    </typesystem>
The `name` attribute is the fully qualified C++ class name. The `package` attribute can be used to override the package of the type system. If there is no C++ base class, the `default-superclass` attribute can be used to specify a superclass for the given type, in the generated Java API. The `polymorphic-base` attribute is used to specify the base class for polymorphic types that do not inherit QObject (like QEvent), i.e. types that do not support introspection. By specifying the base class, introspection is enabled, provided that the subclasses sets the `polymorphic-id-expression` attribute. For example:
    <object-type name="QEvent" polymorphic-base="yes" />
    <object-type name="QTimerEvent"
                 polymorphic-id-expression="%1->type() == QEvent::Timer)" />
The `polymorphic-id-expression` attribute specifies code that determines which subclass, in a polymorphic hierarchy, an object belongs to. Instances of `%1` in the code will be replaced by the name of the object in question. The `expense-cost` and `expense-limit` attributes have the same meaning as for the namespace-type node.
interface-type | The `interface-type` node indicates that the given class is replaced by an interface pattern when mapping from C++ to Java. It is used to resolve multiple base classes which is not supported by Java. Using the `interface-type` node implicitly makes the given type an object type.
    <typesystem ...>
        <interface-type name="..."
            package ="..." (optional)
            default-superclass ="..." (optional)
            polymorphic-base="yes | no" (opt)
            polymorphic-id-expression="..." (opt)
            expense-cost="..." (opt)
            expense-limit="..." (opt)/>
    </typesystem>
The `name` attribute is the fully qualified C++ class name. The `package` attribute can be used to override the package of the type system. If there is no C++ base class, the `default-superclass` attribute can be used to specify a superclass in the generated Java API, for the given class. The `polymorphic-base` and `polymorphic-id-expression` attributes have the same meaning as the object-value node, and the `expense-cost` and `expense-limit` attributes have the same meaning as for the namespace-type node.
suppress-warning | The generator will generate several warnings which may be irrelevant to the user. The `suppress-warning` node suppresses the specified warning, and is a child of the typesystem node.
    <typesystem...>
        <suppress-warning text="..." />
    </typesystem>
The `text` attribute is the warning text to suppress, and may contain the `*` wildcard (use "" to escape regular expression matching if the warning contain a regular "*").
template | The `template` node registers a template that can be used to avoid duplicate code when extending the generated code, and is a child of the typesystem node.
    <typesystem>
        <template name="my_template">
            // the code
        </template>
    </typesystem>
Use the insert-template node to insert the template code (identified by the template's `name` attribute) into the generated code base.

### Value Type Requirements

Node | Description
--- | ---
custom-constructor | In Java, value types are required to have a copy constructor. If a C++ class without a copy constructor is mapped onto Java as a value type, it is possible to provide a custom constructor using the `custom-constructor` node which is a child of the `value-type` node.
    <value-type ...>
        <custom-constructor
             name="..." (optional)
             param-name="..." (optional)>
                // code for custom constructor
        </custom-constructor>
    </value-type>
The custom constructor's signature becomes:
     T *name(T *param-name);
If not specified the name of the constructor becomes `<lowercase type name>_create()` and the parameter name becomes `copy`.
custom-destructor | When a custom constructor is provided using the custom-constructor node, it is most likely required to clean up the allocated memory. For that reason, it is also possible to provide a custom destructor using the `custom-destructor` node which is a child of the `value-type` node.
    <value-type ...>
        <custom-destructor
             name="..." (optional)
             param-name="..." (optional)>
                // code for custom destructor
        </custom-destructor>
    </value-type>
The custom destructor must have the following signature:
     T *name(T *param-name);
If not specified the name of the destructor becomes `<lowercase type name>_delete()` and the parameter name becomes `copy`.
insert-template | Documented in the Using Code Templates section

### Manipulating Object and Value Types

Node | Description
--- | ---
inject-code | The `inject-code` node inserts the given code into the generated code for the given type or function, and is a child of the object-type, value-type and modify-function nodes.
     <value-type ...>
         <inject-code class="java | native | shell | shell-declaration"
             position="beginning | end">
             // the code
         </inject-code>
     </value-type>
The `class` attribute specifies which module of the generated code that will be affected by the code injection. The `class` attribute accepts the following values: `java`: The generated java code `native`: The generated JNI-based methods `shell`: The generated shell class `shell-declaration`: The code will be injected into the generated header file containing the shell class definition. If the position attribute is set to `beginning` (the default), the code is inserted at the beginning of the function. If it is set to `end`, the code is inserted at the end of the function.
modify-field | The `modify-field` node allows you to alter the access privileges for a given C++ field when mapping it onto Java, and is a child of an object-type or a value-type node.
     <object-type ...>
         <modify-field name="..."
             write="true | false" (optional)
             read="true | false" (optional)/>
     </object-type>
The `name` attribute is the name of the field, the optional `write` and `read` attributes specify the field's access privileges in the Java API (both are set to `true` by default).
modify-function | The `modify-function` node allows you to modify a given C++ function when mapping it onto Java, and is a child of an object-type or a value-type node. Use the modify-argument node to specify which argument the modification affects.
     <object-type ...>
         <modify-function signature="..."
                          remove="all | java"
                          access="public | private | protected"
                          rename="..." >
     </object-type>
The `signature` attribute is a normalized C++ signature, excluding return values but including potential `const` declarations. The `remove`, `access` and `rename` attributes are optional attributes for added convenience; they serve the same purpose as the tags remove, access and rename.
include | Documented in the Manipulating Namespace and Interface Types section
extra-includes | Documented in the Manipulating Namespace and Interface Types section
insert-template | Documented in the Using Code Templates section

### Manipulating Namespace and Interface Types

Node | Description
--- | ---
extra-includes | The `extra-includes` node contains declarations of additional include files, and can be a child of the interface-type, namespace-type, value-type and object-type nodes. The generator automatically tries to read the global header for each type. But sometimes it is required to include extra files in the generated C++ code to make sure that the code compiles. These files must be listed using include nodes witin the `extra-include` node:
     <value-type ...>
         <extra-includes>
             <include file-name="..." location="global | local | java"/>
         </extra-includes>
     </value-type>
The `file-name` attribute is the file to include, such as "QStringList". The `location` attribute is where the file is located: `global` means that the file is located in `$INCLUDEPATH` and will be included using `#include <...>`, `local` means that the file is in a local directory and will be included using `#include "..."`. If the `location` is set to `java` then the `file-name` attribute is expected to contain the fully qualified name for a java class and the specified class will be imported in the generated java code.
include | The `include` node specifies the name and location of a file that must be included, and is a child of the interface-type, namespace-type, value-type, object-type or extra-includes nodes The generator automatically tries to read the global header for each type. Use the `include` node to override this behavior, providing an alternative file. The `include` node can also be used to specify extra include files.
     <value-type ...>
         <include file-name="..."
             location="global | local | java"/>
     </value-type>
The `file-name` attribute is the file to include, such as "QStringList". The `location` attribute is where the file is located: `global` means that the file is located in `$INCLUDEPATH` and will be included using `#include <...>`, `local` means that the file is in a local directory and will be included using `#include "..."`. If the `location` attribute is set to `java` in this particular case, it will be ignored.

### Manipulating Enum Types

Node | Description
--- | ---
reject-enum-value | The `reject-enum-value` node rejects the enum value specified by the `name` attribute, and is a child of the enum-type node.
     <enum-type ...>
         <reject-enum-value name="..."/>
     </enum-type>
This node is used when a C++ enum implementation has several identical numeric values, some of which are typically obsolete.

## Modifying Functions

Node | Description
--- | ---
modify-argument | The `modify-argument` node specifies which of the given function's arguments the modification affects, and is a child of the modify-function node. Use the remove-argument, replace-default-expression, remove-default-expression, replace-type, reference-count and define-ownership nodes to specify the details of the modification.
     <modify-function ...>
         <modify-argument index="return | this | 1 ..."
              invalidate-after-use="yes | no" (optional) >
             modifications
         </modify-argument>
     </modify-function>
Set the `index` attribute to "1" for the first argument, "2" for the second one and so on. Alternatively, set it to "return" or "this" if you want to modify the function's return value or the object the function is called upon, respectively. The `invalidate-after-use` attribute is optional and defaults to "no". Setting it to "yes" is only applicable for modifications to virtual functions and will cause the Java object passed as the argument to be invalidated after the virtual function call is complete, if the object is owned by C++ and not by Java. This is used as a measure against crashes caused by users retaining references to objects that are later deleted in the underlying C++ code.
remove | The `remove` node removes the given method from the generated Java code, and is a child of the modify-function node.
     <modify-function ...>
         <remove class="all | java" />
     </modify-function>
If the `class` attribute is set to "java", the function is only removed for the generated java code; the default value is "all".
access | The `access` node changes the access privileges of the given function in the generated Java code, and is a child of the modify-function node.
     <modify-function ...>
         <access modifier="public | protected | private"/>
     </modify-function>
rename | The `rename` node changes the name of the given function in the generated Java code, and is a child of the modify-function node.
     <modify-function...>
         <rename to="..." />
     </modify-function>
The `to` attribute is the new name of the function.
inject-code | Documented in the Manipulating Types section
argument-map | The `argument-map` node maps a C++ argument name to the argument name used in the generated Java code, and is a child of the inject-code node when the latter is a child of a modify-function node.
     <modify-function...>
         <inject-code ...>
             <argument-map index="numeric value"
                 meta-name="string value">
         </inject-code>
     </modify-function>
The `index` attribute is an index, starting at 1, indicating the argument position to which this argument mapping applies. The `meta-name` attribute is the name used within the code injection to adress the argument at the given position.

### Modifying Arguments

Node | Description
--- | ---
remove-argument | The `remove-argument` node removes the given argument from the function's signature, and is a child of the modify-argument node.
     <modify-argument ...>
         <remove-argument />
     </modify-argument>
Typically, when removing an argument, some conversion rules must be specified, e.g., when converting from Java to C++. This can be done using the conversion-rule node.
remove-default-expression | The `remove-default-expression` node disables the use of the default expression for the given argument, and is a child of the modify-argument node.
     <modify-argument...>
         <remove-default-expression />
     </modify-argument>
replace-default-expression | The `replace-default-expression` node replaces the specified argument with the expression specified by the `with` attribute, and is a child of the modify-argument node.
     <modify-argument...>
         <replace-default-expression with="..." />
     </modify-argument>
replace-type | The `replace-type` node replaces the type of the given argument to the one specified by the `modified-type` attribute, and is a child of the modify-argument node.
     <modify-argument...>
         <replace-type modified-type="..." />
     </modify-argument>
If the new type is a class, the `modified-type` attribute must be set to the fully qualified name (including name of the package as well as the class name). Typically, when changing the type of an argument, some conversion rules must be specified. This can be done using the conversion-rule node.
reference-count | The `reference-count` tag indicates that the function holds a reference to the argument object without assuming ownership of it.
     <modify-argument ...>
         <reference-count action="add | add-all | remove | set | ignore"
                          variable-name="..."
                          declare-variable="..."
                          conditional="..."
                          access="public | private | protected | friendly" />
     </modify-argument>
The `action` attribute specifies the action to be taken. `add`, `add-all` and `remove` are collection actions. They will add a single object to a list of references, add all objects in a collection to a list of references or remove a single object from a list of references. `set` will assign the argument to the variable containing the reference (the argument must be a collection if the variable is also used for any of the collection specific actions.) `ignore` will not inject any code, but will cause the method in question to be removed from the log of possible reference counting API. The `variable-name` attribute specifies the name used for the variable that holds the reference(s). The `declare-variable` attribute can be used to specify the fully qualified name of the class that owns the reference. This attribute is optional, and should only be specified if the variable should not be declared in the current class. The specified must be in the superclass hierarchy of the current class. The `conditional` attribute is optional, and specifies a conditional expression which must be true in order for the action of the `reference-count` tag to be taken. The `access` attribute gives the visibility of the variable. Only applicable if `declare-variable` is not specified. The default value of `access` is `private`.
define-ownership | The `define-ownership` tag indicates that the function changes the ownership rules of the arguemnt object. The `class` attribute specifies the class of function in which to inject the ownership altering code. The `owner` attribute specifies the new ownership of the object. It accepts the following values: `java`: Java will assume full ownership of the object. The native resources will be deleted when the Java object is finalized. `c++`: The native code assumes full ownership of the object. The Java object will not be garbage collected. `default`: The object will get default ownership, depending on how it was created.
     <modify-argument ...>
          <define-ownership class="java | shell"
                            owner="java | c++ | default" />
     </modify-argument>
conversion-rule | The `conversion-rule` node allows you to write customized code to convert the given argument between Java and C++, and is a child of the modify-argument node.
     <modify-argument ...>
          <conversion-rule class="shell | native">
             // the code
          </conversion-rule>
     </modify-argument>
This node is typically used in combination with the replace-type and remove-argument nodes. The given code is used instead of the generator's conversion code in the following situations (defined by the modify-argument node's `index` attribute and the `class` attribute as well the function implementation and where the function is called from):
Argument Index | Function Class | Function Implementation | Caller Location
--- | --- | --- | ---
1 | 2 ... | shell | Java (overriding C++) | C++
1 | 2 ... | native | C++ | Java
return | shell | C++ | Java
return | native | Java (overriding C++) | C++
Writing `%N` in the code (where `N` is a number), will insert the name of the nth argument. Alternatively, `%in` and `%out` which will be replaced with the name of the conversion's input and output variable, respectively. Note the output variable must be declared explicitly, for example:
     <conversion-rule class="native">
         bool %out = (bool) %in;
     </conversion-rule>
insert-template | Documented in the Using Code Templates section
replace-value | The `replace-value` attribute lets you replace the return statement of a function with a fixed string. This attribute can only be used for the argument at index 0, which is always the function's return value. Here is an example of how to use `modify-argument`:
     <modify-argument index="0" replace-value="this"/>

## Using Code Templates

Node | Description
--- | ---
insert-template | The `insert-template` node includes the code template identified by the `name` attribute, and can be a child of the inject-code, conversion-rule, template, custom-constructor and custom-destructor nodes. For example;
     <inject-code class="java" position="beginning">
         <insert-template name="my_template" />
     </inject-code>
Use the replace node to modify the template code.
replace | The `replace` node allows you to modify template code before inserting it into the generated code, and can be a child of the insert-template node.
     <insert-template name="my_template">
         <replace from="..." to="..." />
     </insert-template>
Using this node the code specified by the `from` attribute is altered into the code specified by the `to` attribute.