/* * Copyright 2009 Ben Boeckel * * This program 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. * * This program 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 this program. If not, see . */ // Header include #include "TreeModel.h" // Sigmodr tree includes #include "RootTreeItem.h" // Sigmodr widget includes #include // KDE includes #include // Qt includes #include using namespace Sigmod; using namespace Sigmodr::Tree; TreeModel::TreeModel(QObject* parent) : QAbstractItemModel(parent), m_root(new RootTreeItem) { } TreeModel::~TreeModel() { delete m_root; } QVariant TreeModel::data(const QModelIndex& index, const int role) const { if (!index.isValid()) return QVariant(); TreeItem* item = static_cast(index.internalPointer()); if (role == Qt::DisplayRole) { if (!index.column()) return item->text(); } else if (role == Qt::DecorationRole) { switch (index.column()) { case 1: if (item->canEdit()) return KIcon("document-edit"); break; case 2: if (item->canRemove()) return KIcon("list-remove"); break; case 3: if (item->canAddTo()) return KIcon("list-add"); break; default: break; } } else if (role == Qt::EditRole) return QVariant::fromValue(item->editWidget()); else if (role == AcceptedMimeTypesRole) return item->acceptedMimeTypes(); return QVariant(); } QModelIndex TreeModel::index(const int row, const int column, const QModelIndex& parent) const { if (!parent.isValid()) { if ((row == -1) || (column == -1)) return createIndex(0, 0, m_root); return QModelIndex(); } TreeItem* item = static_cast(parent.internalPointer()); if ((row < 0) || (item->childCount() <= row) || (column < 0) || (4 <= column)) return QModelIndex(); return createIndex(row, column, item->childAt(row)); } QModelIndex TreeModel::parent(const QModelIndex& child) const { if (!child.isValid()) return QModelIndex(); TreeItem* parent = static_cast(child.internalPointer())->parent(); if (!parent) return QModelIndex(); return createIndex(parent->row(), 0, parent); } bool TreeModel::hasChildren(const QModelIndex& parent) const { if (!parent.isValid() || (0 < parent.column())) return false; return (0 < static_cast(parent.internalPointer())->childCount()); } bool TreeModel::insertRows(const int row, const int count, const QModelIndex& parent) { if (!parent.isValid()) return false; TreeItem* item = static_cast(parent.internalPointer()); if (!item->canAddTo() || (item == m_root) || (row != item->childCount())) return false; beginInsertRows(parent, row, row + count - 1); for (int i = 0; i < count; ++i) item->addChild(); endInsertRows(); // BUG: Fixed in Qt 4.6 (?) emit(layoutAboutToBeChanged()); emit(layoutChanged()); return true; } bool TreeModel::removeRows(const int row, const int count, const QModelIndex& parent) { if (!parent.isValid()) return false; TreeItem* item = static_cast(parent.internalPointer()); if (item == m_root) return false; for (int i = 0; i < count; ++i) { TreeItem* child = item->childAt(row + i); if (!child || !child->canRemove()) return false; } beginRemoveRows(parent, row, row + count - 1); for (int i = 0; i < count; ++i) item->removeChild(row + i); endRemoveRows(); return true; } int TreeModel::rowCount(const QModelIndex& parent) const { if (!parent.isValid()) return 0; return static_cast(parent.internalPointer())->childCount(); } int TreeModel::columnCount(const QModelIndex& parent) const { if (!parent.isValid()) return 0; return 4; } Qt::ItemFlags TreeModel::flags(const QModelIndex& index) const { if (!index.isValid()) return Qt::ItemFlags(); Qt::ItemFlags f; TreeItem* item = static_cast(index.internalPointer()); switch (index.column()) { case 0: f |= item->flags(); break; case 1: if (item->canEdit()) f |= Qt::ItemIsEnabled; break; case 2: if (item->canRemove()) f |= Qt::ItemIsEnabled; break; case 3: if (item->canAddTo()) f |= Qt::ItemIsEnabled; break; default: break; } return f; } QStringList TreeModel::mimeTypes() const { } QMimeData* TreeModel::mimeData(const QModelIndexList& indexes) const { QMimeData* data = new QMimeData; QDomDocument document("SigmodCopyData"); foreach (const QModelIndex& index, indexes) { if (!index.isValid()) continue; TreeItem* item = static_cast(index.internalPointer()); if (item->canEdit()) document.appendChild(item->copyData()); } data->setData("application/x-sigmod-copy+xml", document.toByteArray()); return data; } bool TreeModel::dropMimeData(const QMimeData* data, Qt::DropAction action, const int row, const int column, const QModelIndex& parent) { } Qt::DropActions TreeModel::supportedDropActions() const { return Qt::CopyAction | Qt::MoveAction; } void TreeModel::addGame(Game* game) { beginInsertRows(index(-1, -1, QModelIndex()), m_root->childCount(), m_root->childCount()); m_root->addGame(game); endInsertRows(); } void TreeModel::deleteGame(const Game* game) { for (int i = 0; i < m_root->childCount(); ++i) { if (m_root->childAt(i)->game() == game) { beginRemoveRows(index(-1, -1, QModelIndex()), i, i); m_root->removeChild(i); endRemoveRows(); break; } } } const Game* TreeModel::findGame(const QModelIndex& index) const { if (!index.isValid()) return NULL; return static_cast(index.internalPointer())->game(); }