diff --git a/Modules/Python/QmitkPythonVariableStackTableModel.cpp b/Modules/Python/QmitkPythonVariableStackTableModel.cpp index 1ab2fa0ec7..2ad27d2fd5 100755 --- a/Modules/Python/QmitkPythonVariableStackTableModel.cpp +++ b/Modules/Python/QmitkPythonVariableStackTableModel.cpp @@ -1,223 +1,223 @@ /*=================================================================== The Medical Imaging Interaction Toolkit (MITK) Copyright (c) German Cancer Research Center, Division of Medical and Biological Informatics. All rights reserved. This software is distributed WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See LICENSE.txt or http://www.mitk.org for details. ===================================================================*/ #include "QmitkPythonVariableStackTableModel.h" #include #include #include #include #include #include const QString QmitkPythonVariableStackTableModel::MITK_IMAGE_VAR_NAME = "mitkImage"; const QString QmitkPythonVariableStackTableModel::MITK_SURFACE_VAR_NAME = "mitkSurface"; QmitkPythonVariableStackTableModel::QmitkPythonVariableStackTableModel(QObject *parent) :QAbstractTableModel(parent) { mitk::ModuleContext* context = mitk::GetModuleContext(); m_PythonServiceRef = context->GetServiceReference(); m_PythonService = context->GetService(m_PythonServiceRef); m_PythonService->AddPythonCommandObserver( this ); } QmitkPythonVariableStackTableModel::~QmitkPythonVariableStackTableModel() { mitk::ModuleContext* context = mitk::GetModuleContext(); context->UngetService( m_PythonServiceRef ); m_PythonService->RemovePythonCommandObserver( this ); } bool QmitkPythonVariableStackTableModel::dropMimeData ( const QMimeData * data, Qt::DropAction action, int row, int column, const QModelIndex & parent ) { // Early exit, returning true, but not actually doing anything (ignoring data). if (action == Qt::IgnoreAction) return true; // Note, we are returning true if we handled it, and false otherwise bool returnValue = false; if(data->hasFormat("application/x-mitk-datanodes")) { MITK_DEBUG("QmitkPythonVariableStackTableModel") << "dropped MITK DataNode"; returnValue = true; QString arg = QString(data->data("application/x-mitk-datanodes").data()); QStringList listOfDataNodeAddressPointers = arg.split(","); QStringList::iterator slIter; int i = 0; int j = 0; for (slIter = listOfDataNodeAddressPointers.begin(); slIter != listOfDataNodeAddressPointers.end(); slIter++) { long val = (*slIter).toLong(); mitk::DataNode* node = static_cast((void*)val); mitk::Image* mitkImage = dynamic_cast(node->GetData()); MITK_DEBUG("QmitkPythonVariableStackTableModel") << "mitkImage is not null " << (mitkImage != 0? "true": "false"); if( mitkImage ) { QString varName = MITK_IMAGE_VAR_NAME; if( i > 0 ) varName = QString("%1%2").arg(MITK_IMAGE_VAR_NAME).arg(i); MITK_DEBUG("QmitkPythonVariableStackTableModel") << "varName" << varName.toStdString(); bool exportAsCvImage = m_PythonService->IsOpenCvPythonWrappingAvailable(); if( mitkImage->GetDimension() == 2 && exportAsCvImage ) { int ret = QMessageBox::question(NULL, "Export option", "2D image detected. Export as OpenCV image to Python instead of an ITK image?", QMessageBox::Yes | QMessageBox::No, QMessageBox::No); exportAsCvImage = ret == QMessageBox::Yes; if(exportAsCvImage) { m_PythonService->CopyToPythonAsCvImage( mitkImage, MITK_IMAGE_VAR_NAME.toStdString() ); ++i; } } if( !exportAsCvImage ) { if( m_PythonService->IsItkPythonWrappingAvailable() ) { m_PythonService->CopyToPythonAsItkImage( mitkImage, MITK_IMAGE_VAR_NAME.toStdString() ); ++i; } else { MITK_ERROR << "ITK Python wrapping not available. Skipping export for image " << node->GetName(); } } } else { mitk::Surface* surface = dynamic_cast(node->GetData()); MITK_DEBUG("QmitkPythonVariableStackTableModel") << "found surface"; if( surface ) { QString varName = MITK_SURFACE_VAR_NAME; MITK_DEBUG("QmitkPythonVariableStackTableModel") << "varName" << varName.toStdString(); if( j > 0 ) varName = QString("%1%2").arg(MITK_SURFACE_VAR_NAME).arg(j); - MITK_DEBUG("varName") << "varName" << varName; + MITK_DEBUG("varName") << "varName" << varName.toStdString(); if( m_PythonService->IsVtkPythonWrappingAvailable() ) { m_PythonService->CopyToPythonAsVtkPolyData( surface, MITK_SURFACE_VAR_NAME.toStdString() ); ++j; } else { MITK_ERROR << "VTK Python wrapping not available. Skipping export for surface " << node->GetName(); } } } } } return returnValue; } QVariant QmitkPythonVariableStackTableModel::headerData(int section, Qt::Orientation orientation, int role) const { QVariant headerData; // show only horizontal header if ( role == Qt::DisplayRole ) { if( orientation == Qt::Horizontal ) { // first column: "Attribute" if(section == 0) headerData = "Attribute"; else if(section == 1) headerData = "Type"; else if(section == 2) headerData = "Value"; } } return headerData; } Qt::ItemFlags QmitkPythonVariableStackTableModel::flags(const QModelIndex &index) const { Qt::ItemFlags flags = QAbstractItemModel::flags(index); if(index.isValid()) return Qt::ItemIsDragEnabled | Qt::ItemIsDropEnabled | flags; else return Qt::ItemIsDropEnabled | flags; } int QmitkPythonVariableStackTableModel::rowCount(const QModelIndex &) const { return m_VariableStack.size(); } int QmitkPythonVariableStackTableModel::columnCount(const QModelIndex &) const { return 3; } QVariant QmitkPythonVariableStackTableModel::data(const QModelIndex &index, int role) const { if (index.isValid() && !m_VariableStack.empty()) { if(role == Qt::DisplayRole) { mitk::PythonVariable item = m_VariableStack.at(index.row()); if(index.column() == 0) return QString::fromStdString(item.m_Name); if(index.column() == 1) return QString::fromStdString(item.m_Type); if(index.column() == 2) return QString::fromStdString(item.m_Value); } } return QVariant(); } QStringList QmitkPythonVariableStackTableModel::mimeTypes() const { return QAbstractTableModel::mimeTypes(); QStringList types; types << "application/x-mitk-datanodes"; types << "application/x-qabstractitemmodeldatalist"; return types; } Qt::DropActions QmitkPythonVariableStackTableModel::supportedDropActions() const { return Qt::CopyAction | Qt::MoveAction; } void QmitkPythonVariableStackTableModel::CommandExecuted(const std::string& pythonCommand) { MITK_DEBUG("QmitkPythonVariableStackTableModel") << "command was executed " << pythonCommand; m_VariableStack = m_PythonService->GetVariableStack(); QAbstractTableModel::reset(); } std::vector QmitkPythonVariableStackTableModel::GetVariableStack() const { return m_VariableStack; } diff --git a/Modules/Python/QmitkPythonVariableStackTableView.cpp b/Modules/Python/QmitkPythonVariableStackTableView.cpp index 71f4cb6daf..a062feb62d 100755 --- a/Modules/Python/QmitkPythonVariableStackTableView.cpp +++ b/Modules/Python/QmitkPythonVariableStackTableView.cpp @@ -1,87 +1,107 @@ /*=================================================================== The Medical Imaging Interaction Toolkit (MITK) Copyright (c) German Cancer Research Center, Division of Medical and Biological Informatics. All rights reserved. This software is distributed WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See LICENSE.txt or http://www.mitk.org for details. ===================================================================*/ #include "QmitkPythonVariableStackTableView.h" #include #include #include #include +#include QmitkPythonVariableStackTableView::QmitkPythonVariableStackTableView(QWidget *parent) :QTableView(parent) { m_TableModel = new QmitkPythonVariableStackTableModel(parent); m_TableModel->CommandExecuted(""); this->setSelectionBehavior( QAbstractItemView::SelectRows ); this->setAlternatingRowColors(true); this->setDropIndicatorShown(true); this->setAcceptDrops(true); this->setModel( m_TableModel ); mitk::ModuleContext* context = mitk::GetModuleContext(); mitk::ServiceReference serviceRef = context->GetServiceReference(); m_PythonService = context->GetService(serviceRef); connect( this, SIGNAL(doubleClicked ( const QModelIndex& )), this, SLOT( OnVariableStackDoubleClicked(const QModelIndex&) ) ); } QmitkPythonVariableStackTableView::~QmitkPythonVariableStackTableView() { } void QmitkPythonVariableStackTableView::SetDataStorage(mitk::DataStorage *_DataStorage) { m_DataStorage = _DataStorage; } void QmitkPythonVariableStackTableView::OnVariableStackDoubleClicked(const QModelIndex &index) { if( m_DataStorage.IsNull() || m_PythonService == 0 ) { MITK_ERROR << "QmitkPythonVariableStackTableView not configured correctly. Quit"; return; } int row = index.row(); std::vector variableStack = m_TableModel->GetVariableStack(); { MITK_DEBUG("QmitkPythonVariableStackTableView") << "row " << row; MITK_DEBUG("QmitkPythonVariableStackTableView") << "variableStack.size(): " << variableStack.size(); } QString varName = QString::fromStdString( variableStack.at(row).m_Name ); QString type = QString::fromStdString( variableStack.at(row).m_Type ); + QString value = QString::fromStdString( variableStack.at(row).m_Value ); { MITK_DEBUG("QmitkPythonVariableStackTableView") << "varName: " << varName.toStdString(); MITK_DEBUG("QmitkPythonVariableStackTableView") << "type: " << type.toStdString(); } - mitk::Image::Pointer mitkImage = m_PythonService->CopyItkImageFromPython(varName.toStdString()); + mitk::Image::Pointer mitkImage; + mitk::Surface::Pointer mitkSurface; - if( mitkImage.IsNotNull() ) + if( type.startsWith("itkImage") ) + { + mitkImage = m_PythonService->CopyItkImageFromPython(varName.toStdString()); + } + else if( type.startsWith("numpy.ndarray") ) { - std::string nodeName = varName.toStdString(); - mitk::DataNode::Pointer node = mitk::DataNode::New(); - node->SetName ( nodeName ); - m_DataStorage->Add(node); + mitkImage = m_PythonService->CopyCvImageFromPython(varName.toStdString()); + } + else if( value.startsWith("(vtkPolyData)") ) + { + mitkSurface = m_PythonService->CopyVtkPolyDataFromPython(varName.toStdString()); + } - node->SetData( mitkImage ); + std::string nodeName = varName.toStdString(); + mitk::DataNode::Pointer node = mitk::DataNode::New(); + node->SetName ( nodeName ); - mitk::RenderingManager::GetInstance()->RequestUpdateAll(); + if( mitkImage.IsNotNull() ) + { + node->SetData( mitkImage ); } + else if( mitkSurface.IsNotNull() ) + { + node->SetData( mitkSurface ); + } + + m_DataStorage->Add(node); + mitk::RenderingManager::GetInstance()->RequestUpdateAll(); } diff --git a/Modules/Python/mitkPythonService.cpp b/Modules/Python/mitkPythonService.cpp index b92fb7f085..4068f2f094 100644 --- a/Modules/Python/mitkPythonService.cpp +++ b/Modules/Python/mitkPythonService.cpp @@ -1,531 +1,532 @@ /*=================================================================== The Medical Imaging Interaction Toolkit (MITK) Copyright (c) German Cancer Research Center, Division of Medical and Biological Informatics. All rights reserved. This software is distributed WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See LICENSE.txt or http://www.mitk.org for details. ===================================================================*/ #include "mitkPythonService.h" #include #include #include #include #include #include "PythonPath.h" -const QString mitk::PythonService::m_TmpImageName("temp_mitk_image"); +const QString mitk::PythonService::m_TmpDataFileName("temp_mitk_data_file"); mitk::PythonService::PythonService() : m_ItkWrappingAvailable( true ), m_OpenCVWrappingAvailable( true ), m_VtkWrappingAvailable( true ), m_ErrorOccured( false ) { { MITK_DEBUG << "will init python if necessary"; } bool pythonInitialized = static_cast( Py_IsInitialized() ); //m_PythonManager.isPythonInitialized() ); { MITK_DEBUG << "pythonInitialized " << pythonInitialized; MITK_DEBUG << "m_PythonManager.isPythonInitialized() " << m_PythonManager.isPythonInitialized(); } // due to strange static var behaviour on windows Py_IsInitialized() returns correct value while // m_PythonManager.isPythonInitialized() does not because it has been constructed and destructed again if( !m_PythonManager.isPythonInitialized() ) { try { if( pythonInitialized ) m_PythonManager.setInitializationFlags(PythonQt::RedirectStdOut|PythonQt::PythonAlreadyInitialized); else m_PythonManager.setInitializationFlags(PythonQt::RedirectStdOut); MITK_DEBUG("PythonService") << "initalizing python"; m_PythonManager.initialize(); MITK_DEBUG("PythonService") << "python initalized"; QString pythonCommand(PYTHONPATH_COMMAND); MITK_DEBUG("PythonService") << "registering python paths" << PYTHONPATH_COMMAND; m_PythonManager.executeString( pythonCommand, ctkAbstractPythonManager::FileInput ); /* //system("export LD_LIBRARY_PATH=/local/muellerm/mitk/bugsquashing/bin-debug/VTK-build/bin:$LD_LIBRARY_PATH"); //m_PythonManager.executeString( "print sys.path", ctkAbstractPythonManager::SingleInput ); //MITK_DEBUG("mitk::PythonService") << "result of 'sys.path': " << result.toString().toStdString(); //m_PythonManager.executeString( "sys.path.append('/usr/share/pyshared/numpy')", ctkAbstractPythonManager::SingleInput ); //m_PythonManager.executeString( "import numpy", ctkAbstractPythonManager::SingleInput ); MITK_DEBUG("mitk::PythonService") << "Trying to import ITK"; m_PythonManager.executeString( "import itk", ctkAbstractPythonManager::SingleInput ); m_ItkWrappingAvailable = !m_PythonManager.pythonErrorOccured(); MITK_DEBUG("mitk::PythonService") << "m_ItkWrappingAvailable: " << (m_ItkWrappingAvailable? "yes": "no"); if( !m_ItkWrappingAvailable ) { MITK_WARN << "ITK Python wrapping not available. Please check build settings or PYTHONPATH settings."; } { MITK_DEBUG("mitk::PythonService") << "Trying to import OpenCv"; PyRun_SimpleString("import cv2\n"); if (PyErr_Occurred()) { PyErr_Print(); } else m_OpenCVWrappingAvailable = true; //m_PythonManager.executeString( "import cv2", ctkAbstractPythonManager::SingleInput ); MITK_DEBUG("mitk::PythonService") << "Investigate if an error occured while importing cv2"; //m_OpenCVWrappingAvailable = !m_PythonManager.pythonErrorOccured(); MITK_DEBUG("mitk::PythonService") << "m_OpenCVWrappingAvailable: " << (m_OpenCVWrappingAvailable? "yes": "no"); if( !m_OpenCVWrappingAvailable ) { MITK_WARN << "OpenCV Python wrapping not available. Please check build settings or PYTHONPATH settings."; } } MITK_DEBUG("mitk::PythonService") << "Trying to import VTK"; m_PythonManager.executeString( "import vtk", ctkAbstractPythonManager::SingleInput ); m_VtkWrappingAvailable = !m_PythonManager.pythonErrorOccured(); MITK_DEBUG("mitk::PythonService") << "m_VtkWrappingAvailable: " << (m_VtkWrappingAvailable? "yes": "no"); if( !m_VtkWrappingAvailable ) { MITK_WARN << "VTK Python wrapping not available. Please check build settings or PYTHONPATH settings."; } */ } catch (...) { MITK_DEBUG("PythonService") << "exception initalizing python"; } } //m_PythonManager.executeString( "for path in sys.path:\n print path\n", ctkAbstractPythonManager::SingleInput ); //m_PythonManager.executeString( "for k, v in os.environ.items():\n print \"%s=%s\" % (k, v)", ctkAbstractPythonManager::SingleInput ); //m_PythonManager.executeFile("/local/muellerm/Dropbox/13-02-11-python-wrapping/interpreterInfo.py"); //std::string result = m_PythonManager.executeString( "5+5", ctkAbstractPythonManager::EvalInput ); //MITK_DEBUG("mitk::PythonService") << "result of '5+5': " << result.toString().toStdString(); } mitk::PythonService::~PythonService() { //QVariant result = m_PythonManager.executeString( "sys.getrefcount(cv2)", ctkAbstractPythonManager::EvalInput ); //MITK_DEBUG("mitk::PythonService") << "sys.getrefcount(cv2): " << result.toString().toStdString(); //m_PythonManager.executeString( "del sys.modules[\"cv2\"]", ctkAbstractPythonManager::SingleInput ); //m_PythonManager.executeString( "del cv2", ctkAbstractPythonManager::SingleInput ); MITK_DEBUG("mitk::PythonService") << "destructing PythonService"; } std::string mitk::PythonService::Execute(const std::string &stdpythonCommand, int commandType) { QString pythonCommand = QString::fromStdString(stdpythonCommand); { MITK_DEBUG("mitk::PythonService") << "pythonCommand = " << pythonCommand.toStdString(); MITK_DEBUG("mitk::PythonService") << "commandType = " << commandType; } QVariant result; bool commandIssued = true; if(commandType == IPythonService::SINGLE_LINE_COMMAND ) result = m_PythonManager.executeString(pythonCommand, ctkAbstractPythonManager::SingleInput ); else if(commandType == IPythonService::MULTI_LINE_COMMAND ) result = m_PythonManager.executeString(pythonCommand, ctkAbstractPythonManager::FileInput ); else if(commandType == IPythonService::EVAL_COMMAND ) result = m_PythonManager.executeString(pythonCommand, ctkAbstractPythonManager::EvalInput ); else commandIssued = false; if(commandIssued) { this->NotifyObserver(pythonCommand.toStdString()); m_ErrorOccured = PythonQt::self()->handleError(); } return result.toString().toStdString(); } void mitk::PythonService::ExecuteScript( const std::string& pythonScript ) { m_PythonManager.executeFile(QString::fromStdString(pythonScript)); } std::vector mitk::PythonService::GetVariableStack() const { std::vector list; PyObject* dict = PyImport_GetModuleDict(); PyObject* object = PyDict_GetItemString(dict, "__main__"); PyObject* dirMain = PyObject_Dir(object); PyObject* tempObject = 0; PyObject* strTempObject = 0; if(dirMain) { std::string name, attrValue, attrType; for(int i = 0; iob_type->tp_name; strTempObject = PyObject_Repr(tempObject); if(strTempObject && ( PyUnicode_Check(strTempObject) || PyString_Check(strTempObject) ) ) attrValue = PyString_AsString(strTempObject); else attrValue = ""; mitk::PythonVariable var; var.m_Name = name; var.m_Value = attrValue; var.m_Type = attrType; list.push_back(var); } } return list; } bool mitk::PythonService::DoesVariableExist(const std::string& name) const { bool varExists = false; std::vector allVars = this->GetVariableStack(); for(int i = 0; i< allVars.size(); i++) { if( allVars.at(i).m_Name == name ) { varExists = true; break; } } return varExists; } void mitk::PythonService::AddPythonCommandObserver(mitk::PythonCommandObserver *observer) { if(!m_Observer.contains(observer)) m_Observer.append(observer); } void mitk::PythonService::RemovePythonCommandObserver(mitk::PythonCommandObserver *observer) { m_Observer.removeOne(observer); } void mitk::PythonService::NotifyObserver(const std::string &command) { MITK_DEBUG("mitk::PythonService") << "number of observer " << m_Observer.size(); for( size_t i=0; i< m_Observer.size(); ++i ) { m_Observer.at(i)->CommandExecuted(command); } } -QString mitk::PythonService::GetTempImageName(const std::string& ext) const +QString mitk::PythonService::GetTempDataFileName(const std::string& ext) const { QString tmpFolder = QDir::tempPath(); - QString fileName = tmpFolder + QDir::separator() + m_TmpImageName + QString::fromStdString(ext); + QString fileName = tmpFolder + QDir::separator() + m_TmpDataFileName + QString::fromStdString(ext); return fileName; } bool mitk::PythonService::CopyToPythonAsItkImage(mitk::Image *image, const std::string &stdvarName) { QString varName = QString::fromStdString( stdvarName ); // save image - QString fileName = this->GetTempImageName( mitk::IOUtil::DEFAULTIMAGEEXTENSION ); + QString fileName = this->GetTempDataFileName( mitk::IOUtil::DEFAULTIMAGEEXTENSION ); fileName = QDir::fromNativeSeparators( fileName ); MITK_DEBUG("PythonService") << "Saving temporary file " << fileName.toStdString(); if( !mitk::IOUtil::SaveImage(image, fileName.toStdString()) ) { MITK_ERROR << "Temporary file could not be created."; } else { // TODO CORRECT TYPE SETUP, MAKE MITK_DEBUG("PythonService") MITK_DEBUG("PythonService") int dim = image->GetDimension(); mitk::PixelType pixelType = image->GetPixelType(); itk::ImageIOBase::IOPixelType ioPixelType = image->GetPixelType().GetPixelTypeId(); // default pixeltype: unsigned short QString type = "US"; if( ioPixelType == itk::ImageIOBase::SCALAR ) { if( pixelType.GetTypeId() == typeid(double) ) type = "D"; else if( pixelType.GetTypeId() == typeid(float) ) type = "F"; if( pixelType.GetTypeId() == typeid(long double) ) type = "LD"; else if( pixelType.GetTypeId() == typeid(short) ) type = "SS"; else if( pixelType.GetTypeId() == typeid(signed char) ) type = "SC"; else if( pixelType.GetTypeId() == typeid(signed int) ) type = "SI"; else if( pixelType.GetTypeId() == typeid(signed long) ) type = "SL"; else if( pixelType.GetTypeId() == typeid(signed short) ) type = "SS"; else if( pixelType.GetTypeId() == typeid(unsigned char) ) type = "UC"; else if( pixelType.GetTypeId() == typeid(unsigned int) ) type = "UI"; else if( pixelType.GetTypeId() == typeid(unsigned long) ) type = "UL"; else if( pixelType.GetTypeId() == typeid(unsigned short) ) type = "US"; } MITK_DEBUG("PythonService") << "Got mitk image with type " << type.toStdString() << " and dim " << dim; QString command; command.append( QString("imageType = itk.Image[itk.%1, %2]\n") .arg( type ).arg( dim ) ); command.append( QString("readerType = itk.ImageFileReader[imageType]\n") ); command.append( QString("reader = readerType.New()\n") ); command.append( QString("reader.SetFileName( \"%1\" )\n") .arg(fileName) ); command.append( QString("reader.Update()\n") ); command.append( QString("%1 = reader.GetOutput()\n").arg( varName ) ); MITK_DEBUG("PythonService") << "Issuing python command " << command.toStdString(); this->Execute( command.toStdString(), IPythonService::MULTI_LINE_COMMAND ); QFile file( fileName ); MITK_DEBUG("PythonService") << "Removing file " << fileName.toStdString(); file.remove(); return true; } return false; } mitk::Image::Pointer mitk::PythonService::CopyItkImageFromPython(const std::string &stdvarName) { QString varName = QString::fromStdString( stdvarName ); mitk::Image::Pointer mitkImage; QString command; - QString fileName = GetTempImageName( mitk::IOUtil::DEFAULTIMAGEEXTENSION ); + QString fileName = GetTempDataFileName( mitk::IOUtil::DEFAULTIMAGEEXTENSION ); fileName = QDir::fromNativeSeparators( fileName ); MITK_DEBUG("PythonService") << "Saving temporary file with python itk code " << fileName.toStdString(); command.append( QString( "writer = itk.ImageFileWriter[ %1 ].New()\n").arg( varName ) ); command.append( QString( "writer.SetFileName( \"%1\" )\n").arg(fileName) ); command.append( QString( "writer.SetInput( %1 )\n").arg(varName) ); command.append( QString( "writer.Update()\n" ) ); MITK_DEBUG("PythonService") << "Issuing python command " << command.toStdString(); this->Execute(command.toStdString(), IPythonService::MULTI_LINE_COMMAND ); try { MITK_DEBUG("PythonService") << "Loading temporary file " << fileName.toStdString() << " as MITK image"; mitkImage = mitk::IOUtil::LoadImage( fileName.toStdString() ); } catch(std::exception& e) { MITK_ERROR << e.what(); } QFile file(fileName); if( file.exists() ) { MITK_DEBUG("PythonService") << "Removing temporary file " << fileName.toStdString(); file.remove(); } return mitkImage; } bool mitk::PythonService::CopyToPythonAsCvImage( mitk::Image* image, const std::string& stdvarName ) { QString varName = QString::fromStdString( stdvarName ); bool convert = false; if(image->GetDimension() != 2) { MITK_ERROR << "Only 2D images allowed for OpenCV images"; return convert; } // try to save mitk image - QString fileName = this->GetTempImageName( ".bmp" ); + QString fileName = this->GetTempDataFileName( ".bmp" ); fileName = QDir::fromNativeSeparators( fileName ); MITK_DEBUG("PythonService") << "Saving temporary file " << fileName.toStdString(); if( !mitk::IOUtil::SaveImage(image, fileName.toStdString()) ) { MITK_ERROR << "Temporary file " << fileName.toStdString() << " could not be created."; return convert; } QString command; command.append( QString("%1 = cv2.imread(\"%2\")\n") .arg( varName ).arg( fileName ) ); MITK_DEBUG("PythonService") << "Issuing python command " << command.toStdString(); this->Execute(command.toStdString(), IPythonService::MULTI_LINE_COMMAND ); MITK_DEBUG("PythonService") << "Removing file " << fileName.toStdString(); QFile file(fileName); file.remove(); convert = true; return convert; } mitk::Image::Pointer mitk::PythonService::CopyCvImageFromPython( const std::string& stdvarName ) { QString varName = QString::fromStdString( stdvarName ); mitk::Image::Pointer mitkImage; QString command; - QString fileName = GetTempImageName( ".bmp" ); + QString fileName = GetTempDataFileName( ".bmp" ); fileName = QDir::fromNativeSeparators( fileName ); MITK_DEBUG("PythonService") << "run python command to save image with opencv to " << fileName.toStdString(); command.append( QString( "cv2.imwrite(\"%1\", %2)\n").arg( fileName ).arg( varName ) ); MITK_DEBUG("PythonService") << "Issuing python command " << command.toStdString(); this->Execute(command.toStdString(), IPythonService::MULTI_LINE_COMMAND ); try { MITK_DEBUG("PythonService") << "Loading temporary file " << fileName.toStdString() << " as MITK image"; mitkImage = mitk::IOUtil::LoadImage( fileName.toStdString() ); } catch(std::exception& e) { MITK_ERROR << e.what(); } QFile file(fileName); if( file.exists() ) { MITK_DEBUG("PythonService") << "Removing temporary file " << fileName.toStdString(); file.remove(); } return mitkImage; } ctkAbstractPythonManager *mitk::PythonService::GetPythonManager() { return &m_PythonManager; } mitk::Surface::Pointer mitk::PythonService::CopyVtkPolyDataFromPython( const std::string& stdvarName ) { QString varName = QString::fromStdString( stdvarName ); mitk::Surface::Pointer newSurface; QString command; - QString fileName = GetTempImageName( ".stl" ); + QString fileName = GetTempDataFileName( ".stl" ); fileName = QDir::fromNativeSeparators( fileName ); MITK_DEBUG("PythonService") << "run python command to save polydata with vtk to " << fileName.toStdString(); command = QString ( "vtkStlWriter = vtk.vtkSTLWriter()\n" "vtkStlWriter.SetInput(%1)\n" "vtkStlWriter.SetFileName(\"%2\")\n" "vtkStlWriter.Write()\n").arg(varName).arg(fileName); MITK_DEBUG("PythonService") << "Issuing python command " << command.toStdString(); this->Execute(command.toStdString(), IPythonService::MULTI_LINE_COMMAND ); try { MITK_DEBUG("PythonService") << "Loading temporary file " << fileName.toStdString() << " as MITK Surface"; newSurface = mitk::IOUtil::LoadSurface( fileName.toStdString() ); } catch(std::exception& e) { MITK_ERROR << e.what(); } QFile file(fileName); if( file.exists() ) { MITK_DEBUG("PythonService") << "Removing temporary file " << fileName.toStdString(); file.remove(); } return newSurface; } bool mitk::PythonService::CopyToPythonAsVtkPolyData( mitk::Surface* surface, const std::string& stdvarName ) { QString varName = QString::fromStdString( stdvarName ); bool convert = false; // try to save mitk image - QString fileName = this->GetTempImageName( ".stl" ); + QString fileName = this->GetTempDataFileName( ".stl" ); fileName = QDir::fromNativeSeparators( fileName ); MITK_DEBUG("PythonService") << "Saving temporary file " << fileName.toStdString(); if( !mitk::IOUtil::SaveSurface( surface, fileName.toStdString() ) ) { MITK_ERROR << "Temporary file " << fileName.toStdString() << " could not be created."; return convert; } QString command; command.append( QString("vtkStlReader = vtk.vtkSTLReader()\n") ); command.append( QString("vtkStlReader.SetFileName(\"%1\")\n").arg( fileName ) ); - command.append( QString("%1 = vtkStlReader.GetOutput()").arg( fileName ) ); + command.append( QString("vtkStlReader.Update()\n") ); + command.append( QString("%1 = vtkStlReader.GetOutput()\n").arg( varName ) ); MITK_DEBUG("PythonService") << "Issuing python command " << command.toStdString(); this->Execute(command.toStdString(), IPythonService::MULTI_LINE_COMMAND ); MITK_DEBUG("PythonService") << "Removing file " << fileName.toStdString(); QFile file(fileName); file.remove(); convert = true; return convert; } bool mitk::PythonService::IsItkPythonWrappingAvailable() { this->Execute( "import itk\n", IPythonService::SINGLE_LINE_COMMAND ); m_ItkWrappingAvailable = !this->PythonErrorOccured(); return m_ItkWrappingAvailable; } bool mitk::PythonService::IsOpenCvPythonWrappingAvailable() { this->Execute( "import cv2\n", IPythonService::SINGLE_LINE_COMMAND ); m_OpenCVWrappingAvailable = !this->PythonErrorOccured(); return m_OpenCVWrappingAvailable; } bool mitk::PythonService::IsVtkPythonWrappingAvailable() { this->Execute( "import vtk", IPythonService::SINGLE_LINE_COMMAND ); m_VtkWrappingAvailable = !this->PythonErrorOccured(); return m_VtkWrappingAvailable; } bool mitk::PythonService::PythonErrorOccured() const { return m_ErrorOccured; } diff --git a/Modules/Python/mitkPythonService.h b/Modules/Python/mitkPythonService.h index 7db01c80d3..9218a19024 100644 --- a/Modules/Python/mitkPythonService.h +++ b/Modules/Python/mitkPythonService.h @@ -1,105 +1,105 @@ /*=================================================================== The Medical Imaging Interaction Toolkit (MITK) Copyright (c) German Cancer Research Center, Division of Medical and Biological Informatics. All rights reserved. This software is distributed WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See LICENSE.txt or http://www.mitk.org for details. ===================================================================*/ #ifndef mitkPythonService_h #define mitkPythonService_h #include "mitkIPythonService.h" #include #include #include "mitkSurface.h" #include "mitkPythonExports.h" namespace mitk { /// /// implementation of the IPythonService using ctkabstractpythonmanager /// \see IPythonService class MITK_PYTHON_EXPORT PythonService: public itk::LightObject, public mitk::IPythonService { public: /// /// instantiate python manager here PythonService(); /// /// empty implementation... ~PythonService(); /// /// \see IPythonService::Execute() std::string Execute( const std::string& pythonCommand, int commandType = SINGLE_LINE_COMMAND ); /// /// \see IPythonService::ExecuteScript() void ExecuteScript(const std::string &pathToPythonScript); /// /// \see IPythonService::PythonErrorOccured() bool PythonErrorOccured() const; /// /// \see IPythonService::GetVariableStack() std::vector GetVariableStack() const; /// /// \see IPythonService::DoesVariableExist() bool DoesVariableExist(const std::string& name) const; /// /// \see IPythonService::AddPythonCommandObserver() void AddPythonCommandObserver( PythonCommandObserver* observer ); /// /// \see IPythonService::RemovePythonCommandObserver() void RemovePythonCommandObserver( PythonCommandObserver* observer ); /// /// \see IPythonService::NotifyObserver() void NotifyObserver( const std::string& command ); /// /// \see IPythonService::IsItkPythonWrappingAvailable() bool IsItkPythonWrappingAvailable(); /// /// \see IPythonService::CopyToPythonAsItkImage() bool CopyToPythonAsItkImage( mitk::Image* image, const std::string& varName ); /// /// \see IPythonService::CopyItkImageFromPython() mitk::Image::Pointer CopyItkImageFromPython( const std::string& varName ); /// /// \see IPythonService::IsOpenCvPythonWrappingAvailable() bool IsOpenCvPythonWrappingAvailable(); /// /// \see IPythonService::CopyToPythonAsCvImage() bool CopyToPythonAsCvImage( mitk::Image* image, const std::string& varName ); /// /// \see IPythonService::CopyCvImageFromPython() mitk::Image::Pointer CopyCvImageFromPython( const std::string& varName ); /// /// \see IPythonService::IsVtkPythonWrappingAvailable() bool IsVtkPythonWrappingAvailable(); /// /// \see IPythonService::CopyToPythonAsVtkPolyData() bool CopyToPythonAsVtkPolyData( mitk::Surface* surface, const std::string& varName ); /// /// \see IPythonService::CopyVtkPolyDataFromPython() mitk::Surface::Pointer CopyVtkPolyDataFromPython( const std::string& varName ); /// /// \return the ctk abstract python manager instance ctkAbstractPythonManager* GetPythonManager(); protected: - QString GetTempImageName(const std::string &ext) const; + QString GetTempDataFileName(const std::string &ext) const; private: QList m_Observer; ctkAbstractPythonManager m_PythonManager; - static const QString m_TmpImageName; + static const QString m_TmpDataFileName; bool m_ItkWrappingAvailable; bool m_OpenCVWrappingAvailable; bool m_VtkWrappingAvailable; bool m_ErrorOccured; }; } #endif diff --git a/Modules/Python/resources/PythonSnippets.xml b/Modules/Python/resources/PythonSnippets.xml index b006605bfc..a301307dd3 100644 --- a/Modules/Python/resources/PythonSnippets.xml +++ b/Modules/Python/resources/PythonSnippets.xml @@ -1,6 +1,7 @@ +