File indexing completed on 2024-05-12 04:37:44
0001 /* 0002 SPDX-FileCopyrightText: 2007-2009 Hamish Rodda <rodda@kde.org> 0003 SPDX-FileCopyrightText: 2009 Lior Mualem <lior.m.kde@gmail.com> 0004 0005 SPDX-License-Identifier: LGPL-2.0-or-later 0006 */ 0007 0008 #ifndef KDEVPLATFORM_CLASSMODELNODE_H 0009 #define KDEVPLATFORM_CLASSMODELNODE_H 0010 0011 #include "classmodel.h" 0012 0013 #include "../duchain/identifier.h" 0014 #include "../duchain/duchainpointer.h" 0015 #include "classmodelnodescontroller.h" 0016 0017 #include <QIcon> 0018 0019 class NodesModelInterface; 0020 0021 namespace KDevelop { 0022 class ClassDeclaration; 0023 class ClassFunctionDeclaration; 0024 class ClassMemberDeclaration; 0025 class Declaration; 0026 } 0027 0028 namespace ClassModelNodes { 0029 /// Base node class - provides basic functionality. 0030 class Node 0031 { 0032 public: 0033 Node(const QString& a_displayName, NodesModelInterface* a_model); 0034 virtual ~Node(); 0035 0036 public: // Operations 0037 /// Clear all the children from the node. 0038 void clear(); 0039 0040 /// Called by the model to collapse the node and remove sub-items if needed. 0041 virtual void collapse() {}; 0042 0043 /// Called by the model to expand the node and populate it with sub-nodes if needed. 0044 virtual void expand() {}; 0045 0046 /// Append a new child node to the list. 0047 void addNode(Node* a_child); 0048 0049 /// Remove child node from the list and delete it. 0050 void removeNode(Node* a_child); 0051 0052 /// Remove this node and delete it. 0053 void removeSelf() { m_parentNode->removeNode(this); } 0054 0055 /// Called once the node has been populated to sort the entire tree / branch. 0056 void recursiveSort(); 0057 0058 public: // Info retrieval 0059 /// Return the parent associated with this node. 0060 Node* parent() const { return m_parentNode; } 0061 0062 /// Get my index in the parent node 0063 int row(); 0064 0065 /// Return the display name for the node. 0066 QString displayName() const { return m_displayName; } 0067 0068 /// Returns a list of child nodes 0069 const QList<Node*>& children() const { return m_children; } 0070 0071 /// Return an icon representation for the node. 0072 /// @note It calls the internal getIcon and caches the result. 0073 QIcon cachedIcon(); 0074 0075 public: // overridables 0076 /// Return a score when sorting the nodes. 0077 virtual int score() const = 0; 0078 0079 /// Return true if the node contains sub-nodes. 0080 virtual bool hasChildren() const { return !m_children.empty(); } 0081 0082 /// We use this string when sorting items. 0083 virtual QString sortableString() const { return m_displayName; } 0084 0085 protected: 0086 /// fill a_resultIcon with a display icon for the node. 0087 /// @param a_resultIcon returned icon. 0088 /// @return true if result was returned. 0089 virtual bool getIcon(QIcon& a_resultIcon) = 0; 0090 0091 private: 0092 Node* m_parentNode; 0093 0094 /// Called once the node has been populated to sort the entire tree / branch. 0095 void recursiveSortInternal(); 0096 0097 protected: 0098 using NodesList = QList<Node*>; 0099 NodesList m_children; 0100 QString m_displayName; 0101 QIcon m_cachedIcon; 0102 NodesModelInterface* m_model; 0103 }; 0104 0105 ////////////////////////////////////////////////////////////////////////////// 0106 ////////////////////////////////////////////////////////////////////////////// 0107 0108 /// Base class for nodes that generate and populate their child nodes dynamically 0109 class DynamicNode 0110 : public Node 0111 { 0112 public: 0113 DynamicNode(const QString& a_displayName, NodesModelInterface* a_model); 0114 0115 /// Return true if the node was populated already. 0116 bool isPopulated() const { return m_populated; } 0117 0118 /// Populate the node and mark the flag - called from expand or can be used internally. 0119 void performPopulateNode(bool a_forceRepopulate = false); 0120 0121 public: // Node overrides. 0122 void collapse() override; 0123 void expand() override; 0124 bool hasChildren() const override; 0125 0126 protected: // overridables 0127 /// Called by the framework when the node is about to be expanded 0128 /// it should be populated with sub-nodes if applicable. 0129 virtual void populateNode() {} 0130 0131 /// Called after the nodes have been removed. 0132 /// It's for derived classes to clean cached data. 0133 virtual void nodeCleared() {} 0134 0135 private: 0136 bool m_populated; 0137 0138 /// Clear all the child nodes and mark flag. 0139 void performNodeCleanup(); 0140 }; 0141 0142 ////////////////////////////////////////////////////////////////////////////// 0143 ////////////////////////////////////////////////////////////////////////////// 0144 0145 /// Base class for nodes associated with a @ref KDevelop::QualifiedIdentifier 0146 class IdentifierNode 0147 : public DynamicNode 0148 { 0149 public: 0150 IdentifierNode(KDevelop::Declaration* a_decl, NodesModelInterface* a_model, 0151 const QString& a_displayName = QString()); 0152 0153 public: 0154 /// Returns the qualified identifier for this node by going through the tree 0155 const KDevelop::IndexedQualifiedIdentifier& identifier() const { return m_identifier; } 0156 0157 public: // Node overrides 0158 bool getIcon(QIcon& a_resultIcon) override; 0159 0160 public: // Overridables 0161 /// Return the associated declaration 0162 /// @note DU CHAIN MUST BE LOCKED FOR READ 0163 virtual KDevelop::Declaration* declaration(); 0164 0165 private: 0166 KDevelop::IndexedQualifiedIdentifier m_identifier; 0167 KDevelop::IndexedDeclaration m_indexedDeclaration; 0168 KDevelop::DeclarationPointer m_cachedDeclaration; 0169 }; 0170 0171 ////////////////////////////////////////////////////////////////////////////// 0172 ////////////////////////////////////////////////////////////////////////////// 0173 0174 /// A node that represents an enum value. 0175 class EnumNode 0176 : public IdentifierNode 0177 { 0178 public: 0179 EnumNode(KDevelop::Declaration* a_decl, NodesModelInterface* a_model); 0180 0181 public: // Node overrides 0182 int score() const override { return 102; } 0183 bool getIcon(QIcon& a_resultIcon) override; 0184 void populateNode() override; 0185 }; 0186 0187 ////////////////////////////////////////////////////////////////////////////// 0188 ////////////////////////////////////////////////////////////////////////////// 0189 0190 /// Provides display for a single class. 0191 class ClassNode 0192 : public IdentifierNode 0193 , public ClassModelNodeDocumentChangedInterface 0194 { 0195 public: 0196 ClassNode(KDevelop::Declaration* a_decl, NodesModelInterface* a_model); 0197 ~ClassNode() override; 0198 0199 /// Lookup a contained class and return the related node. 0200 /// @return the node pointer or 0 if non was found. 0201 ClassNode* findSubClass(const KDevelop::IndexedQualifiedIdentifier& a_id); 0202 0203 public: // Node overrides 0204 int score() const override { return 300; } 0205 void populateNode() override; 0206 void nodeCleared() override; 0207 bool hasChildren() const override { return true; } 0208 0209 protected: // ClassModelNodeDocumentChangedInterface overrides 0210 void documentChanged(const KDevelop::IndexedString& a_file) override; 0211 0212 private: 0213 using SubIdentifiersMap = QMap<uint, Node*>; 0214 /// Set of known sub-identifiers. It's used for updates check. 0215 SubIdentifiersMap m_subIdentifiers; 0216 0217 /// We use this variable to know if we've registered for change notification or not. 0218 KDevelop::IndexedString m_cachedUrl; 0219 0220 /// Updates the node to reflect changes in the declaration. 0221 /// @note DU CHAIN MUST BE LOCKED FOR READ 0222 /// @return true if something was updated. 0223 bool updateClassDeclarations(); 0224 0225 /// Add "Base classes" and "Derived classes" folders, if needed 0226 /// @return true if one of the folders was added. 0227 bool addBaseAndDerived(); 0228 }; 0229 0230 ////////////////////////////////////////////////////////////////////////////// 0231 ////////////////////////////////////////////////////////////////////////////// 0232 0233 /// Provides a display for a single class function. 0234 class FunctionNode 0235 : public IdentifierNode 0236 { 0237 public: 0238 FunctionNode(KDevelop::Declaration* a_decl, NodesModelInterface* a_model); 0239 0240 public: // Node overrides 0241 int score() const override { return 400; } 0242 QString sortableString() const override { return m_sortableString; } 0243 0244 private: 0245 QString m_sortableString; 0246 }; 0247 0248 ////////////////////////////////////////////////////////////////////////////// 0249 ////////////////////////////////////////////////////////////////////////////// 0250 0251 /// Provides display for a single class variable. 0252 class ClassMemberNode 0253 : public IdentifierNode 0254 { 0255 public: 0256 ClassMemberNode(KDevelop::ClassMemberDeclaration* a_decl, NodesModelInterface* a_model); 0257 0258 public: // Node overrides 0259 int score() const override { return 500; } 0260 bool getIcon(QIcon& a_resultIcon) override; 0261 }; 0262 0263 ////////////////////////////////////////////////////////////////////////////// 0264 ////////////////////////////////////////////////////////////////////////////// 0265 0266 /// Provides a folder node with a static list of nodes. 0267 class FolderNode 0268 : public Node 0269 { 0270 public: 0271 FolderNode(const QString& a_displayName, NodesModelInterface* a_model); 0272 0273 public: // Node overrides 0274 bool getIcon(QIcon& a_resultIcon) override; 0275 int score() const override { return 100; } 0276 }; 0277 0278 ////////////////////////////////////////////////////////////////////////////// 0279 ////////////////////////////////////////////////////////////////////////////// 0280 0281 /// Provides a folder node with a dynamic list of nodes. 0282 class DynamicFolderNode 0283 : public DynamicNode 0284 { 0285 public: 0286 DynamicFolderNode(const QString& a_displayName, NodesModelInterface* a_model); 0287 0288 public: // Node overrides 0289 bool getIcon(QIcon& a_resultIcon) override; 0290 int score() const override { return 100; } 0291 }; 0292 0293 ////////////////////////////////////////////////////////////////////////////// 0294 ////////////////////////////////////////////////////////////////////////////// 0295 0296 /// Special folder - the parent is assumed to be a ClassNode. 0297 /// It then displays the base classes for the class it sits in. 0298 class BaseClassesFolderNode 0299 : public DynamicFolderNode 0300 { 0301 public: 0302 explicit BaseClassesFolderNode(NodesModelInterface* a_model); 0303 0304 public: // Node overrides 0305 void populateNode() override; 0306 }; 0307 0308 ////////////////////////////////////////////////////////////////////////////// 0309 ////////////////////////////////////////////////////////////////////////////// 0310 0311 /// Special folder - the parent is assumed to be a ClassNode. 0312 /// It then displays list of derived classes from the parent class. 0313 class DerivedClassesFolderNode 0314 : public DynamicFolderNode 0315 { 0316 public: 0317 explicit DerivedClassesFolderNode(NodesModelInterface* a_model); 0318 0319 public: // Node overrides 0320 void populateNode() override; 0321 }; 0322 } // namespace classModelNodes 0323 0324 #endif