Manipulating Object and Value Types
inject-code
The
inject-codenode inserts the given code into the generated code for the given type or function, and it is a child of the object-type, value-type, modify-function and add-function nodes. It may contain insert-template child nodes.<inject-code class="native | target" position="beginning | end" since="..." file="[file]" snippet="[label]"/>The
classattribute specifies which module of the generated code that will be affected by the code injection (see Code Generation Terminology). Theclassattribute accepts the following values:
native: The c++ code
target: The binding codeIf the
positionattribute 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.For a detailed description of how to above attributes interact, see Code Injection Semantics.
The optional
fileattribute specifies the file name (see Using Snippets From External Files).The optional
snippetattribute specifies the snippet label (see Using Snippets From External Files).There are a number of placeholders which are replaced when injecting code (see Type System Variables).
There are severals ways to specify the code:
Embedding Code into XML
The code can be embedded into XML (be careful to use the correct XML entities for characters like ‘<’, ‘>’, ‘&’):
<value-type> <inject-code class="native | target" position="beginning | end" since="..."> // the code </inject-code> </value-type>
Using a Template Specified in XML
It is possible to create code templates for reuse in XML (see Using Code Templates). This allows for replacing of custom placeholders.
<value-type> <inject-code class="native | target" class="native | target"> <insert-template name="template_name"/> </inject-code> </value-type>
Using Snippets From External Files
Code snippets can also be retrieved from external files found in the typesystem search path (see typesystem-paths).
<value-type> <inject-code class="native | target" position="beginning | end" since="..." file="external_source.cpp" snippet="label"/> </value-type>In the external file
external_source.cpp, the code between annotations of the form:// @snippet label ... // @snippet labelwill be extracted.
modify-field
The
modify-fieldnode allows you to alter the access privileges for a given C++ field when mapping it onto the target language, and it is a child of an object-type or a value-type node.<object-type> <modify-field name="..." write="true | false" read="true | false" remove="true | false" opaque-container = "yes | no" snake-case="yes | no | both" /> </object-type>The
nameattribute is the name of the field, the optionalwriteandreadattributes specify the field’s access privileges in the target language API (both are set to true by default).The
removeattribute is an optional boolean attribute, which can mark the field to be discarded on generation.The optional
renameattribute can be used to change the name of the given field in the generated target language API.The optional
opaque-containerattribute specifies whether an opaque container should be returned on read access (see Opaque Containers).The optional snake-case attribute allows for overriding the value specified on the class entry or typesystem element.
modify-function
The
modify-functionnode allows you to modify a given C++ function when mapping it onto the target language, and it is a child of a function, namespace-type, object-type or a value-type node. Use the modify-argument node to specify which argument the modification affects.<object-type> <modify-function signature="..." since="..." remove="true | false" access="public | private | protected" allow-thread="true | auto | false" exception-handling="off | auto-off | auto-on | on" overload-number="number" rename="..." snake-case="yes | no | both" /> </object-type>The
signatureattribute is a normalized C++ signature, excluding return values but including potential const declarations. It is not required whenmodify-functionappears as a child of a function node to modify a global function.The
sinceattribute specify the API version when this function was modified.The
allow-threadattribute specifies whether a function should be wrapped intoPy_BEGIN_ALLOW_THREADSandPy_END_ALLOW_THREADS, that is, temporarily release the GIL (global interpreter lock). Doing so is required for any thread-related function (wait operations), functions that might call a virtual function (potentially reimplemented in Python), and recommended for lengthy I/O operations or similar. It has performance costs, though. The valueautomeans that it will be turned off for functions for which it is deemed to be safe, for example, simple getters. The attribute defaults tofalse.The
exception-handlingattribute specifies whether to generate exception handling code (nest the function call into try / catch statements). It accepts the following values:
no, false: Do not generate exception handling code
auto-off: Generate exception handling code for functions declaring a non-empty
throwlistauto-on: Generate exception handling code unless function declares
noexceptyes, true: Always generate exception handling code
The optional
overload-numberattribute specifies the position of the overload when checking arguments. Typically, when a number of overloads exists, as for in example in Qt:void QPainter::drawLine(QPointF, QPointF); void QPainter::drawLine(QPoint, QPoint);they will be reordered such that the check for matching arguments for the one taking a
QPointis done first. This is to avoid a potentially costly implicit conversion fromQPointtoQPointFwhen using the 2nd overload. There are cases though in which this is not desired; most prominently when a class inherits from a container and overloads exist for both types as is the case for theQPolygonclass:class QPolygon : public QList<QPoint> {}; void QPainter::drawPolygon(QPolygon); void QPainter::drawPolygon(QList<QPoint>);By default, the overload taking a
QListwill be checked first, trying to avoid constructing aQPolygonfromQList. The type check for a list of points will succeed for a parameter of typeQPolygon, too, since it inheritsQList. This presents a problem since the sequence type check is costly due to it checking that each container element is aQPoint. It is thus preferable to check for theQPolygonoverload first. This is achieved by specifying numbers as follows:<object-type name="QPainter"> <modify-function signature="drawPolygon(QPolygon)" overload-number="0"/> <modify-function signature="drawPolygon(QList<QPoint>)" overload-number="1"/> </object-type>Numbers should be given for all overloads; otherwise, the order will be in declaration order.
The
removeattribute is an optional boolean attribute, which can mark the function to be discarded on generation.The optional
renameattribute can be used to change the name of the given function in the generated target language API.The optional
accessattribute changes the access privileges of the given function in the generated target language API.The optional snake-case attribute allows for overriding the value specified on the class entry or typesystem element.
add-function
The
add-functionnode allows you to add a given function onto the target language, and it is a child of an object-type or value-type nodes if the function is supposed to be a method, or namespace-type and typesystem if the function is supposed to be a function inside a namespace or a global function.Typically when adding a function some code must be injected to provide the function logic. This can be done using the inject-code node.
<object-type> <add-function signature="..." return-type="..." access="public | protected" static="yes | no" classmethod="yes | no" since="..."/> </object-type>The
return-typeattribute defaults to void, theaccessto public and thestaticone to no.The
sinceattribute specifies the API version when this function was added.The
classmethodattribute specifies whether the function should be a Python class method. It sets the METH_CLASS flag which means thatPyTypeObjectinstead of an instancePyObjectis passed as self, which needs to be handled in injected code.Note that the label “static” in Qt’s class documentation almost always means that a Python
classmethodshould be generated, because an object’s class is always accessible from the static C++ code, while Python needs the explicit “self” parameter thatclassmethodprovides.Within the signature, names for the function parameters can be specified by enclosing them within the delimiter @:
void foo(int @parameter1@,float)See Sequence Protocol for adding the respective functions.
declare-function
The
declare-functionnode allows you to declare a function present in the type and it is a child of an object-type or value-type nodes if the function is supposed to be a method, or namespace-type and typesystem if the function is supposed to be a function inside a namespace or a global function.<container-type> <declare-function signature="..." return-type="..." since="..."/> </container-type>The
return-typeattribute defaults to void.The
sinceattribute specifies the API version when this function was added.This is useful to make functions known to shiboken which its code parser does not detect. For example, in Qt 6, the
append()function of theQList<T>container takes an argument ofparameter_typewhich is specialized toTfor simple types andconst T &for complex types by some template expression which the code parser cannot resolve. In that case, the function can be declared with a simple signature:<container-type name="QList"> <declare-function signature="append(T)"/> </container-type>This tells shiboken a public function of that signature exists and bindings will be created in specializations of
QList.
property
The
propertyelement allows you to specify properties consisting of a type and getter and setter functions.It may appear as a child of a complex type such as object-type or value-type.
If the PySide6 extension is not present, code will be generated using the
PyGetSetDefstruct, similar to what is generated for fields.If the PySide6 extension is present, those properties complement the properties obtained from the
Q_PROPERTYmacro in Qt-based code. The properties will be handled inlibpysideunless code generation is forced.<property name="..." type="..." get="..." set="..." generate-getsetdef="yes | no" since="..."/>The
nameattribute specifies the name of the property, thetypeattribute specifies the C++ type and thegetattribute specifies the name of the accessor function.The optional
setattribute specifies name of the setter function.The optional
generate-getsetdefattribute specifies whether to generate code for if the PySide6 extension is present (indicating this property is not handled by libpyside). It defaults to no.The optional
sinceattribute specifies the API version when this property appears.For a typical C++ class, like:
class Test { public: int getValue() const; void setValue(); };
valuecan then be specified to be a property:<value-type name="Test"> <property name="value" type="int" get="getValue" set="setValue"/>With that, a more pythonic style can be used:
test = Test() test.value = 42For Qt classes (with the PySide6 extension present), additional setters and getters that do not appear as
Q_PROPERTY, can be specified to be properties:<object-type name="QMainWindow"> <property name="centralWidget" type="QWidget *" get="centralWidget" set="setCentralWidget"/>in addition to the normal properties of
QMainWindowdefined for Qt Designer usage.Note
In the Qt coding style, the property name typically conflicts with the getter name. It is recommended to exclude the getter from the wrapper generation using the
removefunction modification.

