Program Listing for File vtkMRMLLayerDisplayableManager.cxx
↰ Return to documentation for file (MRMLDM/vtkMRMLLayerDisplayableManager.cxx)
#include "vtkMRMLLayerDisplayableManager.h"
// Layer DM includes
#include "vtkMRMLLayerDMPipelineFactory.h"
#include "vtkMRMLLayerDMPipelineManager.h"
// Slicer includes
#include "vtkMRMLAbstractViewNode.h"
#include "vtkMRMLScene.h"
#include "vtkMRMLSliceViewDisplayableManagerFactory.h"
#include "vtkMRMLThreeDViewDisplayableManagerFactory.h"
// VTK includes
#include <vtkImageData.h>
#include <vtkObjectFactory.h>
#include <vtkRenderWindow.h>
#include <vtkRenderer.h>
// STD includes
#include <cstring>
vtkStandardNewMacro(vtkMRMLLayerDisplayableManager);
vtkMRMLLayerDisplayableManager::vtkMRMLLayerDisplayableManager()
: m_pipelineManager(nullptr)
{
}
bool vtkMRMLLayerDisplayableManager::CanProcessInteractionEvent(vtkMRMLInteractionEventData* eventData, double& distance2)
{
if (!this->m_pipelineManager)
{
return false;
}
return this->m_pipelineManager->CanProcessInteractionEvent(eventData, distance2);
}
bool vtkMRMLLayerDisplayableManager::ProcessInteractionEvent(vtkMRMLInteractionEventData* eventData)
{
if (!this->m_pipelineManager)
{
return false;
}
return this->m_pipelineManager->ProcessInteractionEvent(eventData);
}
void vtkMRMLLayerDisplayableManager::RegisterInDefaultViews()
{
vtkMRMLLayerDisplayableManager::RegisterInFactory(vtkMRMLSliceViewDisplayableManagerFactory::GetInstance());
vtkMRMLLayerDisplayableManager::RegisterInFactory(vtkMRMLThreeDViewDisplayableManagerFactory::GetInstance());
}
void vtkMRMLLayerDisplayableManager::RegisterInFactory(vtkMRMLDisplayableManagerFactory* factory)
{
if (!factory || vtkMRMLLayerDisplayableManager::IsRegisteredInFactory(factory))
{
return;
}
const vtkNew<vtkMRMLLayerDisplayableManager> dm;
factory->RegisterDisplayableManager(dm->GetClassName());
}
bool vtkMRMLLayerDisplayableManager::IsRegisteredInFactory(vtkMRMLDisplayableManagerFactory* factory)
{
if (!factory)
{
return false;
}
const vtkNew<vtkMRMLLayerDisplayableManager> dm;
return factory->IsDisplayableManagerRegistered(dm->GetClassName());
}
vtkSmartPointer<vtkMRMLLayerDMPipelineI> vtkMRMLLayerDisplayableManager::GetNodePipeline(vtkMRMLNode* node) const
{
return m_pipelineManager->GetNodePipeline(node);
}
void vtkMRMLLayerDisplayableManager::OnMRMLSceneStartBatchProcess()
{
if (!this->m_pipelineManager)
{
return;
}
this->m_pipelineManager->BlockRequestRender(true);
}
void vtkMRMLLayerDisplayableManager::OnMRMLSceneEndBatchProcess()
{
if (!this->m_pipelineManager)
{
return;
}
this->m_pipelineManager->BlockRequestRender(false);
this->m_pipelineManager->RequestRender();
}
void vtkMRMLLayerDisplayableManager::OnMRMLSceneNodeAdded(vtkMRMLNode* node)
{
if (!this->m_pipelineManager)
{
return;
}
this->m_pipelineManager->AddNode(node);
}
void vtkMRMLLayerDisplayableManager::OnMRMLSceneNodeRemoved(vtkMRMLNode* node)
{
if (!this->m_pipelineManager)
{
return;
}
this->m_pipelineManager->RemoveNode(node);
}
void vtkMRMLLayerDisplayableManager::UnobserveMRMLScene()
{
if (!this->m_pipelineManager)
{
return;
}
this->m_pipelineManager->ClearDisplayableNodes();
}
void vtkMRMLLayerDisplayableManager::UpdateFromMRML()
{
this->SetUpdateFromMRMLRequested(false);
if (!this->m_pipelineManager)
{
return;
}
this->m_pipelineManager->SetScene(this->GetMRMLScene());
this->m_pipelineManager->UpdateFromScene();
}
void vtkMRMLLayerDisplayableManager::OnMRMLDisplayableNodeModifiedEvent(vtkObject* caller)
{
auto viewNode = vtkMRMLAbstractViewNode::SafeDownCast(caller);
if (!viewNode || !this->m_pipelineManager)
{
return;
}
this->m_pipelineManager->SetViewNode(viewNode);
}
int vtkMRMLLayerDisplayableManager::GetMouseCursor()
{
if (!this->m_pipelineManager)
{
return vtkMRMLAbstractDisplayableManager::GetMouseCursor();
}
return this->m_pipelineManager->GetMouseCursor();
}
void vtkMRMLLayerDisplayableManager::Create()
{
vtkRenderer* renderer = this->GetRenderer();
if (!renderer || !renderer->GetRenderWindow())
{
vtkErrorMacro("vtkMRMLLayerDisplayableManager::Create() failed: renderer is invalid");
return;
}
if (!this->m_pipelineManager)
{
this->m_pipelineManager = vtkSmartPointer<vtkMRMLLayerDMPipelineManager>::New();
}
this->m_pipelineManager->SetRenderWindow(renderer->GetRenderWindow());
this->m_pipelineManager->SetRenderer(renderer);
this->m_pipelineManager->SetFactory(vtkMRMLLayerDMPipelineFactory::GetInstance());
this->m_pipelineManager->SetScene(this->GetMRMLScene());
this->m_pipelineManager->SetViewNode(vtkMRMLAbstractViewNode::SafeDownCast(this->GetMRMLDisplayableNode()));
this->m_pipelineManager->SetRequestRender([this] { this->RequestRender(); });
// Make sure the DM is up to date with the current scene state
this->UpdateFromMRML();
}
void vtkMRMLLayerDisplayableManager::SetRenderer(vtkRenderer* newRenderer)
{
Superclass::SetRenderer(newRenderer);
if (!this->m_pipelineManager)
{
return;
}
this->m_pipelineManager->SetRenderWindow(newRenderer ? newRenderer->GetRenderWindow() : nullptr);
this->m_pipelineManager->SetRenderer(newRenderer);
}
void vtkMRMLLayerDisplayableManager::SetHasFocus(bool hasFocus, vtkMRMLInteractionEventData* eventData)
{
Superclass ::SetHasFocus(hasFocus, eventData);
if (this->m_pipelineManager && !hasFocus)
{
this->m_pipelineManager->LoseFocus(eventData);
}
}
vtkSmartPointer<vtkImageData> vtkMRMLLayerDisplayableManager::RenderWindowBufferToImage(vtkRenderWindow* window)
{
auto imageData = vtkSmartPointer<vtkImageData>::New();
RenderWindowBufferToImage(window, imageData);
return imageData;
}
void vtkMRMLLayerDisplayableManager::RenderWindowBufferToImage(vtkRenderWindow* window, const vtkSmartPointer<vtkImageData>& imageData)
{
if (!window || !imageData)
{
return;
}
// Set image bounds to full RW bounds
const auto size = window->GetSize();
int imageBounds[4] = { 0, size[0] - 1, 0, size[1] - 1 };
// Read pixel data from the back buffer
const auto pixels = window->GetPixelData(imageBounds[0], imageBounds[2], imageBounds[1], imageBounds[3], 0);
if (!pixels)
{
return;
}
// Configure imageData extent and allocate scalars for RGB
imageData->SetExtent(imageBounds[0], imageBounds[1], imageBounds[2], imageBounds[3], 0, 0);
imageData->AllocateScalars(VTK_UNSIGNED_CHAR, 3);
// Copy pixel buffer into vtkImageData
const auto dest = static_cast<unsigned char*>(imageData->GetScalarPointer());
const auto numPixels = static_cast<size_t>(size[0]) * size[1];
std::memcpy(dest, pixels, numPixels * 3 * sizeof(unsigned char));
// Free the pixel buffer allocated by VTK
delete[] pixels;
}