/* * Copyright 2012 Canonical Ltd. * * This program 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; version 3. * * 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 Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . * * Authors: * Renato Araujo Oliveira Filho */ #include "indicatorsmodel.h" #include "indicatorsmanager.h" #include "indicator.h" #include "indicators.h" #include #include #include #include /*! \qmltype IndicatorsModel \inherits QAbstractListModel \brief The IndicatorsModel class defines the list model for indicators \b {This component is under heavy development.} This class expose the available indicators. \code IndicatorsModel { id: menuModel } ListView { id: view model: menuModel Component.onCompleted: menuModel.load() } \endcode */ IndicatorsModel::IndicatorsModel(QObject *parent) : QAbstractListModel(parent) { m_manager = new IndicatorsManager(this); QObject::connect(m_manager, &IndicatorsManager::indicatorLoaded, this, &IndicatorsModel::onIndicatorLoaded); QObject::connect(m_manager, &IndicatorsManager::indicatorAboutToBeUnloaded, this, &IndicatorsModel::onIndicatorAboutToBeUnloaded); QObject::connect(m_manager, &IndicatorsManager::profileChanged, this, &IndicatorsModel::profileChanged); QObject::connect(this, &IndicatorsModel::rowsInserted, this, &IndicatorsModel::countChanged); QObject::connect(this, &IndicatorsModel::rowsRemoved, this, &IndicatorsModel::countChanged); QObject::connect(this, &IndicatorsModel::modelReset, this, &IndicatorsModel::countChanged); } /*! \internal */ IndicatorsModel::~IndicatorsModel() { disconnect(m_manager, 0, 0, 0); m_manager->deleteLater(); } /*! \qmlproperty IndicatorsModel::count The number of data entries in the model. \b Note: methods should only be called after the Component has completed. */ int IndicatorsModel::count() const { return rowCount(); } /*! \qmlproperty IndicatorsModel::profile The indicator profile to use for the model. \b Note: methods should only be called after the Component has completed. */ QString IndicatorsModel::profile() const { return m_manager->profile(); } /*! \qmlproperty IndicatorsModel::setProfile Set the indicator profile to use for the model. \b Note: methods should only be called after the Component has completed. */ void IndicatorsModel::setProfile(const QString &profile) { m_manager->setProfile(profile); } /*! \qmlmethod IndicatorsModel::unload() Load all indicators. */ void IndicatorsModel::load() { m_indicators.clear(); m_manager->load(); } /*! \qmlmethod IndicatorsModel::unload() Unload all indicators. */ void IndicatorsModel::unload() { m_manager->unload(); } /*! \internal */ void IndicatorsModel::onIndicatorLoaded(const QString& indicator_name) { Indicator::Ptr indicator = m_manager->indicator(indicator_name); if (!indicator) { return; } if (m_indicators.indexOf(indicator) >= 0) { return; } // find the insert position int pos = 0; while (pos < count()) { // keep going while the existing position is greater. (put lower position on end) if (indicator->position() >= data(index(pos), IndicatorsModelRole::Position).toInt()) break; pos++; } QObject::connect(indicator.data(), &Indicator::identifierChanged, this, &IndicatorsModel::onIdentifierChanged); QObject::connect(indicator.data(), &Indicator::indicatorPropertiesChanged, this, &IndicatorsModel::onIndicatorPropertiesChanged); beginInsertRows(QModelIndex(), pos, pos); m_indicators.insert(pos, indicator); endInsertRows(); } /*! \internal */ void IndicatorsModel::onIndicatorAboutToBeUnloaded(const QString& indicator_name) { Indicator::Ptr indicator = m_manager->indicator(indicator_name); if (!indicator) { return; } int i = 0; QMutableListIterator iter(m_indicators); while(iter.hasNext()) { if (indicator == iter.next()) { beginRemoveRows(QModelIndex(), i, i); iter.remove(); endRemoveRows(); break; } i++; } } /*! \internal */ void IndicatorsModel::onIdentifierChanged() { notifyDataChanged(QObject::sender(), IndicatorsModelRole::Identifier); } /*! \internal */ void IndicatorsModel::onIndicatorPropertiesChanged() { notifyDataChanged(QObject::sender(), IndicatorsModelRole::IndicatorProperties); } /*! \internal */ void IndicatorsModel::notifyDataChanged(QObject *sender, int role) { Indicator* indicator = qobject_cast(sender); if (!indicator) { return; } int index = 0; QMutableListIterator iter(m_indicators); while(iter.hasNext()) { if (indicator == iter.next()) { QModelIndex changedIndex = this->index(index); dataChanged(changedIndex, changedIndex, QVector() << role); break; } index++; } } /*! \internal */ QHash IndicatorsModel::roleNames() const { static QHash roles; if (roles.isEmpty()) { roles[IndicatorsModelRole::Identifier] = "identifier"; roles[IndicatorsModelRole::Position] = "position"; roles[IndicatorsModelRole::IndicatorProperties] = "indicatorProperties"; } return roles; } /*! \internal */ int IndicatorsModel::columnCount(const QModelIndex &) const { return 1; } QVariant IndicatorsModel::data(int row, int role) const { return data(index(row, 0), role); } /*! \internal */ QVariant IndicatorsModel::data(const QModelIndex &index, int role) const { if (!index.isValid() || index.row() >= m_indicators.size()) return QVariant(); Indicator::Ptr indicator = m_indicators.at(index.row()); switch (role) { case IndicatorsModelRole::Identifier: if (indicator) { return indicator->identifier(); } break; case IndicatorsModelRole::Position: if (indicator) { return indicator->position(); } break; case IndicatorsModelRole::IndicatorProperties: if (indicator) { return indicator->indicatorProperties(); } break; default: break; } return QVariant(); } /*! \internal */ QModelIndex IndicatorsModel::parent(const QModelIndex&) const { return QModelIndex(); } /*! \internal */ int IndicatorsModel::rowCount(const QModelIndex&) const { return m_indicators.count(); }