Hi everyone,
I am trying to get VTK to work in a Multithreaded environment. My goal is to display roughly 6k Vertices as a Mesh that is rendered as a regular 3d Object with indices. The rendered Data comes from a ZeroMQ socket in another thread and gets transferred via some Qt Signal. But when I execute the code I get the following error after maximum 30 Seconds of runtime:
malloc(): invalid size (unsorted) or malloc(): corrupted top size
This is the rendered class:
class VtkSMPLActor {
const static vtkNew<vtkNamedColors> colors;
mutable std::mutex mutex;
vtkNew<vtkCellArray> polys;
vtkNew<vtkPoints> points;
vtkNew<vtkPolyData> smplPolyData;
vtkNew<vtkPolyDataMapper> mapper;
vtkNew<vtkActor> actor;
public:
explicit VtkSMPLActor(const RenderableSMPLData &data);
void setData(const RenderableSMPLData &data);
void addToRenderer(vtkRenderer &renderer) const;
};
VtkSMPLActor::VtkSMPLActor(const RenderableSMPLData &data) {
this->smplPolyData->SetPolys(this->polys);
this->smplPolyData->SetPoints(this->points);
this->mapper->SetInputData(this->smplPolyData);
this->mapper->SetScalarRange(this->smplPolyData->GetScalarRange());
this->actor->SetMapper(this->mapper);
this->setData(data);
}
void VtkSMPLActor::setData(const RenderableSMPLData &data) {
std::lock_guard lock(this->mutex);
auto points = this->smplPolyData->GetPoints();
points->Reset();
for (const auto &vertex: data.getPositions()) {
points->InsertNextPoint(vertex.x(), vertex.y(), vertex.z());
}
auto polys = this->smplPolyData->GetPolys();
polys->Reset();
for (const auto &index: data.getIndices()) {
polys->InsertNextCell(static_cast<int>(index.size()));
for (const auto &value: index) {
polys->InsertCellPoint(value);
}
}
}
void VtkSMPLActor::addToRenderer(vtkRenderer &renderer) const {
renderer.AddActor(this->actor);
}
This is the main method:
int main(int argc, char *argv[]) {
QSurfaceFormat::setDefaultFormat(QVTKOpenGLNativeWidget::defaultFormat());
QApplication app(argc, argv);
// Main window.
QMainWindow mainWindow;
mainWindow.resize(1200, 900);
// Render area.
QPointer<QVTKOpenGLNativeWidget> vtkRenderWidget = new QVTKOpenGLNativeWidget();
mainWindow.setCentralWidget(vtkRenderWidget);
// VTK part.
vtkNew<vtkGenericOpenGLRenderWindow> window;
vtkRenderWidget->setRenderWindow(window.Get());
vtkNew<vtkRenderer> renderer;
window->AddRenderer(renderer);
ApplicationDataInterface subsciber;
vtkNew<vtkNamedColors> colors;
renderer->SetBackground(colors->GetColor3d("black").GetData());
std::unordered_map<std::string, std::unique_ptr<VtkSMPLActor>> smplActors;
std::mutex mutex;
QObject::connect(&subsciber, &ApplicationDataInterface::newPerson,
[&mutex, &smplActors, &renderer]
(QString personId, RenderableSMPLData smplData, SensorData sensorData) {
const auto id = personId.toStdString();
std::lock_guard lock(mutex);
smplActors.try_emplace(id, std::make_unique<VtkSMPLActor>(smplData));
smplActors.at(id)->addToRenderer(*renderer);
});
QObject::connect(&subsciber, &ApplicationDataInterface::renderDataChanged, [&mutex, &smplActors]
(QString personId, RenderableSMPLData smplData, SensorData sensorData) {
std::lock_guard lock(mutex);
smplActors.at(personId.toStdString())->setData(smplData);
});
window->SetSize(600, 600);
QTimer timer(&mainWindow);
vtkNew<vtkCallbackCommand> lockCommand;
vtkNew<vtkCallbackCommand> unlockCommand;
lockCommand->SetClientData(&mutex);
unlockCommand->SetClientData(&mutex);
lockCommand->SetCallback([](vtkObject *caller, long unsigned int evId, void *clientData, void *callData) {
auto mutex = reinterpret_cast<std::mutex *>(clientData);
mutex->lock();
});
unlockCommand->SetCallback([](vtkObject *caller, long unsigned int evId, void *clientData, void *callData) {
auto mutex = reinterpret_cast<std::mutex *>(clientData);
mutex->unlock();
});
renderer->AddObserver(vtkCommand::StartEvent, lockCommand);
renderer->AddObserver(vtkCommand::EndEvent, unlockCommand);
QObject::connect(&timer, &QTimer::timeout, [&window]() {
window->Modified();
window->Render();
});
timer.start(33);
mainWindow.show();
return app.exec();
}
I appreciate any help. If you need more info feel free to ask.