diff --git a/CMakeExternals/CTK.cmake b/CMakeExternals/CTK.cmake index e89e8a20e0..ecf504e761 100644 --- a/CMakeExternals/CTK.cmake +++ b/CMakeExternals/CTK.cmake @@ -1,124 +1,124 @@ #----------------------------------------------------------------------------- # CTK #----------------------------------------------------------------------------- if(MITK_USE_CTK) # Sanity checks if(DEFINED CTK_DIR AND NOT EXISTS ${CTK_DIR}) message(FATAL_ERROR "CTK_DIR variable is defined but corresponds to non-existing directory") endif() set(proj CTK) set(proj_DEPENDENCIES ) set(CTK_DEPENDS ${proj}) if(NOT DEFINED CTK_DIR) set(revision_tag 4d12a3b8) #IF(${proj}_REVISION_TAG) # SET(revision_tag ${${proj}_REVISION_TAG}) #ENDIF() set(ctk_optional_cache_args ) if(MITK_USE_Python) if(NOT MITK_USE_SYSTEM_PYTHON) list(APPEND proj_DEPENDENCIES Python) endif() list(APPEND ctk_optional_cache_args -DCTK_LIB_Scripting/Python/Widgets:BOOL=ON -DCTK_ENABLE_Python_Wrapping:BOOL=ON -DCTK_APP_ctkSimplePythonShell:BOOL=ON -DPYTHON_EXECUTABLE:FILEPATH=${PYTHON_EXECUTABLE} -DPYTHON_INCLUDE_DIR:PATH=${PYTHON_INCLUDE_DIR} -DPYTHON_INCLUDE_DIR2:PATH=${PYTHON_INCLUDE_DIR2} -DPYTHON_LIBRARY:FILEPATH=${PYTHON_LIBRARY} ) else() list(APPEND ctk_optional_cache_args -DCTK_LIB_Scripting/Python/Widgets:BOOL=OFF -DCTK_ENABLE_Python_Wrapping:BOOL=OFF -DCTK_APP_ctkSimplePythonShell:BOOL=OFF ) endif() if(MITK_USE_DCMTK) list(APPEND ctk_optional_cache_args -DDCMTK_DIR:PATH=${DCMTK_DIR} -DDCMTK_CMAKE_DEBUG_POSTFIX:STRING=d ) list(APPEND proj_DEPENDENCIES DCMTK) else() list(APPEND ctk_optional_cache_args -DDCMTK_URL:STRING=${MITK_THIRDPARTY_DOWNLOAD_PREFIX_URL}/CTK_DCMTK_085525e6.tar.gz ) endif() if(CTEST_USE_LAUNCHERS) list(APPEND ctk_optional_cache_args "-DCMAKE_PROJECT_${proj}_INCLUDE:FILEPATH=${CMAKE_ROOT}/Modules/CTestUseLaunchers.cmake" ) endif() set (ctk_qt_args -DCTK_QT_VERSION:STRING=${DESIRED_QT_VERSION}) if (DESIRED_QT_VERSION MATCHES "4") list(APPEND ctk_qt_args -DQT_QMAKE_EXECUTABLE:FILEPATH=${QT_QMAKE_EXECUTABLE}) endif() FOREACH(type RUNTIME ARCHIVE LIBRARY) IF(DEFINED CTK_PLUGIN_${type}_OUTPUT_DIRECTORY) LIST(APPEND mitk_optional_cache_args -DCTK_PLUGIN_${type}_OUTPUT_DIRECTORY:PATH=${CTK_PLUGIN_${type}_OUTPUT_DIRECTORY}) ENDIF() ENDFOREACH() ExternalProject_Add(${proj} LIST_SEPARATOR ${sep} - URL ${MITK_THIRDPARTY_DOWNLOAD_PREFIX_URL}/CTK_${revision_tag}.tar.gz - URL_MD5 135910e407bd1f5de29d2a0a9efe5f80 - #GIT_REPOSITORY https://github.com/commontk/CTK.git - #GIT_TAG origin/master +# URL ${MITK_THIRDPARTY_DOWNLOAD_PREFIX_URL}/CTK_${revision_tag}.tar.gz +# URL /Users/fetzer/proj/ctk/CTK/CTK-XNAT-Upload.tar.gz + URL https://www.dropbox.com/s/imutmjs81ox9vsi/CTK-XNAT-Upload.tar.gz + URL_MD5 c495e7125451b27e557fb8cc4e3f31f2 UPDATE_COMMAND "" INSTALL_COMMAND "" CMAKE_GENERATOR ${gen} CMAKE_ARGS ${ep_common_args} ${ctk_optional_cache_args} ${ctk_qt_args} # The CTK PluginFramework cannot cope with # a non-empty CMAKE_DEBUG_POSTFIX for the plugin # libraries yet. -DCMAKE_DEBUG_POSTFIX:STRING= -DGit_EXECUTABLE:FILEPATH=${GIT_EXECUTABLE} -DGIT_EXECUTABLE:FILEPATH=${GIT_EXECUTABLE} -DCTK_LIB_CommandLineModules/Backend/LocalProcess:BOOL=ON -DCTK_LIB_CommandLineModules/Frontend/QtGui:BOOL=ON -DCTK_LIB_PluginFramework:BOOL=ON -DCTK_LIB_DICOM/Widgets:BOOL=ON -DCTK_LIB_XNAT/Core:BOOL=ON -DCTK_PLUGIN_org.commontk.eventadmin:BOOL=ON -DCTK_PLUGIN_org.commontk.configadmin:BOOL=ON -DCTK_USE_GIT_PROTOCOL:BOOL=OFF -DDCMTK_URL:STRING=${MITK_THIRDPARTY_DOWNLOAD_PREFIX_URL}/CTK_DCMTK_085525e6.tar.gz - -DqRestAPI_URL:STRING=${MITK_THIRDPARTY_DOWNLOAD_PREFIX_URL}/qRestAPI_5f3a03b1.tar.gz # See bug 19073 -DPythonQt_URL:STRING=${MITK_THIRDPARTY_DOWNLOAD_PREFIX_URL}/PythonQt_36ab9c7c.tar.gz + -DqRestAPI_URL:STRING=${MITK_THIRDPARTY_DOWNLOAD_PREFIX_URL}/qRestAPI_4293694a.tar.gz CMAKE_CACHE_ARGS ${ep_common_cache_args} CMAKE_CACHE_DEFAULT_ARGS ${ep_common_cache_default_args} DEPENDS ${proj_DEPENDENCIES} ) ExternalProject_Get_Property(${proj} binary_dir) set(CTK_DIR ${binary_dir}) #set(CTK_DIR ${ep_prefix}) #mitkFunctionInstallExternalCMakeProject(${proj}) else() mitkMacroEmptyExternalProject(${proj} "${proj_DEPENDENCIES}") endif() endif() diff --git a/Modules/XNAT/CMakeLists.txt b/Modules/XNAT/CMakeLists.txt index 37c14d6c2b..7ebf7a6c6a 100644 --- a/Modules/XNAT/CMakeLists.txt +++ b/Modules/XNAT/CMakeLists.txt @@ -1,5 +1,6 @@ MITK_CREATE_MODULE( + DEPENDS MitkCore MitkQtWidgets PACKAGE_DEPENDS PUBLIC CTK|CTKXNATCore - PRIVATE Qt4 Qt5|UiTools+XmlPatterns + PRIVATE Qt4|QtGui Qt5|UiTools+XmlPatterns ) diff --git a/Modules/XNAT/files.cmake b/Modules/XNAT/files.cmake index 766d942c9e..dc73aa11da 100644 --- a/Modules/XNAT/files.cmake +++ b/Modules/XNAT/files.cmake @@ -1,9 +1,15 @@ file(GLOB_RECURSE H_FILES RELATIVE "${CMAKE_CURRENT_SOURCE_DIR}" "${CMAKE_CURRENT_SOURCE_DIR}/include/*") set(CPP_FILES mitkXnatSessionTracker.cpp + QmitkXnatTreeModel.cpp ) set(MOC_H_FILES - include/mitkXnatSessionTracker.h + include/mitkXnatSessionTracker.h + include/QmitkXnatTreeModel.h +) + +set(QRC_FILES + resources/xnat.qrc ) diff --git a/Modules/XNAT/include/QmitkXnatTreeModel.h b/Modules/XNAT/include/QmitkXnatTreeModel.h new file mode 100644 index 0000000000..ad4ab5fd47 --- /dev/null +++ b/Modules/XNAT/include/QmitkXnatTreeModel.h @@ -0,0 +1,51 @@ +/*=================================================================== + +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 QMITKXNATTREEMODEL_H +#define QMITKXNATTREEMODEL_H + +// CTK includes +#include + +// MITK includes +#include "MitkXNATExports.h" + +namespace mitk { +class DataNode; +} + +class MITKXNAT_EXPORT QmitkXnatTreeModel : public ctkXnatTreeModel +{ + Q_OBJECT + +public: + QmitkXnatTreeModel(); + + virtual QVariant data(const QModelIndex& index, int role) const; + + virtual bool dropMimeData(const QMimeData *data, Qt::DropAction action, int row, int column, const QModelIndex &parent); + + using QAbstractItemModel::supportedDropActions; + virtual Qt::DropActions supportedDropActions(); + + virtual Qt::ItemFlags flags(const QModelIndex &index) const; + + signals: + void ResourceDropped(const QList&, ctkXnatObject*); + +}; + +#endif // QMITKXNATTREEMODEL_H diff --git a/Modules/XNAT/resources/experiment.ico b/Modules/XNAT/resources/experiment.ico new file mode 100644 index 0000000000..c3fc5dc17f Binary files /dev/null and b/Modules/XNAT/resources/experiment.ico differ diff --git a/Modules/XNAT/resources/project.ico b/Modules/XNAT/resources/project.ico new file mode 100644 index 0000000000..9c265052c4 Binary files /dev/null and b/Modules/XNAT/resources/project.ico differ diff --git a/Modules/XNAT/resources/server.ico b/Modules/XNAT/resources/server.ico new file mode 100644 index 0000000000..cb161d7cb6 Binary files /dev/null and b/Modules/XNAT/resources/server.ico differ diff --git a/Modules/XNAT/resources/subject.ico b/Modules/XNAT/resources/subject.ico new file mode 100644 index 0000000000..f42b26c240 Binary files /dev/null and b/Modules/XNAT/resources/subject.ico differ diff --git a/Modules/XNAT/resources/xnat.qrc b/Modules/XNAT/resources/xnat.qrc new file mode 100644 index 0000000000..7d6e5f8ecf --- /dev/null +++ b/Modules/XNAT/resources/xnat.qrc @@ -0,0 +1,8 @@ + + + server.ico + project.ico + subject.ico + experiment.ico + + diff --git a/Modules/XNAT/src/QmitkXnatTreeModel.cpp b/Modules/XNAT/src/QmitkXnatTreeModel.cpp new file mode 100644 index 0000000000..64703ceed4 --- /dev/null +++ b/Modules/XNAT/src/QmitkXnatTreeModel.cpp @@ -0,0 +1,111 @@ +/*=================================================================== + +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 "QmitkXnatTreeModel.h" + +#include + +#include + +#include +#include +#include +#include + +QmitkXnatTreeModel::QmitkXnatTreeModel () + : ctkXnatTreeModel() +{ + +} + +QVariant QmitkXnatTreeModel::data(const QModelIndex& index, int role) const +{ + if (!index.isValid()) + { + return QVariant(); + } + + if (role == Qt::DecorationRole) + { + ctkXnatObject* xnatObject = this->xnatObject(index); + QString path; + + if(dynamic_cast(xnatObject)) + { + path = ":/xnat/server.ico"; + } + else if(dynamic_cast(xnatObject)) + { + path = ":/xnat/project.ico"; + } + else if(dynamic_cast(xnatObject)) + { + path = ":/xnat/subject.ico"; + } + else if(dynamic_cast(xnatObject)) + { + path = ":/xnat/experiment.ico"; + } + return QIcon(path); + } + return ctkXnatTreeModel::data(index, role); +} + +bool QmitkXnatTreeModel::dropMimeData(const QMimeData *data, Qt::DropAction action, int /*row*/, int /*column*/, const QModelIndex &parent) +{ + if (action == Qt::IgnoreAction) + return true; + + // Return true if data can be handled + bool returnVal (false); + + if (data->hasFormat(QmitkMimeTypes::DataNodePtrs)) + { + returnVal = true; + QList droppedNodes = QmitkMimeTypes::ToDataNodePtrList(data); + ctkXnatObject* parentObj = this->xnatObject(parent); + emit ResourceDropped(droppedNodes, parentObj); + } + return returnVal; +} + +Qt::DropActions QmitkXnatTreeModel::supportedDropActions() +{ + return Qt::CopyAction; +} + +Qt::ItemFlags QmitkXnatTreeModel::flags(const QModelIndex &index) const +{ + Qt::ItemFlags defaultFlags = ctkXnatTreeModel::flags(index); + + + if (index.isValid()) + { + ctkXnatProject* xnatProj = dynamic_cast(this->xnatObject(index)); + + // No dropping at project level allowed + if (xnatProj == NULL) + { + return Qt::ItemIsDropEnabled | defaultFlags; + } + else + { + return defaultFlags; + } + } + else + return defaultFlags; +} diff --git a/Plugins/org.mitk.gui.qt.xnat/src/internal/QmitkXnatEditor.cpp b/Plugins/org.mitk.gui.qt.xnat/src/internal/QmitkXnatEditor.cpp index 68fb2bd7e5..146673de9c 100644 --- a/Plugins/org.mitk.gui.qt.xnat/src/internal/QmitkXnatEditor.cpp +++ b/Plugins/org.mitk.gui.qt.xnat/src/internal/QmitkXnatEditor.cpp @@ -1,565 +1,573 @@ /*=================================================================== 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 "QmitkXnatEditor.h" // Qmitk #include "QmitkXnatObjectEditorInput.h" #include "org_mitk_gui_qt_xnatinterface_Activator.h" // CTK XNAT Core #include "ctkXnatObject.h" #include "ctkXnatDataModel.h" #include "ctkXnatFile.h" #include "ctkXnatResource.h" #include "ctkXnatScan.h" #include "ctkXnatScanFolder.h" #include "ctkXnatAssessor.h" #include "ctkXnatAssessorFolder.h" #include "ctkXnatReconstruction.h" #include "ctkXnatReconstructionFolder.h" // CTK XNAT Widgets #include "ctkXnatListModel.h" // Blueberry #include #include #include // Qt #include #include #include #include #include #include // MITK #include #include // Poco #include const QString QmitkXnatEditor::EDITOR_ID = "org.mitk.editors.xnat.browser"; QmitkXnatEditor::QmitkXnatEditor() : m_DownloadPath(berry::Platform::GetPreferencesService()-> GetSystemPreferences()->Node("/XnatConnection")->Get("Download Path", "")), m_ListModel(new ctkXnatListModel()), m_Session(0), m_DataStorageServiceTracker(mitk::org_mitk_gui_qt_xnatinterface_Activator::GetContext()), m_SelectionListener(new berry::SelectionChangedAdapter(this, &QmitkXnatEditor::SelectionChanged)) { m_DataStorageServiceTracker.open(); if (m_DownloadPath.isEmpty()) { QString xnatFolder = "XNAT_DOWNLOADS"; QDir dir(mitk::org_mitk_gui_qt_xnatinterface_Activator::GetContext()->getDataFile("").absoluteFilePath()); dir.mkdir(xnatFolder); dir.setPath(dir.path() + "/" + xnatFolder); m_DownloadPath = dir.path() + "/"; } } QmitkXnatEditor::~QmitkXnatEditor() { delete m_ListModel; berry::ISelectionService* s = GetSite()->GetWorkbenchWindow()->GetSelectionService(); s->RemoveSelectionListener(m_SelectionListener.data()); m_DataStorageServiceTracker.close(); } bool QmitkXnatEditor::IsDirty() const { return false; } bool QmitkXnatEditor::IsSaveAsAllowed() const { return false; } void QmitkXnatEditor::Init(berry::IEditorSite::Pointer site, berry::IEditorInput::Pointer input) { this->SetSite(site); berry::QtEditorPart::SetInput(input); this->SetInput(input); } void QmitkXnatEditor::DoSave() { } void QmitkXnatEditor::DoSaveAs() { } void QmitkXnatEditor::SetInput(berry::IEditorInput::Pointer input) { QmitkXnatObjectEditorInput::Pointer oPtr = input.Cast(); if (oPtr.IsNotNull()) { berry::QtEditorPart::SetInput(oPtr); this->GetEditorInput().Cast()->GetXnatObject()->fetch(); } } void QmitkXnatEditor::SetFocus() { } void QmitkXnatEditor::CreateQtPartControl(QWidget *parent) { // create GUI widgets from the Qt Designer's .ui file m_Controls.setupUi(parent); m_Controls.buttonDownload->setEnabled(false); m_Controls.labelDownload->setText("Select a xnat file, resource, scan, or scan folder to download..."); GetSite()->GetWorkbenchWindow()->GetSelectionService()->AddSelectionListener(m_SelectionListener.data()); connect(m_Controls.treeView, SIGNAL(activated(const QModelIndex&)), this, SLOT(OnObjectActivated(const QModelIndex&))); connect(m_Controls.buttonDownload, SIGNAL(clicked()), this, SLOT(DownloadResource())); connect(m_Controls.buttonDataModel, SIGNAL(clicked()), this, SLOT(OnDataModelButtonClicked())); connect(m_Controls.buttonProject, SIGNAL(clicked()), this, SLOT(OnProjectButtonClicked())); connect(m_Controls.buttonSubject, SIGNAL(clicked()), this, SLOT(OnSubjectButtonClicked())); connect(m_Controls.buttonExperiment, SIGNAL(clicked()), this, SLOT(OnExperimentButtonClicked())); connect(m_Controls.buttonKindOfData, SIGNAL(clicked()), this, SLOT(OnKindOfDataButtonClicked())); connect(m_Controls.buttonSession, SIGNAL(clicked()), this, SLOT(OnSessionButtonClicked())); connect(m_Controls.buttonResource, SIGNAL(clicked()), this, SLOT(OnResourceButtonClicked())); connect(m_Controls.treeView, SIGNAL(clicked(const QModelIndex&)), SLOT(itemSelected(const QModelIndex&))); m_Tracker = new mitk::XnatSessionTracker(mitk::org_mitk_gui_qt_xnatinterface_Activator::GetXnatModuleContext()); connect(m_Tracker, SIGNAL(AboutToBeClosed(ctkXnatSession*)), this, SLOT(CleanListModel(ctkXnatSession*))); connect(m_Tracker, SIGNAL(Opened(ctkXnatSession*)), this, SLOT(UpdateSession(ctkXnatSession*))); m_Tracker->Open(); // Makes the breadcrumb feature invisible for (int i = 0; i < m_Controls.breadcrumbHorizontalLayout->count() - 1; i++) { QLayoutItem* child = m_Controls.breadcrumbHorizontalLayout->itemAt(i); child->widget()->setVisible(false); } for (int i = 0; i < m_Controls.breadcrumbDescriptionLayout->count() - 1; i++) { QLayoutItem* child = m_Controls.breadcrumbDescriptionLayout->itemAt(i); child->widget()->setVisible(false); } QmitkXnatObjectEditorInput::Pointer oPtr = GetEditorInput().Cast(); if (oPtr.IsNotNull()) { UpdateList(); } else { ctkXnatSession* session; try { session = mitk::org_mitk_gui_qt_xnatinterface_Activator::GetXnatModuleContext()->GetService( mitk::org_mitk_gui_qt_xnatinterface_Activator::GetXnatModuleContext()->GetServiceReference()); } catch (std::invalid_argument) { session = 0; } UpdateSession(session); } } void QmitkXnatEditor::UpdateList() { QmitkXnatObjectEditorInput::Pointer xoPtr(GetEditorInput().Cast()); if (xoPtr.IsNull()) return; ctkXnatObject* inputObject = xoPtr->GetXnatObject(); if (inputObject == NULL) return; m_Controls.treeView->setModel(m_ListModel); m_ListModel->setRootObject(inputObject); m_Controls.treeView->reset(); // recursive method to check parents of the inputObject m_ParentCount = ParentChecker(inputObject); // breadcrumb labels for (int i = 0; i < m_Controls.breadcrumbHorizontalLayout->count() - 1; i++) { QLayoutItem* child = m_Controls.breadcrumbHorizontalLayout->itemAt(i); child->widget()->setVisible(false); } for (int i = 0; i < m_Controls.breadcrumbDescriptionLayout->count() - 1; i++) { QLayoutItem* child = m_Controls.breadcrumbDescriptionLayout->itemAt(i); child->widget()->setVisible(false); } ctkXnatObject* parent = NULL; for (int i = m_ParentCount * 2; i >= 0; i--) { if (i > 12) break; m_Controls.breadcrumbDescriptionLayout->itemAt(i)->widget()->setVisible(true); QLayoutItem* child = m_Controls.breadcrumbHorizontalLayout->itemAt(i); child->widget()->setVisible(true); if (i > 0) { m_Controls.breadcrumbHorizontalLayout->itemAt(i - 1)->widget()->setVisible(true); m_Controls.breadcrumbDescriptionLayout->itemAt(i - 1)->widget()->setVisible(true); } if (parent == NULL) { parent = inputObject; } // create breadcrumb button QPushButton* breadcrumbButton = dynamic_cast(child->widget()); breadcrumbButton->setText(parent->id()); parent = parent->parent(); i--; } m_Controls.buttonDataModel->setText("root"); m_Controls.buttonDownload->setEnabled(false); m_Controls.labelDownload->setVisible(true); } void QmitkXnatEditor::SelectionChanged(const berry::IWorkbenchPart::Pointer& sourcepart, const berry::ISelection::ConstPointer& selection) { // check for null selection if (selection.IsNull()) { return; } // exclude own selection events and check whether this kind of selection can be handled if (sourcepart != this && selection.Cast()) { berry::IStructuredSelection::ConstPointer currentSelection = selection.Cast(); // iterates over the selection for (berry::IStructuredSelection::iterator itr = currentSelection->Begin(); itr != currentSelection->End(); ++itr) { if (berry::SmartPointer objectPointer = itr->Cast()) { // get object of selected ListWidgetElement ctkXnatObject* object = objectPointer->GetQModelIndex().data(Qt::UserRole).value(); // if a file is selected, don't change the input and list view if (dynamic_cast(object) == NULL) { QmitkXnatObjectEditorInput::Pointer oPtr(new QmitkXnatObjectEditorInput(object)); berry::IEditorInput::Pointer editorInput(oPtr); if (!(editorInput == this->GetEditorInput())) this->SetInput(editorInput); UpdateList(); } } } } } void QmitkXnatEditor::DownloadResource() { - if (!m_Controls.treeView->selectionModel()->hasSelection()) + if (!m_Controls.listView->selectionModel()->hasSelection()) return; - const QModelIndex index = m_Controls.treeView->selectionModel()->currentIndex(); + const QModelIndex index = m_Controls.listView->selectionModel()->currentIndex(); QVariant variant = m_ListModel->data(index, Qt::UserRole); if (variant.isValid()) { ctkXnatObject* resource = variant.value(); if (dynamic_cast(resource) == NULL) { MITK_INFO << "Download started ..."; MITK_INFO << "..."; QString resourceName = m_ListModel->data(index, Qt::DisplayRole).toString(); QString resourcePath = m_DownloadPath + resourceName + ".zip"; resource->download(resourcePath); // Testing if the path exists QDir downDir(m_DownloadPath); if (downDir.exists(resourceName + ".zip")) { MITK_INFO << "Download of " << resourceName.toStdString() << ".zip was completed!"; } else { MITK_INFO << "Download of " << resourceName.toStdString() << ".zip failed!"; } } else { InternalFileDownload(index); } } } +void QmitkXnatEditor::DownloadFile() +{ + if (!m_Controls.listView->selectionModel()->hasSelection()) + return; + const QModelIndex index = m_Controls.listView->selectionModel()->currentIndex(); + InternalFileDownload(index); +} + void QmitkXnatEditor::ToHigherLevel() { ctkXnatObject* parent = GetEditorInput().Cast()->GetXnatObject()->parent(); if (parent == NULL) { return; } QmitkXnatObjectEditorInput::Pointer oPtr(new QmitkXnatObjectEditorInput(parent)); berry::IEditorInput::Pointer editorInput(oPtr); this->SetInput(editorInput); UpdateList(); } void QmitkXnatEditor::OnObjectActivated(const QModelIndex &index) { if (!index.isValid()) return; ctkXnatObject* child = GetEditorInput().Cast()->GetXnatObject()->children().at(index.row()); if (child != NULL) { ctkXnatFile* file = dynamic_cast(child); if (file != NULL) { // Download file and put into datamanager InternalFileDownload(index); mitk::IDataStorageService* dsService = m_DataStorageServiceTracker.getService(); if (dsService != NULL) { QString name = file->property("Name"); QString filePath = m_DownloadPath + name; if (file->property("collection") == "DICOM") { QDirIterator it(m_DownloadPath, QStringList() << name, QDir::Files, QDirIterator::Subdirectories); while (it.hasNext()) { it.next(); filePath = it.filePath(); } } mitk::IDataStorageService* dsService = m_DataStorageServiceTracker.getService(); mitk::DataStorage::Pointer dataStorage = dsService->GetDataStorage()->GetDataStorage(); QStringList list; list << filePath; try { QmitkIOUtil::Load(list, *dataStorage); } catch (const mitk::Exception& e) { MITK_INFO << e; return; } mitk::RenderingManager::GetInstance()->InitializeViewsByBoundingObjects( dsService->GetDataStorage()->GetDataStorage()); } } else { // Updates the root item QmitkXnatObjectEditorInput::Pointer oPtr(new QmitkXnatObjectEditorInput(child)); berry::IEditorInput::Pointer editorInput(oPtr); this->SetInput(editorInput); this->GetEditorInput().Cast()->GetXnatObject()->fetch(); UpdateList(); } } } void QmitkXnatEditor::InternalFileDownload(const QModelIndex& index) { QVariant variant = m_ListModel->data(index, Qt::UserRole); if (variant.isValid()) { ctkXnatFile* file = dynamic_cast(variant.value()); if (file != NULL) { // Testing if the file exists QDir downDir(m_DownloadPath); if (downDir.exists(file->property("Name"))) { MITK_INFO << "File exists already!"; return; } if (file->property("collection") == QString("DICOM")) { ctkXnatObject* parent = file->parent(); QString filePath = m_DownloadPath + parent->property("label") + ".zip"; parent->download(filePath); std::ifstream in(filePath.toStdString().c_str(), std::ios::binary); poco_assert(in); // decompress to XNAT_DOWNLOAD dir Poco::Zip::Decompress dec(in, Poco::Path(m_DownloadPath.toStdString())); dec.decompressAllFiles(); in.close(); QFile::remove(filePath); } else { MITK_INFO << "Download started ..."; MITK_INFO << "..."; QString name = file->property("Name"); QString filePath = m_DownloadPath + name; file->download(filePath); // Testing if the file exists QDir downDir(m_DownloadPath); if (downDir.exists(name)) { MITK_INFO << "Download of " << file->name().toStdString() << " was completed!"; } else { MITK_INFO << "Download of " << file->name().toStdString() << " failed!"; } } } else { MITK_INFO << "Selection was not a file!"; } } } int QmitkXnatEditor::ParentChecker(ctkXnatObject* child) { int sum; if (child->parent() == NULL) { return 0; } else { sum = 1 + ParentChecker(child->parent()); } return sum; } void QmitkXnatEditor::OnDataModelButtonClicked() { for (int i = m_ParentCount; i > 0; i--) { ToHigherLevel(); } } void QmitkXnatEditor::OnProjectButtonClicked() { for (int i = m_ParentCount - 1; i > 0; i--) { ToHigherLevel(); } } void QmitkXnatEditor::OnSubjectButtonClicked() { for (int i = m_ParentCount - 2; i > 0; i--) { ToHigherLevel(); } } void QmitkXnatEditor::OnExperimentButtonClicked() { for (int i = m_ParentCount - 3; i > 0; i--) { ToHigherLevel(); } } void QmitkXnatEditor::OnKindOfDataButtonClicked() { for (int i = m_ParentCount - 4; i > 0; i--) { ToHigherLevel(); } } void QmitkXnatEditor::OnSessionButtonClicked() { for (int i = m_ParentCount - 5; i > 0; i--) { ToHigherLevel(); } } void QmitkXnatEditor::OnResourceButtonClicked() { for (int i = m_ParentCount - 6; i > 0; i--) { ToHigherLevel(); } } void QmitkXnatEditor::UpdateSession(ctkXnatSession* session) { GetSite()->GetWorkbenchWindow()->GetSelectionService()->RemoveSelectionListener(m_SelectionListener.data()); if (session != 0 && session->isOpen()) { m_Controls.labelInfo->setText("Current Position:"); m_Controls.labelInfo->setStyleSheet("QLabel { color: black; }"); // Fill model and show in the GUI QmitkXnatObjectEditorInput::Pointer xoPtr(new QmitkXnatObjectEditorInput(session->dataModel())); berry::IEditorInput::Pointer editorInput(xoPtr); this->SetInput(editorInput); this->GetEditorInput().Cast()->GetXnatObject()->fetch(); UpdateList(); } else { m_Controls.labelInfo->setText("Please check the Preferences of the XNAT Connection.\nMaybe they are not ok."); m_Controls.labelInfo->setStyleSheet("QLabel { color: red; }"); } GetSite()->GetWorkbenchWindow()->GetSelectionService()->AddSelectionListener(m_SelectionListener.data()); } void QmitkXnatEditor::CleanListModel(ctkXnatSession* session) { if (session != 0) { - m_Controls.treeView->setModel(0); + m_Controls.listView->setModel(0); m_ListModel->setRootObject(0); m_Controls.treeView->reset(); } } void QmitkXnatEditor::itemSelected(const QModelIndex &index) { ctkXnatObject* xnatObject = m_ListModel->data(index, Qt::UserRole).value(); bool downloadable = false; downloadable |= dynamic_cast(xnatObject) != NULL; downloadable |= dynamic_cast(xnatObject) != NULL; downloadable |= dynamic_cast(xnatObject) != NULL; downloadable |= dynamic_cast(xnatObject) != NULL; downloadable |= dynamic_cast(xnatObject) != NULL; downloadable |= dynamic_cast(xnatObject) != NULL; downloadable |= dynamic_cast(xnatObject) != NULL; downloadable |= dynamic_cast(xnatObject) != NULL; m_Controls.buttonDownload->setEnabled(downloadable); m_Controls.labelDownload->setVisible(!downloadable); } diff --git a/Plugins/org.mitk.gui.qt.xnat/src/internal/QmitkXnatEditorControls.ui b/Plugins/org.mitk.gui.qt.xnat/src/internal/QmitkXnatEditorControls.ui index 7681d055cf..6bc1ff5385 100644 --- a/Plugins/org.mitk.gui.qt.xnat/src/internal/QmitkXnatEditorControls.ui +++ b/Plugins/org.mitk.gui.qt.xnat/src/internal/QmitkXnatEditorControls.ui @@ -1,473 +1,473 @@ QmitkXnatEditorControls 0 0 719 655 0 0 QmitkTemplate xnat_icon.icoxnat_icon.ico Current Position: 0 0 Server 0 0 >> 0 0 Project 0 0 >> 0 0 Subject 0 0 >> 0 0 Experiment 0 0 >> 0 0 Kind of Data 0 0 >> 0 0 Image Session 0 0 >> 0 0 Resource Folder Qt::Horizontal 40 20 6 QLayout::SetDefaultConstraint 0 0 0 Data Model true 0 0 >> 0 0 Qt::LeftToRight Project 0 0 >> 0 0 Subject 0 0 >> 0 0 Experiment 0 0 >> 0 0 Kind of Data 0 0 >> 0 0 Session 0 0 >> 0 0 Resource Qt::Horizontal 40 20 - + Qt::Horizontal QSizePolicy::Expanding 20 20 0 0 Download diff --git a/Plugins/org.mitk.gui.qt.xnat/src/internal/QmitkXnatTreeBrowserView.cpp b/Plugins/org.mitk.gui.qt.xnat/src/internal/QmitkXnatTreeBrowserView.cpp index 4b0d7cfba1..4bca0689eb 100644 --- a/Plugins/org.mitk.gui.qt.xnat/src/internal/QmitkXnatTreeBrowserView.cpp +++ b/Plugins/org.mitk.gui.qt.xnat/src/internal/QmitkXnatTreeBrowserView.cpp @@ -1,325 +1,560 @@ /*=================================================================== 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 "QmitkXnatTreeBrowserView.h" // Qmitk #include "QmitkXnatObjectEditorInput.h" #include "QmitkXnatEditor.h" #include "org_mitk_gui_qt_xnatinterface_Activator.h" // Blueberry #include #include // CTK XNAT Core +#include +#include +#include +#include #include "ctkXnatFile.h" +#include +#include +#include +#include +#include +#include +#include +#include // Qt +#include #include +#include +#include #include #include #include +#include // MITK #include +#include #include // Poco #include const std::string QmitkXnatTreeBrowserView::VIEW_ID = "org.mitk.views.xnat.treebrowser"; QmitkXnatTreeBrowserView::QmitkXnatTreeBrowserView() : -m_TreeModel(new ctkXnatTreeModel()), +m_DataStorageServiceTracker(mitk::org_mitk_gui_qt_xnatinterface_Activator::GetContext()), +m_TreeModel(new QmitkXnatTreeModel()), m_Tracker(0), -m_DownloadPath(berry::Platform::GetPreferencesService()->GetSystemPreferences()->Node("/XnatConnection")->Get("Download Path", "")), -m_DataStorageServiceTracker(mitk::org_mitk_gui_qt_xnatinterface_Activator::GetContext()) +m_DownloadPath(berry::Platform::GetPreferencesService()->GetSystemPreferences()->Node("/XnatConnection")->Get("Download Path", "")) { m_DataStorageServiceTracker.open(); // Set DownloadPath if (m_DownloadPath.isEmpty()) { QString xnatFolder = "XNAT_DOWNLOADS"; QDir dir(mitk::org_mitk_gui_qt_xnatinterface_Activator::GetContext()->getDataFile("").absoluteFilePath()); dir.mkdir(xnatFolder); dir.setPath(dir.path() + "/" + xnatFolder); m_DownloadPath = dir.path() + "/"; } } QmitkXnatTreeBrowserView::~QmitkXnatTreeBrowserView() { delete m_TreeModel; delete m_Tracker; } void QmitkXnatTreeBrowserView::SetFocus() { } void QmitkXnatTreeBrowserView::CreateQtPartControl(QWidget *parent) { // Create GUI widgets from the Qt Designer's .ui file m_Controls.setupUi(parent); m_Controls.treeView->setModel(m_TreeModel); m_Controls.treeView->header()->hide(); + m_Controls.treeView->setSelectionMode(QAbstractItemView::ExtendedSelection); + m_Controls.treeView->setAcceptDrops(true); + m_Controls.treeView->setDropIndicatorShown(true); m_Controls.labelError->setText("Please use the 'Connect' button in the Preferences."); m_Controls.labelError->setStyleSheet("QLabel { color: red; }"); m_SelectionProvider = new berry::QtSelectionProvider(); this->SetSelectionProvider(); m_Controls.treeView->setSelectionMode(QAbstractItemView::SingleSelection); m_Controls.treeView->setContextMenuPolicy(Qt::CustomContextMenu); m_Tracker = new mitk::XnatSessionTracker(mitk::org_mitk_gui_qt_xnatinterface_Activator::GetXnatModuleContext()); - m_NodeMenu = new QMenu(m_Controls.treeView); + + m_ContextMenu = new QMenu(m_Controls.treeView); connect(m_Controls.treeView, SIGNAL(customContextMenuRequested(const QPoint&)), - this, SLOT(NodeTableViewContextMenuRequested(const QPoint&))); + this, SLOT(OnContextMenuRequested(const QPoint&))); connect(m_Tracker, SIGNAL(AboutToBeClosed(ctkXnatSession*)), this, SLOT(CleanTreeModel(ctkXnatSession*))); connect(m_Tracker, SIGNAL(Opened(ctkXnatSession*)), this, SLOT(UpdateSession(ctkXnatSession*))); m_Tracker->Open(); ctkXnatSession* session; try { session = mitk::org_mitk_gui_qt_xnatinterface_Activator::GetXnatModuleContext()->GetService( mitk::org_mitk_gui_qt_xnatinterface_Activator::GetXnatModuleContext()->GetServiceReference()); } catch (std::invalid_argument) { session = 0; } if (session != 0) { m_Controls.labelError->setVisible(false); } else { m_Controls.labelError->setVisible(true); } connect(m_Controls.treeView, SIGNAL(activated(const QModelIndex&)), this, SLOT(OnActivatedNode(const QModelIndex&))); + connect(m_TreeModel, SIGNAL(ResourceDropped(const QList&, ctkXnatObject*)), this, SLOT(OnUploadResource(const QList&, ctkXnatObject*))); } void QmitkXnatTreeBrowserView::OnActivatedNode(const QModelIndex& index) { if (!index.isValid()) return; berry::IWorkbenchPage::Pointer page = GetSite()->GetPage(); QmitkXnatObjectEditorInput::Pointer oPtr(new QmitkXnatObjectEditorInput(index.data(Qt::UserRole).value())); berry::IEditorInput::Pointer editorInput(oPtr); berry::IEditorPart::Pointer reuseEditor = page->FindEditor(editorInput); if (reuseEditor) { // Just set it activ page->Activate(reuseEditor); } else { QList editors = page->FindEditors(berry::IEditorInput::Pointer(0), QmitkXnatEditor::EDITOR_ID, berry::IWorkbenchPage::MATCH_ID); if (editors.isEmpty()) { ctkXnatFile* file = dynamic_cast(oPtr->GetXnatObject()); if (file != NULL) { // If the selected node is a file, so show it in MITK InternalFileDownload(index, true); } else { // No XnatEditor is currently open, create a new one page->OpenEditor(editorInput, QmitkXnatEditor::EDITOR_ID); } } else { // Reuse an existing editor reuseEditor = editors.front()->GetEditor(true); page->ReuseEditor(reuseEditor.Cast(), editorInput); page->Activate(reuseEditor); } } } void QmitkXnatTreeBrowserView::SetSelectionProvider() { GetSite()->SetSelectionProvider(m_SelectionProvider); } void QmitkXnatTreeBrowserView::UpdateSession(ctkXnatSession* session) { if (session != 0 && session->isOpen()) { m_Controls.labelError->setVisible(false); // Fill model and show in the GUI m_TreeModel->addDataModel(session->dataModel()); m_Controls.treeView->reset(); m_SelectionProvider->SetItemSelectionModel(m_Controls.treeView->selectionModel()); + + connect(session, SIGNAL(progress(QUuid,double)), this, SLOT(OnProgress(QUuid,double))); + connect(session, SIGNAL(uploadFinished()), this, SLOT(OnProgress(QUuid,double))); } } void QmitkXnatTreeBrowserView::CleanTreeModel(ctkXnatSession* session) { if (session != 0) { m_TreeModel->removeDataModel(session->dataModel()); m_Controls.treeView->reset(); } } +void QmitkXnatTreeBrowserView::OnProgress(QUuid /*queryID*/, double progress) +{ + unsigned int currentProgress = progress*100; + if (currentProgress < 1) + mitk::ProgressBar::GetInstance()->AddStepsToDo(100); + else + mitk::ProgressBar::GetInstance()->Progress(); +} + void QmitkXnatTreeBrowserView::InternalFileDownload(const QModelIndex& index, bool loadData) { QVariant variant = m_TreeModel->data(index, Qt::UserRole); if (variant.isValid()) { ctkXnatFile* file = dynamic_cast(variant.value()); if (file != NULL) { QDir downDir(m_DownloadPath); QString filePath = m_DownloadPath + file->name(); // Testing if the file exists already if (downDir.exists(file->name())) { MITK_INFO << "File '" << file->name().toStdString() << "' already exists!"; } else { if (file->property("collection") == QString("DICOM")) { ctkXnatObject* parent = file->parent(); filePath = m_DownloadPath + parent->property("label") + ".zip"; parent->download(filePath); std::ifstream in(filePath.toStdString().c_str(), std::ios::binary); poco_assert(in); // decompress to XNAT_DOWNLOAD dir Poco::Zip::Decompress dec(in, Poco::Path(m_DownloadPath.toStdString())); dec.decompressAllFiles(); in.close(); QFile::remove(filePath); } else { MITK_INFO << "Download started ..."; MITK_INFO << "..."; file->download(filePath); // Testing if the file exists now if (downDir.exists(file->name())) { MITK_INFO << "Download of " << file->name().toStdString() << " was completed!"; } else { MITK_INFO << "Download of " << file->name().toStdString() << " failed!"; } } } if (downDir.exists(file->name()) || file->property("collection") == "DICOM") { if (loadData) { if (file->property("collection") == "DICOM") { // Search for the downloaded file an its file path QDirIterator it(m_DownloadPath, QStringList() << file->name(), QDir::Files, QDirIterator::Subdirectories); while (it.hasNext()) { it.next(); filePath = it.filePath(); } } if (filePath.isEmpty()) { MITK_INFO << "Decompressing failed!"; return; } else if (!QFile(filePath).exists()) { MITK_INFO << "Decompressing failed!"; return; } mitk::IDataStorageService* dsService = m_DataStorageServiceTracker.getService(); mitk::DataStorage::Pointer dataStorage = dsService->GetDataStorage()->GetDataStorage(); QStringList list; list << filePath; try { QmitkIOUtil::Load(list, *dataStorage); } catch (const mitk::Exception& e) { MITK_INFO << e; return; } mitk::RenderingManager::GetInstance()->InitializeViewsByBoundingObjects( dsService->GetDataStorage()->GetDataStorage()); } } } else { MITK_INFO << "Selection was not a file!"; } } } void QmitkXnatTreeBrowserView::OnContextMenuDownloadFile() { QModelIndex index = m_Controls.treeView->currentIndex(); InternalFileDownload(index, false); } void QmitkXnatTreeBrowserView::OnContextMenuDownloadAndOpenFile() { QModelIndex index = m_Controls.treeView->currentIndex(); InternalFileDownload(index, true); } -void QmitkXnatTreeBrowserView::NodeTableViewContextMenuRequested(const QPoint & pos) +void QmitkXnatTreeBrowserView::OnContextMenuCreateResourceFolder() +{ + const QModelIndex index = m_Controls.treeView->selectionModel()->currentIndex(); + ctkXnatObject* parentObject = m_TreeModel->xnatObject(index); + + if (parentObject != nullptr) + { + this->InternalAddResourceFolder(parentObject); + } +} + +ctkXnatResource* QmitkXnatTreeBrowserView::InternalAddResourceFolder(ctkXnatObject *parent) +{ + bool ok; + QString folderName = QInputDialog::getText(m_Controls.treeView, tr("Create XNAT resource folder"), + tr("Folder name:"), QLineEdit::Normal, tr("data"), &ok); + if (ok) + { + if (folderName.isEmpty()) + folderName = "NO LABEL"; + + return parent->addResourceFolder(folderName); + } + else + { + return nullptr; + } +} + +void QmitkXnatTreeBrowserView::InternalFileUpload(ctkXnatFile* file) +{ + try + { + file->save(); + } + catch (ctkXnatException &e) + { + QMessageBox msgbox; + msgbox.setText(e.what()); + msgbox.setIcon(QMessageBox::Critical); + msgbox.exec(); + } +} + +void QmitkXnatTreeBrowserView::OnContextMenuUploadFile() +{ + QString filename = QFileDialog::getOpenFileName(m_Controls.treeView, tr("Open File"), QDir::homePath()); + const QModelIndex index = m_Controls.treeView->selectionModel()->currentIndex(); + ctkXnatResource* resource = dynamic_cast(m_TreeModel->xnatObject(index)); + if (resource) + { + ctkXnatFile* file = new ctkXnatFile(resource); + file->setLocalFilePath(filename); + QFileInfo fileInfo (filename); + file->setName(fileInfo.fileName()); + file->setFileFormat("some format"); + file->setFileContent("some content"); + file->setFileTags("some, tags"); + file->save(); + m_TreeModel->addChildNode(index, file); + } +} + +#include +void QmitkXnatTreeBrowserView::OnUploadResource(const QList& droppedNodes, ctkXnatObject* parentObject) +{ + if (parentObject == nullptr) + return; + + if (dynamic_cast(parentObject)) + MITK_INFO<<"SESSION"; + else if (dynamic_cast(parentObject)) + MITK_INFO<<"DATAMODEL"; + else if (dynamic_cast(parentObject)) + MITK_INFO<<"PROJECT"; + else if (dynamic_cast(parentObject)) + MITK_INFO<<"SUBJECT"; + //1. If not dropped on a resource, create a new folder + //2. Save file locally + //3. Upload file + ctkXnatResource* resource = dynamic_cast(parentObject); + if (resource == nullptr) + { + resource = this->InternalAddResourceFolder(parentObject); + } + + if (resource == nullptr) + { + MITK_WARN << "Could not upload file! No resource available!"; + } + + mitk::DataNode* node = NULL; + foreach (node, droppedNodes) + { + mitk::BaseData* data = node->GetData(); + if (!data) + return; + + + QString fileName (QString::fromStdString(node->GetName())); + + ctkXnatFile* xnatFile = new ctkXnatFile(resource); + + if (dynamic_cast(data)) + { + fileName.append(".nrrd"); + } + else if (dynamic_cast(data)) + { + fileName.append(".vtk"); + } + else if (dynamic_cast(data)) + { + fileName.append(".mps"); + } + + xnatFile->setName(fileName); + + QString xnatFolder = "XNAT_UPLOADS"; + QDir dir(mitk::org_mitk_gui_qt_xnatinterface_Activator::GetContext()->getDataFile("").absoluteFilePath()); + dir.mkdir(xnatFolder); + + fileName = dir.path().append("/" + fileName); + mitk::IOUtil::Save (data, fileName.toStdString()); + + // TODO Check if file exists + // AbstractFileReader::SetDefaultDataNodeProperties + // und in die andere SetDefaultDataNodeProperties + // PropertyName klein: mtime.initial + Kommentar + mitk::StringProperty::Pointer orignalFilePath = mitk::StringProperty::New(); + node->GetProperty(orignalFilePath, "path"); + + xnatFile->setLocalFilePath(fileName); + // + xnatFile->setFileFormat("some format"); + xnatFile->setFileContent("some content"); + xnatFile->setFileTags("some, tags"); + // + xnatFile->save(); + m_TreeModel->addChildNode(m_Controls.treeView->currentIndex(), xnatFile); + parentObject->fetch(); + + // The filename for uploading +// QFileInfo fileInfo; + // if (surface) + // { + // // Save surface + // fileName.append(".stl"); + // xnatFile->setName(fileName); + // dir.setPath(dir.path().append("/" + fileName)); + +// QString origFile = QString::fromStdString(orignalFilePath->GetValueAsString()); +// origFile.append("/" + fileName); + // origFile.append(".stl"); + + // fileInfo.setFile(origFile); + // if (!fileInfo.exists()) + // mitk::IOUtil::SaveSurface(surface, dir.path().toStdString()); + // } +// this->uploadFileToXnat(xnatFile, dir.path()); + + // TODO delete file!!! + } +} + +void QmitkXnatTreeBrowserView::OnContextMenuRequested(const QPoint & pos) { - m_NodeMenu->clear(); + m_ContextMenu->clear(); QModelIndex index = m_Controls.treeView->indexAt(pos); - QVariant variant = m_TreeModel->data(index, Qt::UserRole); - if (variant.isValid()) + + ctkXnatObject* xnatObject = m_TreeModel->xnatObject(index); + + bool downloadable = false; + downloadable |= dynamic_cast(xnatObject)!=NULL; + downloadable |= dynamic_cast(xnatObject)!=NULL; + downloadable |= dynamic_cast(xnatObject)!=NULL; + downloadable |= dynamic_cast(xnatObject)!=NULL; + downloadable |= dynamic_cast(xnatObject)!=NULL; + downloadable |= dynamic_cast(xnatObject)!=NULL; + downloadable |= dynamic_cast(xnatObject)!=NULL; + downloadable |= dynamic_cast(xnatObject)!=NULL; + + bool canHaveResourceFolder = false; + canHaveResourceFolder |= dynamic_cast(xnatObject) != NULL; + canHaveResourceFolder |= dynamic_cast(xnatObject) != NULL; + canHaveResourceFolder |= dynamic_cast(xnatObject) != NULL; + + bool uploadFilePossible = false; + uploadFilePossible |= dynamic_cast(xnatObject) != NULL; + uploadFilePossible |= dynamic_cast(xnatObject) != NULL; + uploadFilePossible |= dynamic_cast(xnatObject) != NULL; + + if (downloadable) { - ctkXnatFile* file = dynamic_cast(variant.value()); - if (file != NULL) + QAction* actDownload = new QAction("Download", m_ContextMenu); + connect(actDownload, SIGNAL(triggered()), this, SLOT(OnContextMenuDownloadFile())); + m_ContextMenu->addAction(actDownload); + ctkXnatFile* file = dynamic_cast(xnatObject); + if (file) { - QAction* actShow = new QAction("Download and Open", m_NodeMenu); - QAction* actDownload = new QAction("Download", m_NodeMenu); - m_NodeMenu->addAction(actShow); - m_NodeMenu->addAction(actDownload); - connect(actShow, SIGNAL(triggered()), this, SLOT(OnContextMenuDownloadAndOpenFile())); - connect(actDownload, SIGNAL(triggered()), this, SLOT(OnContextMenuDownloadFile())); - m_NodeMenu->popup(QCursor::pos()); + QAction* actView = new QAction("Download and Open", m_ContextMenu); + connect(actView, SIGNAL(triggered()), this, SLOT(OnContextMenuDownloadAndOpenFile())); + m_ContextMenu->addAction(actView); } } + + if (canHaveResourceFolder) + { + QAction* actCreateResource = new QAction("Add resource folder", m_ContextMenu); + connect(actCreateResource, SIGNAL(triggered()), this, SLOT(OnContextMenuCreateResourceFolder())); + m_ContextMenu->addAction(actCreateResource); + } + + if (uploadFilePossible) + { + QAction* actUploadFile = new QAction("Upload File", m_ContextMenu); + connect(actUploadFile, SIGNAL(triggered()), this, SLOT(OnContextMenuUploadFile())); + m_ContextMenu->addAction(actUploadFile); + } + m_ContextMenu->popup(QCursor::pos()); } diff --git a/Plugins/org.mitk.gui.qt.xnat/src/internal/QmitkXnatTreeBrowserView.h b/Plugins/org.mitk.gui.qt.xnat/src/internal/QmitkXnatTreeBrowserView.h index 778ebe8571..dd47cdb39c 100644 --- a/Plugins/org.mitk.gui.qt.xnat/src/internal/QmitkXnatTreeBrowserView.h +++ b/Plugins/org.mitk.gui.qt.xnat/src/internal/QmitkXnatTreeBrowserView.h @@ -1,99 +1,108 @@ /*=================================================================== 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 QMITKXNATTREEBROWSERVIEW_H #define QMITKXNATTREEBROWSERVIEW_H #include #include #include "ui_QmitkXnatTreeBrowserViewControls.h" // ctkXnatCore #include "ctkXnatSession.h" // ctkXnatWidget -#include "ctkXnatTreeModel.h" +#include "QmitkXnatTreeModel.h" // MitkXNAT Module #include "mitkXnatSessionTracker.h" #include #include class QMenu; /*! \brief QmitkXnatTreeBrowserView \warning This class is not yet documented. Use "git blame" and ask the author to provide basic documentation. \sa QmitkFunctionality \ingroup ${plugin_target}_internal */ class QmitkXnatTreeBrowserView : public QmitkAbstractView { // this is needed for all Qt objects that should have a Qt meta-object // (everything that derives from QObject and wants to have signal/slots) Q_OBJECT public: QmitkXnatTreeBrowserView(); ~QmitkXnatTreeBrowserView(); static const std::string VIEW_ID; virtual void CreateQtPartControl(QWidget *parent) override; protected slots: /// \brief Opens or reuses the xnat editor with the activated node as root item. void OnActivatedNode(const QModelIndex& index); /// \brief Updates the ctkXnatSession and the user interface void UpdateSession(ctkXnatSession* session); /// \brief Cleans the tree model void CleanTreeModel(ctkXnatSession* session); - void NodeTableViewContextMenuRequested(const QPoint & pos); - + void OnContextMenuRequested(const QPoint & pos); void OnContextMenuDownloadAndOpenFile(); void OnContextMenuDownloadFile(); + void OnContextMenuCreateResourceFolder(); + void OnContextMenuUploadFile(); + + void OnUploadResource(const QList& , ctkXnatObject *); + + void OnProgress(QUuid, double); protected: virtual void SetFocus() override; Ui::QmitkXnatTreeBrowserViewControls m_Controls; private: void InternalFileDownload(const QModelIndex& index, bool loadData); + void InternalFileUpload(ctkXnatFile *file); + ctkXnatResource* InternalAddResourceFolder(ctkXnatObject* parent); + berry::QtSelectionProvider::Pointer m_SelectionProvider; void SetSelectionProvider() override; ctkServiceTracker m_DataStorageServiceTracker; - ctkXnatTreeModel* m_TreeModel; + QmitkXnatTreeModel* m_TreeModel; + mitk::XnatSessionTracker* m_Tracker; QString m_DownloadPath; - QMenu* m_NodeMenu; + QMenu* m_ContextMenu; }; #endif // QMITKXNATTREEBROWSERVIEW_H