/**************************************************************************** ** ** Copyright (C) 2016 Jochen Becher ** Contact: https://www.qt.io/licensing/ ** ** This file is part of Qt Creator. ** ** Commercial License Usage ** Licensees holding valid commercial Qt licenses may use this file in ** accordance with the commercial license agreement provided with the ** Software or, alternatively, in accordance with the terms contained in ** a written agreement between you and The Qt Company. For licensing terms ** and conditions see https://www.qt.io/terms-conditions. For further ** information use the contact form at https://www.qt.io/contact-us. ** ** GNU General Public License Usage ** Alternatively, this file may be used under the terms of the GNU ** General Public License version 3 as published by the Free Software ** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT ** included in the packaging of this file. Please review the following ** information to ensure the GNU General Public License requirements will ** be met: https://www.gnu.org/licenses/gpl-3.0.html. ** ****************************************************************************/ #pragma once #include "handle.h" #include "qmt/infrastructure/qmtassert.h" #include #include namespace qmt { template class Handles { public: typedef QList > value_type; typedef typename value_type::iterator iterator; typedef typename value_type::const_iterator const_iterator; explicit Handles(bool takeOwnership = false) : m_takesOwnership(takeOwnership) { } Handles(const Handles &rhs) : m_handleList(rhs.m_handleList) { } Handles(const Handles &rhs, bool takeOwnership) : m_handleList(rhs.m_handleList), m_takesOwnership(takeOwnership) { if (m_takesOwnership && rhs.m_takesOwnership) const_cast &>(rhs).m_handleList.clear(); } ~Handles() { reset(); } Handles operator=(const Handles &rhs) { if (this != &rhs) { m_handleList = rhs.m_handleList; if (m_takesOwnership && rhs.m_takesOwnership) const_cast &>(rhs).m_handleList.clear(); } return *this; } bool takesOwnership() const { return m_takesOwnership; } bool isEmpty() const { return m_handleList.empty(); } int size() const { return m_handleList.size(); } bool contains(const Uid &uid) const { foreach (const Handle &handle, m_handleList) { if (handle.uid() == uid) return true; } return false; } bool contains(const T *t) const { QMT_ASSERT(t, return false); return contains(t->uid()); } T *find(const Uid &uid) const { foreach (const Handle &handle, m_handleList) { if (handle.uid() == uid) return handle.target(); } return nullptr; } T *at(int index) const { QMT_ASSERT(index >= 0 && index < m_handleList.size(), return nullptr); return m_handleList.at(index).target(); } T *at(int index) { QMT_ASSERT(index >= 0 && index < m_handleList.size(), return nullptr); return m_handleList.at(index); } int indexOf(const Uid &uid) const { int index = 0; foreach (const Handle &handle, m_handleList) { if (handle.uid() == uid) return index; ++index; } return -1; } int indexOf(const T *t) const { QMT_ASSERT(t, return -1); return indexOf(t->uid()); } const value_type &get() const { return m_handleList; } value_type take() { value_type handles = m_handleList; m_handleList.clear(); return handles; } void set(const value_type &handles) { reset(); m_handleList = handles; } void reset() { if (m_takesOwnership) { foreach (const Handle &handle, m_handleList) delete handle.target(); } m_handleList.clear(); } iterator begin() { return m_handleList.begin(); } iterator end() { return m_handleList.end(); } const_iterator begin() const { return m_handleList.begin(); } const_iterator end() const { return m_handleList.end(); } void add(const Uid &uid) { QMT_CHECK(uid.isValid()); m_handleList.append(Handle(uid)); } void add(T *t) { QMT_ASSERT(t, return); m_handleList.append(Handle(t)); } void insert(int beforeIndex, const Uid &uid) { QMT_ASSERT(beforeIndex >= 0 && beforeIndex <= m_handleList.size(), return); QMT_ASSERT(uid.isValid(), return); m_handleList.insert(beforeIndex, Handle(uid)); } void insert(int beforeIndex, T *t) { QMT_ASSERT(beforeIndex >= 0 && beforeIndex <= m_handleList.size(), return); QMT_ASSERT(t, return); m_handleList.insert(beforeIndex, Handle(t)); } void remove(int index) { QMT_ASSERT(index >= 0 && index < size(), return); if (m_takesOwnership) { T *t = m_handleList.at(index).target(); m_handleList.removeAt(index); delete t; } else { m_handleList.removeAt(index); } } void remove(const Uid &uid) { remove(indexOf(uid)); } void remove(T *t) { QMT_ASSERT(t, return); remove(indexOf(t)); } T * take(int index) { QMT_ASSERT(index >= 0 && index < size(), return nullptr); T *t = m_handleList.at(index).target(); m_handleList.removeAt(index); return t; } T *take(const Uid &uid) { return take(indexOf(uid)); } T *take(T *t) { QMT_ASSERT(t, return nullptr); return take(indexOf(t)); } private: value_type m_handleList; bool m_takesOwnership = false; }; template bool operator==(const Handles &lhs, const Handles &rhs) { return lhs.get() == rhs.get(); } template bool operator!=(const Handles &lhs, const Handles &rhs) { return !(lhs == rhs); } } // namespace qmt