summaryrefslogtreecommitdiffstats
path: root/tools/designer/uilib/qwidgetfactory.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'tools/designer/uilib/qwidgetfactory.cpp')
-rw-r--r--tools/designer/uilib/qwidgetfactory.cpp2623
1 files changed, 2623 insertions, 0 deletions
diff --git a/tools/designer/uilib/qwidgetfactory.cpp b/tools/designer/uilib/qwidgetfactory.cpp
new file mode 100644
index 0000000..a1ff1c2
--- /dev/null
+++ b/tools/designer/uilib/qwidgetfactory.cpp
@@ -0,0 +1,2623 @@
+/**********************************************************************
+** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved.
+**
+** This file is part of Qt Designer.
+**
+** This file may be used under the terms of the GNU General
+** Public License versions 2.0 or 3.0 as published by the Free
+** Software Foundation and appearing in the files LICENSE.GPL2
+** and LICENSE.GPL3 included in the packaging of this file.
+** Alternatively you may (at your option) use any later version
+** of the GNU General Public License if such license has been
+** publicly approved by Trolltech ASA (or its successors, if any)
+** and the KDE Free Qt Foundation.
+**
+** Please review the following information to ensure GNU General
+** Public Licensing requirements will be met:
+** http://trolltech.com/products/qt/licenses/licensing/opensource/.
+** If you are unsure which license is appropriate for your use, please
+** review the following information:
+** http://trolltech.com/products/qt/licenses/licensing/licensingoverview
+** or contact the sales department at sales@trolltech.com.
+**
+** Licensees holding valid Qt Commercial licenses may use this file in
+** accordance with the Qt Commercial License Agreement provided with
+** the Software.
+**
+** This file is provided "AS IS" with NO WARRANTY OF ANY KIND,
+** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR
+** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted
+** herein.
+**
+**********************************************************************/
+
+#include "qwidgetfactory.h"
+
+#include "../interfaces/languageinterface.h"
+#include "../interfaces/widgetinterface.h"
+
+#include <qfeatures.h>
+#include "../designer/database2.h"
+#include <qdom.h>
+#include <qdir.h>
+#include <qlayout.h>
+#include <qmetaobject.h>
+#include <domtool.h>
+#include <uib.h>
+#include <qapplication.h>
+#include <qtooltip.h>
+#include <qwhatsthis.h>
+#include <qobjectlist.h>
+#include <private/qpluginmanager_p.h>
+#include <qmime.h>
+#include <qdragobject.h>
+
+#ifndef QT_NO_SQL
+#include <qsqlrecord.h>
+#include <qsqldatabase.h>
+#include <qdatatable.h>
+#endif
+
+// include all Qt widgets we support
+#include <qpushbutton.h>
+#include <qtoolbutton.h>
+#include <qcheckbox.h>
+#include <qradiobutton.h>
+#include <qgroupbox.h>
+#include <qbuttongroup.h>
+#include <qiconview.h>
+#include <qheader.h>
+#ifndef QT_NO_TABLE
+#include <qtable.h>
+#endif
+#include <qlistbox.h>
+#include <qlistview.h>
+#include <qlineedit.h>
+#include <qspinbox.h>
+#include <qmultilineedit.h>
+#include <qlabel.h>
+#include <qwidget.h>
+#include <qtabwidget.h>
+#include <qcombobox.h>
+#include <qdialog.h>
+#include <qwizard.h>
+#include <qlcdnumber.h>
+#include <qprogressbar.h>
+#include <qtextview.h>
+#include <qtextbrowser.h>
+#include <qdial.h>
+#include <qslider.h>
+#include <qframe.h>
+#include <qwidgetstack.h>
+#include <qtoolbox.h>
+#include <qtextedit.h>
+#include <qscrollbar.h>
+#include <qmainwindow.h>
+#include <qsplitter.h>
+#include <qaction.h>
+#include <qpopupmenu.h>
+#include <qmenubar.h>
+#include <qpopupmenu.h>
+#include <qdatetimeedit.h>
+#include <qvbox.h>
+#include <qhbox.h>
+#include <qgrid.h>
+
+#include <stdlib.h>
+
+class QWidgetFactoryPrivate
+{
+public:
+ QCString translationContext;
+ QListViewItem *lastItem;
+ QDict<bool> customWidgets;
+};
+
+static QPtrList<QWidgetFactory> widgetFactories;
+static QPluginManager<LanguageInterface> *languageInterfaceManager = 0;
+static QPluginManager<WidgetInterface> *widgetInterfaceManager = 0;
+
+static QMap<QString, bool> *availableWidgetMap = 0;
+static QStringList *availableWidgetList = 0;
+
+QMap<QWidget*, QString> *qwf_forms = 0;
+QString *qwf_language = 0;
+bool qwf_execute_code = TRUE;
+bool qwf_stays_on_top = FALSE;
+QString qwf_currFileName = "";
+QObject *qwf_form_object = 0;
+QString *qwf_plugin_dir = 0;
+
+static void setupPluginDir()
+{
+ if ( !qwf_plugin_dir )
+ qwf_plugin_dir = new QString( "/designer" );
+}
+
+static void setupWidgetListAndMap()
+{
+ if ( availableWidgetMap )
+ return;
+ setupPluginDir();
+ availableWidgetList = new QStringList;
+ (*availableWidgetList) << "QPushButton" << "QToolButton" << "QCheckBox" << "QRadioButton"
+ << "QGroupBox" << "QButtonGroup" << "QIconView" << "QTable"
+ << "QListBox" << "QListView" << "QLineEdit" << "QSpinBox"
+ << "QMultiLineEdit" << "QLabel" << "TextLabel" << "PixmapLabel"
+ << "QLayoutWidget" << "QTabWidget" << "QComboBox"
+ << "QWidget" << "QDialog" << "QWizard" << "QLCDNumber";
+ // put less stress on the compiler by limiting the template nesting depth
+ (*availableWidgetList) << "QProgressBar" << "QTextView" << "QTextBrowser"
+ << "QDial" << "QSlider" << "QFrame" << "Line" << "QTextEdit"
+ << "QDateEdit" << "QTimeEdit" << "QDateTimeEdit" << "QScrollBar"
+ << "QPopupMenu" << "QWidgetStack" << "QMainWindow"
+ << "QDataTable" << "QDataBrowser" << "QDataView"
+ << "QVBox" << "QHBox" << "QGrid" << "QToolBox" << "QSplitter";
+
+ if ( !widgetInterfaceManager )
+ widgetInterfaceManager =
+ new QPluginManager<WidgetInterface>( IID_Widget, QApplication::libraryPaths(), *qwf_plugin_dir );
+
+ QStringList l = widgetInterfaceManager->featureList();
+ QStringList::Iterator it;
+ for ( it = l.begin(); it != l.end(); ++it )
+ (*availableWidgetList) << *it;
+
+ availableWidgetMap = new QMap<QString, bool>;
+ for ( it = availableWidgetList->begin(); it != availableWidgetList->end(); ++it )
+ availableWidgetMap->insert( *it, TRUE );
+}
+
+static QImage loadImageData( const QString& format, ulong len, QByteArray data )
+{
+ QImage img;
+ if ( format == "XPM.GZ" || format == "XBM.GZ" ) {
+ if ( len < data.size() * 10 )
+ len = data.size() * 10;
+ // qUncompress() expects the first 4 bytes to be the expected length of
+ // the uncompressed data
+ QByteArray dataTmp( data.size() + 4 );
+ memcpy( dataTmp.data()+4, data.data(), data.size() );
+ dataTmp[0] = ( len & 0xff000000 ) >> 24;
+ dataTmp[1] = ( len & 0x00ff0000 ) >> 16;
+ dataTmp[2] = ( len & 0x0000ff00 ) >> 8;
+ dataTmp[3] = ( len & 0x000000ff );
+ QByteArray baunzip = qUncompress( dataTmp );
+ len = baunzip.size();
+ img.loadFromData( (const uchar*)baunzip.data(), len, format.left(format.find('.')) );
+ } else {
+ img.loadFromData( (const uchar*)data.data(), data.size(), format );
+ }
+ return img;
+}
+
+static QSizePolicy::SizeType stringToSizeType( const QString& str )
+{
+ if ( str == "Fixed" ) {
+ return QSizePolicy::Fixed;
+ } else if ( str == "Minimum" ) {
+ return QSizePolicy::Minimum;
+ } else if ( str == "Maximum" ) {
+ return QSizePolicy::Maximum;
+ } else if ( str == "Preferred" ) {
+ return QSizePolicy::Preferred;
+ } else if ( str == "MinimumExpanding" ) {
+ return QSizePolicy::MinimumExpanding;
+ } else if ( str == "Expanding" ) {
+ return QSizePolicy::Expanding;
+ } else {
+ return QSizePolicy::Ignored;
+ }
+}
+
+
+/*!
+ \class QWidgetFactory
+
+ \brief The QWidgetFactory class provides for the dynamic creation of widgets
+ from Qt Designer .ui files.
+
+ This class basically offers two things:
+
+ \list
+
+ \i Dynamically creating widgets from \link designer-manual.book Qt
+ Designer\endlink user interface description files.
+ You can do this using the static function QWidgetFactory::create().
+ This function also performs signal and slot connections, tab
+ ordering, etc., as defined in the .ui file, and returns the
+ top-level widget in the .ui file. After creating the widget you can
+ use QObject::child() and QObject::queryList() to access child
+ widgets of this returned widget.
+
+ \i Adding additional widget factories to be able to create custom
+ widgets. See createWidget() for details.
+
+ \endlist
+
+ This class is not included in the Qt library itself. To use it you
+ must link against \c libqui.so (Unix) or \c qui.lib (Windows), which is
+ built into \c INSTALL/lib if you built \e{Qt Designer} (\c INSTALL is
+ the directory where Qt is installed ).
+
+ If you create a QMainWindow using a QWidgetFactory, be aware that
+ it already has a central widget. Therefore, you need to delete this
+ one before setting another one.
+
+ See the "Creating Dynamic Dialogs from .ui Files" section of the \link
+ designer-manual.book Qt Designer manual\endlink for an example. See
+ also the \l{QWidgetPlugin} class and the \link plugins-howto.html
+ Plugins documentation\endlink.
+*/
+
+/*! Constructs a QWidgetFactory. */
+
+QWidgetFactory::QWidgetFactory()
+ : d( new QWidgetFactoryPrivate() ), dbControls( 0 ),
+ usePixmapCollection( FALSE ), defMargin( 11 ), defSpacing( 6 )
+{
+ widgetFactories.setAutoDelete( TRUE );
+ d->customWidgets.setAutoDelete( TRUE );
+}
+
+/*! \fn QWidgetFactory::~QWidgetFactory()
+ Destructor.
+*/
+QWidgetFactory::~QWidgetFactory()
+{
+ delete d;
+}
+
+/*!
+
+ Loads the \e{Qt Designer} user interface description file \a uiFile
+ and returns the top-level widget in that description. \a parent and
+ \a name are passed to the constructor of the top-level widget.
+
+ This function also performs signal and slot connections, tab
+ ordering, etc., as described in the .ui file. In \e{Qt Designer} it
+ is possible to add custom slots to a form and connect to them. If
+ you want these connections to be made, you must create a class
+ derived from QObject, which implements all these slots. Then pass an
+ instance of the object as \a connector to this function. If you do
+ this, the connections to the custom slots will be done using the \a
+ connector as slot.
+
+ If something fails, 0 is returned.
+
+ The ownership of the returned widget is passed to the caller.
+*/
+
+QWidget *QWidgetFactory::create( const QString &uiFile, QObject *connector,
+ QWidget *parent, const char *name )
+{
+ setupPluginDir();
+ QFile f( uiFile );
+ bool failed = FALSE;
+ if ( !f.open( IO_ReadOnly ) )
+ failed = TRUE;
+ if ( failed && qApp->type() == QApplication::Tty ) {
+ // for QSA: If we have no GUI, we have no form definition
+ // files, but just the code. So try if only the code exists.
+ f.setName( uiFile + ".qs" );
+ failed = !f.open( IO_ReadOnly );
+ }
+ if ( failed )
+ return 0;
+
+ qwf_currFileName = uiFile;
+ QWidget *w = QWidgetFactory::create( &f, connector, parent, name );
+ if ( !qwf_forms )
+ qwf_forms = new QMap<QWidget*, QString>;
+ qwf_forms->insert( w, uiFile );
+ return w;
+}
+
+#undef slots
+
+/*! \overload
+ Loads the user interface description from device \a dev.
+ */
+
+QWidget *QWidgetFactory::create( QIODevice *dev, QObject *connector, QWidget *parent, const char *name )
+{
+ setupPluginDir();
+ QWidget *w = 0;
+ QDomDocument doc;
+ QString errMsg;
+ int errLine;
+
+ QWidgetFactory *widgetFactory = new QWidgetFactory;
+ widgetFactory->toplevel = 0;
+
+ // If we have no GUI, we only want to load the code
+ if ( qApp->type() != QApplication::Tty ) {
+ QIODevice::Offset start = dev->at();
+ Q_UINT32 magic;
+ QDataStream in( dev );
+ in >> magic;
+ if ( magic == UibMagic ) {
+ w = widgetFactory->createFromUibFile( in, connector, parent, name );
+ } else {
+ in.unsetDevice();
+ dev->at( start );
+ if ( doc.setContent( dev, &errMsg, &errLine ) ) {
+ w = widgetFactory->createFromUiFile( doc, connector, parent, name );
+ } else {
+ // qDebug( QString("Parse error: ") + errMsg + QString(" in line %d"), errLine );
+ }
+ }
+ if ( !w ) {
+ delete widgetFactory;
+ return 0;
+ }
+ }
+
+ if ( !languageInterfaceManager )
+ languageInterfaceManager =
+ new QPluginManager<LanguageInterface>( IID_Language, QApplication::libraryPaths(), *qwf_plugin_dir );
+ widgetFactory->loadExtraSource();
+
+ if ( widgetFactory->toplevel ) {
+#ifndef QT_NO_SQL
+ QMap<QWidget*, SqlWidgetConnection>::Iterator cit = widgetFactory->sqlWidgetConnections.begin();
+ for( ; cit != widgetFactory->sqlWidgetConnections.end(); ++cit ) {
+ if ( widgetFactory->noDatabaseWidgets.find( cit.key()->name() ) !=
+ widgetFactory->noDatabaseWidgets.end() )
+ continue;
+ if ( cit.key()->inherits( "QDesignerDataBrowser2" ) )
+ ( (QDesignerDataBrowser2*)cit.key() )->initPreview( (*cit).conn, (*cit).table,
+ cit.key(), *(*cit).dbControls );
+ else if ( cit.key()->inherits( "QDesignerDataView2" ) )
+ ( (QDesignerDataView2*)cit.key() )->initPreview( (*cit).conn, (*cit).table,
+ cit.key(), *(*cit).dbControls );
+ }
+
+ for ( QMap<QString, QStringList>::Iterator it = widgetFactory->dbTables.begin();
+ it != widgetFactory->dbTables.end(); ++it ) {
+ QDataTable *table = (QDataTable*)widgetFactory->toplevel->child( it.key(), "QDataTable" );
+ if ( !table )
+ continue;
+ if ( widgetFactory->noDatabaseWidgets.find( table->name() ) !=
+ widgetFactory->noDatabaseWidgets.end() )
+ continue;
+ QValueList<Field> fieldMap = *widgetFactory->fieldMaps.find( table );
+ QString conn = (*it)[ 0 ];
+ QSqlCursor* c = 0;
+ QSqlDatabase *db = 0;
+ if ( conn.isEmpty() || conn == "(default)" ) {
+ db = QSqlDatabase::database();
+ c = new QSqlCursor( (*it)[ 1 ] );
+ } else {
+ db = QSqlDatabase::database( conn );
+ c = new QSqlCursor( (*it)[ 1 ], TRUE, db );
+ }
+ if ( db ) {
+ table->setSqlCursor( c, fieldMap.isEmpty(), TRUE );
+ table->refresh( QDataTable::RefreshAll );
+ }
+ }
+#endif
+ }
+
+ for ( QMap<QString, QString>::Iterator it = widgetFactory->buddies.begin();
+ it != widgetFactory->buddies.end(); ++it ) {
+ QLabel *label = (QLabel*)widgetFactory->toplevel->child( it.key(), "QLabel" );
+ QWidget *buddy = (QWidget*)widgetFactory->toplevel->child( *it, "QWidget" );
+ if ( label && buddy )
+ label->setBuddy( buddy );
+ }
+
+ delete widgetFactory;
+
+ QApplication::sendPostedEvents();
+
+ return w;
+}
+
+QWidget *QWidgetFactory::createFromUiFile( QDomDocument doc, QObject *connector,
+ QWidget *parent, const char *name )
+{
+ DomTool::fixDocument( doc );
+
+ uiFileVersion = doc.firstChild().toElement().attribute("version");
+ QDomElement e = doc.firstChild().toElement().firstChild().toElement();
+
+ QDomElement variables = e;
+ while ( variables.tagName() != "variables" && !variables.isNull() )
+ variables = variables.nextSibling().toElement();
+
+ QDomElement slots = e;
+ while ( slots.tagName() != "slots" && !slots.isNull() )
+ slots = slots.nextSibling().toElement();
+
+ QDomElement connections = e;
+ while ( connections.tagName() != "connections" && !connections.isNull() )
+ connections = connections.nextSibling().toElement();
+
+ QDomElement imageCollection = e;
+ while ( imageCollection.tagName() != "images" && !imageCollection.isNull() )
+ imageCollection = imageCollection.nextSibling().toElement();
+
+ QDomElement tabOrder = e;
+ while ( tabOrder.tagName() != "tabstops" && !tabOrder.isNull() )
+ tabOrder = tabOrder.nextSibling().toElement();
+
+ QDomElement actions = e;
+ while ( actions.tagName() != "actions" && !actions.isNull() )
+ actions = actions.nextSibling().toElement();
+
+ QDomElement toolbars = e;
+ while ( toolbars.tagName() != "toolbars" && !toolbars.isNull() )
+ toolbars = toolbars.nextSibling().toElement();
+
+ QDomElement menubar = e;
+ while ( menubar.tagName() != "menubar" && !menubar.isNull() )
+ menubar = menubar.nextSibling().toElement();
+
+ QDomElement functions = e;
+ while ( functions.tagName() != "functions" && !functions.isNull() )
+ functions = functions.nextSibling().toElement();
+
+ QDomElement widget;
+ while ( !e.isNull() ) {
+ if ( e.tagName() == "class" ) {
+ d->translationContext = e.firstChild().toText().data();
+ } else if ( e.tagName() == "widget" ) {
+ widget = e;
+ } else if ( e.tagName() == "pixmapinproject" ) {
+ usePixmapCollection = TRUE;
+ } else if ( e.tagName() == "layoutdefaults" ) {
+ defSpacing = e.attribute( "spacing", QString::number( defSpacing ) ).toInt();
+ defMargin = e.attribute( "margin", QString::number( defMargin ) ).toInt();
+ }
+ e = e.nextSibling().toElement();
+ }
+
+ if ( !imageCollection.isNull() )
+ loadImageCollection( imageCollection );
+
+ createWidgetInternal( widget, parent, 0, widget.attribute("class", "QWidget") );
+ QWidget *w = toplevel;
+ if ( !w )
+ return 0;
+
+ if ( !actions.isNull() )
+ loadActions( actions );
+ if ( !toolbars.isNull() )
+ loadToolBars( toolbars );
+ if ( !menubar.isNull() )
+ loadMenuBar( menubar );
+
+ if ( !connections.isNull() )
+ loadConnections( connections, connector );
+ if ( w && name && qstrlen( name ) > 0 )
+ w->setName( name );
+
+ if ( !tabOrder.isNull() )
+ loadTabOrder( tabOrder );
+
+#if 0
+ if ( !functions.isNull() ) // compatibiliy with early 3.0 betas
+ loadFunctions( functions );
+#endif
+
+ return w;
+}
+
+void QWidgetFactory::unpackUInt16( QDataStream& in, Q_UINT16& n )
+{
+ Q_UINT8 half;
+ in >> half;
+ if ( half == 255 ) {
+ in >> n;
+ } else {
+ n = half;
+ }
+}
+
+void QWidgetFactory::unpackUInt32( QDataStream& in, Q_UINT32& n )
+{
+ Q_UINT16 half;
+ in >> half;
+ if ( half == 65535 ) {
+ in >> n;
+ } else {
+ n = half;
+ }
+}
+
+void QWidgetFactory::unpackByteArray( QDataStream& in, QByteArray& array )
+{
+ Q_UINT32 size;
+ unpackUInt32( in, size );
+ array.resize( size );
+ in.readRawBytes( array.data(), size );
+}
+
+void QWidgetFactory::unpackCString( const UibStrTable& strings, QDataStream& in,
+ QCString& cstr )
+{
+ Q_UINT32 n;
+ unpackUInt32( in, n );
+ cstr = strings.asCString( n );
+}
+
+void QWidgetFactory::unpackString( const UibStrTable& strings, QDataStream& in,
+ QString& str )
+{
+ Q_UINT32 n;
+ unpackUInt32( in, n );
+ str = strings.asString( n );
+}
+
+void QWidgetFactory::unpackStringSplit( const UibStrTable& strings,
+ QDataStream& in, QString& str )
+{
+ QString remainder;
+ unpackString( strings, in, str );
+ unpackString( strings, in, remainder );
+ str += remainder;
+}
+
+void QWidgetFactory::unpackVariant( const UibStrTable& strings, QDataStream& in,
+ QVariant& value )
+{
+ QString imageName;
+ Q_UINT32 number;
+ Q_UINT16 count;
+ Q_UINT16 x;
+ Q_UINT16 y;
+ Q_UINT16 width;
+ Q_UINT16 height;
+ Q_UINT8 bit;
+ Q_UINT8 type;
+
+ in >> type;
+
+ switch ( type ) {
+ case QVariant::String:
+ unpackString( strings, in, value.asString() );
+ break;
+ case QVariant::Pixmap:
+ unpackString( strings, in, imageName );
+ if ( imageName.isEmpty() ) {
+ value.asPixmap() = QPixmap();
+ } else {
+ value.asPixmap() = loadPixmap( imageName );
+ }
+ break;
+ case QVariant::Image:
+ unpackString( strings, in, imageName );
+ if ( imageName.isEmpty() ) {
+ value.asImage() = QImage();
+ } else {
+ value.asImage() = loadFromCollection( imageName );
+ }
+ break;
+ case QVariant::IconSet:
+ unpackString( strings, in, imageName );
+ if ( imageName.isEmpty() ) {
+ value.asIconSet() = QIconSet();
+ } else {
+ value.asIconSet() = QIconSet( loadPixmap(imageName) );
+ }
+ break;
+ case QVariant::StringList:
+ unpackUInt16( in, count );
+ while ( count-- ) {
+ QString str;
+ unpackString( strings, in, str );
+ value.asStringList().append( str );
+ }
+ break;
+ case QVariant::Rect:
+ unpackUInt16( in, x );
+ unpackUInt16( in, y );
+ unpackUInt16( in, width );
+ unpackUInt16( in, height );
+ value = QRect( x, y, width, height );
+ break;
+ case QVariant::Size:
+ unpackUInt16( in, width );
+ unpackUInt16( in, height );
+ value = QSize( width, height );
+ break;
+ case QVariant::Color:
+ in >> value.asColor();
+ break;
+ case QVariant::Point:
+ unpackUInt16( in, x );
+ unpackUInt16( in, y );
+ value = QPoint( x, y );
+ break;
+ case QVariant::Int:
+ unpackUInt32( in, number );
+ value = (int) number;
+ break;
+ case QVariant::Bool:
+ in >> bit;
+ value = QVariant( bit != 0, 0 );
+ break;
+ case QVariant::Double:
+ in >> value.asDouble();
+ break;
+ case QVariant::CString:
+ unpackCString( strings, in, value.asCString() );
+ break;
+ case QVariant::Cursor:
+ in >> value.asCursor();
+ break;
+ case QVariant::Date:
+ in >> value.asDate();
+ break;
+ case QVariant::Time:
+ in >> value.asTime();
+ break;
+ case QVariant::DateTime:
+ in >> value.asDateTime();
+ break;
+ default:
+ in >> value;
+ }
+}
+
+void QWidgetFactory::inputSpacer( const UibStrTable& strings, QDataStream& in,
+ QLayout *parent )
+{
+ QCString name;
+ QVariant value;
+ QCString comment;
+ QSizePolicy::SizeType sizeType = QSizePolicy::Preferred;
+ bool vertical = FALSE;
+ int w = 0;
+ int h = 0;
+ Q_UINT16 column = 0;
+ Q_UINT16 row = 0;
+ Q_UINT16 colspan = 1;
+ Q_UINT16 rowspan = 1;
+ Q_UINT8 objectTag;
+
+ in >> objectTag;
+ while ( !in.atEnd() && objectTag != Object_End ) {
+ switch ( objectTag ) {
+ case Object_GridCell:
+ unpackUInt16( in, column );
+ unpackUInt16( in, row );
+ unpackUInt16( in, colspan );
+ unpackUInt16( in, rowspan );
+ break;
+ case Object_VariantProperty:
+ unpackCString( strings, in, name );
+ unpackVariant( strings, in, value );
+
+ if ( name == "orientation" ) {
+ vertical = ( value == "Vertical" );
+ } else if ( name == "sizeHint" ) {
+ w = value.toSize().width();
+ h = value.toSize().height();
+ } else if ( name == "sizeType" ) {
+ sizeType = stringToSizeType( value.toString() );
+ }
+ break;
+ default:
+ qFatal( "Corrupt" );
+ }
+ in >> objectTag;
+ }
+
+ if ( parent != 0 ) {
+ QSpacerItem *spacer;
+ if ( vertical ) {
+ spacer = new QSpacerItem( w, h, QSizePolicy::Minimum, sizeType );
+ } else {
+ spacer = new QSpacerItem( w, h, sizeType, QSizePolicy::Minimum );
+ }
+
+ if ( parent->inherits("QGridLayout") ) {
+ ((QGridLayout *) parent)->addMultiCell( spacer, row,
+ row + rowspan - 1, column, column + colspan - 1,
+ vertical ? Qt::AlignHCenter : Qt::AlignVCenter );
+ } else {
+ parent->addItem( spacer );
+ }
+ }
+}
+
+void QWidgetFactory::inputColumnOrRow( const UibStrTable& strings,
+ QDataStream& in, QObject *parent,
+ bool isRow )
+{
+ QString text;
+ QPixmap pixmap;
+ QString field;
+ bool clickable = TRUE;
+ bool resizable = TRUE;
+
+ QCString name;
+ QVariant value;
+ QCString comment;
+ QString str;
+ Q_UINT8 objectTag;
+
+ in >> objectTag;
+ while ( !in.atEnd() && objectTag != Object_End ) {
+ switch ( objectTag ) {
+ case Object_TextProperty:
+ unpackCString( strings, in, name );
+ unpackCString( strings, in, value.asCString() );
+ unpackCString( strings, in, comment );
+ str = translate( value.asCString().data(), comment.data() );
+
+ if ( name == "field" ) {
+ field = str;
+ } else if ( name == "text" ) {
+ text = str;
+ }
+ break;
+ case Object_VariantProperty:
+ unpackCString( strings, in, name );
+ unpackVariant( strings, in, value );
+
+ if ( name == "clickable" ) {
+ clickable = value.toBool();
+ } else if ( name == "pixmap" ) {
+ pixmap = value.asPixmap();
+ } else if ( name == "resizable" ) {
+ resizable = value.toBool();
+ }
+ break;
+ default:
+ qFatal( "Corrupt" );
+ }
+ in >> objectTag;
+ }
+
+ if ( parent != 0 ) {
+ if ( parent->inherits("QListView") ) {
+ createListViewColumn( (QListView *) parent, text, pixmap, clickable,
+ resizable );
+#ifndef QT_NO_TABLE
+ } else if ( parent->inherits("QTable") ) {
+ createTableColumnOrRow( (QTable *) parent, text, pixmap, field,
+ isRow );
+#endif
+ }
+ }
+}
+
+void QWidgetFactory::inputItem( const UibStrTable& strings, QDataStream& in,
+ QObject *parent, QListViewItem *parentItem )
+{
+ QStringList texts;
+ QValueList<QPixmap> pixmaps;
+ QCString name;
+ QVariant value;
+ QCString comment;
+ Q_UINT8 objectTag;
+
+ QListView *listView = 0;
+ if ( parent != 0 && parent->inherits("QListView") )
+ parent = (QListView *) parent;
+ QListViewItem *item = 0;
+ if ( listView != 0 ) {
+ if ( parentItem == 0 ) {
+ item = new QListViewItem( listView, d->lastItem );
+ } else {
+ item = new QListViewItem( parentItem, d->lastItem );
+ }
+ d->lastItem = item;
+ }
+
+ in >> objectTag;
+ while ( !in.atEnd() && objectTag != Object_End ) {
+ switch ( objectTag ) {
+ case Object_Item:
+ if ( listView != 0 )
+ d->lastItem->setOpen( TRUE );
+ inputItem( strings, in, parent, item );
+ break;
+ case Object_TextProperty:
+ unpackCString( strings, in, name );
+ unpackCString( strings, in, value.asCString() );
+ unpackCString( strings, in, comment );
+
+ if ( name == "text" )
+ texts << translate( value.asCString().data(), comment.data() );
+ break;
+ case Object_VariantProperty:
+ unpackCString( strings, in, name );
+ unpackVariant( strings, in, value );
+
+ if ( name == "pixmap" )
+ pixmaps << value.asPixmap();
+ break;
+ default:
+ qFatal( "Corrupt" );
+ }
+ in >> objectTag;
+ }
+
+ if ( listView != 0 ) {
+ int i = 0;
+ QStringList::ConstIterator t = texts.begin();
+ while ( t != texts.end() ) {
+ item->setText( i, *t );
+ ++i;
+ ++t;
+ }
+
+ int j = 0;
+ QValueList<QPixmap>::ConstIterator p = pixmaps.begin();
+ while ( p != pixmaps.end() ) {
+ item->setPixmap( j, *p );
+ ++j;
+ ++p;
+ }
+ } else {
+ QString text = texts.last();
+ QPixmap pixmap = pixmaps.last();
+
+ if ( parent != 0 ) {
+ if ( parent->inherits("QComboBox") ||
+ parent->inherits("QListBox") ) {
+ QListBox *listBox = (QListBox *) parent->qt_cast( "QListBox" );
+ if ( listBox == 0 )
+ listBox = ((QComboBox *) parent)->listBox();
+
+ if ( pixmap.isNull() ) {
+ (void) new QListBoxText( listBox, text );
+ } else {
+ (void) new QListBoxPixmap( listBox, pixmap, text );
+ }
+ #ifndef QT_NO_ICONVIEW
+ } else if ( parent->inherits("QIconView") ) {
+ (void) new QIconViewItem( (QIconView *) parent, text, pixmap );
+ #endif
+ }
+ }
+ }
+}
+
+void QWidgetFactory::inputMenuItem( QObject **objects,
+ const UibStrTable& strings, QDataStream& in,
+ QMenuBar *menuBar )
+{
+ QCString name;
+ QCString text;
+ Q_UINT16 actionNo;
+ Q_UINT8 objectTag;
+
+ unpackCString( strings, in, name );
+ unpackCString( strings, in, text );
+
+ QPopupMenu *popupMenu = new QPopupMenu( menuBar->parentWidget(), name );
+
+ in >> objectTag;
+ while ( !in.atEnd() && objectTag != Object_End ) {
+ switch ( objectTag ) {
+ case Object_ActionRef:
+ unpackUInt16( in, actionNo );
+ ((QAction *) objects[actionNo])->addTo( popupMenu );
+ break;
+ case Object_Separator:
+ popupMenu->insertSeparator();
+ break;
+ default:
+ qFatal( "Corrupt" );
+ }
+ in >> objectTag;
+ }
+ menuBar->insertItem( translate(text.data()), popupMenu );
+}
+
+QObject *QWidgetFactory::inputObject( QObject **objects, int& numObjects,
+ const UibStrTable& strings,
+ QDataStream& in, QWidget *ancestorWidget,
+ QObject *parent, QCString className )
+{
+ QObject *obj = 0;
+ QWidget *widget = 0;
+ QLayout *layout = 0;
+ QWidget *parentWidget = 0;
+ QLayout *parentLayout = 0;
+
+ bool isQObject = !className.isEmpty();
+ if ( isQObject ) {
+ if ( parent != 0 ) {
+ if ( parent->isWidgetType() ) {
+ if ( parent->inherits("QMainWindow") ) {
+ parentWidget = ((QMainWindow *) parent)->centralWidget();
+ } else {
+ parentWidget = (QWidget *) parent;
+ }
+ } else if ( parent->inherits("QLayout") ) {
+ parentLayout = (QLayout *) parent;
+ parentWidget = ancestorWidget;
+ }
+ }
+
+ if ( className == "QAction" ) {
+ unpackCString( strings, in, className );
+ if ( className == "QActionGroup" ) {
+ obj = new QActionGroup( parent );
+ } else {
+ obj = new QAction( parent );
+ }
+ } else if ( className == "QLayout" ) {
+ unpackCString( strings, in, className );
+ LayoutType type = Grid;
+ if ( className == "QHBoxLayout" ) {
+ type = HBox;
+ } else if ( className == "QVBoxLayout" ) {
+ type = VBox;
+ }
+ if ( parentLayout != 0 && parentLayout->inherits("QGridLayout") ) {
+ layout = createLayout( 0, 0, type );
+ } else {
+ layout = createLayout( parentWidget, parentLayout, type );
+ }
+ obj = layout;
+ } else if ( className == "QMenuBar" ) {
+ unpackCString( strings, in, className );
+ widget = ((QMainWindow *) parent)->menuBar();
+ obj = widget;
+ } else if ( className == "QToolBar" ) {
+ Q_UINT8 dock;
+ in >> dock;
+ unpackCString( strings, in, className );
+ widget = new QToolBar( QString::null, (QMainWindow *) parent,
+ (Qt::Dock) dock );
+ obj = widget;
+ } else if ( className == "QWidget" ) {
+ unpackCString( strings, in, className );
+ widget = createWidget( className, parentWidget, 0 );
+ obj = widget;
+ }
+
+ if ( widget != 0 )
+ ancestorWidget = widget;
+ d->lastItem = 0;
+ objects[numObjects++] = obj;
+ }
+
+ QCString name;
+ QVariant value;
+ QCString comment;
+ QString str;
+ Q_UINT16 actionNo;
+ int metAttribute = 0;
+ Q_UINT16 column = 0;
+ Q_UINT16 row = 0;
+ Q_UINT16 colspan = 1;
+ Q_UINT16 rowspan = 1;
+ Q_UINT8 paletteTag;
+ Q_UINT8 objectTag;
+
+ in >> objectTag;
+ while ( !in.atEnd() && objectTag != Object_End ) {
+ switch ( objectTag ) {
+ case Object_ActionRef:
+ unpackUInt16( in, actionNo );
+ ((QAction *) objects[actionNo])->addTo( (QToolBar *) widget );
+ break;
+ case Object_Attribute:
+ metAttribute = 2;
+ break;
+ case Object_Column:
+ inputColumnOrRow( strings, in, obj, FALSE );
+ break;
+ case Object_Event:
+ unpackCString( strings, in, name );
+ unpackVariant( strings, in, value );
+ // ### do something with value.asStringList()
+ break;
+ case Object_FontProperty:
+ {
+ QFont font;
+ QString family;
+ Q_UINT16 pointSize;
+ Q_UINT8 fontFlags;
+
+ unpackCString( strings, in, name );
+ in >> fontFlags;
+
+ if ( fontFlags & Font_Family ) {
+ unpackString( strings, in, family );
+ font.setFamily( family );
+ }
+ if ( fontFlags & Font_PointSize ) {
+ unpackUInt16( in, pointSize );
+ font.setPointSize( pointSize );
+ }
+ if ( fontFlags & Font_Bold )
+ font.setBold( TRUE );
+ if ( fontFlags & Font_Italic )
+ font.setItalic( TRUE );
+ if ( fontFlags & Font_Underline )
+ font.setUnderline( TRUE );
+ if ( fontFlags & Font_StrikeOut )
+ font.setStrikeOut( TRUE );
+
+ if ( obj != 0 )
+ setProperty( obj, name, font );
+ }
+ break;
+ case Object_GridCell:
+ unpackUInt16( in, column );
+ unpackUInt16( in, row );
+ unpackUInt16( in, colspan );
+ unpackUInt16( in, rowspan );
+ break;
+ case Object_Item:
+ inputItem( strings, in, obj );
+ break;
+ case Object_MenuItem:
+ inputMenuItem( objects, strings, in, (QMenuBar *) widget );
+ break;
+ case Object_PaletteProperty:
+ {
+ QPalette palette;
+ QColorGroup colorGroup;
+ QColor color;
+ int role = -1;
+
+ unpackCString( strings, in, name );
+
+ in >> paletteTag;
+ while ( !in.atEnd() && paletteTag != Palette_End ) {
+ switch ( paletteTag ) {
+ case Palette_Active:
+ palette.setActive( colorGroup );
+ role = -1;
+ break;
+ case Palette_Inactive:
+ palette.setInactive( colorGroup );
+ role = -1;
+ break;
+ case Palette_Disabled:
+ palette.setDisabled( colorGroup );
+ role = -1;
+ break;
+ case Palette_Color:
+ role++;
+ in >> color;
+ colorGroup.setColor( (QColorGroup::ColorRole) role,
+ color );
+ break;
+ case Palette_Pixmap:
+ unpackVariant( strings, in, value );
+ colorGroup.setBrush( (QColorGroup::ColorRole) role,
+ QBrush(color, value.asPixmap()) );
+ break;
+ default:
+ qFatal( "Corrupt" );
+ }
+ in >> paletteTag;
+ }
+ if ( obj != 0 )
+ setProperty( obj, name, palette );
+ }
+ break;
+ case Object_Row:
+ inputColumnOrRow( strings, in, obj, TRUE );
+ break;
+ case Object_Spacer:
+ inputSpacer( strings, in, layout );
+ break;
+ case Object_Separator:
+ ((QToolBar *) widget)->addSeparator();
+ break;
+ case Object_SubAction:
+ inputObject( objects, numObjects, strings, in, parentWidget,
+ obj != 0 ? obj : parent, "QAction" );
+ break;
+ case Object_SubLayout:
+ inputObject( objects, numObjects, strings, in, parentWidget, obj,
+ "QLayout" );
+ break;
+ case Object_SubWidget:
+ inputObject( objects, numObjects, strings, in, parentWidget, obj,
+ "QWidget" );
+ break;
+ case Object_TextProperty:
+ unpackCString( strings, in, name );
+ unpackCString( strings, in, value.asCString() );
+ unpackCString( strings, in, comment );
+ str = translate( value.asCString().data(), comment.data() );
+
+ if ( metAttribute > 0 ) {
+ if ( name == "title" ) {
+ if ( parent != 0 ) {
+ if ( parent->inherits("QTabWidget") ) {
+ ((QTabWidget *) parent)->insertTab( widget, str );
+ } else if ( parent->inherits("QWizard") ) {
+ ((QWizard *) parent)->addPage( widget, str );
+ }
+ }
+ }
+ } else {
+ if ( obj != 0 )
+ setProperty( obj, name, str );
+ }
+ break;
+ case Object_VariantProperty:
+ unpackCString( strings, in, name );
+ unpackVariant( strings, in, value );
+
+ if ( metAttribute > 0 ) {
+ if ( name == "id" ) {
+ if ( parent != 0 && parent->inherits("QWidgetStack") )
+ ((QWidgetStack *) parent)->addWidget( widget, value.toInt() );
+ }
+ } else {
+ if ( obj != 0 )
+ setProperty( obj, name, value );
+ }
+ break;
+ default:
+ qFatal( "Corrupt" );
+ }
+ in >> objectTag;
+ metAttribute--;
+ }
+
+ if ( parentLayout != 0 ) {
+ if ( widget != 0 ) {
+ if ( parentLayout->inherits("QGridLayout") ) {
+ ((QGridLayout *) parentLayout)->addMultiCellWidget(
+ widget, row, row + rowspan - 1, column,
+ column + colspan - 1 );
+ } else {
+ ((QBoxLayout *) parentLayout)->addWidget( widget );
+ }
+ } else if ( layout != 0 ) {
+ if ( parentLayout->inherits("QGridLayout") ) {
+ ((QGridLayout *) parentLayout)->addMultiCellLayout(
+ layout, row, row + rowspan - 1, column,
+ column + colspan - 1 );
+ }
+ }
+ }
+ return obj;
+}
+
+QWidget *QWidgetFactory::createFromUibFile( QDataStream& in,
+ QObject * /* connector */ , QWidget *parent, const char *name )
+{
+#define END_OF_BLOCK() \
+ ( in.atEnd() || in.device()->at() >= nextBlock )
+
+ Q_UINT8 lf;
+ Q_UINT8 cr;
+ in >> lf;
+ in >> cr;
+ if ( lf != '\n' || cr != '\r' ) {
+ qWarning( "File corrupted" );
+ return 0;
+ }
+
+ Q_UINT8 qdatastreamVersion;
+ in >> qdatastreamVersion;
+ if ( (int) qdatastreamVersion > in.version() ) {
+ qWarning( "Incompatible version of Qt" );
+ return 0;
+ }
+ in.setVersion( qdatastreamVersion );
+
+ UibStrTable strings;
+ QObject **objects = 0;
+ int numObjects = 0;
+
+ Q_UINT8 blockType;
+ Q_UINT32 blockSize;
+
+ in >> blockType;
+ while ( !in.atEnd() && blockType != Block_End ) {
+ unpackUInt32( in, blockSize );
+ QIODevice::Offset nextBlock = in.device()->at() + blockSize;
+
+ switch ( blockType ) {
+ case Block_Actions:
+ inputObject( objects, numObjects, strings, in, toplevel, toplevel );
+ break;
+ case Block_Buddies:
+ {
+ Q_UINT16 labelNo;
+ Q_UINT16 buddyNo;
+
+ do {
+ unpackUInt16( in, labelNo );
+ unpackUInt16( in, buddyNo );
+ QLabel *label =
+ (QLabel *) objects[labelNo]->qt_cast( "QLabel" );
+ if ( label != 0 )
+ label->setBuddy( (QWidget *) objects[buddyNo] );
+ } while ( !END_OF_BLOCK() );
+ }
+ break;
+ case Block_Connections:
+ {
+ QString language = "C++";
+ Q_UINT16 senderNo = 0;
+ QString signal = "clicked()";
+ Q_UINT16 receiverNo = 0;
+ QString slot = "accept()";
+ Q_UINT8 connectionFlags;
+
+ do {
+ in >> connectionFlags;
+ if ( connectionFlags & Connection_Language )
+ unpackString( strings, in, language );
+ if ( connectionFlags & Connection_Sender )
+ unpackUInt16( in, senderNo );
+ if ( connectionFlags & Connection_Signal )
+ unpackStringSplit( strings, in, signal );
+ if ( connectionFlags & Connection_Receiver )
+ unpackUInt16( in, receiverNo );
+ if ( connectionFlags & Connection_Slot )
+ unpackStringSplit( strings, in, slot );
+ // ###
+#if 0
+ qWarning( "connect( %p, %s, %p, %s )", objects[senderNo],
+ signal.latin1(), objects[receiverNo],
+ slot.latin1() );
+#endif
+ } while ( !END_OF_BLOCK() );
+ }
+ break;
+ case Block_Functions:
+ // ###
+ qWarning( "Block_Functions not supported" );
+ in.device()->at( nextBlock );
+ break;
+ case Block_Images:
+ {
+ QString format;
+ Q_UINT32 length;
+ QByteArray data;
+ Image image;
+
+ do {
+ unpackString( strings, in, image.name );
+ unpackString( strings, in, format );
+ unpackUInt32( in, length );
+ unpackByteArray( in, data );
+ image.img = loadImageData( format, length, data );
+ images += image;
+ } while ( !END_OF_BLOCK() );
+ }
+ break;
+ case Block_Intro:
+ {
+ Q_INT16 defaultMargin;
+ Q_INT16 defaultSpacing;
+ Q_UINT16 maxObjects;
+ Q_UINT8 introFlags;
+
+ in >> introFlags;
+ in >> defaultMargin;
+ in >> defaultSpacing;
+ unpackUInt16( in, maxObjects );
+ unpackCString( strings, in, d->translationContext );
+
+ if ( introFlags & Intro_Pixmapinproject )
+ usePixmapCollection = TRUE;
+ if ( defaultMargin != -32768 )
+ defMargin = defaultMargin;
+ if ( defaultSpacing != -32768 )
+ defSpacing = defaultSpacing;
+ objects = new QObject *[maxObjects];
+ }
+ break;
+ case Block_Menubar:
+ inputObject( objects, numObjects, strings, in, toplevel, toplevel,
+ "QMenuBar" );
+ break;
+ case Block_Slots:
+ {
+ QString language;
+ QString slot;
+
+ do {
+ unpackString( strings, in, language );
+ unpackStringSplit( strings, in, slot );
+ } while ( !END_OF_BLOCK() );
+ }
+ break;
+ case Block_Strings:
+ strings.readBlock( in, blockSize );
+ break;
+ case Block_Tabstops:
+ {
+ Q_UINT16 beforeNo;
+ Q_UINT16 afterNo;
+
+ unpackUInt16( in, beforeNo );
+ while ( !END_OF_BLOCK() ) {
+ unpackUInt16( in, afterNo );
+ toplevel->setTabOrder( (QWidget *) objects[beforeNo],
+ (QWidget *) objects[afterNo] );
+ beforeNo = afterNo;
+ }
+ }
+ break;
+ case Block_Toolbars:
+ do {
+ inputObject( objects, numObjects, strings, in, toplevel,
+ toplevel, "QToolBar" );
+ } while ( !END_OF_BLOCK() );
+ break;
+ case Block_Variables:
+ // ###
+ qWarning( "Block_Variables not supported" );
+ in.device()->at( nextBlock );
+ break;
+ case Block_Widget:
+ toplevel = (QWidget *)
+ inputObject( objects, numObjects, strings, in, toplevel, parent,
+ "QWidget" );
+ if ( toplevel != 0 )
+ toplevel->setName( name );
+ break;
+ default:
+ qWarning( "Version error" );
+ return 0;
+ }
+ in >> blockType;
+ }
+ delete[] objects;
+ return toplevel;
+}
+
+/*! Installs a widget factory \a factory, which normally contains
+ additional widgets that can then be created using a QWidgetFactory.
+ See createWidget() for further details.
+*/
+
+void QWidgetFactory::addWidgetFactory( QWidgetFactory *factory )
+{
+ widgetFactories.append( factory );
+}
+
+/*!
+ Creates a widget of the type \a className passing \a parent and \a
+ name to its constructor.
+
+ If \a className is a widget in the Qt library, it is directly
+ created by this function. If the widget isn't in the Qt library,
+ each of the installed widget plugins is asked, in turn, to create
+ the widget. As soon as a plugin says it can create the widget it
+ is asked to do so. It may occur that none of the plugins can
+ create the widget, in which case each installed widget factory is
+ asked to create the widget (see addWidgetFactory()). If the widget
+ cannot be created by any of these means, 0 is returned.
+
+ If you have a custom widget, and want it to be created using the
+ widget factory, there are two approaches you can use:
+
+ \list 1
+
+ \i Write a widget plugin. This allows you to use the widget in
+ \e{Qt Designer} and in this QWidgetFactory. See the widget plugin
+ documentation for further details. (See the "Creating Custom
+ Widgets with Plugins" section of the \link designer-manual.book Qt
+ Designer manual\endlink for an example.
+
+ \i Subclass QWidgetFactory. Then reimplement this function to
+ create and return an instance of your custom widget if \a
+ className equals the name of your widget, otherwise return 0. Then
+ at the beginning of your program where you want to use the widget
+ factory to create widgets do a:
+ \code
+ QWidgetFactory::addWidgetFactory( new MyWidgetFactory );
+ \endcode
+ where MyWidgetFactory is your QWidgetFactory subclass.
+
+ \endlist
+*/
+
+QWidget *QWidgetFactory::createWidget( const QString &className, QWidget *parent,
+ const char *name ) const
+{
+ // create widgets we know
+ if ( className == "QPushButton" ) {
+ return new QPushButton( parent, name );
+ } else if ( className == "QToolButton" ) {
+ return new QToolButton( parent, name );
+ } else if ( className == "QCheckBox" ) {
+ return new QCheckBox( parent, name );
+ } else if ( className == "QRadioButton" ) {
+ return new QRadioButton( parent, name );
+ } else if ( className == "QGroupBox" ) {
+ return new QGroupBox( parent, name );
+ } else if ( className == "QButtonGroup" ) {
+ return new QButtonGroup( parent, name );
+ } else if ( className == "QIconView" ) {
+#if !defined(QT_NO_ICONVIEW)
+ return new QIconView( parent, name );
+#endif
+ } else if ( className == "QTable" ) {
+#if !defined(QT_NO_TABLE)
+ return new QTable( parent, name );
+#endif
+ } else if ( className == "QListBox" ) {
+ return new QListBox( parent, name );
+ } else if ( className == "QListView" ) {
+ return new QListView( parent, name );
+ } else if ( className == "QLineEdit" ) {
+ return new QLineEdit( parent, name );
+ } else if ( className == "QSpinBox" ) {
+ return new QSpinBox( parent, name );
+ } else if ( className == "QMultiLineEdit" ) {
+ return new QMultiLineEdit( parent, name );
+ } else if ( className == "QLabel" || className == "TextLabel" || className == "PixmapLabel" ) {
+ return new QLabel( parent, name );
+ } else if ( className == "QLayoutWidget" ) {
+ return new QWidget( parent, name );
+ } else if ( className == "QTabWidget" ) {
+ return new QTabWidget( parent, name );
+ } else if ( className == "QComboBox" ) {
+ return new QComboBox( FALSE, parent, name );
+ } else if ( className == "QWidget" ) {
+ if ( !qwf_stays_on_top )
+ return new QWidget( parent, name );
+ return new QWidget( parent, name, Qt::WStyle_StaysOnTop );
+ } else if ( className == "QDialog" ) {
+ if ( !qwf_stays_on_top )
+ return new QDialog( parent, name );
+ return new QDialog( parent, name, FALSE, Qt::WStyle_StaysOnTop );
+ } else if ( className == "QWizard" ) {
+ return new QWizard( parent, name );
+ } else if ( className == "QLCDNumber" ) {
+ return new QLCDNumber( parent, name );
+ } else if ( className == "QProgressBar" ) {
+ return new QProgressBar( parent, name );
+ } else if ( className == "QTextView" ) {
+ return new QTextView( parent, name );
+ } else if ( className == "QTextBrowser" ) {
+ return new QTextBrowser( parent, name );
+ } else if ( className == "QDial" ) {
+ return new QDial( parent, name );
+ } else if ( className == "QSlider" ) {
+ return new QSlider( parent, name );
+ } else if ( className == "QFrame" ) {
+ return new QFrame( parent, name );
+ } else if ( className == "QSplitter" ) {
+ return new QSplitter( parent, name );
+ } else if ( className == "Line" ) {
+ QFrame *f = new QFrame( parent, name );
+ f->setFrameStyle( QFrame::HLine | QFrame::Sunken );
+ return f;
+ } else if ( className == "QTextEdit" ) {
+ return new QTextEdit( parent, name );
+ } else if ( className == "QDateEdit" ) {
+ return new QDateEdit( parent, name );
+ } else if ( className == "QTimeEdit" ) {
+ return new QTimeEdit( parent, name );
+ } else if ( className == "QDateTimeEdit" ) {
+ return new QDateTimeEdit( parent, name );
+ } else if ( className == "QScrollBar" ) {
+ return new QScrollBar( parent, name );
+ } else if ( className == "QPopupMenu" ) {
+ return new QPopupMenu( parent, name );
+ } else if ( className == "QWidgetStack" ) {
+ return new QWidgetStack( parent, name );
+ } else if ( className == "QToolBox" ) {
+ return new QToolBox( parent, name );
+ } else if ( className == "QVBox" ) {
+ return new QVBox( parent, name );
+ } else if ( className == "QHBox" ) {
+ return new QHBox( parent, name );
+ } else if ( className == "QGrid" ) {
+ return new QGrid( 4, parent, name );
+ } else if ( className == "QMainWindow" ) {
+ QMainWindow *mw = 0;
+ if ( !qwf_stays_on_top )
+ mw = new QMainWindow( parent, name );
+ else
+ mw = new QMainWindow( parent, name, Qt::WType_TopLevel | Qt::WStyle_StaysOnTop );
+ mw->setCentralWidget( new QWidget( mw, "qt_central_widget" ) );
+ mw->centralWidget()->show();
+ (void)mw->statusBar();
+ return mw;
+
+ }
+#if !defined(QT_NO_SQL)
+ else if ( className == "QDataTable" ) {
+ return new QDataTable( parent, name );
+ } else if ( className == "QDataBrowser" ) {
+ return new QDesignerDataBrowser2( parent, name );
+ } else if ( className == "QDataView" ) {
+ return new QDesignerDataView2( parent, name );
+ }
+#endif
+
+ setupPluginDir();
+ // try to create it using the loaded widget plugins
+ if ( !widgetInterfaceManager )
+ widgetInterfaceManager =
+ new QPluginManager<WidgetInterface>( IID_Widget, QApplication::libraryPaths(),
+ *qwf_plugin_dir );
+
+ QInterfacePtr<WidgetInterface> iface = 0;
+ widgetInterfaceManager->queryInterface( className, &iface );
+ if ( iface ) {
+ QWidget *w = iface->create( className, parent, name );
+ if ( w ) {
+ d->customWidgets.replace( className.latin1(), new bool(TRUE) );
+ return w;
+ }
+ }
+
+ // hope we have a factory which can do it
+ for ( QWidgetFactory* f = widgetFactories.first(); f; f = widgetFactories.next() ) {
+ QWidget *w = f->createWidget( className, parent, name );
+ if ( w )
+ return w;
+ }
+
+ // no success
+ return 0;
+}
+
+/*! Returns the names of the widgets this factory can create. */
+
+QStringList QWidgetFactory::widgets()
+{
+ setupWidgetListAndMap();
+ return *availableWidgetList;
+}
+
+/*! Returns TRUE if the widget factory can create the specified \a widget;
+otherwise returns FALSE. */
+
+bool QWidgetFactory::supportsWidget( const QString &widget )
+{
+ setupWidgetListAndMap();
+ return ( availableWidgetMap->find( widget ) != availableWidgetMap->end() );
+}
+
+QWidget *QWidgetFactory::createWidgetInternal( const QDomElement &e, QWidget *parent,
+ QLayout* layout, const QString &classNameArg )
+{
+ d->lastItem = 0;
+ QDomElement n = e.firstChild().toElement();
+ QWidget *w = 0; // the widget that got created
+ QObject *obj = 0; // gets the properties
+
+ QString className = classNameArg;
+
+ int row = e.attribute( "row" ).toInt();
+ int col = e.attribute( "column" ).toInt();
+ int rowspan = e.attribute( "rowspan" ).toInt();
+ int colspan = e.attribute( "colspan" ).toInt();
+ if ( rowspan < 1 )
+ rowspan = 1;
+ if ( colspan < 1 )
+ colspan = 1;
+
+ bool isQLayoutWidget = FALSE;
+
+ if ( !className.isEmpty() ) {
+ if ( !layout && className == "QLayoutWidget" ) {
+ className = "QWidget";
+ isQLayoutWidget = TRUE;
+ }
+ if ( layout && className == "QLayoutWidget" ) {
+ // hide layout widgets
+ w = parent;
+ } else {
+ obj = QWidgetFactory::createWidget( className, parent, 0 );
+ if ( !obj )
+ return 0;
+ w = (QWidget*)obj;
+ if ( !toplevel )
+ toplevel = w;
+ if ( w->inherits( "QMainWindow" ) )
+ w = ( (QMainWindow*)w )->centralWidget();
+ if ( layout ) {
+ switch( layoutType( layout ) ) {
+ case HBox:
+ ( (QHBoxLayout*)layout )->addWidget( w );
+ break;
+ case VBox:
+ ( (QVBoxLayout*)layout )->addWidget( w );
+ break;
+ case Grid:
+ ( (QGridLayout*)layout )->addMultiCellWidget( w, row, row + rowspan - 1,
+ col, col + colspan - 1 );
+ break;
+ default:
+ break;
+ }
+ }
+
+ layout = 0;
+ }
+ }
+#ifdef QT_CONTAINER_CUSTOM_WIDGETS
+ QString parentClassName = parent ? parent->className() : 0;
+ bool isPlugin = parent ? !!d->customWidgets.find( parent->className() ) : FALSE;
+ if ( isPlugin )
+ qWarning( "####### loading custom container widgets without page support not implemented!" );
+ // ### TODO loading for custom container widgets without pages
+#endif
+
+ int idx = 0;
+ while ( !n.isNull() ) {
+ if ( n.tagName() == "spacer" ) {
+ createSpacer( n, layout );
+ } else if ( n.tagName() == "widget" ) {
+ QMap< QString, QString> *oldDbControls = dbControls;
+ createWidgetInternal( n, w, layout, n.attribute( "class", "QWidget" ) );
+ dbControls = oldDbControls;
+ } else if ( n.tagName() == "hbox" ) {
+ QLayout *parentLayout = layout;
+ if ( layout && layout->inherits( "QGridLayout" ) )
+ layout = createLayout( 0, 0, QWidgetFactory::HBox, isQLayoutWidget );
+ else
+ layout = createLayout( w, layout, QWidgetFactory::HBox, isQLayoutWidget );
+ obj = layout;
+ n = n.firstChild().toElement();
+ if ( parentLayout && parentLayout->inherits( "QGridLayout" ) )
+ ( (QGridLayout*)parentLayout )->addMultiCellLayout( layout, row,
+ row + rowspan - 1, col, col + colspan - 1 );
+ continue;
+ } else if ( n.tagName() == "grid" ) {
+ QLayout *parentLayout = layout;
+ if ( layout && layout->inherits( "QGridLayout" ) )
+ layout = createLayout( 0, 0, QWidgetFactory::Grid, isQLayoutWidget );
+ else
+ layout = createLayout( w, layout, QWidgetFactory::Grid, isQLayoutWidget );
+ obj = layout;
+ n = n.firstChild().toElement();
+ if ( parentLayout && parentLayout->inherits( "QGridLayout" ) )
+ ( (QGridLayout*)parentLayout )->addMultiCellLayout( layout, row,
+ row + rowspan - 1, col, col + colspan - 1 );
+ continue;
+ } else if ( n.tagName() == "vbox" ) {
+ QLayout *parentLayout = layout;
+ if ( layout && layout->inherits( "QGridLayout" ) )
+ layout = createLayout( 0, 0, QWidgetFactory::VBox, isQLayoutWidget );
+ else
+ layout = createLayout( w, layout, QWidgetFactory::VBox, isQLayoutWidget );
+ obj = layout;
+ n = n.firstChild().toElement();
+ if ( parentLayout && parentLayout->inherits( "QGridLayout" ) )
+ ( (QGridLayout*)parentLayout )->addMultiCellLayout( layout, row,
+ row + rowspan - 1, col, col + colspan - 1 );
+ continue;
+ } else if ( n.tagName() == "property" && obj ) {
+ setProperty( obj, n.attribute( "name" ), n.firstChild().toElement() );
+ } else if ( n.tagName() == "attribute" && w ) {
+ QString attrib = n.attribute( "name" );
+ QVariant v = DomTool::elementToVariant( n.firstChild().toElement(), QVariant() );
+ if ( parent ) {
+ if ( parent->inherits( "QTabWidget" ) ) {
+ if ( attrib == "title" )
+ ( (QTabWidget*)parent )->insertTab( w, translate( v.toString() ) );
+ } else if ( parent->inherits( "QWidgetStack" ) ) {
+ if ( attrib == "id" )
+ ( (QWidgetStack*)parent )->addWidget( w, v.toInt() );
+ } else if ( parent->inherits( "QToolBox" ) ) {
+ if ( attrib == "label" )
+ ( (QToolBox*)parent )->addItem( w, v.toString() );
+ } else if ( parent->inherits( "QWizard" ) ) {
+ if ( attrib == "title" )
+ ( (QWizard*)parent )->addPage( w, translate( v.toString() ) );
+#ifdef QT_CONTAINER_CUSTOM_WIDGETS
+ } else if ( isPlugin ) {
+ if ( attrib == "label" ) {
+ WidgetInterface *iface = 0;
+ widgetInterfaceManager->queryInterface( parentClassName, &iface );
+ if ( iface ) {
+ QWidgetContainerInterfacePrivate *iface2 = 0;
+ iface->queryInterface( IID_QWidgetContainer,
+ (QUnknownInterface**)&iface2 );
+ if ( iface2 ) {
+ iface2->insertPage( parentClassName,
+ (QWidget*)parent, translate( v.toString() ), -1, w );
+ iface2->release();
+ }
+ iface->release();
+ }
+ }
+#endif
+ }
+ }
+ } else if ( n.tagName() == "item" ) {
+ createItem( n, w );
+ } else if ( n.tagName() == "column" || n.tagName() == "row" ) {
+ createColumn( n, w );
+ }
+
+ n = n.nextSibling().toElement();
+ idx++;
+ }
+
+ return w;
+}
+
+QLayout *QWidgetFactory::createLayout( QWidget *widget, QLayout* layout,
+ LayoutType type, bool isQLayoutWidget )
+{
+ int spacing = defSpacing;
+ int margin = defMargin;
+
+ if ( layout || !widget || isQLayoutWidget )
+ margin = 0;
+
+ if ( !layout && widget && widget->inherits( "QTabWidget" ) )
+ widget = ((QTabWidget*)widget)->currentPage();
+
+ if ( !layout && widget && widget->inherits( "QWizard" ) )
+ widget = ((QWizard*)widget)->currentPage();
+
+ if ( !layout && widget && widget->inherits( "QWidgetStack" ) )
+ widget = ((QWidgetStack*)widget)->visibleWidget();
+
+ if ( !layout && widget && widget->inherits( "QToolBox" ) )
+ widget = ((QToolBox*)widget)->currentItem();
+
+ QLayout *l = 0;
+ int align = 0;
+ if ( !layout && widget && widget->inherits( "QGroupBox" ) ) {
+ QGroupBox *gb = (QGroupBox*)widget;
+ gb->setColumnLayout( 0, Qt::Vertical );
+ layout = gb->layout();
+ layout->setMargin( 0 );
+ layout->setSpacing( 0 );
+ align = Qt::AlignTop;
+ }
+ if ( layout ) {
+ switch ( type ) {
+ case HBox:
+ l = new QHBoxLayout( layout );
+ break;
+ case VBox:
+ l = new QVBoxLayout( layout );
+ break;
+ case Grid:
+ l = new QGridLayout( layout );
+ break;
+ default:
+ return 0;
+ }
+ } else {
+ switch ( type ) {
+ case HBox:
+ l = new QHBoxLayout( widget );
+ break;
+ case VBox:
+ l = new QVBoxLayout( widget );
+ break;
+ case Grid:
+ l = new QGridLayout( widget );
+ break;
+ default:
+ return 0;
+ }
+ }
+ l->setAlignment( align );
+ l->setMargin( margin );
+ l->setSpacing( spacing );
+ return l;
+}
+
+QWidgetFactory::LayoutType QWidgetFactory::layoutType( QLayout *layout ) const
+{
+ if ( layout->inherits( "QHBoxLayout" ) )
+ return HBox;
+ else if ( layout->inherits( "QVBoxLayout" ) )
+ return VBox;
+ else if ( layout->inherits( "QGridLayout" ) )
+ return Grid;
+ return NoLayout;
+}
+
+void QWidgetFactory::setProperty( QObject* obj, const QString &prop,
+ QVariant value )
+{
+ int offset = obj->metaObject()->findProperty( prop, TRUE );
+
+ if ( offset != -1 ) {
+ if ( prop == "geometry" && obj == toplevel ) {
+ toplevel->resize( value.toRect().size() );
+ } else if ( prop == "accel" ) {
+ obj->setProperty( prop, value.toKeySequence() );
+ } else {
+ if ( value.type() == QVariant::String ||
+ value.type() == QVariant::CString ) {
+ const QMetaProperty *metaProp =
+ obj->metaObject()->property( offset, TRUE );
+ if ( metaProp != 0 && metaProp->isEnumType() ) {
+ if ( metaProp->isSetType() ) {
+ QStrList flagsCStr;
+ QStringList flagsStr =
+ QStringList::split( '|', value.asString() );
+ QStringList::ConstIterator f = flagsStr.begin();
+ while ( f != flagsStr.end() ) {
+ flagsCStr.append( *f );
+ ++f;
+ }
+ value = QVariant( metaProp->keysToValue(flagsCStr) );
+ } else {
+ QCString key = value.toCString();
+ value = QVariant( metaProp->keyToValue(key) );
+ }
+ }
+ }
+ obj->setProperty( prop, value );
+ }
+ } else {
+ if ( obj->isWidgetType() ) {
+ if ( prop == "toolTip" ) {
+ if ( !value.toString().isEmpty() )
+ QToolTip::add( (QWidget*)obj, translate( value.toString() ) );
+ } else if ( prop == "whatsThis" ) {
+ if ( !value.toString().isEmpty() )
+ QWhatsThis::add( (QWidget*)obj, translate( value.toString() ) );
+ } else if ( prop == "buddy" ) {
+ buddies.insert( obj->name(), value.toCString() );
+ } else if ( prop == "buttonGroupId" ) {
+ if ( obj->inherits( "QButton" ) && obj->parent()->inherits( "QButtonGroup" ) )
+ ( (QButtonGroup*)obj->parent() )->insert( (QButton*)obj, value.toInt() );
+#ifndef QT_NO_SQL
+ } else if ( prop == "database" && !obj->inherits( "QDataView" )
+ && !obj->inherits( "QDataBrowser" ) ) {
+ const QStringList& lst = value.asStringList();
+ if ( lst.count() > 2 ) {
+ if ( dbControls )
+ dbControls->insert( obj->name(), lst[ 2 ] );
+ } else if ( lst.count() == 2 ) {
+ dbTables.insert( obj->name(), lst );
+ }
+ } else if ( prop == "database" ) {
+ const QStringList& lst = value.asStringList();
+ if ( lst.count() == 2 && obj->inherits( "QWidget" ) ) {
+ SqlWidgetConnection conn( lst[ 0 ], lst[ 1 ] );
+ sqlWidgetConnections.insert( (QWidget*)obj, conn );
+ dbControls = conn.dbControls;
+ }
+#endif
+ } else if ( prop == "frameworkCode" ) {
+ if ( value.isValid() && !value.toBool() )
+ noDatabaseWidgets << obj->name();
+ }
+ }
+ }
+}
+
+void QWidgetFactory::setProperty( QObject* widget, const QString &prop, const QDomElement &e )
+{
+ QString comment;
+ QVariant value( DomTool::elementToVariant( e, QVariant(), comment ) );
+
+ if ( e.tagName() == "string" ) {
+ value = translate( value.asString(), comment );
+ } else if ( e.tagName() == "pixmap" ) {
+ QPixmap pix = loadPixmap( value.toString() );
+ if ( !pix.isNull() )
+ value = pix;
+ } else if ( e.tagName() == "iconset" ) {
+ QPixmap pix = loadPixmap( value.toString() );
+ if ( !pix.isNull() )
+ value = QIconSet( pix );
+ } else if ( e.tagName() == "image" ) {
+ value = loadFromCollection( value.toString() );
+ } else if ( e.tagName() == "palette" ) {
+ QDomElement n = e.firstChild().toElement();
+ QPalette p;
+ while ( !n.isNull() ) {
+ QColorGroup cg;
+ if ( n.tagName() == "active" ) {
+ cg = loadColorGroup( n );
+ p.setActive( cg );
+ } else if ( n.tagName() == "inactive" ) {
+ cg = loadColorGroup( n );
+ p.setInactive( cg );
+ } else if ( n.tagName() == "disabled" ) {
+ cg = loadColorGroup( n );
+ p.setDisabled( cg );
+ }
+ n = n.nextSibling().toElement();
+ }
+ value = p;
+ }
+ setProperty( widget, prop, value );
+}
+
+void QWidgetFactory::createSpacer( const QDomElement &e, QLayout *layout )
+{
+ QDomElement n = e.firstChild().toElement();
+ int row = e.attribute( "row" ).toInt();
+ int col = e.attribute( "column" ).toInt();
+ int rowspan = e.attribute( "rowspan" ).toInt();
+ int colspan = e.attribute( "colspan" ).toInt();
+
+ Qt::Orientation orient = Qt::Horizontal;
+ int w = 0, h = 0;
+ QSizePolicy::SizeType sizeType = QSizePolicy::Preferred;
+ while ( !n.isNull() ) {
+ if ( n.tagName() == "property" ) {
+ QString prop = n.attribute( "name" );
+ if ( prop == "orientation" ) {
+ if ( n.firstChild().firstChild().toText().data() == "Horizontal" )
+ orient = Qt::Horizontal;
+ else
+ orient = Qt::Vertical;
+ } else if ( prop == "sizeType" ) {
+ sizeType = stringToSizeType( n.firstChild().firstChild().toText().data() );
+ } else if ( prop == "sizeHint" ) {
+ w = n.firstChild().firstChild().firstChild().toText().data().toInt();
+ h = n.firstChild().firstChild().nextSibling().firstChild().toText().data().toInt();
+ }
+ }
+ n = n.nextSibling().toElement();
+ }
+
+ if ( rowspan < 1 )
+ rowspan = 1;
+ if ( colspan < 1 )
+ colspan = 1;
+ QSpacerItem *item = new QSpacerItem( w, h, orient == Qt::Horizontal ? sizeType : QSizePolicy::Minimum,
+ orient == Qt::Vertical ? sizeType : QSizePolicy::Minimum );
+ if ( layout ) {
+ if ( layout->inherits( "QBoxLayout" ) )
+ ( (QBoxLayout*)layout )->addItem( item );
+ else
+ ( (QGridLayout*)layout )->addMultiCell( item, row, row + rowspan - 1, col, col + colspan - 1,
+ orient == Qt::Horizontal ? Qt::AlignVCenter : Qt::AlignHCenter );
+ }
+}
+
+static QImage loadImageData( QDomElement &n2 )
+{
+ QString format = n2.attribute( "format", "PNG" );
+ QString hex = n2.firstChild().toText().data();
+ int n = hex.length() / 2;
+ QByteArray data( n );
+ for ( int i = 0; i < n; i++ )
+ data[i] = (char) hex.mid( 2 * i, 2 ).toUInt( 0, 16 );
+ return loadImageData( format, n2.attribute("length").toULong(), data );
+}
+
+void QWidgetFactory::loadImageCollection( const QDomElement &e )
+{
+ QDomElement n = e.firstChild().toElement();
+ while ( !n.isNull() ) {
+ if ( n.tagName() == "image" ) {
+ Image img;
+ img.name = n.attribute( "name" );
+ QDomElement n2 = n.firstChild().toElement();
+ while ( !n2.isNull() ) {
+ if ( n2.tagName() == "data" )
+ img.img = loadImageData( n2 );
+ n2 = n2.nextSibling().toElement();
+ }
+ images.append( img );
+ n = n.nextSibling().toElement();
+ }
+ }
+}
+
+QImage QWidgetFactory::loadFromCollection( const QString &name )
+{
+ QValueList<Image>::Iterator it = images.begin();
+ for ( ; it != images.end(); ++it ) {
+ if ( ( *it ).name == name )
+ return ( *it ).img;
+ }
+ return QImage();
+}
+
+QPixmap QWidgetFactory::loadPixmap( const QString& name )
+{
+ QPixmap pix;
+ if ( usePixmapCollection ) {
+ const QMimeSource *m = QMimeSourceFactory::defaultFactory()->data( name );
+ if ( m )
+ QImageDrag::decode( m, pix );
+ } else {
+ pix.convertFromImage( loadFromCollection(name) );
+ }
+ return pix;
+}
+
+QPixmap QWidgetFactory::loadPixmap( const QDomElement &e )
+{
+ return loadPixmap( e.firstChild().toText().data() );
+}
+
+QColorGroup QWidgetFactory::loadColorGroup( const QDomElement &e )
+{
+ QColorGroup cg;
+ int r = -1;
+ QDomElement n = e.firstChild().toElement();
+ QColor col;
+ while ( !n.isNull() ) {
+ if ( n.tagName() == "color" ) {
+ r++;
+ cg.setColor( (QColorGroup::ColorRole)r, (col = DomTool::readColor( n ) ) );
+ } else if ( n.tagName() == "pixmap" ) {
+ QPixmap pix = loadPixmap( n );
+ cg.setBrush( (QColorGroup::ColorRole)r, QBrush( col, pix ) );
+ }
+ n = n.nextSibling().toElement();
+ }
+ return cg;
+}
+
+struct Connection
+{
+ QObject *sender, *receiver;
+ QCString signal, slot;
+ bool operator==( const Connection &c ) const {
+ return sender == c.sender && receiver == c.receiver &&
+ signal == c.signal && slot == c.slot ;
+ }
+
+ Connection() : sender( 0 ), receiver( 0 ) { }
+};
+
+class NormalizeObject : public QObject
+{
+public:
+ NormalizeObject() : QObject() {}
+ static QCString normalizeSignalSlot( const char *signalSlot ) { return QObject::normalizeSignalSlot( signalSlot ); }
+};
+
+void QWidgetFactory::loadConnections( const QDomElement &e, QObject *connector )
+{
+ QDomElement n = e.firstChild().toElement();
+ while ( !n.isNull() ) {
+ if ( n.tagName() == "connection" ) {
+ QString lang = n.attribute( "language", "C++" );
+ QDomElement n2 = n.firstChild().toElement();
+ Connection conn;
+ while ( !n2.isNull() ) {
+ if ( n2.tagName() == "sender" ) {
+ QString name = n2.firstChild().toText().data();
+ if ( name == "this" || qstrcmp( toplevel->name(), name ) == 0 ) {
+ conn.sender = toplevel;
+ } else {
+ if ( name == "this" )
+ name = toplevel->name();
+ QObjectList *l = toplevel->queryList( 0, name, FALSE );
+ if ( l ) {
+ if ( l->first() )
+ conn.sender = l->first();
+ delete l;
+ }
+ }
+ if ( !conn.sender )
+ conn.sender = findAction( name );
+ } else if ( n2.tagName() == "signal" ) {
+ conn.signal = n2.firstChild().toText().data();
+ } else if ( n2.tagName() == "receiver" ) {
+ QString name = n2.firstChild().toText().data();
+ if ( name == "this" || qstrcmp( toplevel->name(), name ) == 0 ) {
+ conn.receiver = toplevel;
+ } else {
+ QObjectList *l = toplevel->queryList( 0, name, FALSE );
+ if ( l ) {
+ if ( l->first() )
+ conn.receiver = l->first();
+ delete l;
+ }
+ }
+ } else if ( n2.tagName() == "slot" ) {
+ conn.slot = n2.firstChild().toText().data();
+ }
+ n2 = n2.nextSibling().toElement();
+ }
+
+ conn.signal = NormalizeObject::normalizeSignalSlot( conn.signal );
+ conn.slot = NormalizeObject::normalizeSignalSlot( conn.slot );
+
+ if ( !conn.sender || !conn.receiver ) {
+ n = n.nextSibling().toElement();
+ continue;
+ }
+
+ QObject *sender = 0, *receiver = 0;
+ QObjectList *l = toplevel->queryList( 0, conn.sender->name(), FALSE );
+ if ( qstrcmp( conn.sender->name(), toplevel->name() ) == 0 ) {
+ sender = toplevel;
+ } else {
+ if ( !l || !l->first() ) {
+ delete l;
+ n = n.nextSibling().toElement();
+ continue;
+ }
+ sender = l->first();
+ delete l;
+ }
+ if ( !sender )
+ sender = findAction( conn.sender->name() );
+
+ if ( qstrcmp( conn.receiver->name(), toplevel->name() ) == 0 ) {
+ receiver = toplevel;
+ } else {
+ l = toplevel->queryList( 0, conn.receiver->name(), FALSE );
+ if ( !l || !l->first() ) {
+ delete l;
+ n = n.nextSibling().toElement();
+ continue;
+ }
+ receiver = l->first();
+ delete l;
+ }
+
+ QString s = "2""%1";
+ s = s.arg( conn.signal );
+ QString s2 = "1""%1";
+ s2 = s2.arg( conn.slot );
+
+ QStrList signalList = sender->metaObject()->signalNames( TRUE );
+ QStrList slotList = receiver->metaObject()->slotNames( TRUE );
+
+ // if this is a connection to a custom slot and we have a connector, try this as receiver
+ if ( slotList.find( conn.slot ) == -1 && receiver == toplevel && connector ) {
+ slotList = connector->metaObject()->slotNames( TRUE );
+ receiver = connector;
+ }
+
+ // avoid warnings
+ if ( signalList.find( conn.signal ) == -1 ||
+ slotList.find( conn.slot ) == -1 ) {
+ n = n.nextSibling().toElement();
+ continue;
+ }
+ QObject::connect( sender, s, receiver, s2 );
+ }
+ n = n.nextSibling().toElement();
+ }
+}
+
+void QWidgetFactory::loadTabOrder( const QDomElement &e )
+{
+ QWidget *last = 0;
+ QDomElement n = e.firstChild().toElement();
+ while ( !n.isNull() ) {
+ if ( n.tagName() == "tabstop" ) {
+ QString name = n.firstChild().toText().data();
+ QObjectList *l = toplevel->queryList( 0, name, FALSE );
+ if ( l ) {
+ if ( l->first() ) {
+ QWidget *w = (QWidget*)l->first();
+ if ( last )
+ toplevel->setTabOrder( last, w );
+ last = w;
+ }
+ delete l;
+ }
+ }
+ n = n.nextSibling().toElement();
+ }
+}
+
+void QWidgetFactory::createListViewColumn( QListView *lv, const QString& txt,
+ const QPixmap& pix, bool clickable,
+ bool resizable )
+{
+ if ( pix.isNull() ) {
+ lv->addColumn( txt );
+ } else {
+ lv->addColumn( pix, txt );
+ }
+
+ int i = lv->header()->count() - 1;
+ if ( !pix.isNull() )
+ lv->header()->setLabel( i, pix, txt );
+ if ( !clickable )
+ lv->header()->setClickEnabled( clickable, i );
+ if ( !resizable )
+ lv->header()->setResizeEnabled( resizable, i );
+}
+
+#ifndef QT_NO_TABLE
+void QWidgetFactory::createTableColumnOrRow( QTable *table, const QString& txt,
+ const QPixmap& pix,
+ const QString& field, bool isRow )
+{
+#ifndef QT_NO_SQL
+ bool isSql = table->inherits( "QDataTable" );
+#endif
+ if ( isRow )
+ table->setNumRows( table->numRows() + 1 );
+ else {
+#ifndef QT_NO_SQL
+ if ( !isSql )
+#endif
+ table->setNumCols( table->numCols() + 1 );
+ }
+
+ QValueList<Field> fieldMap;
+ if ( fieldMaps.find( table ) != fieldMaps.end() ) {
+ fieldMap = *fieldMaps.find( table );
+ fieldMaps.remove( table );
+ }
+
+ int i = isRow ? table->numRows() - 1 : table->numCols() - 1;
+ QHeader *h = !isRow ? table->horizontalHeader() : table->verticalHeader();
+ if ( !pix.isNull() ) {
+#ifndef QT_NO_SQL
+ if ( isSql )
+ ((QDataTable*)table)->addColumn( field, txt, -1, pix );
+ else
+#endif
+ h->setLabel( i, pix, txt );
+ } else {
+#ifndef QT_NO_SQL
+ if ( isSql )
+ ((QDataTable*)table)->addColumn( field, txt );
+ else
+#endif
+ h->setLabel( i, txt );
+ }
+ if ( !isRow && !field.isEmpty() ) {
+ fieldMap.append( Field( txt, pix, field ) );
+ fieldMaps.insert( table, fieldMap );
+ }
+
+}
+#endif
+
+void QWidgetFactory::createColumn( const QDomElement &e, QWidget *widget )
+{
+ if ( widget->inherits( "QListView" ) && e.tagName() == "column" ) {
+ QListView *lv = (QListView*)widget;
+ QDomElement n = e.firstChild().toElement();
+ QPixmap pix;
+ QString txt;
+ bool clickable = TRUE, resizable = TRUE;
+ while ( !n.isNull() ) {
+ if ( n.tagName() == "property" ) {
+ QString attrib = n.attribute( "name" );
+ QVariant v = DomTool::elementToVariant( n.firstChild().toElement(), QVariant() );
+ if ( attrib == "text" )
+ txt = translate( v.toString() );
+ else if ( attrib == "pixmap" )
+ pix = loadPixmap( n.firstChild().toElement().toElement() );
+ else if ( attrib == "clickable" )
+ clickable = v.toBool();
+ else if ( attrib == "resizable" || attrib == "resizeable" )
+ resizable = v.toBool();
+ }
+ n = n.nextSibling().toElement();
+ }
+ createListViewColumn( lv, txt, pix, clickable, resizable );
+ }
+#ifndef QT_NO_TABLE
+ else if ( widget->inherits( "QTable" ) ) {
+ QTable *table = (QTable*)widget;
+
+ QDomElement n = e.firstChild().toElement();
+ QPixmap pix;
+ QString txt;
+ QString field;
+
+ while ( !n.isNull() ) {
+ if ( n.tagName() == "property" ) {
+ QString attrib = n.attribute( "name" );
+ QVariant v = DomTool::elementToVariant( n.firstChild().toElement(), QVariant() );
+ if ( attrib == "text" )
+ txt = translate( v.toString() );
+ else if ( attrib == "pixmap" ) {
+ if ( !n.firstChild().firstChild().toText().data().isEmpty() )
+ pix = loadPixmap( n.firstChild().toElement().toElement() );
+ } else if ( attrib == "field" )
+ field = translate( v.toString() );
+ }
+ n = n.nextSibling().toElement();
+ }
+ createTableColumnOrRow( table, txt, pix, field, e.tagName() == "row" );
+ }
+#endif
+}
+
+void QWidgetFactory::loadItem( const QDomElement &e, QPixmap &pix, QString &txt, bool &hasPixmap )
+{
+ QDomElement n = e;
+ hasPixmap = FALSE;
+ while ( !n.isNull() ) {
+ if ( n.tagName() == "property" ) {
+ QString attrib = n.attribute( "name" );
+ QVariant v = DomTool::elementToVariant( n.firstChild().toElement(), QVariant() );
+ if ( attrib == "text" )
+ txt = translate( v.toString() );
+ else if ( attrib == "pixmap" ) {
+ pix = loadPixmap( n.firstChild().toElement() );
+ hasPixmap = !pix.isNull();
+ }
+ }
+ n = n.nextSibling().toElement();
+ }
+}
+
+void QWidgetFactory::createItem( const QDomElement &e, QWidget *widget, QListViewItem *i )
+{
+ if ( widget->inherits( "QListBox" ) || widget->inherits( "QComboBox" ) ) {
+ QDomElement n = e.firstChild().toElement();
+ QPixmap pix;
+ bool hasPixmap = FALSE;
+ QString txt;
+ loadItem( n, pix, txt, hasPixmap );
+ QListBox *lb = 0;
+ if ( widget->inherits( "QListBox" ) ) {
+ lb = (QListBox*)widget;
+ } else {
+ QComboBox *cb = (QComboBox*)widget;
+ lb = cb->listBox();
+ if (!lb) {
+ lb = new QListBox(cb);
+ cb->setListBox(lb);
+ }
+ }
+ if ( hasPixmap ) {
+ new QListBoxPixmap( lb, pix, txt );
+ } else {
+ new QListBoxText( lb, txt );
+ }
+#ifndef QT_NO_ICONVIEW
+ } else if ( widget->inherits( "QIconView" ) ) {
+ QDomElement n = e.firstChild().toElement();
+ QPixmap pix;
+ bool hasPixmap = FALSE;
+ QString txt;
+ loadItem( n, pix, txt, hasPixmap );
+
+ QIconView *iv = (QIconView*)widget;
+ new QIconViewItem( iv, txt, pix );
+#endif
+ } else if ( widget->inherits( "QListView" ) ) {
+ QDomElement n = e.firstChild().toElement();
+ QPixmap pix;
+ QValueList<QPixmap> pixmaps;
+ QStringList textes;
+ QListViewItem *item = 0;
+ QListView *lv = (QListView*)widget;
+ if ( i )
+ item = new QListViewItem( i, d->lastItem );
+ else
+ item = new QListViewItem( lv, d->lastItem );
+ while ( !n.isNull() ) {
+ if ( n.tagName() == "property" ) {
+ QString attrib = n.attribute( "name" );
+ QVariant v = DomTool::elementToVariant( n.firstChild().toElement(), QVariant() );
+ if ( attrib == "text" )
+ textes << translate( v.toString() );
+ else if ( attrib == "pixmap" ) {
+ QString s = v.toString();
+ if ( s.isEmpty() ) {
+ pixmaps << QPixmap();
+ } else {
+ pix = loadPixmap( n.firstChild().toElement() );
+ pixmaps << pix;
+ }
+ }
+ } else if ( n.tagName() == "item" ) {
+ item->setOpen( TRUE );
+ createItem( n, widget, item );
+ }
+
+ n = n.nextSibling().toElement();
+ }
+
+ for ( int i = 0; i < lv->columns(); ++i ) {
+ item->setText( i, textes[ i ] );
+ item->setPixmap( i, pixmaps[ i ] );
+ }
+ d->lastItem = item;
+ }
+}
+
+
+
+void QWidgetFactory::loadChildAction( QObject *parent, const QDomElement &e )
+{
+ QDomElement n = e;
+ QAction *a = 0;
+ bool hasMenuText = FALSE;
+ if ( n.tagName() == "action" ) {
+ a = new QAction( parent );
+ QDomElement n2 = n.firstChild().toElement();
+
+ while ( !n2.isNull() ) {
+ if ( n2.tagName() == "property" ) {
+ QString prop(n2.attribute("name"));
+ if (prop == "menuText")
+ hasMenuText = TRUE;
+ setProperty( a, prop, n2.firstChild().toElement() );
+ }
+ n2 = n2.nextSibling().toElement();
+ }
+ if ( !parent->inherits( "QAction" ) )
+ actionList.append( a );
+ } else if ( n.tagName() == "actiongroup" ) {
+ a = new QActionGroup( parent );
+ QDomElement n2 = n.firstChild().toElement();
+ while ( !n2.isNull() ) {
+ if ( n2.tagName() == "property" ) {
+ QString prop(n2.attribute("name"));
+ if (prop == "menuText")
+ hasMenuText = TRUE;
+ setProperty( a, prop, n2.firstChild().toElement() );
+ } else if ( n2.tagName() == "action" ||
+ n2.tagName() == "actiongroup" ) {
+ loadChildAction( a, n2 );
+
+ }
+ n2 = n2.nextSibling().toElement();
+ }
+ if ( !parent->inherits( "QAction" ) )
+ actionList.append( a );
+ }
+
+ if (a && !hasMenuText && !a->text().isEmpty() && uiFileVersion < "3.3")
+ a->setMenuText(a->text());
+}
+
+void QWidgetFactory::loadActions( const QDomElement &e )
+{
+ QDomElement n = e.firstChild().toElement();
+ while ( !n.isNull() ) {
+ if ( n.tagName() == "action" ) {
+ loadChildAction( toplevel, n );
+ } else if ( n.tagName() == "actiongroup" ) {
+ loadChildAction( toplevel, n );
+ }
+ n = n.nextSibling().toElement();
+ }
+}
+
+void QWidgetFactory::loadToolBars( const QDomElement &e )
+{
+ QDomElement n = e.firstChild().toElement();
+ QMainWindow *mw = ( (QMainWindow*)toplevel );
+ QToolBar *tb = 0;
+ while ( !n.isNull() ) {
+ if ( n.tagName() == "toolbar" ) {
+ Qt::Dock dock = (Qt::Dock)n.attribute( "dock" ).toInt();
+ tb = new QToolBar( QString::null, mw, dock );
+ tb->setLabel( n.attribute( "label" ) );
+ tb->setName( n.attribute( "name" ) );
+ QDomElement n2 = n.firstChild().toElement();
+ while ( !n2.isNull() ) {
+ if ( n2.tagName() == "action" ) {
+ QAction *a = findAction( n2.attribute( "name" ) );
+ if ( a )
+ a->addTo( tb );
+ } else if ( n2.tagName() == "separator" ) {
+ tb->addSeparator();
+ } else if ( n2.tagName() == "widget" ) {
+ (void)createWidgetInternal( n2, tb, 0, n2.attribute( "class", "QWidget" ) );
+ } else if ( n2.tagName() == "property" ) {
+ setProperty( tb, n2.attribute( "name" ), n2.firstChild().toElement() );
+ }
+ n2 = n2.nextSibling().toElement();
+ }
+ }
+ n = n.nextSibling().toElement();
+ }
+}
+
+void QWidgetFactory::loadMenuBar( const QDomElement &e )
+{
+ QDomElement n = e.firstChild().toElement();
+ QMainWindow *mw = ( (QMainWindow*)toplevel );
+ QMenuBar *mb = mw->menuBar();
+ while ( !n.isNull() ) {
+ if ( n.tagName() == "item" ) {
+ QPopupMenu *popup = new QPopupMenu( mw );
+ loadPopupMenu( popup, n );
+ popup->setName( n.attribute( "name" ) );
+ mb->insertItem( translate( n.attribute( "text" ) ), popup );
+ } else if ( n.tagName() == "property" ) {
+ setProperty( mb, n.attribute( "name" ), n.firstChild().toElement() );
+ } else if ( n.tagName() == "separator" ) {
+ mb->insertSeparator();
+ }
+ n = n.nextSibling().toElement();
+ }
+}
+
+void QWidgetFactory::loadPopupMenu( QPopupMenu *p, const QDomElement &e )
+{
+ QMainWindow *mw = ( (QMainWindow*)toplevel );
+ QDomElement n = e.firstChild().toElement();
+ while ( !n.isNull() ) {
+ if ( n.tagName() == "action" || n.tagName() == "actiongroup" ) {
+ QAction *a = findAction( n.attribute( "name" ) );
+ QDomElement n2 = n.nextSibling().toElement();
+ if ( n2.tagName() == "item") { // load submenu
+ QPopupMenu *popup = new QPopupMenu( mw );
+ popup->setName( n2.attribute( "name" ) );
+ if ( a ) {
+ p->setAccel( a->accel(), p->insertItem( a->iconSet(),
+ translate( n2.attribute( "text" ).utf8().data() ),
+ popup ) );
+ } else {
+ p->insertItem( translate( n2.attribute( "text" ).utf8().data() ), popup );
+ }
+ loadPopupMenu( popup, n2 );
+ n = n2;
+ } else {
+ if ( a ) {
+ a->addTo( p );
+ }
+ }
+ a = 0;
+ } else if ( n.tagName() == "separator" ) {
+ p->insertSeparator();
+ }
+ n = n.nextSibling().toElement();
+ }
+}
+
+// compatibility with early 3.0 betas
+// ### remove for 4.0
+void QWidgetFactory::loadFunctions( const QDomElement & )
+{
+}
+
+QAction *QWidgetFactory::findAction( const QString &name )
+{
+ for ( QAction *a = actionList.first(); a; a = actionList.next() ) {
+ if ( QString( a->name() ) == name )
+ return a;
+ QAction *ac = (QAction*)a->child( name.latin1(), "QAction" );
+ if ( ac )
+ return ac;
+ }
+ return 0;
+}
+
+/*!
+ If you use a pixmap collection (which is the default for new
+ projects) rather than saving the pixmaps within the .ui XML file,
+ you must load the pixmap collection. QWidgetFactory looks in the
+ default QMimeSourceFactory for the pixmaps. Either add it there
+ manually, or call this function and specify the directory where
+ the images can be found, as \a dir. This is normally the
+ directory called \c images in the project's directory.
+*/
+
+void QWidgetFactory::loadImages( const QString &dir )
+{
+ QDir d( dir );
+ QStringList l = d.entryList( QDir::Files );
+ for ( QStringList::Iterator it = l.begin(); it != l.end(); ++it )
+ QMimeSourceFactory::defaultFactory()->setPixmap( *it, QPixmap( d.path() + "/" + *it, "PNG" ) );
+
+}
+
+void QWidgetFactory::loadExtraSource()
+{
+ if ( !qwf_language || !languageInterfaceManager )
+ return;
+ QString lang = *qwf_language;
+ LanguageInterface *iface = 0;
+ languageInterfaceManager->queryInterface( lang, &iface );
+ if ( !iface )
+ return;
+ QFile f( qwf_currFileName + iface->formCodeExtension() );
+ if ( f.open( IO_ReadOnly ) ) {
+ QTextStream ts( &f );
+ code = ts.read();
+ }
+}
+
+QString QWidgetFactory::translate( const QString& sourceText, const QString& comment )
+{
+ return qApp->translate( d->translationContext, sourceText.utf8(), comment.utf8(),
+ QApplication::UnicodeUTF8 );
+}
+
+QString QWidgetFactory::translate( const char *sourceText, const char *comment )
+{
+ return qApp->translate( d->translationContext, sourceText, comment,
+ QApplication::UnicodeUTF8 );
+}