1 #include "ImageTreeWidget.h"
6 #include <QApplication>
10 #include <QProgressBar>
15 #include "Directory.h"
16 #include "IException.h"
19 #include "ImageList.h"
20 #include "ImageTreeWidgetItem.h"
21 #include "ProgressBar.h"
33 m_queuedSelectionChanged =
false;
34 m_directory = directory;
38 ImageTreeWidgetItem::TreeColumn col = ImageTreeWidgetItem::NameColumn;
39 while(col < ImageTreeWidgetItem::BlankColumn) {
40 header << ImageTreeWidgetItem::treeColumnToString(col);
41 col = (ImageTreeWidgetItem::TreeColumn)(col + 1);
44 setHeaderLabels(header);
46 hideColumn(ImageTreeWidgetItem::ImageColumn);
47 hideColumn(ImageTreeWidgetItem::LabelColumn);
48 hideColumn(ImageTreeWidgetItem::ResolutionColumn);
49 hideColumn(ImageTreeWidgetItem::EmissionAngleColumn);
50 hideColumn(ImageTreeWidgetItem::IncidenceAngleColumn);
51 hideColumn(ImageTreeWidgetItem::PhaseAngleColumn);
52 hideColumn(ImageTreeWidgetItem::AspectRatioColumn);
53 hideColumn(ImageTreeWidgetItem::SampleResolutionColumn);
54 hideColumn(ImageTreeWidgetItem::LineResolutionColumn);
55 hideColumn(ImageTreeWidgetItem::NorthAzimuthColumn);
56 hideColumn(ImageTreeWidgetItem::BlankColumn);
60 FileName(QString(
"$HOME/.Isis/%1/fileList.config").arg(QApplication::applicationName()))
62 QSettings::NativeFormat);
63 settings.beginGroup(
"ColumnsVisible");
65 col = ImageTreeWidgetItem::FootprintColumn;
66 while(col < ImageTreeWidgetItem::BlankColumn) {
67 bool visible = !isColumnHidden(col);
69 if (settings.value(QString(
"%1Visible").arg(ImageTreeWidgetItem::treeColumnToString(col)),
70 visible).
toBool() != visible) {
77 col = (ImageTreeWidgetItem::TreeColumn)(col + 1);
81 setContextMenuPolicy(Qt::DefaultContextMenu);
83 setSortingEnabled(
true);
84 sortItems(ImageTreeWidgetItem::NameColumn, Qt::AscendingOrder);
88 connect(
this, SIGNAL(itemSelectionChanged()),
89 this, SLOT(onSelectionChanged()));
93 connect(
this, SIGNAL(queueSelectionChanged()),
94 this, SLOT(onQueuedSelectionChanged()), Qt::QueuedConnection);
97 connect(
this, SIGNAL(queueReadDisplayProperties()),
98 this, SLOT(onQueuedReadDisplayProperties()), Qt::QueuedConnection);
100 setSelectionMode(QAbstractItemView::ExtendedSelection);
101 setDragDropOverwriteMode(
false);
105 ImageTreeWidget::~ImageTreeWidget() {
107 foreach(contextAction, actions()) {
108 removeAction(contextAction);
116 if (!m_setFileListColsAct) {
117 m_setFileListColsAct =
new QAction(
"Set Current File List &Columns as Default",
this);
118 m_setFileListColsAct->setWhatsThis(tr(
"Use the currently visible columns in the file list as "
119 "the default when no project has been opened"));
120 connect(m_setFileListColsAct, SIGNAL(triggered(
bool)),
121 this, SLOT(setDefaultFileListCols()));
123 results.append(m_setFileListColsAct);
136 verticalScrollBar()->setMaximum(verticalScrollBar()->maximum() + 25);
144 imageListItem = invisibleRootItem();
146 if (groupName.isEmpty()) {
147 groupName = QString(
"Group %1").arg(imageListItem->childCount() + 1);
151 result->setText(0, groupName);
152 result->setFlags(Qt::ItemIsEditable |
153 Qt::ItemIsUserCheckable |
155 Qt::ItemIsSelectable |
156 Qt::ItemIsDragEnabled |
157 Qt::ItemIsDropEnabled);
158 result->setData(0, Qt::UserRole, ImageGroupType);
161 index = imageListItem->childCount();
164 imageListItem->insertChild(index, result);
167 result->setExpanded(
true);
173 QTreeWidgetItem *ImageTreeWidget::createImageListNameItem(QString name) {
175 result->setText(0, name);
176 result->setData(0, Qt::UserRole, ImageListNameType);
177 result->setExpanded(
true);
183 void ImageTreeWidget::refit() {
184 ImageTreeWidgetItem::TreeColumn col = ImageTreeWidgetItem::NameColumn;
185 while(col < ImageTreeWidgetItem::BlankColumn) {
187 if (col == ImageTreeWidgetItem::NameColumn) {
189 for (
int groupIndex = 0; groupIndex < topLevelItemCount(); groupIndex++) {
190 expandedStates.append(topLevelItem(groupIndex)->isExpanded());
191 topLevelItem(groupIndex)->setExpanded(
true);
194 resizeColumnToContents(col);
196 for (
int groupIndex = 0; groupIndex < topLevelItemCount(); groupIndex++) {
197 topLevelItem(groupIndex)->setExpanded(expandedStates[groupIndex]);
201 resizeColumnToContents(col);
204 col = (ImageTreeWidgetItem::TreeColumn)(col + 1);
209 void ImageTreeWidget::disableSort() {
210 sortItems(ImageTreeWidgetItem::BlankColumn, Qt::AscendingOrder);
214 void ImageTreeWidget::enqueueReadDisplayProperties(ImageTreeWidgetItem *item) {
215 m_queuedReadDisplayPropertiesItems.append(item);
217 if (m_queuedReadDisplayPropertiesItems.count() == 1) {
218 emit queueReadDisplayProperties();
224 if (m_viewActs.empty()) {
225 ImageTreeWidgetItem::TreeColumn col =
226 ImageTreeWidgetItem::FootprintColumn;
228 while(col < ImageTreeWidgetItem::BlankColumn) {
230 showHide->setData(col);
232 connect(showHide, SIGNAL(triggered()),
233 this, SLOT(toggleColumnVisible()));
235 m_viewActs.append(showHide);
237 col = (ImageTreeWidgetItem::TreeColumn)(col + 1);
247 void ImageTreeWidget::updateViewActs() {
248 if (!m_viewActs.empty()) {
249 int viewActIndex = 0;
250 ImageTreeWidgetItem::TreeColumn col =
251 ImageTreeWidgetItem::FootprintColumn;
253 while(col < ImageTreeWidgetItem::BlankColumn) {
254 bool visible = !isColumnHidden(col);
255 QAction *showHide = m_viewActs[viewActIndex];
258 showHide->setText(
"Show " +
259 ImageTreeWidgetItem::treeColumnToString(col) +
" Column");
262 showHide->setText(
"Hide " +
263 ImageTreeWidgetItem::treeColumnToString(col) +
" Column");
266 col = (ImageTreeWidgetItem::TreeColumn)(col + 1);
276 void ImageTreeWidget::setDefaultFileListCols() {
279 QString(
"$HOME/.Isis/%1/fileList.config").arg(QApplication::applicationName()))
281 QSettings::NativeFormat);
282 settings.beginGroup(
"ColumnsVisible");
284 ImageTreeWidgetItem::TreeColumn col =
285 ImageTreeWidgetItem::FootprintColumn;
287 while(col < ImageTreeWidgetItem::BlankColumn) {
288 bool visible = !isColumnHidden(col);
290 settings.setValue(QString(
"%1Visible").arg(ImageTreeWidgetItem::treeColumnToString(col)),
293 col = (ImageTreeWidgetItem::TreeColumn)(col + 1);
300 ImageTreeWidgetItem *ImageTreeWidget::prepCube(ImageList *imageList, Image *image) {
302 ImageTreeWidgetItem *item =
new ImageTreeWidgetItem(imageList, image);
304 connect(image->displayProperties(), SIGNAL(destroyed(
QObject *)),
305 this, SLOT(imageDeleted(
QObject *)));
306 connect(image->displayProperties(), SIGNAL(propertyChanged(DisplayProperties *)),
307 this, SLOT(propertiesChanged(DisplayProperties *)));
309 m_displayPropsToTreeItemLookup[image->displayProperties()] = item;
313 catch(IException &e) {
321 ImageList ImageTreeWidget::imagesInView() {
324 QTreeWidgetItemIterator it(
this, QTreeWidgetItemIterator::UserFlag);
329 if (item->type() == QTreeWidgetItem::UserType) {
330 ImageTreeWidgetItem *mosItem = (ImageTreeWidgetItem *)item;
331 results.append(mosItem->image());
341 ImageTreeWidget::ImagePosition::ImagePosition() {
346 ImageTreeWidget::ImagePosition::ImagePosition(
int outerIndex,
int innerIndex) {
349 setPosition(outerIndex, innerIndex);
353 ImageTreeWidget::ImagePosition::ImagePosition(
const ImagePosition &other) :
354 m_group(other.m_group), m_index(other.m_index) {
358 ImageTreeWidget::ImagePosition::~ImagePosition() {
363 void ImageTreeWidget::ImagePosition::setPosition(
int group,
int index) {
364 if (group >= 0 && index >= 0) {
374 int ImageTreeWidget::ImagePosition::group()
const {
379 int ImageTreeWidget::ImagePosition::index()
const {
384 bool ImageTreeWidget::ImagePosition::isValid()
const {
385 return (m_group != -1 && m_index != -1);
389 void ImageTreeWidget::ImagePosition::swap(ImagePosition &other) {
390 std::swap(m_group, other.m_group);
391 std::swap(m_index, other.m_index);
395 bool ImageTreeWidget::ImagePosition::operator<(
const ImagePosition &rhs) {
396 bool lessThan =
false;
397 if (group() < rhs.group()) {
400 else if (group() == rhs.group() && index() < rhs.index()) {
408 ImageTreeWidget::ImagePosition &ImageTreeWidget::ImagePosition::operator=(
409 const ImagePosition &rhs) {
410 ImagePosition copy(rhs);
417 void ImageTreeWidget::ImagePosition::init() {
422 void ImageTreeWidget::dropEvent(QDropEvent *event) {
429 if(droppedAtGroup->type() != QTreeWidgetItem::Type)
430 droppedAtGroup = droppedAtItem->parent();
432 bool draggedGroup = groupInList(selectedItems());
433 bool draggedItem = mosaicItemInList(selectedItems());
436 if(draggedItem && !draggedGroup) {
437 int insertPosition = 0;
439 if(droppedAtGroup != droppedAtItem) {
440 insertPosition = droppedAtGroup->indexOfChild(droppedAtItem) + 1;
444 foreach(toBeMoved, selectedItems()) {
445 if(toBeMoved != droppedAtItem) {
450 int childOrigIndex = parent->indexOfChild(toBeMoved);
452 parent->takeChild(childOrigIndex);
454 int actualInsertPos = insertPosition;
456 if(parent == droppedAtGroup && childOrigIndex < insertPosition)
459 droppedAtGroup->insertChild(actualInsertPos, toBeMoved);
462 if(insertPosition != droppedAtGroup->childCount())
467 else if(!draggedItem && draggedGroup) {
470 foreach(toBeMoved, selectedItems()) {
471 if(toBeMoved != droppedAtGroup) {
472 int dropPosition = indexOfTopLevelItem(droppedAtGroup);
474 takeTopLevelItem(indexOfTopLevelItem(toBeMoved));
475 insertTopLevelItem(dropPosition, toBeMoved);
598 switch(event->type()) {
599 case QEvent::MouseButtonPress: {
600 if (event->button() == Qt::RightButton &&
601 itemAt(event->pos()) == NULL) {
602 setCurrentItem(NULL);
611 QTreeWidget::mousePressEvent(event);
615 void ImageTreeWidget::contextMenuEvent(QContextMenuEvent *event) {
616 ImageList selectedCubes = selectedDisplays();
618 bool selectedGroup = groupInList(selectedItems());
619 bool selectedCube = mosaicItemInList(selectedItems());
624 project = m_directory->
project();
629 supportedActions.append(NULL);
634 foreach(
QAction *action, supportedActions) {
636 menu.addAction(action);
643 if (!selectedCube && selectedGroup) {
644 if (selectedItems().size() == 1 && selectedItems()[0]->childCount()) {
645 QAction *close = menu.addAction(
"Close Cubes in Group");
646 connect(close, SIGNAL(triggered()),
647 this, SLOT(requestCloseSelected()));
650 if (selectedItems().size() == 1) {
651 QAction *rename = menu.addAction(
"Rename Group");
652 connect(rename, SIGNAL(triggered()),
653 this, SLOT(renameSelectedGroup()));
655 QAction *group = menu.addAction(
"Insert Group");
656 connect(group, SIGNAL(triggered()),
662 if (selectedItems().size() == 1)
663 removeGroup = menu.addAction(
"Delete Group");
665 removeGroup = menu.addAction(
"Delete Groups");
667 connect(removeGroup, SIGNAL(triggered()),
668 this, SLOT(deleteSelectedGroups()));
671 if (selectedCube && !selectedGroup) {
674 if (selectedItems().size() == 1)
675 close = menu.addAction(
"Close Cube");
677 close = menu.addAction(
"Close Cubes");
679 connect(close, SIGNAL(triggered()),
680 this, SLOT(requestCloseSelected()));
683 if (!selectedCube && !selectedGroup) {
684 QAction *group = menu.addAction(
"Add Group");
686 connect(group, SIGNAL(triggered()),
690 menu.exec(event->globalPos());
704 QString newGroupParentText =
"";
706 if (selectedItems().size() == 1) {
707 if (selectedItems()[0]->data(0, Qt::UserRole).
toInt() == ImageGroupType) {
708 newGroupParent = selectedItems()[0]->parent();
709 if (newGroupParent) {
710 index = newGroupParent->indexOfChild(selectedItems()[0]);
713 newGroupParent = invisibleRootItem();
714 index = indexOfTopLevelItem(selectedItems()[0]);
717 else if (selectedItems()[0]->data(0, Qt::UserRole).
toInt() == ImageListNameType) {
718 newGroupParent = selectedItems()[0];
722 if (newGroupParent) {
723 newGroupParentText = newGroupParent->text(0);
725 return addGroup(newGroupParentText,
"", index);
729 void ImageTreeWidget::deleteSelectedGroups() {
731 requestCloseSelected();
734 foreach(toBeDeleted, selectedItems()) {
735 if (toBeDeleted->type() == QTreeWidgetItem::Type) {
742 void ImageTreeWidget::imageDeleted(
QObject *imageObj) {
743 ImageDisplayProperties *imagedisp = (ImageDisplayProperties *)imageObj;
744 ImageTreeWidgetItem *item = treeItem(imagedisp);
746 if (item && item->parent()) {
747 m_displayPropsToTreeItemLookup.remove(imagedisp);
750 delete item->parent()->takeChild( item->parent()->indexOfChild(item) );
756 if (item->type() == QTreeWidgetItem::UserType) {
757 ((ImageTreeWidgetItem *)item)->update(
true);
762 void ImageTreeWidget::onSelectionChanged() {
763 if (!m_queuedSelectionChanged) {
764 emit queueSelectionChanged();
765 m_queuedSelectionChanged =
true;
770 void ImageTreeWidget::onQueuedReadDisplayProperties() {
773 foreach (ImageTreeWidgetItem *item, m_queuedReadDisplayPropertiesItems) {
774 bool wasSelected = item->isSelected();
777 if (!wasSelected && item->isSelected()) {
778 newlySelectedItem = item;
782 if (newlySelectedItem) {
783 scrollToItem(newlySelectedItem);
786 m_queuedReadDisplayPropertiesItems.clear();
790 void ImageTreeWidget::onQueuedSelectionChanged() {
793 m_queuedSelectionChanged =
false;
795 QTreeWidgetItemIterator it(
this, QTreeWidgetItemIterator::UserFlag);
800 if (item->type() == QTreeWidgetItem::UserType) {
801 ImageTreeWidgetItem *imageItem = (ImageTreeWidgetItem *)item;
802 imageItem->update(
true);
808 updateDragAndDropability();
812 void ImageTreeWidget::propertiesChanged(DisplayProperties *changed) {
813 enqueueReadDisplayProperties(treeItem(changed));
817 void ImageTreeWidget::renameSelectedGroup() {
818 if (selectedItems().size() == 1 &&
819 selectedItems()[0]->type() == QTreeWidgetItem::Type) {
821 editItem(groupToEdit);
826 void ImageTreeWidget::requestCloseSelected() {
827 QTreeWidgetItemIterator it(
this, QTreeWidgetItemIterator::UserFlag);
833 if (item->type() == QTreeWidgetItem::UserType) {
834 if (item->isSelected() || item->parent()->isSelected()) {
835 ImageTreeWidgetItem *mosItem = (ImageTreeWidgetItem *)item;
836 mosItem->image()->deleteLater();
845 void ImageTreeWidget::toggleColumnVisible() {
846 int column = ((
QAction *)sender())->data().toInt();
847 setColumnHidden(column, !isColumnHidden(column));
849 if (!m_viewActs.empty())
856 void ImageTreeWidget::updateDragAndDropability() {
858 bool selectedGroup = groupInList(selected);
859 bool selectedItem = mosaicItemInList(selected);
861 if (selectedGroup && selectedItem) {
862 setDragDropMode(QAbstractItemView::NoDragDrop);
865 setDragDropMode(QAbstractItemView::DragDrop);
871 QListIterator<QTreeWidgetItem *> it(items);
873 while (it.hasNext()) {
876 if (item->type() == QTreeWidgetItem::Type)
885 QListIterator<QTreeWidgetItem *> it(items);
887 while (it.hasNext()) {
890 if (item->type() == QTreeWidgetItem::UserType)
897 ImageList ImageTreeWidget::selectedDisplays() {
899 QTreeWidgetItemIterator it(
this, QTreeWidgetItemIterator::UserFlag);
905 if (item->type() == QTreeWidgetItem::UserType) {
906 ImageTreeWidgetItem *mosItem = (ImageTreeWidgetItem *)item;
907 if (mosItem->isSelected() || mosItem->parent()->isSelected()) {
908 selected.append(mosItem->image());
930 if (imageListName.isEmpty()) {
931 result = invisibleRootItem();
934 QTreeWidgetItemIterator it(
this);
936 while(*it && !result) {
939 if (item->data(0, Qt::UserRole).toInt() == ImageListNameType) {
940 if (item->text(0) == imageListName) {
950 result = createImageListNameItem(imageListName);
951 addTopLevelItem(result);
959 return m_displayPropsToTreeItemLookup[displayProps];
963 ImageTreeWidgetItem *ImageTreeWidget::treeItem(Image *image) {
964 return treeItem(image->displayProperties());