Add AbstractDeclarationNavigationContext, and move the html-method from
[kdevelopdvcssupport.git] / language / duchain / uses.cpp
blob52933791d51722e6c287c5b00bfdee6d9abdbba1
1 /* This file is part of KDevelop
2 Copyright 2008 David Nolden <david.nolden.kdevelop@art-master.de>
4 This library is free software; you can redistribute it and/or
5 modify it under the terms of the GNU Library General Public
6 License version 2 as published by the Free Software Foundation.
8 This library is distributed in the hope that it will be useful,
9 but WITHOUT ANY WARRANTY; without even the implied warranty of
10 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
11 Library General Public License for more details.
13 You should have received a copy of the GNU Library General Public License
14 along with this library; see the file COPYING.LIB. If not, write to
15 the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
16 Boston, MA 02110-1301, USA.
19 #include <QHash>
20 #include <QVector>
22 #include "uses.h"
23 #include "declarationid.h"
24 #include "duchainpointer.h"
25 #include "repositories/itemrepository.h"
26 #include "topducontext.h"
28 namespace KDevelop {
30 DEFINE_LIST_MEMBER_HASH(UsesItem, uses, IndexedTopDUContext)
32 class UsesItem {
33 public:
34 UsesItem() {
35 initializeAppendedLists();
37 UsesItem(const UsesItem& rhs) : declaration(rhs.declaration) {
38 initializeAppendedLists();
39 copyListsFrom(rhs);
42 ~UsesItem() {
43 freeAppendedLists();
46 unsigned int hash() const {
47 //We only compare the declaration. This allows us implementing a map, although the item-repository
48 //originally represents a set.
49 return declaration.hash();
52 unsigned short int itemSize() const {
53 return dynamicSize();
56 uint classSize() const {
57 return sizeof(UsesItem);
60 DeclarationId declaration;
62 START_APPENDED_LISTS(UsesItem);
63 APPENDED_LIST_FIRST(UsesItem, IndexedTopDUContext, uses);
64 END_APPENDED_LISTS(UsesItem, uses);
67 class UsesRequestItem {
68 public:
70 UsesRequestItem(const UsesItem& item) : m_item(item) {
72 enum {
73 AverageSize = 30 //This should be the approximate average size of an Item
76 unsigned int hash() const {
77 return m_item.hash();
80 size_t itemSize() const {
81 return m_item.itemSize();
84 void createItem(UsesItem* item) const {
85 item->initializeAppendedLists(false);
86 item->declaration = m_item.declaration;
87 item->copyListsFrom(m_item);
90 bool equals(const UsesItem* item) const {
91 return m_item.declaration == item->declaration;
94 const UsesItem& m_item;
98 struct UsesPrivate {
99 UsesPrivate() : m_uses("Use Map") {
101 //Maps declaration-ids to Uses
102 ItemRepository<UsesItem, UsesRequestItem> m_uses;
105 Uses::Uses() : d(new UsesPrivate())
109 Uses::~Uses()
111 delete d;
114 void Uses::addUse(const DeclarationId& id, const IndexedTopDUContext& use)
116 UsesItem item;
117 item.declaration = id;
118 item.usesList().append(use);
119 UsesRequestItem request(item);
121 uint index = d->m_uses.findIndex(item);
123 if(index) {
124 //Check whether the item is already in the mapped list, else copy the list into the new created item
125 const UsesItem* oldItem = d->m_uses.itemFromIndex(index);
126 for(unsigned int a = 0; a < oldItem->usesSize(); ++a) {
127 if(oldItem->uses()[a] == use)
128 return; //Already there
129 item.usesList().append(oldItem->uses()[a]);
132 d->m_uses.deleteItem(index);
135 //This inserts the changed item
136 d->m_uses.index(request);
139 void Uses::removeUse(const DeclarationId& id, const IndexedTopDUContext& use)
141 UsesItem item;
142 item.declaration = id;
143 UsesRequestItem request(item);
145 uint index = d->m_uses.findIndex(item);
147 if(index) {
148 //Check whether the item is already in the mapped list, else copy the list into the new created item
149 const UsesItem* oldItem = d->m_uses.itemFromIndex(index);
150 for(unsigned int a = 0; a < oldItem->usesSize(); ++a)
151 if(!(oldItem->uses()[a] == use))
152 item.usesList().append(oldItem->uses()[a]);
154 d->m_uses.deleteItem(index);
155 Q_ASSERT(d->m_uses.findIndex(item) == 0);
157 //This inserts the changed item
158 if(item.usesSize() != 0)
159 d->m_uses.index(request);
163 KDevVarLengthArray<IndexedTopDUContext> Uses::uses(const DeclarationId& id) const
165 KDevVarLengthArray<IndexedTopDUContext> ret;
167 UsesItem item;
168 item.declaration = id;
169 UsesRequestItem request(item);
171 uint index = d->m_uses.findIndex(item);
173 if(index) {
174 const UsesItem* repositoryItem = d->m_uses.itemFromIndex(index);
175 FOREACH_FUNCTION(IndexedTopDUContext decl, repositoryItem->uses)
176 ret.append(decl);
179 return ret;