/**************************************************************************** Copyright (C) 2010-2012 the Office National des Forêts (ONF), France and the Association de Recherche Technologie et Sciences (ARTS), Ecole Nationale Suprieure d'Arts et Métiers (ENSAM), Cluny, France. All rights reserved. Contact : alexandre.piboule@onf.fr Developers : Michaël KREBS (ARTS/ENSAM) This file is part of Computree version 2.0. Computree is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. Computree is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Computree. If not, see . *****************************************************************************/ #include "gdocumentmanagerview.h" #include "dm_guimanager.h" #include "gdocumentviewforgraphics.h" #include "gdocumentviewforitemmodel.h" #include "view/DocumentView/ItemModelViews/gtreeview.h" #include "view/DocumentView/GraphicsViews/3D/gosggraphicsview.h" #include "view/DocumentView/GraphicsViews/ggraphicsviewsynchronizedgroup.h" #include "ct_result/abstract/ct_abstractresult.h" #include "ct_result/tools/iterator/ct_resultiterator.h" #include GDocumentManagerView::GDocumentManagerView(QWidget *parent) : QMdiArea(parent), DM_DocumentManagerView() { m_mutex = new QMutex(QMutex::Recursive); m_windowCount = 0; m_timer.setInterval(100); m_syncMan = NULL; m_lastDocumentActivated = NULL; m_manualModeEnabled = false; m_manualModeEnabledByStep = NULL; connect(this, SIGNAL(subWindowActivated(QMdiSubWindow*)), this, SLOT(subWindowHasBeenActivated(QMdiSubWindow*))); connect(&m_timer, SIGNAL(timeout()), this, SLOT(verifyNumberWindow())); } GDocumentManagerView::~GDocumentManagerView() { delete m_mutex; } void GDocumentManagerView::setSyncManager(const GGraphicsViewSynchronizedGroup *syncMan) { m_syncMan = (GGraphicsViewSynchronizedGroup*)syncMan; } void GDocumentManagerView::addDocumentView(GDocumentView &view, bool fromGui, bool inLoadConfigurationFromMainWindow) { view.getSubWindow()->setParent(this); view.setDocumentCloseFilter(this); view.setDocumentAddFilter(this); if(inLoadConfigurationFromMainWindow) { view.getSubWindow()->showNormal(); } else { if(subWindowList().isEmpty()) { view.getSubWindow()->showMaximized(); } else { if((activeSubWindow() != NULL) && activeSubWindow()->isMaximized()) activeSubWindow()->showNormal(); view.getSubWindow()->showNormal(); tileSubWindows(); } } connect(&view, SIGNAL(closed(DM_DocumentView*)), this, SIGNAL(documentToBeClosed(DM_DocumentView*)), Qt::DirectConnection); connect(&view, SIGNAL(destroyed()), this, SLOT(slotDocumentDestroyed()), Qt::DirectConnection); connect(&view, SIGNAL(destroyed()), &m_timer, SLOT(start())); if(m_manualModeEnabled) { m_docToCloseAfterQuitManualMode.append(&view); if(fromGui) m_docFromGuiAddedInManualMode.append(&view); } else { m_docAddedInNormalMode.append(&view); } emit documentAdded(&view); ++m_windowCount; m_lastDocumentActivated = view.getSubWindow(); setActiveSubWindow(view.getSubWindow()); emit documentActivated(&view); } bool GDocumentManagerView::addAllItemDrawableOfResultToActiveDocument(CT_AbstractResult &res, DM_AsynchroneProgress &progress) { DM_DocumentView *activeDoc = getActiveDocumentView(); return addAllItemDrawableOfResultToDocument(res, activeDoc, progress); } bool GDocumentManagerView::addAllItemDrawableOfModelToDocument(CT_AbstractResult &res, CT_OutAbstractItemModel &model, DM_DocumentView *doc, DM_AsynchroneProgress &progress) { if((doc != NULL) && !res.isBusy()) { progress.setProgress(0); res.setBusy(true); CT_ResultIterator it((CT_ResultGroup*)&res, &model); int n = it.size(); if(n != 0) { int i = 0; if(n > 1) doc->beginAddMultipleItemDrawable(); while(it.hasNext()) { CT_AbstractItemDrawable *item = (CT_AbstractItemDrawable*)it.next(); doc->addItemDrawable(*item); ++i; progress.setProgress(((float)(i*100))/n); } if(n > 1) doc->endAddMultipleItemDrawable(); } progress.setProgress(100); res.setBusy(false); return true; } return false; } bool GDocumentManagerView::addAllItemDrawableOfResultToDocument(CT_AbstractResult &res, DM_DocumentView *doc, DM_AsynchroneProgress &progress) { if((doc != NULL) && !res.isBusy()) { progress.setProgress(0); res.setBusy(true); CT_ResultIterator it((CT_ResultGroup*)&res, false); int n = it.size(); if(n != 0) { int i = 0; if(n > 1) doc->beginAddMultipleItemDrawable(); while(it.hasNext()) { CT_AbstractItemDrawable *item = (CT_AbstractItemDrawable*)it.next(); doc->addItemDrawable(*item); ++i; progress.setProgress(((float)(i*100))/n); } if(n > 1) doc->endAddMultipleItemDrawable(); } progress.setProgress(100); res.setBusy(false); return true; } return false; } bool GDocumentManagerView::addAllItemDrawableOfListToActiveDocument(QList &itemList, DM_AsynchroneProgress &progress) { DM_DocumentView *activeDoc = getActiveDocumentView(); return addAllItemDrawableOfListToDocument(itemList, activeDoc, progress); } bool GDocumentManagerView::addAllItemDrawableOfListToDocument(QList &itemList, DM_DocumentView *doc, DM_AsynchroneProgress &progress) { if(doc != NULL) { progress.setProgress(0); if(!itemList.isEmpty()) { int n = itemList.size(); int i = 0; QListIterator it(itemList); if(n > 1) doc->beginAddMultipleItemDrawable(); while(it.hasNext()) { doc->addItemDrawable(*(it.next())); ++i; progress.setProgress(((float)(i*100))/n); } if(n > 1) doc->endAddMultipleItemDrawable(); } progress.setProgress(100); return true; } return false; } bool GDocumentManagerView::removeAllItemDrawableOfResultFromDocuments(CT_AbstractResult &res, DM_AsynchroneProgress &progress) { progress.setProgress(0); QList list = subWindowList(); QListIterator it(list); int i = 0; int n = list.size(); while(it.hasNext()) { DM_DocumentView *dv = ((MyQMdiSubWindow*)it.next())->getDocumentView(); dv->removeAllItemDrawableOfResult(res); ++i; progress.setProgress(((float)(i*100))/n); } progress.setProgress(100); return true; } bool GDocumentManagerView::removeAllItemDrawableOfModelFromDocuments(CT_OutAbstractItemModel &model, DM_AsynchroneProgress &progress) { progress.setProgress(0); QList list = subWindowList(); QListIterator it(list); int i = 0; int n = list.size(); while(it.hasNext()) { DM_DocumentView *dv = ((MyQMdiSubWindow*)it.next())->getDocumentView(); dv->removeAllItemDrawableOfModel(model); ++i; progress.setProgress(((float)(i*100))/n); } progress.setProgress(100); return true; } bool GDocumentManagerView::removeAllItemDrawableOfModelFromDocument(CT_OutAbstractItemModel &model, DM_DocumentView *doc, DM_AsynchroneProgress &progress) { progress.setProgress(0); if(doc != NULL) doc->removeAllItemDrawableOfModel(model); progress.setProgress(100); return true; } bool GDocumentManagerView::removeAllItemDrawableOfListFromDocuments(QList &itemList, DM_AsynchroneProgress &progress) { progress.setProgress(0); if(!itemList.isEmpty()) { int i = 0; int n = itemList.size(); QListIterator itItem(itemList); while(itItem.hasNext()) { CT_AbstractItemDrawable *item = itItem.next(); if(item->isDisplayed()) { QList itemDocList = item->document(); QListIterator itDoc(itemDocList); while(itDoc.hasNext()) { itDoc.next()->removeItemDrawable(*item); } } ++i; progress.setProgress(((float)(i*100))/n); } } progress.setProgress(100); return true; } bool GDocumentManagerView::removeAllItemDrawableOfListFromDocument(QList &itemList, DM_DocumentView *doc, DM_AsynchroneProgress &progress) { progress.setProgress(0); if(!itemList.isEmpty()) { int i = 0; int n = itemList.size(); QListIterator itItem(itemList); while(itItem.hasNext()) { CT_AbstractItemDrawable *item = itItem.next(); if(item->isDisplayed() && item->document().contains(doc)) doc->removeItemDrawable(*item); ++i; progress.setProgress(((float)(i*100))/n); } } progress.setProgress(100); return true; } DM_DocumentView* GDocumentManagerView::getActiveDocumentView() { if(activeSubWindow() == NULL) { QList list = subWindowList(); if((m_lastDocumentActivated != NULL) && list.contains(m_lastDocumentActivated)) { setActiveSubWindow(m_lastDocumentActivated); } else if(!list.isEmpty()) { m_lastDocumentActivated = list.first(); setActiveSubWindow(m_lastDocumentActivated); } } if(activeSubWindow() != NULL) { m_lastDocumentActivated = activeSubWindow(); return ((MyQMdiSubWindow*)activeSubWindow())->getDocumentView(); } else { m_lastDocumentActivated = NULL; } return NULL; } DM_DocumentView* GDocumentManagerView::getDocumentView(int index) const { QList list = subWindowList(); if((index >=0) && (index < list.size())) return ((MyQMdiSubWindow*)list.at(index))->getDocumentView(); return NULL; } int GDocumentManagerView::nbDocumentView() const { return subWindowList().size(); } bool GDocumentManagerView::containsDocument(DM_Document *document) const { QList list = subWindowList(); QListIterator it(list); while(it.hasNext()) { if(((MyQMdiSubWindow*)it.next())->getDocumentView() == document) return true; } return false; } void GDocumentManagerView::redrawAllDocument() { m_mutex->lock(); QList list = subWindowList(); QListIterator it(list); while(it.hasNext()) ((MyQMdiSubWindow*)it.next())->getDocumentView()->redrawGraphics(); m_mutex->unlock(); } DocumentInterface *GDocumentManagerView::new3DDocument(bool fromGui, bool inLoadConfigurationFromMainWindow, float pointSize, bool orthographic, QColor *color) { GDocumentViewForGraphics *doc = new GDocumentViewForGraphics(*this, tr("Document %1").arg(GDocumentView::NUMBER), "NORMAL"); doc->init(); GOsgGraphicsView *graphics = new GOsgGraphicsView(doc->getSubWindow()); doc->addGraphics(graphics); connect(doc, SIGNAL(syncEnabled(const GDocumentViewForGraphics*)), m_syncMan, SLOT(addAllGraphicsFromDocumentView(const GDocumentViewForGraphics*))); connect(doc, SIGNAL(syncDisabled(const GDocumentViewForGraphics*)), m_syncMan, SLOT(removeDocumentView(const GDocumentViewForGraphics*))); addDocumentView(*doc, fromGui, inLoadConfigurationFromMainWindow); graphics->init(); DM_GraphicsViewOptions opt; opt.updateFromOtherOptions(graphics->constGetOptionsInternal()); opt.setPointSize(pointSize); if (color != NULL) {opt.setBackgroudColor(*color);} if (orthographic) {opt.setCameraType(CameraInterface::ORTHOGRAPHIC);} else {opt.setCameraType(CameraInterface::PERSPECTIVE);} graphics->setOptions(opt); graphics->validateOptions(); return doc; } DocumentInterface *GDocumentManagerView::new2DDocument(bool fromGui, bool inLoadConfigurationFromMainWindow) { GDocumentViewForGraphics *doc = new GDocumentViewForGraphics(*this, tr("Document %1 (2D)").arg(GDocumentView::NUMBER), "2D"); doc->init(); GOsgGraphicsView *graphics = new GOsgGraphicsView(doc->getSubWindow()); graphics->active2dView(true); doc->addGraphics(graphics); connect(doc, SIGNAL(syncEnabled(const GDocumentViewForGraphics*)), m_syncMan, SLOT(addAllGraphicsFromDocumentView(const GDocumentViewForGraphics*))); connect(doc, SIGNAL(syncDisabled(const GDocumentViewForGraphics*)), m_syncMan, SLOT(removeDocumentView(const GDocumentViewForGraphics*))); addDocumentView(*doc, fromGui, inLoadConfigurationFromMainWindow); graphics->init(); return doc; } DocumentInterface *GDocumentManagerView::newTreeViewDocument(bool fromGui, bool inLoadConfigurationFromMainWindow) { GDocumentViewForItemModel *doc = new GDocumentViewForItemModel(*this, tr("Document %1 (ItemModel)").arg(GDocumentView::NUMBER)); doc->init(); GTreeView *treeView = new GTreeView(doc->getSubWindow()); doc->addView(treeView); treeView->init(); connect(treeView, SIGNAL(syncWith(const GItemModelView*)), m_syncMan, SLOT(syncItemModelWith(const GItemModelView*))); addDocumentView(*doc, fromGui, inLoadConfigurationFromMainWindow); return doc; } void GDocumentManagerView::lockAllDocuments() { m_mutex->lock(); QList list = subWindowList(); QListIterator it(list); while(it.hasNext()) { ((MyQMdiSubWindow*)it.next())->getDocumentView()->lock(); } m_mutex->unlock(); } void GDocumentManagerView::unlockAllDocuments() { m_mutex->lock(); QList list = subWindowList(); QListIterator it(list); while(it.hasNext()) { ((MyQMdiSubWindow*)it.next())->getDocumentView()->unlock(); } m_mutex->unlock(); } DocumentInterface* GDocumentManagerView::new3DDocument(float pointSize, bool orthographic, QColor *color) { return new3DDocument(false, false, pointSize, orthographic, color); } DocumentInterface* GDocumentManagerView::new2DDocument() { return new2DDocument(false, false); } DocumentInterface* GDocumentManagerView::newTreeViewDocument() { return newTreeViewDocument(false, false); } int GDocumentManagerView::nDocuments() const { return nbDocumentView(); } DocumentInterface* GDocumentManagerView::documentAt(const int &index) const { return getDocumentView(index); } QList GDocumentManagerView::documents() const { QList list = subWindowList(); QList lRet; while(!list.isEmpty()) { lRet.append(((MyQMdiSubWindow*)list.takeFirst())->getDocumentView()); } return lRet; } DocumentInterface* GDocumentManagerView::activeDocument() { return getActiveDocumentView(); } void GDocumentManagerView::activateDocument(DocumentInterface *doc) { QMdiSubWindow *subW = subWindowFromDocument(doc); if(subW != NULL) setActiveSubWindow(subW); } bool GDocumentManagerView::closeDocument(DocumentInterface *doc) { QMdiSubWindow *subW = subWindowFromDocument(doc); if(subW != NULL) return subW->close(); return true; } bool GDocumentManagerView::closeDocument(const int &index) { return subWindowList().at(index)->close(); } bool GDocumentManagerView::canClose(const DM_Document *document) const { if(m_manualModeEnabled) { if(m_docAddedInNormalMode.contains((GDocumentView*)document)) return (m_docAddedInNormalMode.size() > 1); if(m_docFromGuiAddedInManualMode.contains((GDocumentView*)document)) return true; if(m_docToCloseAfterQuitManualMode.contains((GDocumentView*)document)) return false; } return (nbDocumentView() > 1); } bool GDocumentManagerView::canAddItemDrawable(const DM_Document *document, const CT_AbstractItemDrawable *item) const { Q_UNUSED(item) return ((DM_DocumentView*)document)->isVisible(); } QMdiSubWindow* GDocumentManagerView::subWindowFromDocument(DocumentInterface *doc) const { QList list = subWindowList(); while(!list.isEmpty()) { MyQMdiSubWindow *w = (MyQMdiSubWindow*)list.takeFirst(); if(w->getDocumentView() == doc) return w; } return NULL; } void GDocumentManagerView::stepRequiredManualMode(CT_VirtualAbstractStep *step) { if((m_manualModeEnabledByStep != NULL) && (m_manualModeEnabledByStep != step)) { stepFinished(m_manualModeEnabledByStep); } if(m_manualModeEnabledByStep == NULL) { m_manualModeEnabled = true; m_manualModeEnabledByStep = step; // hide all documents QListIterator it(m_docAddedInNormalMode); while(it.hasNext()) { GDocumentView *dView = it.next(); dView->getSubWindow()->showNormal(); dView->getSubWindow()->hide(); emit documentHidden(dView); } } } void GDocumentManagerView::stepFinished(CT_VirtualAbstractStep *step) { if((m_manualModeEnabledByStep != NULL) && (m_manualModeEnabledByStep == step)) { // close all documents added in manual mode while(!m_docToCloseAfterQuitManualMode.isEmpty()) m_docToCloseAfterQuitManualMode.takeFirst()->getSubWindow()->close(); m_docFromGuiAddedInManualMode.clear(); // show all documents QListIterator it(m_docAddedInNormalMode); while(it.hasNext()) { GDocumentView *dView = it.next(); dView->getSubWindow()->show(); emit documentShowned(dView); } m_manualModeEnabledByStep = NULL; m_manualModeEnabled = false; } } void GDocumentManagerView::slotDocumentDestroyed() { m_docToCloseAfterQuitManualMode.removeOne((GDocumentView*)sender()); m_docFromGuiAddedInManualMode.removeOne((GDocumentView*)sender()); m_docAddedInNormalMode.removeOne((GDocumentView*)sender()); } void GDocumentManagerView::subWindowHasBeenActivated(QMdiSubWindow *window) { Q_UNUSED(window) emit documentActivated(getActiveDocumentView()); } void GDocumentManagerView::verifyNumberWindow() { if(m_windowCount != nbDocumentView()) { m_windowCount = nbDocumentView(); m_timer.stop(); emit documentRemoved(); } else { m_timer.start(); } }