1/****************************************************************************
2**
3** Copyright (C) 2016 The Qt Company Ltd.
4** Contact: https://www.qt.io/licensing/
5**
6** This file is part of the Qt Designer of the Qt Toolkit.
7**
8** $QT_BEGIN_LICENSE:GPL-EXCEPT$
9** Commercial License Usage
10** Licensees holding valid commercial Qt licenses may use this file in
11** accordance with the commercial license agreement provided with the
12** Software or, alternatively, in accordance with the terms contained in
13** a written agreement between you and The Qt Company. For licensing terms
14** and conditions see https://www.qt.io/terms-conditions. For further
15** information use the contact form at https://www.qt.io/contact-us.
16**
17** GNU General Public License Usage
18** Alternatively, this file may be used under the terms of the GNU
19** General Public License version 3 as published by the Free Software
20** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
21** included in the packaging of this file. Please review the following
22** information to ensure the GNU General Public License requirements will
23** be met: https://www.gnu.org/licenses/gpl-3.0.html.
24**
25** $QT_END_LICENSE$
26**
27****************************************************************************/
28
29#include "qextensionmanager.h"
30
31QT_BEGIN_NAMESPACE
32
33/*!
34 \class QExtensionManager
35
36 \brief The QExtensionManager class provides extension management
37 facilities for Qt Designer.
38
39 \inmodule QtDesigner
40
41 In \QD the extensions are not created until they are required. For
42 that reason, when implementing an extension, you must also create
43 a QExtensionFactory, i.e a class that is able to make an instance
44 of your extension, and register it using \QD's extension manager.
45
46 The registration of an extension factory is typically made in the
47 QDesignerCustomWidgetInterface::initialize() function:
48
49 \snippet lib/tools_designer_src_lib_extension_qextensionmanager.cpp 0
50
51 The QExtensionManager is not intended to be instantiated
52 directly. You can retrieve an interface to \QD's extension manager
53 using the QDesignerFormEditorInterface::extensionManager()
54 function. A pointer to \QD's current QDesignerFormEditorInterface
55 object (\c formEditor in the example above) is provided by the
56 QDesignerCustomWidgetInterface::initialize() function's
57 parameter. When implementing a custom widget plugin, you must
58 subclass the QDesignerCustomWidgetInterface to expose your plugin
59 to \QD.
60
61 Then, when an extension is required, \QD's extension manager will
62 run through all its registered factories calling
63 QExtensionFactory::createExtension() for each until the first one
64 that is able to create the requested extension for the selected
65 object, is found. This factory will then make an instance of the
66 extension.
67
68 There are four available types of extensions in \QD:
69 QDesignerContainerExtension , QDesignerMemberSheetExtension,
70 QDesignerPropertySheetExtension and
71 QDesignerTaskMenuExtension. \QD's behavior is the same whether the
72 requested extension is associated with a container, a member
73 sheet, a property sheet or a task menu.
74
75 For a complete example using the QExtensionManager class, see the
76 \l {taskmenuextension}{Task Menu Extension example}. The
77 example shows how to create a custom widget plugin for Qt
78 Designer, and how to to use the QDesignerTaskMenuExtension class
79 to add custom items to \QD's task menu.
80
81 \sa QExtensionFactory, QAbstractExtensionManager
82*/
83
84/*!
85 Constructs an extension manager with the given \a parent.
86*/
87QExtensionManager::QExtensionManager(QObject *parent)
88 : QObject(parent)
89{
90}
91
92
93/*!
94 Destroys the extension manager
95*/
96QExtensionManager::~QExtensionManager() = default;
97
98/*!
99 Register the extension specified by the given \a factory and
100 extension identifier \a iid.
101*/
102void QExtensionManager::registerExtensions(QAbstractExtensionFactory *factory, const QString &iid)
103{
104 if (iid.isEmpty()) {
105 m_globalExtension.prepend(t: factory);
106 return;
107 }
108
109 FactoryMap::iterator it = m_extensions.find(akey: iid);
110 if (it == m_extensions.end())
111 it = m_extensions.insert(akey: iid, avalue: FactoryList());
112
113 it.value().prepend(t: factory);
114}
115
116/*!
117 Unregister the extension specified by the given \a factory and
118 extension identifier \a iid.
119*/
120void QExtensionManager::unregisterExtensions(QAbstractExtensionFactory *factory, const QString &iid)
121{
122 if (iid.isEmpty()) {
123 m_globalExtension.removeAll(t: factory);
124 return;
125 }
126
127 const FactoryMap::iterator it = m_extensions.find(akey: iid);
128 if (it == m_extensions.end())
129 return;
130
131 FactoryList &factories = it.value();
132 factories.removeAll(t: factory);
133
134 if (factories.isEmpty())
135 m_extensions.erase(it);
136}
137
138/*!
139 Returns the extension specified by \a iid, for the given \a
140 object.
141*/
142QObject *QExtensionManager::extension(QObject *object, const QString &iid) const
143{
144 const FactoryMap::const_iterator it = m_extensions.constFind(akey: iid);
145 if (it != m_extensions.constEnd()) {
146 const FactoryList::const_iterator fcend = it.value().constEnd();
147 for (FactoryList::const_iterator fit = it.value().constBegin(); fit != fcend; ++fit)
148 if (QObject *ext = (*fit)->extension(object, iid))
149 return ext;
150 }
151 const FactoryList::const_iterator gfcend = m_globalExtension.constEnd();
152 for (FactoryList::const_iterator git = m_globalExtension.constBegin(); git != gfcend; ++git)
153 if (QObject *ext = (*git)->extension(object, iid))
154 return ext;
155
156 return nullptr;
157}
158
159QT_END_NAMESPACE
160

source code of qttools/src/designer/src/lib/extension/qextensionmanager.cpp