Skip to content

Using Qt3D

Felix Richter edited this page Aug 11, 2020 · 5 revisions

Using Qt3D

RBDL-Toolkit uses the Qt3D framework to create 3D scenes displaying the models and other data. In this article i will give a brief overview on how to use Qt3D and give links to some additional resources.

Basics

Normally when creating 3D scenes as a programmer you need to be familiar with OpenGL and graphics programming, which involves a lot of math and deals with the lower levels of how 3D data is represented in memory.

With Qt3D you don't need to deal with this. Instead we can describe our scene and our view as a tree of objects, that describe what objects are in the scene, which material they have and where the camera is positioned. So basically we can just describe the parts of our scene and the Qt3D rendering engine will do all the hard work of actually displaying the scene correctly.

Displaying an Object in the Scene

Every Object we want to display is described as an QEntity object in Qt3D. The QEntity acts as a container for different QComponents that then describe what the object is all about. For example there is a QMesh component, that can be given an meshfile to be displayed. There is also a QTransform component which is used to describe the position of the QEntity relative to it's parent component.

Qt3D Entity Structure

The picture shows some of the components available to Entities, up to this point RBDL-Toolkit mostly only uses Transforms, Meshes, and Materials.

When displaying a scene we give the forward renderer of Qt3d one root QEntity which acts as the scene root. Every QEntity that needs to be displayed is a child of the root entity and is positioned and displayed according to its components relative to it. Of course every child entity may have more children creating the scene tree.

Adding Visuals to models

So we covered the basics of how Qt3D works, and there is a lot more to be learned about Qt3D, because there is also another tree structure describing not the scene but how it gets displayed. But for the purposes of this Wiki article this is not so interesting. Instead since RBDL-Toolkit is based around RBDL-Models let us talk about how to add new visuals to an existing loaded model.

Static Visuals

The simplest thing you can do is add a static visual to a model, that has a fixed position on one of the model segments. When interacting with and RBDL-Model within RBDL-Toolkit you will be interacting with the RBDLModelWrapper class. It has a function void addStaticVisual(std::string segment_name, Qt3DCore::QEntity* visual); to do this. So all we need to do is create an new QEntity fill it with the required components and call this function with the segment name we wish to add the visual to:

// create new entity 
Qt3DCore::QEntity* visual = new QEntity;
//setting the property Scene.ObjGroup enables disabling/enabling rendering of the visual via the render selection dialog
visual->setProperty("Scene.ObjGroup", QVariant("StaticVisual"));

//create a material component and set color
Qt3DExtras::QPhongAlphaMaterial* material = new Qt3DExtras::QPhongAlphaMaterial;
material->setAmbient(color);
material->setAlpha((float)color.alpha() / 255.);

//create Transform and set visual position
Qt3DCore::QTransform* position = new Qt3DCore::QTransform;
position->setTranslation(QVector3D(p[0], p[1], p[2]));
position->setScale(size);

//create Mesh and set source file
Qt3DRender::QMesh* mesh = new QMesh;
mesh->setSource(QUrl::fromLocalFile(findFile(QString("unit_sphere_medres.obj"))));

// add components to entity
visual->addComponent(mesh);
visual->addComponent(position);
visual->addComponent(material);

//display visual by adding it as a static visual to the model
model->addStaticVisual("UpperBody", marker_visual);

Updating Visuals

If you need to update your visuals in sync with the timeline you will need to create a WrapperExtention and add it to the model. These extensions are used to keep track of everything we might want to do with a model, like the animation data, or force and torque data, but they are also used to display this extra information. Since this is a common task when building new things for RBDL-Toolkit there is a seperate Wiki Article about them. Creating Visuals is the same process, but if you want to update them it is best to save pointers to the components that you want to update within your WrapperExtention subclass. Updating them is then just a matter of calling the components functions to for example change the position of the Transform. Qt3D will then automatically update the visual.

Additional Resources

Overview Qt3D Part 1
Overview Qt3D Part 2
Qt3D Advanced Rendering Whitepaper

Clone this wiki locally