~oif-team/ubuntu/natty/qt4-x11/xi2.1

« back to all changes in this revision

Viewing changes to tools/designer/src/lib/shared/widgetfactory.cpp

  • Committer: Bazaar Package Importer
  • Author(s): Adam Conrad
  • Date: 2005-08-24 04:09:09 UTC
  • Revision ID: james.westby@ubuntu.com-20050824040909-xmxe9jfr4a0w5671
Tags: upstream-4.0.0
ImportĀ upstreamĀ versionĀ 4.0.0

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/****************************************************************************
 
2
**
 
3
** Copyright (C) 1992-2005 Trolltech AS. All rights reserved.
 
4
**
 
5
** This file is part of the designer application of the Qt Toolkit.
 
6
**
 
7
** This file may be distributed under the terms of the Q Public License
 
8
** as defined by Trolltech AS of Norway and appearing in the file
 
9
** LICENSE.QPL included in the packaging of this file.
 
10
**
 
11
** This file may be distributed and/or modified under the terms of the
 
12
** GNU General Public License version 2 as published by the Free Software
 
13
** Foundation and appearing in the file LICENSE.GPL included in the
 
14
** packaging of this file.
 
15
**
 
16
** See http://www.trolltech.com/pricing.html or email sales@trolltech.com for
 
17
**   information about Qt Commercial License Agreements.
 
18
** See http://www.trolltech.com/qpl/ for QPL licensing information.
 
19
** See http://www.trolltech.com/gpl/ for GPL licensing information.
 
20
**
 
21
** Contact info@trolltech.com if any conditions of this licensing are
 
22
** not clear to you.
 
23
**
 
24
** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
 
25
** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
 
26
**
 
27
****************************************************************************/
 
28
 
 
29
#include "widgetfactory_p.h"
 
30
#include "widgetdatabase_p.h"
 
31
#include "qlayout_widget_p.h"
 
32
#include "qdesigner_widget_p.h"
 
33
#include "qdesigner_tabwidget_p.h"
 
34
#include "qdesigner_toolbox_p.h"
 
35
#include "qdesigner_stackedbox_p.h"
 
36
#include "qdesigner_promotedwidget_p.h"
 
37
#include "abstractformwindow.h"
 
38
 
 
39
// shared
 
40
#include "layoutinfo_p.h"
 
41
#include "spacer_widget_p.h"
 
42
#include "layout_p.h"
 
43
 
 
44
// sdk
 
45
#include <QtDesigner/QtDesigner>
 
46
 
 
47
#include <QtGui/QtGui>
 
48
#include <QtCore/qdebug.h>
 
49
 
 
50
QPointer<QWidget> *WidgetFactory::m_lastPassiveInteractor = new QPointer<QWidget>();
 
51
bool WidgetFactory::m_lastWasAPassiveInteractor = false;
 
52
 
 
53
 
 
54
WidgetFactory::WidgetFactory(QDesignerFormEditorInterface *core, QObject *parent)
 
55
    : QDesignerWidgetFactoryInterface(parent),
 
56
      m_core(core)
 
57
{
 
58
}
 
59
 
 
60
WidgetFactory::~WidgetFactory()
 
61
{
 
62
}
 
63
 
 
64
void WidgetFactory::loadPlugins()
 
65
{
 
66
    m_customFactory.clear();
 
67
 
 
68
    PluginManager *pluginManager = m_core->pluginManager();
 
69
 
 
70
    QList<QDesignerCustomWidgetInterface*> lst = pluginManager->registeredCustomWidgets();
 
71
    foreach (QDesignerCustomWidgetInterface *c, lst) {
 
72
        m_customFactory.insert(c->name(), c);
 
73
    }
 
74
}
 
75
 
 
76
QWidget *WidgetFactory::createWidget(const QString &widgetName, QWidget *parentWidget) const
 
77
{
 
78
    if (QDesignerPromotedWidget *promoted = qobject_cast<QDesignerPromotedWidget*>(parentWidget))
 
79
        parentWidget = promoted->child();
 
80
 
 
81
    QDesignerFormWindowInterface *fw = QDesignerFormWindowInterface::findFormWindow(parentWidget);
 
82
 
 
83
    QWidget *w = 0;
 
84
 
 
85
    if (QDesignerCustomWidgetInterface *f = m_customFactory.value(widgetName)) {
 
86
        return f->createWidget(parentWidget);
 
87
    } else if (widgetName == QLatin1String("Line")) {
 
88
        w = new Line(parentWidget);
 
89
    } else if (widgetName == QLatin1String("QLabel")) {
 
90
        w = new QDesignerLabel(parentWidget);
 
91
    } else if (widgetName == QLatin1String("QTabWidget")) {
 
92
        w = new QDesignerTabWidget(parentWidget);
 
93
    } else if (widgetName == QLatin1String("QStackedWidget")) {
 
94
        w = new QDesignerStackedWidget(parentWidget);
 
95
    } else if (widgetName == QLatin1String("QToolBox")) {
 
96
        w = new QDesignerToolBox(parentWidget);
 
97
    } else if (widgetName == QLatin1String("Spacer")) {
 
98
        w = new Spacer(parentWidget);
 
99
    } else if (widgetName == QLatin1String("QLayoutWidget")) {
 
100
        w = fw ? new QLayoutWidget(fw, parentWidget) : new QWidget(parentWidget);
 
101
    } else if (widgetName == QLatin1String("QDialog")) {
 
102
        if (fw) {
 
103
             w = new QDesignerDialog(fw, parentWidget);
 
104
        } else {
 
105
            w = new QDialog(parentWidget);
 
106
        }
 
107
    } else if (widgetName == QLatin1String("QWidget")) {
 
108
        if (fw && parentWidget &&
 
109
             (qobject_cast<QDesignerFormWindowInterface*>(parentWidget) || qt_extension<QDesignerContainerExtension*>(m_core->extensionManager(), parentWidget))) {
 
110
             w = new QDesignerWidget(fw, qobject_cast<QDesignerFormWindowInterface*>(parentWidget) ? parentWidget : 0);
 
111
        } else {
 
112
            w = new QWidget(parentWidget);
 
113
        }
 
114
    }
 
115
 
 
116
#define DECLARE_LAYOUT(L, C)
 
117
#define DECLARE_COMPAT_WIDGET(W, C) /*DECLARE_WIDGET(W, C)*/
 
118
#define DECLARE_WIDGET(W, C) else if (widgetName == QLatin1String(#W)) { Q_ASSERT(w == 0); w = new W(parentWidget); }
 
119
 
 
120
#include "widgets.table"
 
121
 
 
122
#undef DECLARE_COMPAT_WIDGET
 
123
#undef DECLARE_LAYOUT
 
124
#undef DECLARE_WIDGET
 
125
 
 
126
    if (w == 0) {
 
127
        QDesignerWidgetDataBaseInterface *db = core()->widgetDataBase();
 
128
        QDesignerWidgetDataBaseItemInterface *item = db->item(db->indexOfClassName(widgetName));
 
129
 
 
130
        if (item == 0) {
 
131
            item = new WidgetDataBaseItem(widgetName, tr("%1 Widget").arg(widgetName));
 
132
            item->setCustom(true);
 
133
            item->setPromoted(true);
 
134
            item->setExtends(QLatin1String("QWidget"));
 
135
            item->setContainer(true);
 
136
            item->setIncludeFile(widgetName.toLower() + QLatin1String(".h"));
 
137
            db->append(item);
 
138
        }
 
139
 
 
140
        QString baseClass = item->extends();
 
141
        if (baseClass.isEmpty())
 
142
            baseClass = QLatin1String("QWidget");
 
143
 
 
144
        QDesignerPromotedWidget *promoted = new QDesignerPromotedWidget(item, parentWidget);
 
145
        QWidget *child = createWidget(baseClass, promoted);
 
146
        promoted->setChildWidget(child);
 
147
 
 
148
        w = promoted;
 
149
    }
 
150
 
 
151
    Q_ASSERT(w != 0);
 
152
 
 
153
    if (fw != 0)
 
154
        initialize(w);
 
155
 
 
156
    return w;
 
157
}
 
158
 
 
159
const char *WidgetFactory::classNameOf(QObject* o)
 
160
{
 
161
    if (o == 0)
 
162
        return 0;
 
163
 
 
164
    if (qobject_cast<QDesignerTabWidget*>(o))
 
165
        return "QTabWidget";
 
166
    else if (qobject_cast<QDesignerStackedWidget*>(o))
 
167
        return "QStackedWidget";
 
168
    else if (qobject_cast<QDesignerToolBox*>(o))
 
169
        return "QToolBox";
 
170
    else if (qobject_cast<QDesignerDialog*>(o))
 
171
        return "QDialog";
 
172
    else if (qobject_cast<QDesignerWidget*>(o))
 
173
        return "QWidget";
 
174
    else if (qobject_cast<QDesignerLabel*>(o))
 
175
        return "QLabel";
 
176
    else if (qstrcmp(o->metaObject()->className(), "QAxBase") == 0)
 
177
        return "QAxWidget";
 
178
    else if (QDesignerPromotedWidget *promoted = qobject_cast<QDesignerPromotedWidget*>(o))
 
179
        return promoted->customClassName();
 
180
 
 
181
    return o->metaObject()->className();
 
182
}
 
183
 
 
184
/*!  Creates a layout on the widget \a widget of the type \a type
 
185
  which can be \c HBox, \c VBox or \c Grid.
 
186
*/
 
187
 
 
188
QLayout *WidgetFactory::createLayout(QWidget *widget, QLayout *parentLayout, int type) const // ### (sizepolicy)
 
189
{
 
190
    QDesignerMetaDataBaseInterface *metaDataBase = core()->metaDataBase();
 
191
 
 
192
    if (parentLayout == 0) {
 
193
        widget = containerOfWidget(widget);
 
194
    }
 
195
 
 
196
    Q_ASSERT(metaDataBase->item(widget) != 0); // ensure the widget is managed
 
197
 
 
198
    if (parentLayout == 0 && metaDataBase->item(widget->layout()) == 0) {
 
199
        parentLayout = widget->layout();
 
200
    }
 
201
 
 
202
    QWidget *parentWidget = parentLayout != 0 ? 0 : widget;
 
203
 
 
204
    QLayout *layout = 0;
 
205
    switch (type) {
 
206
    case LayoutInfo::HBox:
 
207
        layout = new QHBoxLayout(parentWidget);
 
208
        break;
 
209
    case LayoutInfo::VBox:
 
210
        layout = new QVBoxLayout(parentWidget);
 
211
        break;
 
212
    case LayoutInfo::Grid:
 
213
        layout = new QGridLayout(parentWidget);
 
214
        break;
 
215
    case LayoutInfo::Stacked:
 
216
        layout = new QStackedLayout(parentWidget);
 
217
        break;
 
218
    default:
 
219
        Q_ASSERT(0);
 
220
        return 0;
 
221
    } // end switch
 
222
 
 
223
    metaDataBase->add(layout); // add the layout in the MetaDataBase
 
224
 
 
225
    if (QLayoutWidget *layoutWidget = qobject_cast<QLayoutWidget*>(widget)) {
 
226
        layoutWidget->setLayoutMargin(0);
 
227
    }
 
228
 
 
229
    if (QDesignerPropertySheetExtension *sheet = qt_extension<QDesignerPropertySheetExtension*>(core()->extensionManager(), layout)) {
 
230
        sheet->setChanged(sheet->indexOf(QLatin1String("margin")), true);
 
231
        sheet->setChanged(sheet->indexOf(QLatin1String("spacing")), true);
 
232
        sheet->setChanged(sheet->indexOf(QLatin1String("alignment")), true);
 
233
    }
 
234
 
 
235
    if (widget && metaDataBase->item(widget->layout()) == 0) {
 
236
        Q_ASSERT(layout->parent() == 0);
 
237
        QBoxLayout *box = qobject_cast<QBoxLayout*>(widget->layout());
 
238
        Q_ASSERT(box != 0); // we support only unmanaged box layouts
 
239
        box->addLayout(layout);
 
240
    }
 
241
 
 
242
    return layout;
 
243
}
 
244
 
 
245
/*!  Returns the widget into which children should be inserted when \a
 
246
  w is a container known to the designer.
 
247
 
 
248
  Usually that is \a w itself, sometimes it is different (e.g. a
 
249
  tabwidget is known to the designer as a container but the child
 
250
  widgets should be inserted into the current page of the
 
251
  tabwidget. So in this case this function returns the current page of
 
252
  the tabwidget.)
 
253
 */
 
254
QWidget* WidgetFactory::containerOfWidget(QWidget *w) const
 
255
{
 
256
    if (QDesignerPromotedWidget *promoted = qobject_cast<QDesignerPromotedWidget*>(w))
 
257
        return promoted->child();
 
258
    else if (QDesignerContainerExtension *container = qt_extension<QDesignerContainerExtension*>(core()->extensionManager(), w))
 
259
        return container->widget(container->currentIndex());
 
260
 
 
261
    return w;
 
262
}
 
263
 
 
264
/*!  Returns the actual designer widget of the container \a w. This is
 
265
  normally \a w itself, but might be a parent or grand parent of \a w
 
266
  (e.g. when working with a tabwidget and \a w is the container which
 
267
  contains and layouts childs, but the actual widget known to the
 
268
  designer is the tabwidget which is the parent of \a w. So this
 
269
  function returns the tabwidget then.)
 
270
*/
 
271
 
 
272
QWidget* WidgetFactory::widgetOfContainer(QWidget *w) const
 
273
{
 
274
    // ### cleanup
 
275
    if (!w)
 
276
        return 0;
 
277
 
 
278
    if (QDesignerPromotedWidget *promoted = qobject_cast<QDesignerPromotedWidget*>(w))
 
279
        return widgetOfContainer(promoted->child());
 
280
 
 
281
    if (w->parentWidget() && w->parentWidget()->parentWidget() &&
 
282
         w->parentWidget()->parentWidget()->parentWidget() &&
 
283
         qobject_cast<QToolBox*>(w->parentWidget()->parentWidget()->parentWidget()))
 
284
        return w->parentWidget()->parentWidget()->parentWidget();
 
285
 
 
286
    while (w != 0) {
 
287
        if (core()->widgetDataBase()->isContainer(w) ||
 
288
             w && qobject_cast<QDesignerFormWindowInterface*>(w->parentWidget()))
 
289
            return w;
 
290
 
 
291
        w = w->parentWidget();
 
292
    }
 
293
 
 
294
    return w;
 
295
}
 
296
 
 
297
QDesignerFormEditorInterface *WidgetFactory::core() const
 
298
{
 
299
    return m_core;
 
300
}
 
301
 
 
302
void WidgetFactory::initialize(QObject *object) const
 
303
{
 
304
    QDesignerPropertySheetExtension *sheet = qt_extension<QDesignerPropertySheetExtension*>(m_core->extensionManager(), object);
 
305
 
 
306
    if (object->metaObject()->indexOfProperty("focusPolicy") != -1)
 
307
        object->setProperty("focusPolicy", Qt::NoFocus);
 
308
 
 
309
    if (!sheet)
 
310
        return;
 
311
 
 
312
    sheet->setChanged(sheet->indexOf(QLatin1String("objectName")), true);
 
313
    sheet->setChanged(sheet->indexOf(QLatin1String("geometry")), true);
 
314
 
 
315
    if (qobject_cast<Spacer*>(object))
 
316
        sheet->setChanged(sheet->indexOf(QLatin1String("sizeHint")), true);
 
317
 
 
318
    int o = sheet->indexOf(QLatin1String("orientation"));
 
319
    if (o != -1)
 
320
        sheet->setChanged(o, true);
 
321
 
 
322
    if (QWidget *widget = qobject_cast<QWidget*>(object)) {
 
323
        QSize sz = widget->sizeHint();
 
324
        if (sz.width() <= 0 && sz.height() <= 0)
 
325
            widget->setMinimumSize(QSize(16, 16));
 
326
    }
 
327
}
 
328
 
 
329
bool WidgetFactory::isPassiveInteractor(QWidget *widget)
 
330
{
 
331
    if (m_lastPassiveInteractor != 0 && (QWidget*)(*m_lastPassiveInteractor) == widget)
 
332
        return m_lastWasAPassiveInteractor;
 
333
 
 
334
    m_lastWasAPassiveInteractor = false;
 
335
    (*m_lastPassiveInteractor) = widget;
 
336
 
 
337
    if (QApplication::activePopupWidget()) // if a popup is open, we have to make sure that this one is closed, else X might do funny things
 
338
        return (m_lastWasAPassiveInteractor = true);
 
339
    else if (widget == 0)
 
340
        return m_lastWasAPassiveInteractor;
 
341
 
 
342
    if (qobject_cast<QTabBar*>(widget))
 
343
        return (m_lastWasAPassiveInteractor = true);
 
344
    else if (qobject_cast<QSizeGrip*>(widget))
 
345
        return (m_lastWasAPassiveInteractor = true);
 
346
    else if (qobject_cast<QAbstractButton*>(widget) && (qobject_cast<QTabBar*>(widget->parent()) || qobject_cast<QToolBox*>(widget->parent())))
 
347
        return (m_lastWasAPassiveInteractor = true);
 
348
    else if (qobject_cast<QMenuBar*>(widget))
 
349
        return (m_lastWasAPassiveInteractor = true);
 
350
    else if (qstrcmp(widget->metaObject()->className(), "QDockSeparator") == 0)
 
351
        return (m_lastWasAPassiveInteractor = true);
 
352
    else if (qstrcmp(widget->metaObject()->className(), "QDockWidgetSeparator") == 0)
 
353
        return (m_lastWasAPassiveInteractor = true);
 
354
    else if (qstrcmp(widget->metaObject()->className(), "QDockWidgetTitle") == 0)
 
355
        return (m_lastWasAPassiveInteractor = true);
 
356
    else if (qstrcmp(widget->metaObject()->className(), "QToolBarHandle") == 0)
 
357
        return (m_lastWasAPassiveInteractor = true);
 
358
    else if (widget->objectName().startsWith(QLatin1String("__qt__passive_")))
 
359
        return (m_lastWasAPassiveInteractor = true);
 
360
 
 
361
    return m_lastWasAPassiveInteractor;
 
362
}
 
363