aboutsummaryrefslogtreecommitdiff
path: root/libs/uibase/src/sortabletreewidget.cpp
diff options
context:
space:
mode:
authorSulfurNitride <SulfurNitride@users.noreply.github.com>2026-02-11 02:37:39 -0600
committerSulfurNitride <SulfurNitride@users.noreply.github.com>2026-02-11 02:37:39 -0600
commit7ee008e150bc5bcf76082d726f719ee0fdfda982 (patch)
tree27fb39be241fdb5ac2734c574de678977d1856d0 /libs/uibase/src/sortabletreewidget.cpp
Fluorine Manager: full Linux port of Mod Organizer 2
Complete native Linux port with FUSE-based virtual filesystem, Proton/umu-run integration, and Flatpak packaging. Key features: - FUSE VFS replacing Windows USVFS (in-process + standalone helper for Flatpak) - Proton/GE-Proton/umu-run launcher with env var forwarding - Flatpak support (sandbox-aware VFS, NXM handler, umu-run) - Wine prefix management UI - Case-insensitive path resolution for Linux filesystems - QSettings-safe INI handling (avoids Bethesda INI corruption) - Portable instance support with auto-generated launcher scripts Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Diffstat (limited to 'libs/uibase/src/sortabletreewidget.cpp')
-rw-r--r--libs/uibase/src/sortabletreewidget.cpp116
1 files changed, 116 insertions, 0 deletions
diff --git a/libs/uibase/src/sortabletreewidget.cpp b/libs/uibase/src/sortabletreewidget.cpp
new file mode 100644
index 0000000..5cfbdd4
--- /dev/null
+++ b/libs/uibase/src/sortabletreewidget.cpp
@@ -0,0 +1,116 @@
+/*
+Mod Organizer shared UI functionality
+
+Copyright (C) 2013 Sebastian Herbord. All rights reserved.
+
+This library is free software; you can redistribute it and/or
+modify it under the terms of the GNU Lesser General Public
+License as published by the Free Software Foundation; either
+version 3 of the License, or (at your option) any later version.
+
+This library 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
+Lesser General Public License for more details.
+
+You should have received a copy of the GNU Lesser General Public
+License along with this library; if not, write to the Free Software
+Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
+*/
+
+#include <uibase/sortabletreewidget.h>
+#include <QDropEvent>
+
+namespace MOBase
+{
+
+SortableTreeWidget::SortableTreeWidget(QWidget* parent)
+ : QTreeWidget(parent), m_LocalMoveOnly(false)
+{}
+
+void SortableTreeWidget::setLocalMoveOnly(bool localOnly)
+{
+ m_LocalMoveOnly = localOnly;
+}
+
+void SortableTreeWidget::dropEvent(QDropEvent* event)
+{
+ // only react on internal drag&drop
+ if (event->source() == this) {
+ QTreeWidget::dropEvent(event);
+ }
+}
+
+Qt::DropActions SortableTreeWidget::supportedDropActions() const
+{
+ // we do our own drop handling, this ensures dropMimeData is called.
+ return Qt::CopyAction;
+}
+
+bool SortableTreeWidget::dropMimeData(QTreeWidgetItem* parent, int index,
+ const QMimeData*, Qt::DropAction)
+{
+ // TODO: ignores type of action set up in designer, always moves
+ return this->moveSelection(parent, index);
+}
+
+bool SortableTreeWidget::moveSelection(QTreeWidgetItem* parent, int idx)
+{
+ QModelIndex parentIndex = indexFromItem(parent);
+ std::vector<QPersistentModelIndex> persistentIndices;
+ Q_FOREACH (const QModelIndex& index, selectedIndexes()) {
+ if (index == parentIndex)
+ return false;
+ if (m_LocalMoveOnly && (parentIndex != index.parent()))
+ return false;
+ if (index.column() != 0)
+ continue;
+ persistentIndices.push_back(index);
+ }
+
+ int targetRow = -1;
+ if (itemsExpandable() || !parentIndex.isValid()) {
+ targetRow = model()->index(idx, 0, parentIndex).row();
+
+ if (targetRow < 0) {
+ targetRow = idx;
+ }
+ } else {
+ // if items aren't expandable, we can't be placing items on sublevels
+ targetRow = parentIndex.row();
+ parentIndex = QModelIndex();
+ }
+
+ // remove items from the list, store in temporary location
+ QList<QTreeWidgetItem*> temp;
+ for (auto iter = persistentIndices.rbegin(); iter != persistentIndices.rend();
+ ++iter) {
+ QTreeWidgetItem* item = itemFromIndex(*iter);
+ if (item == nullptr)
+ continue;
+ if ((item == nullptr) || (item->parent() == nullptr)) {
+ temp.append(takeTopLevelItem(iter->row()));
+ } else {
+ temp.append(item->parent()->takeChild(iter->row()));
+ }
+ }
+
+ if (idx == -1) {
+ // append
+ if (parentIndex.isValid()) {
+ parent->addChildren(temp);
+ } else {
+ addTopLevelItems(temp);
+ }
+ } else {
+ if (parentIndex.isValid()) {
+ parent->insertChildren(std::min<int>(targetRow, parent->childCount()), temp);
+ } else {
+ insertTopLevelItems(std::min<int>(targetRow, topLevelItemCount()), temp);
+ }
+ }
+ emit itemsMoved();
+ return true;
+}
+
+} // namespace MOBase